Well, if it helps, here's the find text code from my editor (also RichEdit based):
;====================================
; Find that text!
;====================================
do_find:
; Get the direction & case-sensitivity settings:
INVOKE IsDlgButtonChecked, hWin, $upRadio
MOV DL, FALSE
CMP EAX, BST_CHECKED
JE @F
MOV DL, TRUE
@@: MOV FindDirDown, DL
; Set case sensitivity flag to checkbox setting:
INVOKE IsDlgButtonChecked, hWin, $caseChk
MOV DL, TRUE
CMP EAX, BST_CHECKED
JE @F
MOV DL, FALSE
@@: MOV FindCaseSensitive, DL
; Get the text to find:
INVOKE GetDlgItemText, hWin, $findEdit, OFFSET FindTextBuffer, SIZEOF FindTextBuffer
; Are we finding up or down?
CMP FindDirDown, FALSE
JE findUp
; See if there's anything to find:
CMP FindTextBuffer[0], NULL
JE focus
; Get the selection from the edit control, if there is one:
INVOKE SendMessage, EditHandle, EM_GETSEL, ADDR startSel, ADDR endSel
MOV EAX, startSel
CMP EAX, endSel
JNE fsel
;If end sel. = start sel., no selection, so start at startSel
MOV EAX, startSel
JMP SHORT fsel1
; Since there's a selection, start from its end:
fsel: MOV EAX, endSel
fsel1: MOV ft.chrg.cpMin, EAX
MOV ft.chrg.cpMax, -1
MOV ft.lpstrText, OFFSET FindTextBuffer
; Set case sensitivity according to current flag setting:
MOV EDX, FR_DOWN
CMP FindCaseSensitive, TRUE
JNE @F
OR EDX, FR_MATCHCASE
; Returns -1 if nothing found, index of 1st char. of search text if found.
@@: INVOKE SendMessage, EditHandle, EM_FINDTEXTEX, EDX, ADDR ft
CMP EAX, -1
JNE @F
INVOKE wsprintf, ADDR buffer, OFFSET FindTextFmt, OFFSET FindTextBuffer, OFFSET NotFoundStr
INVOKE SendMessage, StatusHandle, SB_SETTEXT, 1, ADDR buffer
JMP focus
@@: MOV startSel, EAX
MOV EAX, OFFSET FindTextBuffer
CALL strlen
ADD EAX, startSel
INVOKE SendMessage, EditHandle, EM_SETSEL, startSel, EAX
INVOKE SendMessage, EditHandle, EM_HIDESELECTION, 0, 0
INVOKE SendMessage, StatusHandle, SB_SETTEXT, 1, ADDR DummyText
JMP focus
;===================================
; Find text (up):
;===================================
findUp:
; Get the selection from the edit control, if there is one:
INVOKE SendMessage, EditHandle, EM_GETSEL, ADDR startSel, ADDR endSel
MOV EAX, startSel
TEST EAX, EAX ;Already @ start?
JZ @F
DEC EAX ; No, so back up 1.
@@: MOV ft.chrg.cpMin, EAX
MOV ft.chrg.cpMax, 0 ;Is this ignored for this op? YES.
MOV ft.lpstrText, OFFSET FindTextBuffer
; Set case sensitivity according to current flag setting:
XOR EDX, EDX
CMP FindCaseSensitive, TRUE
JNE @F
OR EDX, FR_MATCHCASE
; Returns -1 if nothing found, index of 1st char. of search text if found.
@@: INVOKE SendMessage, EditHandle, EM_FINDTEXTEX, EDX, ADDR ft
CMP EAX, -1
JNE @F
INVOKE wsprintf, ADDR buffer, OFFSET FindTextFmt, OFFSET FindTextBuffer, OFFSET NotFoundStr
INVOKE SendMessage, StatusHandle, SB_SETTEXT, 1, ADDR buffer
JMP focus
@@: MOV startSel, EAX
MOV EAX, OFFSET FindTextBuffer
CALL strlen
ADD EAX, startSel
INVOKE SendMessage, EditHandle, EM_SETSEL, startSel, EAX
INVOKE SendMessage, EditHandle, EM_HIDESELECTION, 0, 0
INVOKE SendMessage, StatusHandle, SB_SETTEXT, 1, ADDR DummyText
JMP focus
Most of this is just a wrapper for the EM_FINDTEXTEX message which does the actual heavy lifting here. The code checks the settings of the direction radio buttons (up/down) and the case-sensitivity checkbox (which just sets the FR_MATCHCASE flag if the user wants case sensitivity). Not much else going on here. Notice that there are two branches, since searching up instead of down involves a different dance to go backwards instead of forwards to find the next match.
The "focus" label sets the focus back to the edit control so you don't have to do an extra (and annoying!) mouse click once the dialog is closed to resume editing.