Sequentially Highlight Words (Of Selection)

Category: Controls - RichEdit

Date: 02-16-2022

Return to Index


 
'Sometimes a programmer needs to walk through each word in a richedit control,
'possibly performing some action on each of the words. This snippets shows how
'to walk through each word (of an initial selection), highlighting each word in turn.
 
'Compiler Comments:
'This code is written to compile with PBWin10. To compile with PBWin9,
'add this line:
#Include "CommCtrl.inc"
 
'Primary Code:
'The basic approach is to use Extract$ to get the first word, then removing the
'first word with Remain$, so that Extract$ can get the next word.  The position
'starting position of the multi-word text is passed to the function, which tracks
'the position of each 'next word'. The position and length are enough information
'to highlight the word (in this case, within a RichEdit control).
 
Sub HighlightWords (iPos&, ByVal txt$)
      Local i As Long, NextWord$, P As CharRange
      Do While Len(txt$)
         NextWord$ = Extract$ (txt$, Any Chr$(0 To 47, 58 To 64, 91 To 96, 123 To 128) )
 
         'select the NextWord and pause to show that it is highlighted
         P.cpmin = iPos& : P.cpmax = iPos& + Len(NextWord)
         SendMessage hRichEdit, %EM_EXSetSel,  0, VarPTR(P)
         If Len(NextWord$) Then Sleep 500
 
         'unselect all in preparation for highlighting of the next NextWord
         P.cpmin = -1 : P.cpmax = 0
         SendMessage hRichEdit, %EM_EXSetSel, 0, VarPTR(P)
 
         'continues
         iPos& = iPos& + Len(NextWord$) + 1                                'starting position of the next NextWord
         txt$ = Remain$( txt$, Any Chr$(0 To 47, 58 To 64, 91 To 96, 123 To 128) )  'remove current word and leading delimiter
      Loop
End Sub
 
'Compilable Example:  (Jose Includes)
'In this example, the individual words of selected text are sequentially
'highlighted (once started, initial highlighting is removed, then individual
'words are highlighted).
#Compiler PBWin 10
#Compile EXE
#Dim All
%Unicode=1
#Include "win32api.inc
#Include "RichEdit.inc"
Global hDlg As Dword, hRichEdit As Dword
%ID_RichEdit = 500
 
Function PBMain() As Long
   Local style&, buf$
   buf$ =  "This is sample" + $CrLf + "text for the" + $CrLf + "edit control."
   style& = %WS_Child Or %WS_Visible Or %ES_MultiLine Or %WS_VScroll Or %ES_AutoHScroll _
      Or %WS_HScroll Or %ES_AutoVScroll Or %ES_WantReturn Or %ES_NoHideSel Or %WS_TabStop
   Dialog New Pixels, 0, "Test Code",300,300,200,150, %WS_OverlappedWindow To hDlg
   Control Add Button, hDlg, 100,"Push", 30,10,140,20
   LoadLibrary("riched32.dll") : InitCommonControls
   Control Add "RichEdit", hDlg, %ID_RichEdit, buf$,20,40,160,100, style&, %WS_Ex_ClientEdge
   Control Handle hDlg, %ID_RichEdit To hRichEdit
   Dialog Show Modal hDlg Call DlgProc
End Function
 
CallBack Function DlgProc() As Long
   If CB.Msg = %WM_Command AND CB.Ctl = 100 AND CB.Ctlmsg = %BN_Clicked Then
      'For this example, words in the selected text will be parsed - the highlighting
      'removed, then each word that was in the selected sequentially highlighted
 
      'Char Positions   EM_EXGetSel  0, ptr-CHARRANGE   (start/end pos)
      '                  EM_EXSetSel  0, ptr-CHARRANGE   (start/end pos)
      'Text Content    EM_GetTextRange  0, ptr-TEXTRANGE   (start/end pos)
 
      Local temp$, i As Long, x$, iStart&, P As CharRange, tempZ As AsciiZ*200
 
      'get start/end pos of selected text
      SendMessage hRichEdit, %EM_ExGetSel, 0,VarPTR(P)
      iStart& = P.cpmin
 
      'get selected text
      SendMessage hRichEdit, %EM_GetSelText,  0, VarPTR(tempZ)
 
      'unselect all so highlighting is visible in Sub
      P.cpmin = -1 : P.cpmax = 0
      SendMessage hRichEdit, %EM_EXSetSel, 0, VarPTR(P)
 
      temp$ = tempZ
      HighLightWords iStart&, temp$
 
      MsgBox "... done"
   End If
End Function
 
Sub HighlightWords (iPos&, ByVal txt$)
   Local i As Long, NextWord$, P As CharRange
   Do While Len(txt$)
      NextWord$ = Extract$ (txt$, Any Chr$(0 To 47, 58 To 64, 91 To 96, 123 To 128) )
 
      'select the NextWord and pause to show that it is highlighted
      P.cpmin = iPos& : P.cpmax = iPos& + Len(NextWord)
      SendMessage hRichEdit, %EM_EXSetSel,  0, VarPTR(P)
      If Len(NextWord$) Then Sleep 500
 
      'unselect all in preparation for highlighting of the next NextWord
      P.cpmin = -1 : P.cpmax = 0
      SendMessage hRichEdit, %EM_EXSetSel, 0, VarPTR(P)
 
      'continues
      iPos& = iPos& + Len(NextWord$) + 1                                'starting position of the next NextWord
      txt$ = Remain$( txt$, Any Chr$(0 To 47, 58 To 64, 91 To 96, 123 To 128) )  'remove current word and leading delimiter
   Loop
End Sub
 
'gbs_00374
'Date: 03-10-2012


created by gbSnippets
http://www.garybeene.com/sw/gbsnippets.htm