转载

Windows程序消息机制浅析

1、消息

消息是由MSG结构体来表示的。如下:

1 typedef struct tagMSG { 2   HWND   hwnd; 3   UINT   message; 4   WPARAM wParam; 5   LPARAM lParam; 6   DWORD  time; 7   POINT  pt; 8 } MSG

2、WinMain函数的定义

WinMain函数的原型声明如下:

1 int WINAPI WinMain( 2   HINSTANCE hInstance,            // handle to current instance 3   HINSTANCE hPrevInstance,        // handle to previous instance 4   LPSTR lpCmdLine,                // command line 5   int nCmdShow                    // show state 6 );

3、窗口的创建:设计一个窗口类、注册窗口类、创建窗口、显示及更新窗口。

设计一个窗口:WNDCLASS结构体的定义如下:

 1 typedef struct _WNDCLASS {  2     UINT       style;  3     WNDPROC    lpfnWndProc;  4     int        cbClsExtra;  5     int        cbWndExtra;  6     HINSTANCE  hInstance;  7     HICON      hIcon;  8     HCURSOR    hCursor;  9     HBRUSH     hbrBackground; 10     LPCTSTR    lpszMenuName; 11     LPCTSTR    lpszClassName; 12 } WNDCLASS;

注册窗口类:注册函数的原型声明如下:

1 ATOM RegisterClass( 2   CONST WNDCLASS *lpWndClass  // class data 3 );

创建窗口:CreateWindow函数的原型声明如下:

 1 HWND CreateWindow(  2   LPCTSTR lpClassName,  // registered class name  3   LPCTSTR lpWindowName, // window name  4   DWORD dwStyle,        // window style  5   int x,                // horizontal position of window  6   int y,                // vertical position of window  7   int nWidth,           // window width  8   int nHeight,          // window height  9   HWND hWndParent,      // handle to parent or owner window 10   HMENU hMenu,          // menu handle or child identifier 11   HINSTANCE hInstance,  // handle to application instance 12   LPVOID lpParam        // window-creation data 13 );

更新及更新窗口:显示窗口ShowWindow函数的原型声明如下:

1 BOOL ShowWindow( 2   HWND hWnd,     // handle to window 3   int nCmdShow   // show state 4 );

更新及更新窗口:更新窗口UpdateWindow函数的原型声明如下:

1 BOOL UpdateWindow(HWND hWnd);

4、消息循环:不断从消息队列中取出消息,并进行响应。

1 BOOL GetMessage( 2   LPMSG lpMsg,         // message information 3   HWND hWnd,           // handle to window 4   UINT wMsgFilterMin,  // first message 5   UINT wMsgFilterMax   // last message 6 );

Windows应用程序消息处理机制如下图所示:

Windows程序消息机制浅析

Windows程序消息机制浅析

  1. 操作系统接收到应用程序的窗口消息,将消息投递到应用程序的消息队列中。

  2. 应用程序在消息循环中调用GetMessage函数从消息队列中取出一条一条的消息。取出消息后,应用程序可以对消息进行一些预处理,例如,放弃对某些消息的响应,或者调用TranslateMessage产生新的消息。

  3. 应用程序调用DispatchMessage,将消息回传给操作系统。消息是由MSG结构体对象来表示的,其中就包含了接收消息的窗口的句柄。因此,DispatchMessage函数总能进行正确的传递。

  4. 系统利用WNDCLASS结构体的lpfnWndProc成员保存的窗口过程函数的指针调用窗口过程,对消息进行处理(即“系统给应用程序发送了消息”)。

5、编写窗口过程函数:窗口过程函数的声明形式如下:

1 LRESULT CALLBACK WindowProc( 2   HWND hwnd,      // handle to window 3   UINT uMsg,      // message identifier 4   WPARAM wParam,  // first message parameter 5   LPARAM lParam   // second message parameter 6 );

提示:系统通过窗口过程函数的地址(指针)来调用窗口过程函数,而不是名字。

例:WinMain.cpp

 1 #include <windows.h>  2 #include <stdio.h>  3   4 LRESULT CALLBACK WinSunProc(  5                   HWND hwnd,      // handle to window  6                   UINT uMsg,      // message identifier  7                   WPARAM wParam,  // first message parameter  8                   LPARAM lParam   // second message parameter  9                 ); 10  11 int WINAPI WinMain( 12             HINSTANCE hInstance,      // handle to current instance 13             HINSTANCE hPrevInstance,  // handle to previous instance 14             LPSTR lpCmdLine,          // command line 15             int nCmdShow              // show state 16            ) 17 { 18     WNDCLASS wndcls; 19     wndcls.cbClsExtra=0; 20     wndcls.cbWndExtra=0; 21     wndcls.hbrBackground=(HBRUSH)GetStockObject(BLACK_BRUSH); 22     wndcls.hCursor=LoadCursor(NULL,IDC_CROSS); 23     wndcls.hIcon=LoadIcon(NULL,IDI_ERROR); 24     wndcls.hInstance=hInstance; 25     wndcls.lpfnWndProc=WinSunProc; 26     wndcls.lpszClassName="bedrock32"; 27     wndcls.lpszMenuName=NULL; 28     wndcls.style=CS_HREDRAW | CS_VREDRAW; 29     RegisterClass(&wndcls); 30  31     HWND hwnd; 32     hwnd=CreateWindow("bedrock32","http://www.cnblogs.com/bedrock32",WS_OVERLAPPEDWINDOW, 33         0,0,600,400,NULL,NULL,hInstance,NULL); 34  35     ShowWindow(hwnd,SW_SHOWNORMAL); 36     UpdateWindow(hwnd); 37  38     MSG msg; 39     while(GetMessage(&msg,NULL,0,0)) 40     { 41         TranslateMessage(&msg); 42         DispatchMessage(&msg); 43     } 44     return msg.wParam; 45 } 46  47 LRESULT CALLBACK WinSunProc( 48                   HWND hwnd,      // handle to window 49                   UINT uMsg,      // message identifier 50                   WPARAM wParam,  // first message parameter 51                   LPARAM lParam   // second message parameter 52                 ) 53 { 54     switch(uMsg) 55     { 56     case WM_CHAR: 57         char szChar[20]; 58         sprintf(szChar,"char code is %d",wParam); 59         MessageBox(hwnd,szChar,"char",0); 60         break; 61     case WM_LBUTTONDOWN: 62         MessageBox(hwnd,"mouse clicked","message",0); 63         HDC hdc; 64         hdc=GetDC(hwnd); 65         TextOut(hdc,0,50,"我是高手",strlen("我是高手")); 66         //ReleaseDC(hwnd,hdc); 67         break; 68     case WM_PAINT: 69         HDC hDC; 70         PAINTSTRUCT ps; 71         hDC=BeginPaint(hwnd,&ps); 72         TextOut(hDC,0,0,"http://www.cnblogs.com/bedrock32",strlen("http://www.cnblogs.com/bedrock32")); 73         EndPaint(hwnd,&ps); 74         break; 75     case WM_CLOSE: 76         if(IDYES==MessageBox(hwnd,"是否真的结束?","message",MB_YESNO)) 77         { 78             DestroyWindow(hwnd); 79         } 80         break; 81     case WM_DESTROY: 82         PostQuitMessage(0); 83         break; 84     default: 85         return DefWindowProc(hwnd,uMsg,wParam,lParam); 86     } 87     return 0; 88 }

Windows程序消息机制浅析

正文到此结束
Loading...