Prevent Editbl ComBox OnDataEntry Automatic select HitItem

Share your advanced PureBasic knowledge/code with the community.
LiK137
Enthusiast
Enthusiast
Posts: 282
Joined: Wed Jun 23, 2010 5:13 pm

Prevent Editbl ComBox OnDataEntry Automatic select HitItem

Post by LiK137 »

Hi,
In the below example there is a simple window with a simple editable ComboBox.
Contents of Combo is filled every time on EditField of Combo is changed (character entry)
If we input a character which is present in any position of ComboList items but not first letter then everything is OK.
But if we input a character which present in first letter then the hit item is overwriting the letter we input into edit field of Combobox thus preventing further character entry.

How it is possible to make edit field not overwritten?
Huge Thanks.


Code: Select all

 Procedure IsMouseOver(hWnd) 
  GetWindowRect_(hWnd,r.RECT) 
  GetCursorPos_(p.POINT) 
  Result = PtInRect_(r,p\y << 32 + p\x) 
  ProcedureReturn Result 
EndProcedure 

Procedure InitMemQLite()
  UseSQLiteDatabase()

  Define hQLite = OpenDatabase(#PB_Any, ":memory:", "", "")
  If hQLite  
    If DatabaseUpdate(hQLite, "CREATE TABLE ComboTable (ComboField1 Integer, ComboField2 VARCHAR(255));" )       
      For iKantr = 1 To 20
          DatabaseUpdate(hQLite, "INSERT INTO ComboTable (ComboField1, ComboField2) VALUES ( " + Str(iKantr) + ", '" + Chr(Random(90,65)) + Chr(Random(90,65)) + Chr(Random(90,65)) + Chr(Random(90,65)) + Chr(Random(90,65)) + Chr(Random(90,65)) + Chr(Random(90,65)) + Chr(Random(90,65)) + "' )")
      Next
    Else
      Debug DatabaseError()
    EndIf
  Else
      Debug DatabaseError()    
  EndIf
  
  ProcedureReturn hQLite
  
EndProcedure

Procedure.s TriggeredFillCombo(hDB, gdCombo, MatchString.s = "")  
  
  Protected gdComboEntry.s = MatchString
  
  Protected Col1.s,
            Col2
  
  ClearGadgetItems(gdCombo)

  If MatchString = ""
     MatchString = "%"
  EndIf  
  
  MatchString = ReplaceString(MatchString, "*","%")
  MatchString = ReplaceString(MatchString, "?","_")
  
  If Left(MatchString, 1) <> "%"
    MatchString = "%"+MatchString
  EndIf
  If Right(MatchString, 1) <> "%"
    MatchString = MatchString+"%"
  EndIf
    
  
  ;{ RetrieveCBFilds
  Protected qSQL.s = " SELECT ComboField1, ComboField2 FROM ComboTable WHERE ComboField2 LIKE '"+MatchString+"' ORDER BY ComboField1 "
      
  Debug MatchString
  Debug qSQL
  
  If DatabaseQuery(hDB, qSQL) 
    While NextDatabaseRow(hDB) 
      Col1 = GetDatabaseString(hDB, DatabaseColumnIndex(hDB, "ComboField2"))
      Col2 = GetDatabaseLong(hDB, DatabaseColumnIndex(hDB, "ComboField1"))      
      AddGadgetItem(gdCombo, -1, Col1)
      SetGadgetItemData(gdCombo, CountGadgetItems(gdCombo) - 1, Col2)
    Wend
    FinishDatabaseQuery(hDB)
  Else
    Debug DatabaseError()+#CRLF$+#PB_Compiler_Line
  EndIf
  ;}
        
  If Len(gdComboEntry) > 0
    SetGadgetText(gdCombo, gdComboEntry)
    SetActiveGadget(gdCombo)
;   SendMessage_(GadgetID(HRCombo),#CB_SETEDITSEL,1,0)  ; Cursor at start.
    SendMessage_(GadgetID(gdCombo),#CB_SETEDITSEL,0,-1) ; Cursor at end.
  EndIf  
        
  ProcedureReturn gdComboEntry
EndProcedure  

Enumeration 
  #cmdGo
  #cmdEsc
EndEnumeration

Procedure Main()
;{ Declz    
  Protected DropStat = #True
  Protected CurActiveGadget = -1  
  Protected ESCounter,
            cbString.s,  
            selItem = -1,
            i_FilterGrid,
            j_FilterGrid,
            k_FilterGrid
  
  Protected FilterGrid_WinWidz = 200, FilterGrid_WinHeyt = 200
  
  Protected FilterGrid_chWinID = OpenWindow(#PB_Any, (GetSystemMetrics_(#SM_CXSCREEN)-FilterGrid_WinWidz)/2 , 
                             (GetSystemMetrics_(#SM_CYSCREEN)-FilterGrid_WinHeyt)/2 , FilterGrid_WinWidz, FilterGrid_WinHeyt, "Main", #PB_Window_BorderLess) 
  ;}
  If FilterGrid_chWinID
    
    hQlite = InitMemQLite()
    Debug hQlite
  ;{ AssignKeybShCut
    AddKeyboardShortcut(FilterGrid_chWinID, #PB_Shortcut_Return, #cmdGo)
    AddKeyboardShortcut(FilterGrid_chWinID, #PB_Shortcut_Escape, #cmdEsc)
  ;}
  ;{ WinTune
    UpdateWindow_(WindowID(FilterGrid_chWinID)) 
    RedrawWindow_(WindowID(FilterGrid_chWinID),0,0,#RDW_INVALIDATE | #RDW_ERASE) 
    StickyWindow(FilterGrid_chWinID,#True)
    SetWindowLong_(WindowID(FilterGrid_chWinID),#GWL_STYLE,#WS_DLGFRAME )
    SmartWindowRefresh(FilterGrid_chWinID,1)
    HideWindow(FilterGrid_chWinID,1)
  ;}
  ;{ Gadgetz
    ;{ FilterGrid_Combo1
    Protected FilterGrid_Combo1 = ComboBoxGadget(#PB_Any, 70, 125, 100, 25, #PB_ComboBox_Editable)
    ;{ FillCombo
    TriggeredFillCombo(hQlite, FilterGrid_Combo1)
    ;}
    ;}
  ;}
    
;{ ShoWin
    HideWindow(FilterGrid_chWinID,0,#PB_Window_ScreenCentered)
    UpdateWindow_(WindowID(FilterGrid_chWinID))
    ;}
;{ chWinLoop
    Repeat
      
      Select WaitWindowEvent()
          
        Case #PB_Event_CloseWindow
          Break
        Case #PB_Event_Menu
          Select EventMenu()
            Case #cmdEsc
              ESCounter+1
              CurActiveGadget = GetActiveGadget()    
              If CurActiveGadget >= 0 And GadgetType(CurActiveGadget) = #PB_GadgetType_ComboBox
                If SendMessage_(GadgetID(CurActiveGadget),#CB_GETDROPPEDSTATE, 0, 0)
                  SendMessage_(GadgetID(CurActiveGadget),#CB_SHOWDROPDOWN, #False, #Null) 
                  ESCounter = 0  
                EndIf
              EndIf
              
              SetActiveGadget(-1)

              If ESCounter > 1
                Break
              EndIf
              
              
            Case #cmdGo
              CurActiveGadget = GetActiveGadget()    
              If GadgetType(CurActiveGadget) = #PB_GadgetType_ComboBox And SendMessage_(GadgetID(CurActiveGadget),#CB_GETDROPPEDSTATE, 0, 0)
;{ CurActiveGadget
                selItem = GetGadgetState(CurActiveGadget)
                SendMessage_(GadgetID(CurActiveGadget),#CB_SHOWDROPDOWN, #False, #Null) 
                selItem = -1
                SetActiveGadget(-1)
 ;}                  
              EndIf  
              
          EndSelect    
          
        Case #WM_LBUTTONDOWN 
;{ EventLButton
          If GetActiveWindow() = FilterGrid_chWinID
;{ LButtonDown
            If IsMouseOver(GadgetID(FilterGrid_Combo1))
              
              DropStat!#True
              
              If DropStat = #True 
                SendMessage_(GadgetID(FilterGrid_Combo1),#CB_SHOWDROPDOWN, #False, #Null) 
              Else
                SendMessage_(GadgetID(FilterGrid_Combo1),#CB_SHOWDROPDOWN, #True, 0) 
              EndIf  
              
            EndIf  
;}            
          EndIf  
;}            
        Case #WM_KEYDOWN; #WM_CHAR  ;        Case #WM_KEYUP
          CurActiveGadget = GetActiveGadget() 
          If GadgetType(CurActiveGadget) = #PB_GadgetType_ComboBox 
            SendMessage_(GadgetID(CurActiveGadget),#CB_SHOWDROPDOWN, #True, 0)
          EndIf  
        Case #WM_CHAR; #WM_CHAR  ;        Case #WM_KEYUP
          CurActiveGadget = GetActiveGadget() 
          Select CurActiveGadget
            Case FilterGrid_Combo1
              cbString = GetGadgetText(FilterGrid_Combo1)
              TriggeredFillCombo(hQlite, FilterGrid_Combo1, cbString)
              SetGadgetText(FilterGrid_Combo1, cbString)
              SetActiveGadget(FilterGrid_Combo1)
              SendMessage_(GadgetID(FilterGrid_Combo1),#CB_SETEDITSEL,0,-1) ; Cursor at end.
              SendMessage_(GadgetID(FilterGrid_Combo1),#CB_SHOWDROPDOWN, #True, 0)
              
          EndSelect      
        Case #PB_Event_Gadget
          Select EventGadget()
;{ EvtGadget              
            Case FilterGrid_Combo1  
              Select EventType()
                Case #PB_EventType_Change
                  DropStat = #True    
                  
              EndSelect    
            EndSelect
;}
        EndSelect
    ForEver  
;}    
;{ FReesources
      RemoveKeyboardShortcut(FilterGrid_chWinID, #cmdGo)
      RemoveKeyboardShortcut(FilterGrid_chWinID, #cmdEsc)
      CloseWindow(FilterGrid_chWinID)
;}
      

  EndIf  
EndProcedure

Main()
LiK137
Enthusiast
Enthusiast
Posts: 282
Joined: Wed Jun 23, 2010 5:13 pm

Re: Prevent Editbl ComBox OnDataEntry Automatic select HitIt

Post by LiK137 »

Mechanically I can solve this as simply adding [SPACE] character to start of character entry in Main() procedure

Code: Select all

        Case #WM_CHAR; #WM_CHAR  ;        Case #WM_KEYUP
          CurActiveGadget = GetActiveGadget() 
          Select CurActiveGadget
            Case FilterGrid_Combo1
              cbString = GetGadgetText(FilterGrid_Combo1)
              
              If Len(cbString) = 1 ; --------------------------------------------------------------> Here attaching garbage char
                If cbString = " "
                  cbString = ""
                Else  
                  cbString = " " + cbString
                EndIf  
                SetGadgetText(FilterGrid_Combo1, cbString)
              EndIf
              
              TriggeredFillCombo(hQlite, FilterGrid_Combo1, cbString, " ")   ; -------------------------->  Here passing garbage char
              SetGadgetText(FilterGrid_Combo1, cbString)
              SetActiveGadget(FilterGrid_Combo1)
              SendMessage_(GadgetID(FilterGrid_Combo1),#CB_SETEDITSEL,0,-1) ; Cursor at end.
              SendMessage_(GadgetID(FilterGrid_Combo1),#CB_SHOWDROPDOWN, #True, 0)
              
          EndSelect      
        Case #PB_Event_Gadget
and in the TriggeredFillCombo() procedure removing this initial [SPACE] character

Code: Select all

Procedure.s TriggeredFillCombo(hDB, gdCombo, MatchString.s = "", Charbage.s = "")  
  
  Protected gdComboEntry.s = MatchString
  
  Protected Col1.s,
            Col2
  
  ClearGadgetItems(gdCombo)

  If MatchString = ""
     MatchString = "%"
  EndIf  
  
  If Charbage <> "" And Left(MatchString, 1) = Charbage
    MatchString = Right(MatchString, Len(MatchString) - 1)
  EndIf  
But if there is simpler WinAPI solution...
Post Reply