win32应用程序消息机制(窗口的建立过程)
来源:互联网 发布:.tv域名前景 编辑:程序博客网 时间:2024/05/16 23:40
窗口创建过程
注册窗口类
- win32中通过调用RegisterClassEx API来注册窗口样式,相当于指定一个窗口模板.
- 通过WNDCLASSEX结构体来指定窗口类的样式,WNDCLASSEX 是一个窗口风格样式的设置结构体.
具体代码如下
//由入口函数WinMain调用此函数ATOM MyRegisterClass(HINSTANCE hInstance){ //指定窗口类的样式的结构体 WNDCLASSEXW wcex; wcex.cbSize = sizeof(WNDCLASSEX); wcex.style = CS_HREDRAW | CS_VREDRAW; wcex.lpfnWndProc = WndProc; wcex.cbClsExtra = 0; wcex.cbWndExtra = 0; wcex.hInstance = hInstance; wcex.hIcon = LoadIcon(hInstance, MAKEINTRESOURCE(IDI_WIN32DEMO)); wcex.hCursor = LoadCursor(nullptr, IDC_ARROW); wcex.hbrBackground = (HBRUSH)(COLOR_WINDOW+1); wcex.lpszMenuName = MAKEINTRESOURCEW(IDC_WIN32DEMO); wcex.lpszClassName = szWindowClass; wcex.hIconSm = LoadIcon(wcex.hInstance, MAKEINTRESOURCE(IDI_SMALL)); //RegisterClassExW函数的功能就是根据给定窗口类的样式的结构体wcex注册窗口类 return RegisterClassExW(&wcex);}
cbSize
存储表示该结构大小的字节数,通常以sizeof(WNDCLASSEX)的形式对该域进行设置 一定要确保在调用
一定要在 GetClassInfoEx 前设置该值
style
存储表示窗口类风格的整数,它决定了该窗口的外观和内在特征。
可以使用’|‘进行多个选项绑定
具体绑定原理参见:枚举值的组合使用
lpfnWndProc
- lp :ong point 指针。
- fn :Function 函数。
- wnd :window 窗口
proc :process 过程,步骤
所以lpfnWndProc就是指向窗口处理过程的函数指针
必须使用 CallWindowProc 函数去调用窗口过程
cbClsExtra
为窗口类的额外信息做记录,初始化为0。
一般用得很少
cbWndExtra
记录窗口实例的额外信息,系统初始为0
如果应用程序使用WNDCLASSEX注册在资源文件中使用CLASS指令创建的对话框, 则必须将此成员设置为DLGWINDOWEXTRA
hInstance
该窗口类的窗口过程所属的应用实例
hIcon
存储该类窗口的图标的句柄
如果设置为NULL, 系统将提供默认图标
hCursor
存储该窗口光标的句柄
- 该域必须是一个光标资源的句柄。
- 如果为NULL, 则只要鼠标移动到应用程序的窗口中, 应用程序就必须显式设置光标形状
hbrBackground
窗口类的背景刷.
为背景刷句柄,也可以为系统颜色值
lpszMenuName
存储以空结尾的指定类菜单资源名的字符串指针
- 类菜单资源名已经在资源文件中进行了定义。
- 如果使用整数来标识菜单, 请使用MAKEINTRESOURCE宏
- 如果此成员为NULL, 属于此类的Windows没有默认菜单
lpszClassName
当前窗口类的名称
使用当前窗口类的唯一标识符
hIconSm
存储该类窗口小图标的句柄。
创建窗口
注册窗口类后,就可以创建窗口了,创建窗口的有关语句如下:
////由入口函数WinMain调用此函数BOOL InitInstance(HINSTANCE hInstance, int nCmdShow){ hInst = hInstance; // 将实例句柄存储在全局变量中 // 通过调用CreateWindowW来创建窗口 HWND hWnd = CreateWindowW(szWindowClass, szTitle, WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, 0, CW_USEDEFAULT, 0, nullptr, nullptr, hInstance, nullptr); if (!hWnd) { return FALSE; } ShowWindow(hWnd, nCmdShow); UpdateWindow(hWnd); return TRUE;}
参数说明
参数1:登记的窗口类名,这个类名刚才咱们在注册窗口时已经定义过了。
参数2:用来表明窗口的标题。
参数3: 用来表明窗口的风格,如有无最大化,最小化按纽啊什么的。
参数4,5: 用来表明程序运行后窗口在屏幕中的坐标值。
参数6,7: 用来表明窗口初始化时(即程序初运行时)窗口的大小,即宽度与高度。
参数8: 在创建窗口时可以指定其父窗口,这里没有父窗口则参数值为0。
参数9: 用以指明窗口的菜单,菜单以后会讲,这里暂时为0。
参数10:该窗口类的窗口过程所属的应用实例
最后一个参数是附加数据,会被传递到窗口过程中。一般都是0。
显示和更新窗口
API函数CreateWindow创建完窗口后,要想把它显示出现,还必须调用另一个API函数ShowWindows.形式为:
ShowWindow (hWnd, nCmdShow);
- hwnd: 窗口句柄,告诉ShowWindow()显示哪一个窗口
- nCmdShow:告诉它如何显示这个窗口.
- 最小化(SW_MINIMIZE)
- 普通(SW_SHOWNORMAL)
- 最大化(SW_SHOWMAXIMIZED)
WinMain在创建完窗口后就调用ShowWindow函数,并把iCmdShow参数传送给这个窗口。
WinMain()调用完ShowWindow后,还需要调用函数UpdateWindow使窗口得到更新.
创建消息循环
Windows为每个正在运行的应用程序都保持一个消息队列。
息响应机制是在Win32子系统中实现的.
- 为什么不在内核中实现?
- 因为内核越简单越好
- 如果在内核中实现, 则会使内核占用大量资源
- 可能会引起不稳定
过程
- 当按下鼠标或者键盘时,Windows并不是把这个输入事件直接送给应用程序,
- 而是将输入的事件先翻译成一个消息,
- 然后把这个消息放入到这个应用程序的消息队列中去。
- 应用程序的WinMain函数通过执行一段代码(主消息循环)从她的队列中来检索Windows送往她的消息。
- 然后WinMain就把这些消息分配给相应的窗口函数以便处理它们,
这段代码是一段循环代码,故称为”消息循环”
具体代码如下
// 主消息循环: //通过GetMessage函数获取当前应用程序的消息队列的消息 while (GetMessage(&msg, nullptr, 0, 0)) { if (!TranslateAccelerator(msg.hwnd, hAccelTable, &msg)) { //消息翻译 TranslateMessage(&msg); //消息分发 DispatchMessage(&msg); } }//MSG的定义 在WinUser.h中typedef struct tagMSG { HWND hwnd; UINT message; WPARAM wParam; LPARAM lParam; DWORD time; POINT pt;#ifdef _MAC DWORD lPrivate;#endif} MSG, *PMSG, NEAR *NPMSG, FAR *LPMSG;
MSG结构体参数解析
- hwnd
- 消息要发送到的那个窗口的句柄,
- 这个窗口就是用CreateWindows函数创建的那一个。
- 如果是在一个有多个窗口的应用程序中,用这个参数就可决定让哪个窗口接收消息。
- message
- 消息值, UINT类型,它唯一标识了一种消息类型。
- 每种消息类型都在Windows文件中定义了,这些常量都以WM_开始后面带一些描述了消息特性的名称。
- wParam,lParam
- 一个32位的附加信息,UINT类型,这个值的意义由message决定
- wParam,lParam和message一起决定要进行怎样的操作
- 通常作为指针来使用
- time
- 消息创建的时间
- 在这个域中写入的并不是日期,而是从Windows启动后所测量的时间值
- Windows用这个域来使用消息保持正确的顺序。
- pt
- 消息创建时鼠标所在屏幕当中的位置
GetMessage
GetMessage( _Out_ LPMSG lpMsg, _In_opt_ HWND hWnd, _In_ UINT wMsgFilterMin, _In_ UINT wMsgFilterMax);
- 第一个参数是要接收消息的MSG结构的地址,
- 第二个参数表示窗口句柄,NULL则表示要获取该应用程序创建的所有窗口的消息;
- 第三,四参数指定消息范围。
在接收到除WM_QUIT之外的任何一个消息后,GetMessage()都返回TRUE。
如果GetMessage收到一个WM_QUIT消息,则返回FALSE,结束消息循环,从而终止应用程序。
TranslateMessage
将用GetMessage读入的消息翻译成一些键盘消息
对大多数消息来说它并不起什么作用
DispatchMessage
在注册窗口类时曾提到过,注册窗口类时,指定Windows把函数WindosProc作为窗口处理过程。就是说,Windows会调用函数WindowsProc()来处理这个消息。在WindowProc()处理完消息后,代码又循环到开始去接收另一个消息,这样就完成了一个消息循环。
- win32应用程序消息机制(窗口的建立过程)
- Win32消息机制(窗口实现过程)
- Win32消息机制(窗口实现过程)
- Win32的消息机制
- 浅谈Win32的窗口建立
- opengl win32窗口的建立
- win32多窗口的建立
- cocos2d-x 建立自己的层级窗口消息机制
- cocos2d-x 建立自己的层级窗口消息机制 .
- Win32中窗口的创建和消息机制以及MFC对Win32的封装简介
- Win32中窗口的创建和消息机制以及MFC对Win32的封装简介
- [Win32]Win32窗口应用程序的框架
- 从Windows消息的角度看窗口应用程序运行过程
- Win32创建窗口的过程
- Win32窗口机制和消息机制整体流程
- Directx(Win32消息机制)
- win32开发(消息机制)
- vc++窗口的创建过程(MFC消息机制的经典文章)
- 欢迎使用CSDN-markdown编辑器
- 《计算机网络》谢希仁(第7版) 第三章
- 大前端资源汇总
- dubbo直连、只订阅、只注册
- LeetCode 29. Divide Two Integers
- win32应用程序消息机制(窗口的建立过程)
- C语言示例的反汇编生成以及堆栈调用分析
- 【Linux】管道容量及缓冲区的存储方式
- 数据库SQL优化大总结之 百万级数据库优化方案
- 单例模式
- SpringMVC文件上传(转载)
- HDU 5974
- 杭电 Is It A Tree? 并查集 有向图是否为树
- 文件拷贝-上传文件