从属窗口在z次序中总是在它的属主窗口的上面。
windows系统在销毁属主窗口时自动地销毁从属窗口。
从属窗门在其属主窗口最小化时是被隐藏
只有覆盖或弹出窗口可以是一个属主窗口,子窗口则不能。
应用程序创建一个从属 窗口是通过在创建具有WS_OVERLAPPED或WS_POPUP风格的窗口时,把函数CreateWindowEx的参数hwndParent设置成属主窗门的句柄;参数hwndParent必须标识一个覆盖或弹出窗口。如果hwndParent标识的是一个子窗口,windows系统就会把所属关系赋给这个子窗口的顶层父窗口。创建了从属窗口之后,应用程序就不能再把窗口的
所属关系传给别的窗口。
对话框和消息框一般是从属窗口,因此应用程序在调用一个函数创建对话框或消息时要指定的属主窗口
程序可以通过设置GW_OWNER标志来调用GetWindow函数来检索属主窗口的句柄。
被禁止的窗口
窗口是可以被禁止的,被禁止的窗口不再接收键盘或鼠标输入,们它能接收来自其它窗口,或是来自其它应用程序以及windows系统的消息。应用程序禁止一个窗口是防止用户使用这个窗口,例如,应用程序可能会禁止对话框中的一个按钮防止用户对它的选择。应用程序可在任何时候再允许一个被禁止的窗口,允许一个窗口也就恢复了正常的输入。缺省情况下,一个窗口在刚被创建时是被允许的,但程序能够通过设置WS_DISABLED风格来禁止一个新窗口。应用程序通过函数EnableWindow允许或禁止一个存在的窗口,windows系统在窗口的允许状态将要改变时向它发送一条WM_ENABLE消息.应用程序使用函数IsWindowEnabled以确定—个窗口是否被允许。如果一个于窗口被禁止,windows系统就会把这个子窗口的鼠标输入传给其父窗口,父窗口通过这条消息确定是否需要允许这个子窗口。
在同一时间只有一个窗口能够接收键盘输入,也就是说这个窗口拥有键盘焦点。如果应用程序用函数EnableWindow来禁止一个拥有焦点的窗口.这个窗口在被禁止的同时也失去了键盘焦点,EnableWindow把键盘焦点设置成NULL,意思是说没有窗口具有焦点。如果一个子窗口或其它的子孙窗口有了键盘焦点、子孙窗口也会在父窗口被禁止时失去键盘焦点。
前台窗口和后台窗口
每一个进程可运行多个线程,每个线程部能创建窗口。创建正在使用窗口的线程称之为前台线程,这个窗口就称之为前台窗口。所有其它的线程都是后台线程.由后台线程所创建的窗门叫后台窗口.
每一个线程都有一个优先等级,它决定了该线程占有cpu的时间。尽管应用程序能够设留它的线程的优先等级,但通常前台线程具有比后台线程稍高的优先等级.正因为如此,前台线程所占cpu时间比后台线程要长。通常,前台线程具有的优先级是9,而后台线程是7。
用户是通过单击一个窗口、使用alt+tab或alt+esc组合键来设置前台窗口,应用程序则用函数SetForegroundWindow设置前台窗口如果新的前台窗口是一个顶层窗口,那么windows系统就激活它,换句话说,windows系统激活相应的顶层窗口。应
用程序通过函数GetForegroundWindow来检取前台窗口的句柄。
显示状态
在任何时候,窗口可以是活动的或是被禁止的;隐藏的或是可见的;最小化、最大化或是被恢复,这些统称为窗口的显示状态。
活动窗口
活动窗口是应用程序的顶层窗口,也就是当前使用的窗口,为了使用户能很容易地识别活动窗口,windows系统把它放在z次序的顶部,并把标题栏和边框的颜色设置成系统定义的活动窗口的颜色。只有个顶层窗口可以是活动窗口.如果用户使用的是一个子窗口,windows系统就激活与这个子窗口相应的顶层窗口。
任何时候系统中只能有一个项层窗口是活动的。用户是通过单击窗口(或其中的一个子窗口)、使用alt+esc或alt+tab组合键来激活一个顶层窗口,应用程序则调用函数SetActiveWindow来激活一个顶层窗口,还有另外一些函数windows系统用来激活不同的顶层窗口包括:SetWindowPos, DeferWindowPos, SetWindowPlacement, 和 DestroyWindow.。尽管一个应用程序也能在任何时候激活一个不同的顶层窗口,但为避免困惑用户,应该只根据用户的要求做出响应。应用程序通过函数GetActiveWindow来检取活动窗口的句柄。
如果活动状态从—个应用程序的某个顶层窗口改变到另一个应用程序的顶层窗口,windows系统就要向两个应用程序发送wM AcrIvATEAl)P消息来通知它们。如果是在同一个应用程序的不同顶层窗门之间改变活动特性,windows系统就向两个窗口发送WM_ACTIVATE消息。
可见性
窗口既可以是可见的,也可以被隐藏。windows系统只在屏幕上显示一个可见的窗口,对隐藏的窗口只是不画它罢了。如果一个窗口是可见的,用户可通过窗口进行输入以及查看窗口的输出。如果窗口是被隐藏着的,则相当于被有效地禁止了。隐藏的窗口可处理来自windows系统或其它窗口的消息,但它不能处理用户的输入或是显示输出。应用程序在创建某项口时就设置了它的可见状态,后面应用程序还可以改变其可见状态。
如果为窗口设置了WS_VISIBLE风格,则窗口是可见的。通常,除非应用程序设置了WS_VISIBLE风格.否则函数CreateWindowEx只是创建了一个隐藏的窗口。应用程序一般是在创建了一个窗口之后设置WS_VISIBLE风格,主要是不让用户看到创建过程的细节。例如,应用程序在定制窗口的外观时,新窗口是被隐藏的。如果在函数CreateWindowEx中指定了WS_VISIBLE风格,windows系统就会在创建了窗口之后,在显示该窗口之前向它发送WM_SHOWWINDOW消息.
应用程序可通过函数IsWindowVisible确认一个窗口是否可见,应用程序通过函数ShowWindow, SetWindowPos, DeferWindowPos, or SetWindowPlacement显示(使可见)或隐藏一个窗口,这些函数是通过设置或删除窗口的WS_VISIBLE风格来显示或隐藏窗口的,它们也在显示或隐藏窗口之前向其发送WM_SHOWWINDOW消息。
如果一个属主窗口被最小化了,windows系统会自动隐藏相应的从属窗口。同样,在一个属主窗口被恢复时,windows系统也会自动地显示相应的从属窗口。这两种情况下.windows系统都要在隐藏或显示拥有窗口之前,向其发送WM_SHOWWINDOW消息。偶尔,应用程序也有可能在不最小化或隐藏属主窗口情况下需要隐藏从属窗口.那么应用程序就使用函数ShowOwnedPopups,这个函数设置或删除所有从属窗口的WS_VISIBLE风格,并在隐藏或显示拥有窗口之前向它们发送WM_SHOWWINDOW消息.隐藏一个属主窗口并不影响其拥有窗口的显示状态。
如果一个父窗口是可见的,则与之相应的子窗口也是可见的。同样,在父窗口被隐藏时,子窗口也被隐藏。最小化父窗口也不影响子窗口的可见状态.这就是说,子窗口也随着父窗口被最小化,但其WS_VISIBLE风格依然没有改变.
尽管某一个窗口具有WS_VISIBLE风格,用户也有可能在屏幕上看不到这个窗口,因为其它的窗口可能会完全盖住了它,或是由于移动而超出了屏幕的边沿。一个可见的子窗口也是遵循由父子关系所建立的裁剪规则的.如果窗口的父窗口是不可见的,那么它也是不可见的。因为子窗口是相对于其父窗口的左上角,如果父窗口的移动超出了屏幕的边沿,子窗口也有可能这样。例如,尽管子窗口及其父窗口都具有WS_VISIBLE风格,但如果用户把父窗口移动到远远超出了屏幕的边沿,用户就不能看到子窗口。
最小最大化和恢复窗口
最大化窗口是具有WS_MAXIMIZE风格的窗口,通常,windows系统会把最大化窗口放大到填满整个屏幕,如果是子窗口,则可填满父窗口的客户区。尽管窗口的尺寸可被设置成与最大化窗口一样大,但最大化窗口还是稍有不同的,windows系统会自动地把窗口的标题栏移到屏幕或父窗口客户区的顶部,wmdows系统还要禁止窗口的改变大小边框和标题栏的窗口定位能力(这样,用户就不能通过拖动标题栏来移动窗口)。
最小化窗口是具有WS_MINIMIZE风格的窗口,通常,windows系统把窗口的尺寸减少到一个图符的尺寸,并把它移到屏幕或父窗口客户区的底部,屏幕或父窗口客户区的底部有时叫做图符区。如果应用程序不设定位置.windows系统则把最小化窗口移到图符区中第一个可用的位置。恢复窗口是恢复到原来的最小或最大尺寸相位置的窗口。
如果应用程序在函数CreateWindowEx中指定WS_MAXIMIZE or WS_MINIMIZE风格,那么窗口一开始就是最大化的或是最小化的。在创建了窗口之后,应用程序可通过函数CloseWindow最小化这个窗口,函数ArrangeIconicWindows用来把最小化的顶层窗口排列在屏幕的底部,或是把父窗口的最小化的子窗口排列在父窗口客户区的底部。
函数ShowWindow可以最小化、最大化或恢复一个窗口.同时还能设定窗口的可见性和激活状态,函数SetWindowPlacement与ShowWindow有相同的功能,但它还能屏蔽窗口默认的最小、最大和被恢复的位置。
函数IsZoomed用来确定一个窗口是否是最大,函数IsIconic确定—个窗口是否是最小化的。函数GetWindowPlacement检取窗门的最小、最大和被恢复的位置,也能用来确定窗口的显示状态。
如果windows系统接收到一条最大或恢复最小窗 口的命令,windows系统就向这个窗口发送一条WM_QUERYOPEN消息,如果窗口过程返回FALSE,windows系统就会忽略这条最大化或恢复命令。
windows系统自动把最大窗口的尺寸和位置设置成系统定义的最大窗口的默认值,应用程序能够通过函数SetWindowPlacement ,或是处理windows系统在将要最大化窗口时窗口接收到的WM_GETMINMAXINFO消息来屏蔽默认值.这条消息含有MINMAXINFO结构的指针.结构中含有windows系统用来设置最大尺少和位置的值,重置这些值也就改变了默认设置。
尺寸和位置
窗口的尺寸和位置是由一个限定矩形来表示的,它给出了相对于屏幕或父窗口的坐标。这个坐标是顶层窗口相对于屏幕左上角,或是子窗口相对于父窗口的左上角的坐标.应用程序在创建窗口时指定窗口的初始尺寸和位置,也可随时改变窗口的尺寸和位置。
窗口的尺寸(宽和高)是以象素为单位的,一个窗口的高度和宽度都可以为o,如果程序把某个窗口的高度和宽度都置成0,windows系统就把尺寸置成默认的最小窗口尺寸。应用程序是通过带有SM_CXMIN 和 SM_CYMIN标志的函数GetSystemMetrics来获取最小窗口的默认尺寸的。
应用程序可能要创建具有一定尺寸的客户区的窗口,函数AdjustWindowRect 和 AdjustWindowRectEx可根据所设计的客户区尺寸来计算所需窗口的尺寸,应用程序再把计算结果传给函数CreateWindowEx。
应用程序可把窗口的尺寸改变得很大,但最好不要超过屏幕的大小。在设置窗口的尺寸之前,应用程序应该用带有SM_CXSCREEN and SM_CYSCREEN 标志的函数GetSystemMetrics来检查屏幕的宽度和高度。
窗口的位置是由它左上角的坐标决定的,这些坐标有时叫做窗口坐标,总是相对于屏幕的左上角,对于子窗口来说,则是相对于其父窗口客户区的左上角。例如,某个顶层窗口的坐标是(10,10),那么它就被定位在屏幕左上角向右10个象素,向下10个象素的位置。如果—个子窗口的坐标是(10,10).那么它就被定位在其父窗口客户区定上角向右10个象素.向下10个象素的位置。
函数WindowFromPoint用来检取占取屏幕上某一点的窗口的句柄,函数ChildWindowFromPoint 和 ChildWindowFromPointEx则用来检取占取父窗口客户区中某一点的子窗口的句柄。
默认的尺寸和位置
应用程序可让windows系统计算一个顶层窗口的初始尺寸相位置,这是通过在函数CreateWindowEx.中指定CW_USEDEFAULT常量。如果应用程序把窗口的坐标置成CW_USEDEFAULT,而且应用程序还没有创建别的顶层窗口,windows系统就把新窗口的位置设置在相对于屏幕左上角的位置上,否则windows系统就把窗口的位置设置在相对于应用程序最近创建的顶层窗口的位置。同样,如果宽度和高度都设置成CW_USEDEFAULT. windows系统就会计算新窗口的尺寸,如果应用程序已创建了其它的顶层窗口,windows系统就根据应用程序最近创建的顶层窗口的尺寸来计算新窗口的尺寸。如果在创建子窗口或弹出窗口时设置CW_USEDEFAULT风格,那么windows系统就把窗口的尺寸设置成默认的最小窗口的尺寸.
跟踪尺寸
windows系统管理具有WS_THICKFRAME风格的窗口的最小和最大跟踪尺寸,具有这种风格的窗口有一个改变大小边框。最小跟踪尺寸是用户通过拖动窗口大小边框所能达到的最小窗口尺寸。同样,最大跟踪尺寸是用户通过拖动窗口大小边框所能达到的最大窗口尺寸。
窗门的最小和最大跟踪尺寸是在windows系统创建窗口时设置的系统定义的默认值。应用程序可通过处理WM_GETMINMAXINFO消息来获取或改变这些默认值。
系统命令
如果应用程序有一个带有系统菜单的窗口,就可以通过发送系统命令改变窗口的大小相位置,系统命令是在用户从系统菜单中选择命令时产生的,应用程序可通过向窗口发送WM_SYSCOMMAND消息来模拟用户的活动。下表列出的系统命令影响窗口的人小和位置:
命令 描述
SC_CLOSE 关闭窗口,这条命令向窗口发送一条WM_CLOSE消息,窗口完成消除和销毁所要做的每步工作
SC_MAXIMIZE 最大化窗口
SC_MINIMIZE 最小化窗口
SC_RESTORE 恢复最小或最大窗口到原来的大小和位置
SC_SIZE 启动一个改变大小命令,用户可以使用鼠标或键盘改变一个窗口的大小。
改变和位置大小的函数
创建了窗口之后,应用程序可调用下列函数来设置窗口的大小和位置,这些函数是SetWindowPlacement, MoveWindow, SetWindowPos, and DeferWindowPos,SetWindowPlacement设置窗口的最小化位置,最大化位置,恢复大小和位置和显示状态。MoveWindow和SetWindowPos函数很相似,都用来设置单个应用程序窗口的大小和位置,函数SetWindowPos则含有一系列影响窗口显示状态的标志,函数MoveWindow则不包含这些标志。使用函数BeginDeferWindowPos, DeferWindowPos,和EndDeferWindowPos 一起起用来同时设置一些窗口的大小、位置、Z次序中的位置和显示状态。
应用程序使用函数GetWindowRect检取窗口限定矩形的坐标.GetWindowRect用窗口的左上角和右下角填充RECT结构,这些坐标是相对于屏幕左上角的,对于窗口也一样。函数ScreenToClient 或 MapWindowPoints把子窗口限定矩形的屏幕坐标映射成相对于父窗口客户区的坐标。
函数GetClientRect用于检取窗口客户区的坐标,GetClientRect用客户区左上角和右下角坐标填充RECT结构,但这里的坐标是相对于客户区本身的。这就是说.客户区左上角的坐标总是(o,o),右下角的坐标是客户区的宽度和高度。
函数CascadeWindows该函数层叠排列指定父窗口的各指定子窗口。TileWindows该函数并到显示指定父窗口的各指定子窗口。
尺寸和位置消息
windows系统要向将要改变大小和位置的窗口发送WM_GETMINMAXINFO消息,例如,用户从系统菜单上选中Move或 Size命令或单击了大小边框或是标题栏,或者应用程序调用函数SetWindowPos移动或改变窗口大小时.发送WM_GETMINMAXINFO消息。WM_GETMINMAXINFO消息含有一个MINMAXINFO结构的指针,这个结构是窗口的默认的最大尺寸和位置,以及窗口的最小和最大跟踪尺寸。应用程序可以通过处理WM_GETMINMAXINFO消息并给MINMAXINFO结构的成员适当的设置来改变这些默认值。接收WM_GETMINMAXINFO消息的窗口必须具有WS_THICKFRAME 或 WS_CAPTION风格,具有WS_THICKFRAME风格的窗口在窗口创建过程中,或是在移动或改变大小时会接收到这条稍息。
windows系统还会向一个将要改变大小、位置、在z中的次序及显示状态时的窗口发送一条WM_WINDOWPOSCHANGING消息,这条消息含有一个WINDOWPOS结构的指针,这个结构指定了窗口新的尺寸、位置、z次序中的位置及显示状态。设置WM_WINDOWPOSCHANGED消息的WINDOWPOS结构成员对窗口并没有影响,一个必须处理WM_SIZE 和 WM_MOVE消息的窗口必须把WM_WINDOWPOSCHANGED消息传给函数DefWindowProc,否则windows系统不会向窗口发送WM_SIZE 和 WM_MOVE消息。
windows系统在某窗口创建或被改变大小的时候向该窗口发送WM_NCCALCSIZE消息,windows系统使用这条消息计算窗口客户区的大小以及相对于窗口的左上角的客户区的位置,窗口通常把这条消息传给默认的窗口过程,但是这条消息对要定制窗口客户区或在改变窗口大小时保留客户区的某一部分的应用程序来说是很有用的。
窗口销毁
通常,应用程序必须销毁所有由它创建的窗口,这是调用函数DestroyWindow来实现的。如果一个窗口被销毁,系统就会隐藏这个窗口,如果它是可见的,那么与该窗口相应的所有内部数据都被删除,这就使窗口句柄失效,应用程序也就不能再用它。
有许多窗口会在应用程序创建它们不久就删除,例如,应用程序通常在从用户得到足够的输入后删除对话框,并继续执行下去。应用程序最终要删除应用程序的主窗口(在结束之前)。
在销毁一个窗口之前,应用程序保留或删除所有与窗口相关的数据.还应该释放为窗口分配的所有系统资源,如果应用程序不释放这些资源,则由windows系统来释放这些资源。
销毁一个窗口并不影响创建这个窗口的窗口类,新窗口还可用这个窗口类来创建,由这种窗口类创建的所有窗口还会继续运转下去。
销毁一个窗口同时也销毁了窗口的子孙窗口,函数DestroyWindow首先把WM_DESTROY消息发给窗口.然后再传给它的子窗口和子孙窗门,这样窗口的子孙窗口随着窗口的销毁而销毁。
带有系统菜单的窗口在用户从系统中选中CLOSE时会接收到一条WM_CLOSE消息.通过处理这条消息,应用程序可在销毁窗口之前提示用户确认.如果用户确认窗口可以被销毁,应用程序就可调用函数DestroyWindow来销毁这个窗口。
如果将销毁的窗口是一个活动窗口,那么活动及焦点状态就会转到另一个窗口上,这个将要成为活动的窗口就是由alt+esc组合键确定的下一个窗口,这个新的活动窗口也就决定那一个窗口接收键盘焦点。
使用窗口
下一节讲解如何在应用程序中创建和使用窗口,如何管理父子窗口关系以及如何移动和改变一个窗口的大小。
创建主窗口
应用程序创建的第一个窗口通常是主窗口.创建主窗口是调用函数CreateWindowEx指定窗口类、窗口名、窗口风格、大小、位置、菜单句柄、实例句柄和创建数据。主窗口属于应用程序定义的窗口类,所以必须在创建主窗口之前,注册窗口类并提供窗口过程。
绝大多数应用程序部使用WS_OVERLAPPEDWINDOW风格来创建主窗口.这种风格给窗口一个标题栏、系统菜单、改变大小边框、最小和最大框,函数CreateWindowEx返回一个唯一标识此窗口的句柄。下面的范例创建了一个屑于应用程序定义的窗口类的主窗口,窗口名"Main Window"显示在窗口标题栏中。通过把WS_VSCROLL 和 WS_HSCROLL 与WS_OVERLAPPEDWINDOW风格组合使用,应用程序创建的主窗口除了具有由WS_OVERLAPPEDWINDOW风格所创建的窗口成员外,还有水平和垂直滚动条。出现了4次的CW_USEDEFAULT常量把窗口的初始尺寸和位置设置成系统定义的默认值,指定NULL而不是菜单句柄意思是说窗口有为该窗口类定义的菜单。
HINSTANCE hinst;
HWND hwndMain;
// Create the main window.
hwndMain = CreateWindowEx(
0, // no extended styles
"MainWClass", // class name
"Main Window", // window name
WS_OVERLAPPEDWINDOW | // overlapped window
WS_HSCROLL | // horizontal scroll bar
WS_VSCROLL, // vertical scroll bar
CW_USEDEFAULT, // default horizontal position
CW_USEDEFAULT, // default vertical position
CW_USEDEFAULT, // default width
CW_USEDEFAULT, // default height
(HWND) NULL, // no parent or owner window
(HMENU) NULL, // class menu used
hinstance, // instance handle
NULL); // no window creation data
if (!hwndMain)
return FALSE;
// Show the window using the flag specified by the program
// that started the application, and send the application
// a WM_PAINT message.
ShowWindow(hwndMain, SW_SHOWDEFAULT);
UpdateWindow(hwndMain); HINSTANCE hinst;
HWND hwndMain;
// Create the main window.
hwndMain = CreateWindowEx(
0, // no extended styles
"MainWClass", // class name
"Main Window", // window name
WS_OVERLAPPEDWINDOW | // overlapped window
WS_HSCROLL | // horizontal scroll bar
WS_VSCROLL, // vertical scroll bar
CW_USEDEFAULT, // default horizontal position
CW_USEDEFAULT, // default vertical position
CW_USEDEFAULT, // default width
CW_USEDEFAULT, // default height
(HWND) NULL, // no parent or owner window
(HMENU) NULL, // class menu used
hinstance, // instance handle
NULL); // no window creation data
if (!hwndMain)
return FALSE;
// Show the window using the flag specified by the program
// that started the application, and send the application
// a WM_PAINT message.
ShowWindow(hwndMain, SW_SHOWDEFAULT);
UpdateWindow(hwndMain);
注意前面的例子中,创建了主窗口之后调用函数ShowWindow,这是因为windows系统在创建了窗口之后并不会自动地显示它,给ShowWindow传给SW_SHOWDEFAULT标志.应用程序就可让启动应用程序的程序设置主窗口的初始显示状态,函数UpdateWindow向窗口发送了第一条WM_PAINT消息。
创建,统计子窗口及改变子窗口的大小
使用于窗口把窗口的客户区划分成不同的功能区域.创建一个子窗口也象创建一个主窗口一样调用函数CreateWindowEx。要创建一个应用程序定义的窗口类窗口,就必须在创建子窗口之前注册窗口类并提供窗口过程。必须给子窗口设置WS_CHILD风格并在创建子窗口时指定它的父窗口。
下面的例子通过创建3个大小相同的子窗口把应用程序主窗口的客户区分成3个功能区,每个子窗口的高度与主窗口的客户区等高,而宽度是客户区宽度的三分之一。主窗口创建子窗口是对WM_CREATE消息做出响应,这条消息是主窗口在它自己的窗口创建进程中收到的。因为每个子窗口都有WS_BORDER风格,那么每个子窗口都有一个边框。又因为没有指定WS_VISIBLE风格,每个子窗口在开始都是隐藏的。还要注意每个子窗口都赋予了一个子窗口标识。
主窗口改变子窗口的大小和位置以响应WM_SIZE消息,这条消息是主窗口在它的尺寸将要改变时接收到的。为响应WM_SIZE消息.主窗口调用函数GetWindowRect检取它的客户区的尺寸,又把这个尺寸传给函数EnumChildWindows, EnumChildWindows再把每—个子窗口的句柄传给应用程序定义的回调函数EnumChildProc,这个函数调用函数MoveWindow来改变每个子窗口的大小和位置;大小部位置取决于主窗口的客户区的尺寸及子窗口的标识。然后,EnumChildProc调用函数ShowWindow使得窗口可见。
#define ID_FIRSTCHILD 100
#define ID_SECONDCHILD 101
#define ID_THIRDCHILD 102
LONG APIENTRY MainWndProc(hwnd, uMsg, wParam, lParam)
HWND hwnd;
UINT uMsg;
UINT wParam;
LONG lParam;
{
RECT rcClient;
int i;
switch(uMsg) {
case WM_CREATE: // creating main window
// Create three invisible child windows.
for (i = 0; i < 3; i++)
CreateWindowEx( 0, "ChildWClass", (LPCTSTR) NULL, WS_CHILD | WS_BORDER, 0,0,0,0,
hwnd, (HMENU) (int) (ID_FIRSTCHILD + i), hinst, NULL);
return 0;
case WM_SIZE: // main window changed size
// Get the dimensions of the main window's client
// area, and enumerate the child windows. Pass the
// dimensions to the child windows during enumeration.
GetClientRect(hwnd, &rcClient);
EnumChildWindows(hwnd, EnumChildProc, (LPARAM) &rcClient);
return 0;
// Process other messages.
}
return DefWindowProc(hwnd, uMsg, wParam, lParam);
}
BOOL CALLBACK EnumChildProc(hwndChild, lParam)
HWND hwndChild;
LPARAM lParam;
{
LPRECT rcParent;
int i, idChild;
// Retrieve the child-window identifier. Use it to set the
// position of the child window.
idChild = GetWindowLong(hwndChild, GWL_ID);
if (idChild == ID_FIRSTCHILD)
i = 0;
else if (idChild == ID_SECONDCHILD)
i = 1;
else
i = 2;
// Size and position the child window.
rcParent = (LPRECT) lParam;
MoveWindow(hwndChild, (rcParent->right / 3) * i, 0, rcParent->right / 3, rcParent->bottom, TRUE);
// Make sure the child window is visible.
ShowWindow(hwndChild, SW_SHOW);
return TRUE;
}
销毁窗口
函数DestroyWindow用来销毁一个窗口。通常,在销毁一个窗口之前要发送一条WM_CLOSE消息,给窗口一个机会提示用户在窗口被销毁之前确认一下。含有系统菜单的窗口在用户选中菜单中的Close命令时会自动地接收到一条WM_CLOSE消息,如果用户确认这个窗口可以被销毁,应用程序就调用DestroyWindow,windows系统在窗口从屏幕上删除后发送一条WM_DESTROY消息。为响应WM_DESTROY消息,窗口保存数据并释放所有分配给它的资源。主窗口调用函数PostQuitMessage结束对WM_DESTROY消息的处理,退出这个应用程序。
下面的范例说明了在销毁窗口之前,如何提示用户确认.为响应WM_CLOSE,这个例子显示了一个含有Yes, OK, 和 Cancel按钮的对话框,如果用户单击Yes按钮,DestroyWindow就被调用,否则,窗口就不会被销毁。因为将要销毁的是一个主窗口,这个例子调用PostQuitMessage来响应WM_DESTROY。
case WM_CLOSE:
// Create the message box. If the user clicks
// the Yes button, destroy the main window.
if (MessageBox(hwnd, szConfirm, szAppName, MB_YESNOCANCEL) == IDYES)
DestroyWindow(hwndMain);
else
return 0;
case WM_DESTROY:
// Post the WM_QUIT message to
// quit the application terminate.
PostQuitMessage(0);
return 0;
窗口函数 结构 消息
AdjustWindowRect
AdjustWindowRectEx
ArrangeIconicWindows
BeginDeferWindowPos
BringWindowToTop
CascadeWindows
ChildWindowFromPoint
ChildWindowFromPointEx
CloseWindow
CreateWindow
CreateWindowEx
DeferWindowPos
DestroyWindow
EnableWindow
EndDeferWindowPos
EnumChildProc
EnumChildWindows
EnumThreadWindows
EnumThreadWndProc
EnumWindows
EnumWindowsProc
FindWindow
FindWindowEx
GetClientRect
GetDesktopWindow
GetForegroundWindow
GetLastActivePopup
GetNextWindow
GetParent
GetTopWindow
GetWindow
GetWindowPlacement
GetWindowRect
GetWindowText
GetWindowTextLength
GetWindowThreadProcessId
IsChild
IsIconic
IsWindow
IsWindowUnicode
IsWindowVisible
IsZoomed
MoveWindow
OpenIcon
SetForegroundWindow
SetParent
SetWindowLong
SetWindowPlacement
SetWindowPos
SetWindowText
ShowOwnedPopups
ShowWindow
ShowWindowAsync
TileWindows
WindowFromPoint
WinMain
Obsolete Functions
AnyPopup
EnumTaskWindows
GetSysModalWindow
GetWindowTask
SetSysModalWindow
CLIENTCREATESTRUCT
COPYDATASTRUCT
CREATESTRUCT
MDICREATESTRUCT
MINMAXINFO
NCCALCSIZE_PARAMS
STYLESTRUCT
WINDOWPLACEMENT
WINDOWPOS
WM_ACTIVATE
WM_ACTIVATEAPP
WM_CANCELMODE
WM_CHILDACTIVATE
WM_CLOSE
WM_COMPACTING
WM_COPYDATA
WM_CREATE
WM_DESTROY
WM_ENABLE
WM_ENTERSIZEMOVE
WM_EXITSIZEMOVE
WM_GETICON
WM_GETMINMAXINFO
WM_GETTEXT
WM_GETTEXTLENGTH
WM_INPUTLANGCHANGE
WM_INPUTLANGCHANGEREQUEST
WM_MOVE
WM_MOVING
WM_NCACTIVATE
WM_NCCALCSIZE
WM_NCCREATE
WM_NCDESTROY
WM_PARENTNOTIFY
WM_POWER
WM_QUERYDRAGICON
WM_QUERYOPEN
WM_QUIT
WM_SETICON
WM_SETTEXT
WM_SETTINGCHANGE
WM_SHOWWINDOW
WM_SIZE
WM_SIZING
WM_STYLECHANGED
WM_STYLECHANGING
WM_USERCHANGED
WM_WINDOWPOSCHANGED
WM_WINDOWPOSCHANGING
WM_WININICHANGE