|
[VC++学习]《精通MFC》——第二章(I) 读书笔记
|
第二章 窗口
2.1 窗口结构
MFC的CWnd类提供了对窗口句柄的包装。窗口就是一个CWnd对象。
窗口就是一个数据结构,这个结构就是WNDCLASS 。在Windows.h头文件中,该结构是这样定义的:
typedef struct_WNDCLASS
{
UINT style;
WNDPROC lpfnWndProc;
int cbClsExtra;
int cbWndExtra;
HINSTANCE hInstance;
HICON hIcon;
HCURSOR hCursor;
HBRUSH hbrBackground;
LPCTSTR lpszMenuName;
LPCTSTR lpszClassName;
}WNDCLASS, *PWNDCLASS;
style: 不同的窗口可以有不同的风格。
lpfnWndProc: 该参数从本质上决定了窗口的行为,也就是它能为我们作什么。这个参数定义了一个函数指针,这个函数指针指向的函数负责对窗口消息进行处理。
窗口过程的定义必须满足如下的形式:
LRESULT CALLBACK WindowProc(
HWND hwnd, //窗口句柄
UINT uMsg, //消息标志
WPARAM wParam, //第一个消息参数
LPARAM lParam //第二个消息参数
);
hInstance: 表示当前的句柄。通过此参数,窗口可以区分不同的实例,还可以利用此参数加载资源。
hIcon:窗口图标。当窗口正常显示时,图标会在窗口的左上角绘制,当窗口停靠到工具栏时,则在工具栏上绘制。
hCursor: 窗口的光标。
hbrBackground: 这个参数决定了用什么样的画刷绘制窗口的客户区。
lpszMenuName: 菜单资源名。如果用一个整数式菜单资源,则需要用MAKEEINTRESOURCE将其转化为内部的资源字符串形式。该参数如果为NULL,表示该窗口将没有默认的菜单。
lpszClassName:窗口的类名。
2.2 窗口类型
1 可重叠(Overlapped)窗口
这种窗口式有标题栏、边框、客户区域的顶层窗口。
在调用CreateWindowEx创建窗口时,指定窗口风格参数为WS_OVERLAPPED,有标题栏和边框,或WS_OVERLAPPEDWINDOW,有标题栏、可变大小的边框、窗口菜单、最大化和最小化按钮。例如:
hwndMain = (
0, //无扩展风格
“MainWClass”, //类名
“Main Window”, //窗口名
WS_OVERLAPPEDWINDOW| //可重叠窗口
WS_HSCROLL| //有水平滚动条
WS_VSCROLL, //有垂直滚动条
CW_USEDEFAULT, //水平滚动条的默认位置
CW_USEDEFAULT, //垂直滚动条的默认位置
CW_USEDEFAULT, //默认宽度
CW_USEDEFAULT, //默认高度
(HWND)NULL, //无父窗口
(HMENU)NULL, //无菜单
Hinstance, //实例句柄
NULL); //创建此窗口没有额外的数据
2 弹出(Pop-up)窗口
这类窗口有可重叠窗口的全部特征,但其标题栏是可选的。这类窗口是在应用程序的主窗口中出现的临时窗口。
在用CreateWindowEx创建窗口时,指定风格为WS_POPUP就会创建一个有边框和菜单的弹出窗口。为了拥有标题栏,需同时指定WS_CAPTION风格,为了使窗口菜单可见,需同时指定WS_POPUUWINDOW风格。
3 子(Child)窗口
子窗口具有WS_CHILD风格,并限制在父窗口的客户区域绘制。创建子窗口的方法是调用CreateWindowEx时,指定WS_CHILD作为窗口风格参数并同时指定父窗口。
除非特殊指定,子窗口仅有一个客户区而没有其他特征。但通过指定其他参数,可使子窗口拥有标题栏、窗口菜单、最大最小化按钮、边框或滚动条。子窗口不能拥有菜单。
3 消息窗口
这类窗口只能发送或接收消息。它们没有边框、没有Z序、不能被枚举、不能接受广播消息。创建方法是调用CreateWindowEx时将父窗口句柄设为常量HWND_MESSSAGE。
除此之外,通过对已有的窗口调用SetParent,并将HWND_MESSAGE传入hWndNewParent参数,也会把一个窗口转化为消息窗口。
查找消息窗口时,要将FindWindowEx的hwndParent参数设为HWND_MESSAGE。
2.3 窗口关系
1 父子关系
应用程序可以在运行时对一个已有的窗口调用SetParent,改变其父窗口。如果SetParent中传入NULL,难么桌面将成为新的父窗口。跟SetParent动态设置父窗口相对应,GetParent函数可获得子窗口的父窗口。
应用程序可以通过调用IsChild判断一个给定的窗口是否为某个窗口的后代窗口:
BOOL IsChild(
HWND hWndParent, //父窗口的句柄
HWND hWnd //被测试的窗口的句柄
);
函数EnumChildWindows提供了枚举起始窗口所有后代窗口的方法:
BOOL EnumChildWindows(
HWND hWndParent, //父窗口
WNDENUMPROC lpEnumFunc, //回调函数
LPARAM lParam //应用定义的的值,将作为回调函数的参数
|
|
|
|