Disabled item in combobox???
Disabled item in combobox???
Disabled item in combobox???
A disabled item is nonSelectable and colored by GrayColor
is there a sample for this request?
A disabled item is nonSelectable and colored by GrayColor
is there a sample for this request?
Re: Disabled item in combobox???
if not possible for combobox, maybe be for ListViewGadget???
if it possible for ListViewGadget, it will be great and i can use ListViewGadget Instead combobox
however for my purpose , combobox is better than other gadget
if it possible for ListViewGadget, it will be great and i can use ListViewGadget Instead combobox
however for my purpose , combobox is better than other gadget
Re: Disabled item in combobox???
As far as I know it's not possible with native PB commands. That makes us focus on the API. But we need to know the OS.
If it's Windows you should take a look on subclassing and ownerdrawing.
If it's Windows you should take a look on subclassing and ownerdrawing.

Re: Disabled item in combobox???
need for Win xp and next OS only.
have you a keyword or more help, please?
have you a keyword or more help, please?
Re: Disabled item in combobox???
I've used CallWindowProc_(CBCB, ...) because it's faster than SendMessage_(). It skips all subclassing.
Not sure if the keyboard support (arrow keys) is flawless. It still needs some testing.
Not sure if the keyboard support (arrow keys) is flawless. It still needs some testing.
Code: Select all
wc.WNDCLASSEX\cbSize = SizeOf(WNDCLASSEX)
GetClassInfoEx_(GetModuleHandle_(0), @"ComboBox", @wc)
Global PrevItm.i, LastKey.i, *Text=AllocateMemory(128), CBCB = wc\lpfnWndProc
Procedure ComboProc(hWnd, uMsg, wParam, lParam)
OldProc = GetProp_(hWnd, "MyCB")
Select uMsg
Case #WM_KEYDOWN
LastKey = wParam
Case #WM_NCDESTROY
RemoveProp_(hWnd, "MyCB")
EndSelect
ProcedureReturn CallWindowProc_(OldProc, hWnd, uMsg, wParam, lParam)
EndProcedure
Procedure WinCallback(hWnd, uMsg, wParam, lParam)
Select uMsg
Case #WM_DRAWITEM
*lpdis.DRAWITEMSTRUCT = lParam : SetBkMode_(*lpdis\hDC, #TRANSPARENT)
If *lpdis\CtlType = #ODT_COMBOBOX
If *lpdis\itemState & #ODS_SELECTED
If CallWindowProc_(CBCB, *lpdis\hwndItem, #CB_GETITEMDATA, *lpdis\itemID, 0);SendMessage_()
*lpdis\CtlType = GetSysColorBrush_(#COLOR_BTNFACE)
Else
*lpdis\CtlType = GetSysColorBrush_(#COLOR_HIGHLIGHT)
EndIf
Else
*lpdis\CtlType = GetSysColorBrush_(#COLOR_WINDOW)
EndIf
FillRect_(*lpdis\hDC, *lpdis\rcItem, *lpdis\CtlType) : *lpdis\rcItem\left+4
CallWindowProc_(CBCB, *lpdis\hwndItem, #CB_GETLBTEXT, *lpdis\itemID, *Text);SendMessage_()
If CallWindowProc_(CBCB, *lpdis\hwndItem, #CB_GETITEMDATA, *lpdis\itemID, 0);SendMessage_()
SetTextColor_(*lpdis\hDC, #Gray);GetSysColor_(#COLOR_GRAYTEXT)
EndIf
DrawText_(*lpdis\hDC, *Text, -1, *lpdis\rcItem, #DT_NOCLIP|#DT_VCENTER|#DT_SINGLELINE)
SetTextColor_(*lpdis\hDC, GetSysColor_(#COLOR_WINDOWTEXT))
EndIf
Case #WM_COMMAND
Select (wParam>>16) & $FFFF;HIWORD
Case #CBN_SELCHANGE
Var = CallWindowProc_(CBCB, lParam, #CB_GETCURSEL, 0, 0);SendMessage_()
If Var <> PrevItm
If CallWindowProc_(CBCB, lParam, #CB_GETITEMDATA, Var, 0);SendMessage_()
If LastKey = 38 Or LastKey = 37
For i=Var-1 To 0 Step -1
If CallWindowProc_(CBCB, lParam, #CB_GETITEMDATA, i, 0) = #False
PrevItm = i : Break
EndIf
Next
ElseIf LastKey = 40 Or LastKey = 39
For i=Var+1 To CallWindowProc_(CBCB, lParam, #CB_GETCOUNT, 0, 0)-1
If CallWindowProc_(CBCB, lParam, #CB_GETITEMDATA, i, 0) = #False
PrevItm = i : Break
EndIf
Next
EndIf
CallWindowProc_(CBCB, lParam, #CB_SETCURSEL, PrevItm, 0);SendMessage_()
Else
PrevItm = Var
EndIf
EndIf
Case #CBN_DROPDOWN
LastKey = 0
EndSelect
EndSelect
ProcedureReturn #PB_ProcessPureBasicEvents
EndProcedure
OpenWindow(0, 0, 0, 270, 140, "ComboBoxGadget", #PB_Window_SystemMenu | #PB_Window_ScreenCentered)
ComboBoxGadget(1, 10, 40, 250, 21, #CBS_OWNERDRAWFIXED)
For n = 1 To 10
AddGadgetItem(1, -1, "ComboBox Item " + Str(n))
Next
SendMessage_(GadgetID(1), #CB_SETITEMDATA, 3, #True);DISABLE ITEM
SendMessage_(GadgetID(1), #CB_SETITEMDATA, 4, #True);DISABLE ITEM
SendMessage_(GadgetID(1), #CB_SETITEMDATA, 9, #True);DISABLE ITEM
SetProp_(GadgetID(1), "MyCB", SetWindowLong_(GadgetID(1), #GWL_WNDPROC, @ComboProc()))
SetWindowCallback(@WinCallback(), 0)
Repeat
Select WaitWindowEvent()
Case #PB_Event_CloseWindow
Break
EndSelect
ForEver
Last edited by klaver on Fri Sep 11, 2009 1:14 pm, edited 1 time in total.

Re: Disabled item in combobox???
wow
very well thanks klaver, that's great

very well thanks klaver, that's great

Re: Disabled item in combobox???
Hello
i need this sweet code, but sorry it's don't work in Win 7 64bit
can you update it for new Os's ?
i need work in xp and 7 together ...

i need this sweet code, but sorry it's don't work in Win 7 64bit
can you update it for new Os's ?
i need work in xp and 7 together ...

PB v 5.6 

Re: Disabled item in combobox???
Code: Select all
[...]
ComboBoxGadget(1, 10, 40, 250, 21, #CBS_OWNERDRAWFIXED|#CBS_HASSTRINGS)
[...]
Re: Disabled item in combobox???
Updated version with few bugs fixed (drawing, PgUp/PgDn, multiple CB support).
Code: Select all
Structure MyCB
oldProc.i
prevItm.i
lastKey.i
EndStructure
wc.WNDCLASSEX\cbSize = SizeOf(WNDCLASSEX)
GetClassInfoEx_(GetModuleHandle_(0), @"ComboBox", @wc)
Global *TmpCB.MyCB, *Text=AllocateMemory(128), CBCB = wc\lpfnWndProc
Procedure ComboProc(hWnd, uMsg, wParam, lParam)
*TmpCB = GetProp_(hWnd, "MyCB")
If *TmpCB
oldProc = *TmpCB\oldProc
Else
oldProc = CBCB;#WM_DELETEITEM
EndIf
Select uMsg
Case #WM_KEYDOWN
*TmpCB\lastKey = wParam
Case #WM_NCDESTROY
RemoveProp_(hWnd, "MyCB")
FreeMemory(*TmpCB)
EndSelect
ProcedureReturn CallWindowProc_(oldProc, hWnd, uMsg, wParam, lParam)
EndProcedure
Procedure WinCallback(hWnd, uMsg, wParam, lParam)
Select uMsg
Case #WM_DRAWITEM
*lpdis.DRAWITEMSTRUCT = lParam
SetBkMode_(*lpdis\hDC, #TRANSPARENT)
If *lpdis\CtlType = #ODT_COMBOBOX
If *lpdis\itemState & #ODS_SELECTED
If CallWindowProc_(CBCB, *lpdis\hwndItem, #CB_GETITEMDATA, *lpdis\itemID, 0) And *lpdis\itemID > -1
*lpdis\CtlType = GetSysColorBrush_(#COLOR_BTNFACE)
Else
*lpdis\CtlType = GetSysColorBrush_(#COLOR_HIGHLIGHT)
EndIf
Else
*lpdis\CtlType = GetSysColorBrush_(#COLOR_WINDOW)
EndIf
FillRect_(*lpdis\hDC, *lpdis\rcItem, *lpdis\CtlType)
*lpdis\rcItem\left+4
If CallWindowProc_(CBCB, *lpdis\hwndItem, #CB_GETLBTEXT, *lpdis\itemID, *Text) > -1
If CallWindowProc_(CBCB, *lpdis\hwndItem, #CB_GETITEMDATA, *lpdis\itemID, 0);SendMessage_()
SetTextColor_(*lpdis\hDC, #Gray);GetSysColor_(#COLOR_GRAYTEXT)
EndIf
DrawText_(*lpdis\hDC, *Text, -1, *lpdis\rcItem, #DT_NOCLIP|#DT_VCENTER|#DT_SINGLELINE)
SetTextColor_(*lpdis\hDC, GetSysColor_(#COLOR_WINDOWTEXT))
EndIf
EndIf
Case #WM_COMMAND
*TmpCB = GetProp_(lParam, "MyCB"); it should be checked if pointer isn't NULL (too lazy for that)
Select (wParam>>16) & $FFFF;HIWORD
Case #CBN_SELCHANGE
Var = CallWindowProc_(CBCB, lParam, #CB_GETCURSEL, 0, 0);SendMessage_()
If Var <> *TmpCB\prevItm
If CallWindowProc_(CBCB, lParam, #CB_GETITEMDATA, Var, 0);SendMessage_()
If *TmpCB\lastKey = 38 Or *TmpCB\lastKey = 37;Up
For i=Var-1 To 0 Step -1
If CallWindowProc_(CBCB, lParam, #CB_GETITEMDATA, i, 0) = #False
*TmpCB\prevItm = i : Break
EndIf
Next
ElseIf *TmpCB\lastKey = 40 Or *TmpCB\lastKey = 39;Down
For i=Var+1 To CallWindowProc_(CBCB, lParam, #CB_GETCOUNT, 0, 0)-1
If CallWindowProc_(CBCB, lParam, #CB_GETITEMDATA, i, 0) = #False
*TmpCB\prevItm = i : Break
EndIf
Next
ElseIf *TmpCB\lastKey = 33;PgUp
For i=0 To CallWindowProc_(CBCB, lParam, #CB_GETCOUNT, 0, 0)-1
If CallWindowProc_(CBCB, lParam, #CB_GETITEMDATA, i, 0) = #False
*TmpCB\prevItm = i : Break
EndIf
Next
ElseIf *TmpCB\lastKey = 34;PgDn
For i=CallWindowProc_(CBCB, lParam, #CB_GETCOUNT, 0, 0)-1 To 0 Step -1
If CallWindowProc_(CBCB, lParam, #CB_GETITEMDATA, i, 0) = #False
*TmpCB\prevItm = i : Break
EndIf
Next
EndIf
CallWindowProc_(CBCB, lParam, #CB_SETCURSEL, *TmpCB\prevItm, 0);SendMessage_()
Else
*TmpCB\prevItm = Var
EndIf
EndIf
Case #CBN_DROPDOWN
*TmpCB\lastKey = 0
EndSelect
EndSelect
ProcedureReturn #PB_ProcessPureBasicEvents
EndProcedure
Procedure MakeMyCB(ID)
*TmpCB = AllocateMemory(SizeOf(MyCB))
*TmpCB\prevItm = SendMessage_(GadgetID(ID), #CB_GETCURSEL, 0, 0)
*TmpCB\oldProc = SetWindowLongPtr_(GadgetID(ID), #GWL_WNDPROC, @ComboProc())
SetProp_(GadgetID(ID), "MyCB", *TmpCB)
EndProcedure
OpenWindow(0, 0, 0, 270, 140, "ComboBoxGadget", #PB_Window_SystemMenu | #PB_Window_ScreenCentered)
ComboBoxGadget(1, 10, 40, 250, 21, #CBS_OWNERDRAWFIXED|#CBS_HASSTRINGS)
ComboBoxGadget(2, 10, 70, 250, 21, #CBS_OWNERDRAWFIXED|#CBS_HASSTRINGS)
For i = 1 To 10
AddGadgetItem(1, -1, "ComboBox A Item " + Str(i))
AddGadgetItem(2, -1, "ComboBox B Item " + Str(i))
Next
MakeMyCB(1)
SendMessage_(GadgetID(1), #CB_SETITEMDATA, 3, #True);DISABLE ITEM
SendMessage_(GadgetID(1), #CB_SETITEMDATA, 4, #True);DISABLE ITEM
SendMessage_(GadgetID(1), #CB_SETITEMDATA, 9, #True);DISABLE ITEM
MakeMyCB(2)
SendMessage_(GadgetID(2), #CB_SETITEMDATA, 2, #True);DISABLE ITEM
SendMessage_(GadgetID(2), #CB_SETITEMDATA, 6, #True);DISABLE ITEM
SendMessage_(GadgetID(2), #CB_SETITEMDATA, 7, #True);DISABLE ITEM
SetWindowCallback(@WinCallback(), 0)
Repeat
Select WaitWindowEvent()
Case #PB_Event_CloseWindow
Break
EndSelect
ForEver

Re: Disabled item in combobox???
nice code really ,many thanks dear klaver 

Re: Disabled item in combobox???
Hello,
is there also any updates for Win 10/11 ?
is there also any updates for Win 10/11 ?
Re: Disabled item in combobox???
The last code above by klaver works on Win 10 for me.
Re: Disabled item in combobox???
Thank you BarryG, it stays now a successful test on Window 11...
Re: Disabled item in combobox???
also works under win 11.
Minimal restriction: you see the disabled item for a short time in the edit field, but it disappears again immediately.
Minimal restriction: you see the disabled item for a short time in the edit field, but it disappears again immediately.
Just because it worked doesn't mean it works.
PureBasic 6.04 (x86) and <latest stable version and current alpha/beta> (x64) on Windows 11 Home. Now started with Linux (VM: Ubuntu 22.04).
PureBasic 6.04 (x86) and <latest stable version and current alpha/beta> (x64) on Windows 11 Home. Now started with Linux (VM: Ubuntu 22.04).