该函数CallWindowProc将消息信息传送给指定的窗口过程。
函数原型:
LRESULT CallWindowProc(WNDPROC lpPrevWndFunc,HWND hWnd.UINT Msg,WPARAM wParam,LPARAMIParam);
参数:
lpPrevWndFunc:参数主要是指向你要调用的函数句柄
hWnd:指向接收消息的窗口过程的句柄。
Msg:指定消息类型。
wParam:指定其余的、消息特定的信息。该参数的内容与Msg参数值有关。
IParam:指定其余的、消息特定的信息。该参数的内容与Msg参数值有关。
返回值:返回值指定了消息处理结果,它与发送的消息有关。
备注:使用函数CallWindowsProc可进行窗口子分类。通常来说,同一类的所有窗口共享一个窗口过程。子类是一个窗口或者相同类的一套窗口,在其消息被传送到该类的窗口过程之前,这些消息是由另一个窗口过程进行解释和处理的。
SetWindowLoog函数通过改变与特定窗口相关的窗口过程,使系统调用新的窗口过程来创建子类,新的窗口过程替换了以前的窗口过程。应用程序必须通过调用CallWindowsProc来将新窗日过程没有处理的任何消息传送到以前的窗口过程中,这样就允许应用程序创建一系列窗口过程。
SetWindowLong的用途是子类化一个窗口。本质上讲,窗口子类化是使应用程序从先前存在的窗口类派生出新窗口类的一个实例。子类化的典型应用是修改窗口控件的行为,例如一个Edit控件。
SetWindowLong() 函数
说明
在窗口结构中为指定的窗口设置信息
返回值 Long,指定数据的前一个值
参数表
参数 类型及说明
hwnd Long,欲为其取得信息的窗口的句柄
nIndex Long,请参考GetWindowLong函数的nIndex参数的说明
dwNewLong Long,由nIndex指定的窗口信息的新值
在窗口结构中为指定的窗口设置信息
返回值 Long,指定数据的前一个值
参数表
参数 类型及说明
hwnd Long,欲为其取得信息的窗口的句柄
nIndex Long,请参考GetWindowLong函数的nIndex参数的说明
dwNewLong Long,由nIndex指定的窗口信息的新值
GetWindowLong()函数从指定窗口的结构中取得信息
返回值 Long,由nIndex决定。零表示出错。会设置 GetLastError
参数表
参数 类型及说明
hwnd Long,欲为其获取信息的窗口的句柄
nIndex Long,欲取回的信息,可以是下述任何一个常数:
GWL_EXSTYLE 扩展窗口样式
GWL_STYLE 窗口样式
GWL_WNDPROC 该窗口的窗口函数的地址
GWL_HINSTANCE 拥有窗口的实例的句柄
GWL_HWNDPARENT 该窗口之父的句柄。不要用SetWindowWord来改变这个值
GWL_ID 对话框中一个子窗口的标识符
GWL_USERDATA 含义由应用程序规定
DWL_DLGPROC 这个窗口的对话框函数地址
DWL_MSGRESULT 在对话框函数中处理的一条消息返回的值
DWL_USER 含义由应用程序规定
返回值 Long,由nIndex决定。零表示出错。会设置 GetLastError
参数表
参数 类型及说明
hwnd Long,欲为其获取信息的窗口的句柄
nIndex Long,欲取回的信息,可以是下述任何一个常数:
GWL_EXSTYLE 扩展窗口样式
GWL_STYLE 窗口样式
GWL_WNDPROC 该窗口的窗口函数的地址
GWL_HINSTANCE 拥有窗口的实例的句柄
GWL_HWNDPARENT 该窗口之父的句柄。不要用SetWindowWord来改变这个值
GWL_ID 对话框中一个子窗口的标识符
GWL_USERDATA 含义由应用程序规定
DWL_DLGPROC 这个窗口的对话框函数地址
DWL_MSGRESULT 在对话框函数中处理的一条消息返回的值
DWL_USER 含义由应用程序规定
子类化的过程实际上是很简单的。先创建一个窗口过程来为被子类化的窗口提供新功能,再用基础窗口类创建一个窗口。然后为该窗口调用
GetWindowLong来获得并保存一个指向其初始窗口过程的指针,之后调用
SetWindowLong函数,将窗口实例的窗口过程设置成新的窗口过程。这样,新的窗口过程就开始接收发给该窗口的消息了。任何没有被新窗口过程响应的消息都通过调用
CallWindowProc传递给到旧的窗口过程。下面的代码展示了窗口创建及被子类化的过程。子类化窗口过程截获了
WM_LBUTTONDOWN消息,并且在窗口收到该消息时使扬声器发出声音。
//原窗口响应回调函数
LRESULT CALLBACK SCWndProc(HWND hWnd, UINT wMsg, WPARAM wParam, LPARAM lParam);
// Variable that holds the pointer to the original WndProc
WNDPROC lpfnOldProc = 0;
//
//w创建相应窗口并得到句柄
lpfnOldProc = (WNDPROC)SetWindowLong(GetSafeHwnd(), DWL_DLGPROC, (DWORD)SCWndProc);
// 新窗口响应函数,对未截取的消息,返回原消息响应函数执行
LRESULT CALLBACK SCWndProc(HWND hWnd, UINT wMsg, WPARAM wParam,LPARAM lParam)
{
switch (wMsg) {
case WM_LBUTTONDOWN:
MessageBeep(0);
break;
}
return CallWindowProc (lpfnOldProc, hWnd, wMsg, wParam, lParam);
}
要去除窗口的子类化,只要调用SetWindowLong,把WndProc指针设置回最初的窗口过程即可。