Windows 32 is quite fun. I bought a book on Windows 32 and learned how Windows 32 really works, especially the message loop. In fact, the most important thing about Windows 32 is the proc function you wrote, the windowproc function you write is called to receive any messages in a message loop. If someone finds it painful to get started with Windows 32, we suggest you take a look at Sun Xin's c ++ 20 lecture in the first lecture to ensure that there are gains.
Windows32 does not need to re-start or end the code by yourself. You can use msdn with skills to copy the function prototype... after writing it for the first time, you can copy it for the second time, and then modify it.
There are two ways to obtain HDC (device environment handle)
Use beginpaint (hwnd, & PS) and endpaint (hwnd, & PS) in pairs );
2. Use getdc (hwnd), releasedc (hwnd, HDC) in pairs );
Just now, I used two methods to test the effect:
#include<windows.h>LRESULT CALLBACK WindowProc( HWND hwnd, // handle to window UINT uMsg, // message identifier WPARAM wParam, // first message parameter LPARAM lParam // second message parameter);int WINAPI WinMain( HINSTANCE hInstance, // handle to current instance HINSTANCE hPrevInstance, // handle to previous instance LPSTR lpCmdLine, // command line int nCmdShow // show state ){static TCHAR szAppName[]=TEXT("AppName");HWND hwnd;MSG msg;WNDCLASS wndclass;wndclass.cbClsExtra=0;wndclass.cbWndExtra=0;wndclass.hbrBackground=(HBRUSH)GetStockObject(WHITE_BRUSH);wndclass.hCursor=LoadCursor(NULL,IDC_ARROW);wndclass.hIcon=LoadIcon(NULL,IDI_APPLICATION);wndclass.hInstance=hInstance;wndclass.lpfnWndProc=WindowProc;wndclass.lpszClassName=szAppName;wndclass.lpszMenuName=NULL;wndclass.style=CS_HREDRAW|CS_VREDRAW;if(!RegisterClass(&wndclass)){MessageBox(NULL,TEXT("This program requires Windows NT"),szAppName,MB_ICONERROR);}hwnd=CreateWindow( szAppName, // registered class name TEXT("This is title"), // window name WS_OVERLAPPEDWINDOW, // window style CW_USEDEFAULT, // horizontal position of window CW_USEDEFAULT, // vertical position of window CW_USEDEFAULT, // window width CW_USEDEFAULT, // window height NULL, // handle to parent or owner window NULL, // menu handle or child identifier hInstance, // handle to application instance NULL // window-creation data);ShowWindow(hwnd,nCmdShow);UpdateWindow(hwnd);while(GetMessage(&msg,NULL,0,0)){TranslateMessage(&msg);DispatchMessage(&msg);}return msg.wParam;}LRESULT CALLBACK WindowProc( HWND hwnd, // handle to window UINT uMsg, // message identifier WPARAM wParam, // first message parameter LPARAM lParam // second message parameter){HDC hdc;PAINTSTRUCT ps;TCHAR zsBuffer[20];switch(uMsg){case WM_CREATE://hdc=GetDC(hwnd);//TextOut(hdc,0,0,TEXT("hello,world"),strlen("hello,world"));//ReleaseDC(hwnd,hdc);return 0;case WM_PAINT:hdc=BeginPaint(hwnd,&ps);TextOut(hdc,0,0,TEXT("WM_PAINT"),strlen("WM_PAINT"));EndPaint(hwnd,&ps);return 0;case WM_DESTROY:PostQuitMessage(0);return 0;}return DefWindowProc(hwnd,uMsg,wParam,lParam);}
The effect is the same as expected.
However:
#include<windows.h>LRESULT CALLBACK WindowProc( HWND hwnd, // handle to window UINT uMsg, // message identifier WPARAM wParam, // first message parameter LPARAM lParam // second message parameter);int WINAPI WinMain( HINSTANCE hInstance, // handle to current instance HINSTANCE hPrevInstance, // handle to previous instance LPSTR lpCmdLine, // command line int nCmdShow // show state ){static TCHAR szAppName[]=TEXT("AppName");HWND hwnd;MSG msg;WNDCLASS wndclass;wndclass.cbClsExtra=0;wndclass.cbWndExtra=0;wndclass.hbrBackground=(HBRUSH)GetStockObject(WHITE_BRUSH);wndclass.hCursor=LoadCursor(NULL,IDC_ARROW);wndclass.hIcon=LoadIcon(NULL,IDI_APPLICATION);wndclass.hInstance=hInstance;wndclass.lpfnWndProc=WindowProc;wndclass.lpszClassName=szAppName;wndclass.lpszMenuName=NULL;wndclass.style=CS_HREDRAW|CS_VREDRAW;if(!RegisterClass(&wndclass)){MessageBox(NULL,TEXT("This program requires Windows NT"),szAppName,MB_ICONERROR);}hwnd=CreateWindow( szAppName, // registered class name TEXT("This is title"), // window name WS_OVERLAPPEDWINDOW, // window style CW_USEDEFAULT, // horizontal position of window CW_USEDEFAULT, // vertical position of window CW_USEDEFAULT, // window width CW_USEDEFAULT, // window height NULL, // handle to parent or owner window NULL, // menu handle or child identifier hInstance, // handle to application instance NULL // window-creation data);ShowWindow(hwnd,nCmdShow);UpdateWindow(hwnd);while(GetMessage(&msg,NULL,0,0)){TranslateMessage(&msg);DispatchMessage(&msg);}return msg.wParam;}LRESULT CALLBACK WindowProc( HWND hwnd, // handle to window UINT uMsg, // message identifier WPARAM wParam, // first message parameter LPARAM lParam // second message parameter){HDC hdc;PAINTSTRUCT ps;TCHAR zsBuffer[20];switch(uMsg){case WM_CREATE://hdc=GetDC(hwnd);//TextOut(hdc,0,0,TEXT("hello,world"),strlen("hello,world"));//ReleaseDC(hwnd,hdc);return 0;case WM_PAINT:hdc=GetDC(hwnd);TextOut(hdc,0,0,TEXT("WM_PAINT"),strlen("WM_PAINT"));ReleaseDC(hwnd,hdc);return 0;case WM_DESTROY:PostQuitMessage(0);return 0;}return DefWindowProc(hwnd,uMsg,wParam,lParam);}
Wm_paint is displayed in the form, but it is obvious that the screen is still flashing.
Textout is used for output:
Let's take a look at its definition:
Textout and drawtext are both used to write functions. What is the difference between them? As a matter of fact, you only need to check the two function prototypes of msdn, and you will all know that textout is used to determine the specific location, and drawtext is used to determine the region.
With the function prototype, everything can be solved.
Which of the following has helped me to explain the differences between the above two methods for obtaining HDC? Why is there a pop-up screen?
The answer has been found:
case WM_PAINT:hdc=BeginPaint(hwnd,&ps);//TextOut(hdc,0,0,TEXT("WM_PAINT"),strlen("WM_PAINT"));//TextOut(hdc,200,200,TEXT("WM_PAINT"),strlen("WM_PAINT"));//SetTextAlign(hdc,TA_RIGHT);for(int i=0;i<10;++i){for(int j=0;j<10;++j){TextOut(hdc,i*50,j*50,TEXT("HELLO"),strlen("HELLO"));}}EndPaint(hwnd,&ps);return 0;
You can also use textout to output variables:
case WM_PAINT:hdc=BeginPaint(hwnd,&ps);//TextOut(hdc,0,0,TEXT("WM_PAINT"),strlen("WM_PAINT"));//TextOut(hdc,200,200,TEXT("WM_PAINT"),strlen("WM_PAINT"));SetTextAlign(hdc,TA_RIGHT);for( i=0;i<10;++i){for( j=0;j<10;++j){TextOut(hdc,i*50,j*50,szBuffer,wsprintf(szBuffer,TEXT("%d"),i*j));}}//TextOut(hdc,200,200,szBuffer,wsprintf(szBuffer,TEXT("%d"),i*j));EndPaint(hwnd,&ps);return 0;
Textmeric related operations:
Lresult callback windowproc (hwnd, // handle to window uint umsg, // message identifier wparam, // first message parameter lparam // second message parameter) {static int cxclient, cyclient; HDC; paintstruct pS; int I = 50, j = 20; tchar szbuffer [20]; textmetric TM; Switch (umsg) {Case wm_create: // HDC = getdc (hwnd); // textout (HDC, 0, 0, text ("Hello, world"), strlen ("Hello, world ")); // releasedc (hwnd, HDC); Return 0; Case wm_paint: HDC = beginpaint (hwnd, & PS); gettextmetrics (HDC, & TM); textout (HDC, 0, 0, szbuffer, wsprintf (szbuffer, text ("% d"), TM. tmavecharwidth); // character width textout (HDC, szbuffer, wsprintf (szbuffer, text ("% d"), TM. tmheight + TM. tmexternalleading); // character height endpaint (hwnd, & PS); Return 0; Case wm_size: HDC = beginpaint (hwnd, & PS); cxclient = loword (lparam ); cyclient = hiword (lparam); gettextmetrics (HDC, & TM); textout (HDC, 0,100, szbuffer, wsprintf (szbuffer, text ("% d"), cxclient/TM. tmavecharwidth); // The maximum number of characters displayed in a row in textout (HDC, 0,150, szbuffer, wsprintf (szbuffer, text ("% d"), cyclient/(TM. tmheight + TM. tmexternalleading); // maximum number of characters of endpaint (hwnd, & PS) displayed in a column; return 0; Case wm_destroy: postquitmessage (0); Return 0 ;} return defwindowproc (hwnd, umsg, wparam, lparam );}