Problem in subclassing of Combobox
-
Hi, i have subclassed one comboobox in my application using the following code
LONG FAR PASCAL SubClassFunc(HWND hWnd, UINT Message, WPARAM wParam, LONG lParam); FARPROC lpfnOldWndProc; BOOL NcClass::OnInitDialog() { cbi.cbSize = sizeof(COMBOBOXINFO); GetComboBoxInfo(m_SignalsLabel_ctl.m_hWnd, &cbi); pfnOldWndProc = (FARPROC)SetWindowLong(cbi.hwndItem, GWL_WNDPROC, (DWORD)SubClassFunc); return TRUE; } LONG FAR PASCAL SubClassFunc(HWND hWnd, UINT Message, WPARAM wParam, LONG lParam) { if(Message == WM_KEYDOWN) { if(wParam == VK_TAB) { HWND hChild, hParent; hParent = ::GetParent(hWnd); hChild = ::GetWindow(hParent, GW_HWNDNEXT); ::SetFocus(hChild); } } if( Message == WM_GETDLGCODE ) return DLGC_WANTTAB; return CallWindowProc(WNDPROC(lpfnOldWndProc), hWnd, Message, wParam, lParam); }
Even though i am calling CallWindowProc()from my window procedure, mouse click and other thing are not woking for the combobox which i have subclassed and application is having some effect on other comboboxes also. I have also tried by commenting the whole code of SubClassFunc() except the last line, but still the behaviour of application is same. My problem is that i can't create seperate class for the combobox. Thanks.You mean even if the code is just as below, it is not working?
LONG FAR PASCAL SubClassFunc(HWND hWnd, UINT Message, WPARAM wParam, LONG lParam) { return CallWindowProc(WNDPROC(lpfnOldWndProc), hWnd, Message, wParam, lParam); }
Are your sure that you need to subclass the edit control in the combobox? If yes, are you sure that the combobox is having dropdown style (having edit box inside)?- NS - [ODBaseBtn]
-
You mean even if the code is just as below, it is not working?
LONG FAR PASCAL SubClassFunc(HWND hWnd, UINT Message, WPARAM wParam, LONG lParam) { return CallWindowProc(WNDPROC(lpfnOldWndProc), hWnd, Message, wParam, lParam); }
Are your sure that you need to subclass the edit control in the combobox? If yes, are you sure that the combobox is having dropdown style (having edit box inside)?- NS - [ODBaseBtn]
Yes, it is of DropDown style only and i am doing all this just to move the focus. For other combobox of style DropList type the tab key is working fine. I am sending message from some other class to the dialog containing the combobox to set the focus. Thanks
-
Yes, it is of DropDown style only and i am doing all this just to move the focus. For other combobox of style DropList type the tab key is working fine. I am sending message from some other class to the dialog containing the combobox to set the focus. Thanks
ashtwin wrote:
I am sending message from some other class to the dialog containing the combobox to set the focus.
How are you sending the message? Code fragment will be helpful.
- NS - [ODBaseBtn]
-
ashtwin wrote:
I am sending message from some other class to the dialog containing the combobox to set the focus.
How are you sending the message? Code fragment will be helpful.
- NS - [ODBaseBtn]
Hi, from the function below i am sending the message.
BOOL MyBaseClass::PreTranslateMessage(MSG *pMsg) { HWND hParent, hChild; if(::FindWindow(NULL, _T("My Dialog"))) { if(pMsg->message == WM_KEYDOWN) { if(pMsg->wParam == VK_TAB) { hChild = ::GetFocus(); hParent = ::GetParent(hChild); ::PostMessage(hParent, WM_MYMESSAGE, /*pMsg->wParam*/0, /*pMsg->lParam*/0); } } } return MyBaseClass::PreTranslateMessage(pMsg); }
I am doing this because due to some reasons the keyboard messages are going to the above function. MyBaseclass is the class from the child class of whom i am creating the modeless dialog.modified on Monday, January 07, 2008 8:31:43 AM
-
Hi, from the function below i am sending the message.
BOOL MyBaseClass::PreTranslateMessage(MSG *pMsg) { HWND hParent, hChild; if(::FindWindow(NULL, _T("My Dialog"))) { if(pMsg->message == WM_KEYDOWN) { if(pMsg->wParam == VK_TAB) { hChild = ::GetFocus(); hParent = ::GetParent(hChild); ::PostMessage(hParent, WM_MYMESSAGE, /*pMsg->wParam*/0, /*pMsg->lParam*/0); } } } return MyBaseClass::PreTranslateMessage(pMsg); }
I am doing this because due to some reasons the keyboard messages are going to the above function. MyBaseclass is the class from the child class of whom i am creating the modeless dialog.modified on Monday, January 07, 2008 8:31:43 AM
First of all, are you missing the call to base class's PreTranslateMessage ? PS: The following should be noted.
if(::FindWindow(NULL, _T("My Dialog"))) { if(pMsg->message == WM_KEYDOWN) { if(pMsg->wParam == VK_TAB) {
is not good. Change as follows...if(pMsg->message == WM_KEYDOWN) { if(pMsg->wParam == VK_TAB) { if(::FindWindow(NULL, _T("My Dialog"))) {
- NS - [ODBaseBtn]
-
First of all, are you missing the call to base class's PreTranslateMessage ? PS: The following should be noted.
if(::FindWindow(NULL, _T("My Dialog"))) { if(pMsg->message == WM_KEYDOWN) { if(pMsg->wParam == VK_TAB) {
is not good. Change as follows...if(pMsg->message == WM_KEYDOWN) { if(pMsg->wParam == VK_TAB) { if(::FindWindow(NULL, _T("My Dialog"))) {
- NS - [ODBaseBtn]
-
Hi, from the function below i am sending the message.
BOOL MyBaseClass::PreTranslateMessage(MSG *pMsg) { HWND hParent, hChild; if(::FindWindow(NULL, _T("My Dialog"))) { if(pMsg->message == WM_KEYDOWN) { if(pMsg->wParam == VK_TAB) { hChild = ::GetFocus(); hParent = ::GetParent(hChild); ::PostMessage(hParent, WM_MYMESSAGE, /*pMsg->wParam*/0, /*pMsg->lParam*/0); } } } return MyBaseClass::PreTranslateMessage(pMsg); }
I am doing this because due to some reasons the keyboard messages are going to the above function. MyBaseclass is the class from the child class of whom i am creating the modeless dialog.modified on Monday, January 07, 2008 8:31:43 AM
ashtwin wrote:
return MyBaseClass::PreTranslateMessage(pMsg);
OK...
ashtwin wrote:
::PostMessage(hParent, WM_MYMESSAGE, /*pMsg->wParam*/0, /*pMsg->lParam*/0);
I think this WM_MYMESSAGE is WM_USER + nonzero message, right? If so what is the exact value? Or it a registered message? Also did you tried by excluding the subclassing done in the InitDialog, but keeping this MyBaseClass::PreTranslateMessage function as now?
- NS - [ODBaseBtn]
-
ashtwin wrote:
return MyBaseClass::PreTranslateMessage(pMsg);
OK...
ashtwin wrote:
::PostMessage(hParent, WM_MYMESSAGE, /*pMsg->wParam*/0, /*pMsg->lParam*/0);
I think this WM_MYMESSAGE is WM_USER + nonzero message, right? If so what is the exact value? Or it a registered message? Also did you tried by excluding the subclassing done in the InitDialog, but keeping this MyBaseClass::PreTranslateMessage function as now?
- NS - [ODBaseBtn]
-
Hi, from the function below i am sending the message.
BOOL MyBaseClass::PreTranslateMessage(MSG *pMsg) { HWND hParent, hChild; if(::FindWindow(NULL, _T("My Dialog"))) { if(pMsg->message == WM_KEYDOWN) { if(pMsg->wParam == VK_TAB) { hChild = ::GetFocus(); hParent = ::GetParent(hChild); ::PostMessage(hParent, WM_MYMESSAGE, /*pMsg->wParam*/0, /*pMsg->lParam*/0); } } } return MyBaseClass::PreTranslateMessage(pMsg); }
I am doing this because due to some reasons the keyboard messages are going to the above function. MyBaseclass is the class from the child class of whom i am creating the modeless dialog.modified on Monday, January 07, 2008 8:31:43 AM
One thing I noticed just now... :( <blockquote class="FQ"><div class="FQA">ashtwin wrote:</div>hChild = ::GetFocus(); hParent = ::GetParent(hChild); ::PostMessage(hParent, WM_MYMESSAGE, /*pMsg->wParam*/0, /*pMsg->lParam*/0); </blockquote> So the parent is the combobox itself, and the message is posted to it. So this message is going to be received by combobox, not the parent of the combobox. Is it expected? What is happening exactly with the subclassing?
- NS - [ODBaseBtn]
-
One thing I noticed just now... :( <blockquote class="FQ"><div class="FQA">ashtwin wrote:</div>hChild = ::GetFocus(); hParent = ::GetParent(hChild); ::PostMessage(hParent, WM_MYMESSAGE, /*pMsg->wParam*/0, /*pMsg->lParam*/0); </blockquote> So the parent is the combobox itself, and the message is posted to it. So this message is going to be received by combobox, not the parent of the combobox. Is it expected? What is happening exactly with the subclassing?
- NS - [ODBaseBtn]
No it is not expected, i want to send the message to the parent dialog and not to the combobox. Because in dialog class i am setting the focus to the next control after receiving the message i.e why i have done subclassing for combobox. But after doing subclassing mouse clicks and other things are not working for combobox and even it is effecting other comboboxes also(eg they are appearing as disabled untill i am cliking the mouse on them). Thanks
-
No it is not expected, i want to send the message to the parent dialog and not to the combobox. Because in dialog class i am setting the focus to the next control after receiving the message i.e why i have done subclassing for combobox. But after doing subclassing mouse clicks and other things are not working for combobox and even it is effecting other comboboxes also(eg they are appearing as disabled untill i am cliking the mouse on them). Thanks
So you should check whether it is the correct control or not. You can check control ID since you have to do it in only one control. Calling ::GetMenu( hWndCombo ) will give you the ID, provided hWndCombo is the handle to the combobox obtained by calling GetParent( hWndEdit ). You should only change the focus if the control ID is of the specified combo.
- NS - [ODBaseBtn]
-
So you should check whether it is the correct control or not. You can check control ID since you have to do it in only one control. Calling ::GetMenu( hWndCombo ) will give you the ID, provided hWndCombo is the handle to the combobox obtained by calling GetParent( hWndEdit ). You should only change the focus if the control ID is of the specified combo.
- NS - [ODBaseBtn]
Hi, now after doing the following changes the application is working fine but still i don't know about the problem with subclassing.
BOOL MyBaseClass::PreTranslateMessage(MSG *pMsg) { if(::FindWindow(NULL, _T("Temporary Catheter Connections"))) { if(pMsg->message == WM_KEYDOWN) { if(pMsg->wParam == VK_TAB) { COMBOBOXINFO cbi; hChild = ::GetFocus(); hParent = ::GetParent(hChild); cbi.cbSize = sizeof(COMBOBOXINFO); if(GetComboBoxInfo(hParent, &cbi)) { hParent = ::GetParent(hParent);//Get dialog handle for combobox } ::PostMessage(hParent, WM_MYMESSAGE, /*pMsg->wParam*/0, /*pMsg->lParam*/0); } } } return BaseClass::PreTranslateMessage(pMsg); }
Thanks -
Hi, now after doing the following changes the application is working fine but still i don't know about the problem with subclassing.
BOOL MyBaseClass::PreTranslateMessage(MSG *pMsg) { if(::FindWindow(NULL, _T("Temporary Catheter Connections"))) { if(pMsg->message == WM_KEYDOWN) { if(pMsg->wParam == VK_TAB) { COMBOBOXINFO cbi; hChild = ::GetFocus(); hParent = ::GetParent(hChild); cbi.cbSize = sizeof(COMBOBOXINFO); if(GetComboBoxInfo(hParent, &cbi)) { hParent = ::GetParent(hParent);//Get dialog handle for combobox } ::PostMessage(hParent, WM_MYMESSAGE, /*pMsg->wParam*/0, /*pMsg->lParam*/0); } } } return BaseClass::PreTranslateMessage(pMsg); }
ThanksOK... :) Please confirm my understanding. You need to change the focus to the next control when the focus is set to combo using Tab key. Am I right?
- NS - [ODBaseBtn]
-
OK... :) Please confirm my understanding. You need to change the focus to the next control when the focus is set to combo using Tab key. Am I right?
- NS - [ODBaseBtn]
-
Then removing the WS_TABSTOP property wasn't enough?
- NS - [ODBaseBtn]
-
Then removing the WS_TABSTOP property wasn't enough?
- NS - [ODBaseBtn]