前言
Win32窗口程序基础教程,前期项目设置:
右键打开项目属性:

按图配置:


这里Debug和Release模式要分开设置;


因为我的项目不需要太高的精度;



WinMain
WinMain是windows的关键字,类似控制台程序的mian函数,都窗口程序的入口;
1 2 3 4
| HINSTANCE hInstance HINSTANCE hPrevInstance LPSTR lpCmdLine int nCmdShow
|
创建窗口关键api(这里使用Ex版本):
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37
| WNDCLASSEX wc;
RegisterClassEx(&w); HWND hWnd = CreateWindowExA( DWORD dwExStyle, LPCSTR lpClassName, LPCSTR lpWindowName, DWORD dwStyle, int X, int Y, int nWidth, int nHeight, HWND hWndParent, HMENU hMenu, HINSTANCE hInstance, LPVOID lpParam ); ShowWindow( HWND hWnd, int nCmdShow ); GetMessage( LPMSG lpMsg, HWND hWnd, UINT wMsgFilterMin, UINT wMsgFilterMax );
TranslateMessage( const MSG *lpMsg );
DispatchMessage( const MSG *lpMsg );
|
WinMain的完整代码:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50
| int __stdcall WinMain( HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow) { const auto pClassName = "littlePerilla"; WNDCLASSEX wc = { 0 }; wc.cbSize = sizeof(wc); wc.style = CS_OWNDC; wc.lpfnWndProc = WindowProc; wc.cbClsExtra = 0; wc.cbWndExtra = 0; wc.hInstance = hInstance; wc.hIcon = nullptr; wc.hCursor = nullptr; wc.hbrBackground = nullptr; wc.lpszMenuName = nullptr; wc.lpszClassName = pClassName; wc.hIconSm = nullptr; RegisterClassEx(&wc); HWND hWnd = CreateWindowExA( 0, pClassName, "Happy National Day", WS_CAPTION | WS_MINIMIZEBOX | WS_SYSMENU, 200, 200, 800, 600, nullptr, nullptr, hInstance, nullptr ); ShowWindow(hWnd, SW_SHOW); MSG msg; BOOL gResult; while ((gResult = GetMessage(&msg, nullptr, 0, 0)) > 0) { TranslateMessage(&msg); DispatchMessage(&msg); }
if (gResult == -1) return -1;
return msg.wParam; }
|
Windows消息机制
WindowProc之前,先了解Windows的消息机制;
系统中发生了某个事件。
Windows把这个事件翻译为消息,然后把它放到消息队列中。
应用程序从消息队列中接收到这个消息,把它存放在Msg记录中。
应用程序把消息传递给一个适当的窗口的窗口过程。
窗口过程响应这个消息并进行处理。

WindowProc
只是个函数名,不固定,可以更改,只要赋值给窗口结构体的lpfnWndProc即可;
msg: 代表系统消息事件的种类,多达上千种?
每种不同的msg,对应的wParam和lParam参数的作用不一样,可查看MSDN了解具体作用;
在WndProc中拦截不同的消息做相应的处理;
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44
| LRESULT __stdcall WindowProc( HWND hWnd, UINT msg, WPARAM wParam, LPARAM lParam) { switch (uMsg) { case WM_CLOSE: PostQuitMessage(69); break; case WM_KEYDOWN: if (wParam == 'F') { SetWindowText(hWnd, "RESPECT"); } break; case WM_KEYUP: if (wParam == 'F') { SetWindowText(hWnd, "FUCKYOU"); } break; case WM_CHAR: { static std::string title; title.push_back((char)wParam); SetWindowText(hWnd, title.c_str()); } break; case WM_LBUTTONDOWN: { POINTS pt = MAKEPOINTS(lParam); std::ostringstream oss; oss << "(" << pt.x << "," << pt.y << ")"; SetWindowText(hWnd, oss.str().c_str()); } break; case WM_DESTROY: PostQuitMessage(96); break; } return DefWindowProc(hWnd, uMsg, wParam, lParam); }
|