下面我以 WM_COMMAND為例分析訊息的分流
1. 我們知道,每個訊息都有 wParam 和 lParam,如WM_COMMAND,wParam包含兩個不同的值,其中:
wParam:低位元組是控制項的id,高位元組是通知碼 notifyCode
lParam: 強制轉換為按鈕或控制項的控制代碼值 hWndCtl
2. HAND_MSG宏定義,第五版是chHANDLE_DLGMSG (windowsx.h)
// The normal HANDLE_MSG macro in WindowsX.h does not work properly for dialog
// boxes because DlgProc returns a BOOL instead of an LRESULT (like
// WndProcs). This chHANDLE_DLGMSG macro corrects the problem:
#define chHANDLE_DLGMSG(hWnd, message, fn) \
case (message): return (SetDlgMsgResult(hWnd, uMsg, \
HANDLE_##message((hWnd), (wParam), (lParam), (fn))))
#define HANDLE_MSG(hwnd,message,fn) \
case (message): \
Return HANDLE_##message((hwnd),(wParam),(lParam),(fn))
3. 如遇到 WM_COMMAND,則語句擴充成
case (WM_COMMAND):
return (SetDlgMsgResult(hWnd, uMsg, \
HANDLE_WM_COMMAND((hWnd), (wParam), (lParam), (Dlg_OnCommand))
4. 這裡,你可以看一下HAND_WM_COMMAND宏的擴充 (windowsx.h)
#define HANDLE_WM_COMMAND(hwnd,wParam,lParam,fn) \
((fn) ((hwnd),(int)(LOWORD(wParam)),(HWND)(lParam),
(UINT)HIWORD(wParam)),0L)
5. 應用視窗的回呼函數定義
INT_PTR WINAPI Dlg_Proc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam) {
switch (uMsg) {
chHANDLE_DLGMSG(hWnd, WM_INITDIALOG, Dlg_OnInitDialog);
chHANDLE_DLGMSG(hWnd, WM_COMMAND, Dlg_OnCommand);
}
return(FALSE);
}
6. 應用視窗的回呼函數實現
void Dlg_OnCommand(HWND hWnd, int id, HWND hWndCtl, UINT codeNotify)
{
switch (id)
{
case IDCANCEL:
EndDialog(hWnd, id);
break;
case IDC_BTN_STOP:
{
// StopProcessing can't be called from the UI thread
// or a deadlock will occur: SendMessage() is used
// to fill up the listboxes
// --> Another thread is required
DWORD dwThreadID;
CloseHandle(chBEGINTHREADEX(NULL, 0, StoppingThread, NULL, 0, &dwThreadID));
// This button can't be pushed twice,這個控制項的控制代碼
Button_Enable(hWndCtl, FALSE);
}
break;
}
}