开发者

win32: WM_PAINT calls but not supposed to be!

开发者 https://www.devze.com 2023-02-01 08:17 出处:网络
I have a problem with WM_PAINT. Basically I want WM_PAINT to be called after a user WM_COMMAND, but for some reason it\'s开发者_高级运维 called anyway in the main function.

I have a problem with WM_PAINT. Basically I want WM_PAINT to be called after a user WM_COMMAND, but for some reason it's开发者_高级运维 called anyway in the main function.

 case WM_PAINT:
    {
     createFont();
     PAINTSTRUCT ps;
     HBRUSH hbruzh = CreateSolidBrush(RGB(0,0,0));
     HDC hdz = BeginPaint(hWnd,&ps);
     string s = "Memory Address";

     SelectBrush(hdz,hbruzh);
     SelectFont(hdz,hf);
     TextOut(hdz,0,0,s.c_str(),s.length());
     EndPaint(hWnd,&ps);

     DeleteObject(hbruzh);
     DeleteObject(hdz);

     break;
    }




int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance,
               LPSTR lpCmdLine, int nCmdShow)
{
    HWND hWnd;
    WNDCLASSEX wc;
    ZeroMemory(&wc, sizeof(WNDCLASSEX));
 hThisInstance = hInstance;
 LoadLibrary("Riched20.dll");

 wc.cbSize = sizeof(WNDCLASSEX);
 wc.style = CS_HREDRAW | CS_VREDRAW;
 wc.lpfnWndProc = WindowProc;
 wc.hInstance = hInstance;
 wc.lpszMenuName = MAKEINTRESOURCE(IDR_MYMENU);
 if(!(wc.hIcon = LoadIcon(hInstance,MAKEINTRESOURCE(IDI_MYICON)))) {
  HRESULT res = GetLastError();

 }
 wc.hCursor = LoadCursor(NULL, IDC_ARROW);
 wc.hbrBackground = (HBRUSH)COLOR_WINDOW;
 wc.lpszClassName = TEXT("Testcpp");
 RegisterClassEx(&wc);

 hWnd = CreateWindowEx(NULL, 
       wc.lpszClassName,
       TEXT("uTest"),
       WS_OVERLAPPEDWINDOW,
       300,
       200,
       450,
       300,
       NULL,
       NULL,
       hInstance,
       NULL);
 ShowWindow(hWnd,nCmdShow);

 MSG msg;
 while (GetMessage(&msg, NULL,0,0)) {
  TranslateMessage(&msg);
  DispatchMessage(&msg);

 }


 return msg.wParam;
}

According to MSDN, WM_PAINT is only called automatically after either UpdateWindow() or ReDrawWindow(), or when you SendMessage with it as message. I do none, however. I basically only want to call WM_PAINT after a user interaction, not before... is there any way to fix this? What is causing this? (I guess its some bizare side-effect I cant find documentation for >.<)


WM_PAINT is called any time your window needs to be redrawn. That's what it's for. Showing the window, resizing the window, restoring the window from minimized state, bringing the window to the front after it's been covered by another window, minimizing another app that was covering up your window... these are just a few of the things that will send a WM_PAINT.

I think you're trying to use WM_PAINT for something it's not intended for.


What is causing this?

My guess is that when the user selects the menu item from the menu, the act of displaying the menu has covered part of the client window.

So when the menu is finally remove, a *WM_PAINT* message is generated to recreated that missing portion of the client window.


According to MSDN, WM_PAINT is only called automatically after either UpdateWindow() or ReDrawWindow(), or when you SendMessage with it as message.

It's more complicated than that. WM_PAINT might be generated almost any time; for example see also Synchronous and Asynchronous Drawing.

I don't think you can prevent a WM_PAINT. You can:

  • Force an immediate WM_PAINT (e.g. by calling Update)
  • Try to combine/delay several paints into one (e.g. by using several calls to InvalidateRect)

Instead of preventing WM_PAINT, you should concentrate on avoiding/fixing whatever "side effect" you say you're getting when WM_PAINT is processed.

0

精彩评论

暂无评论...
验证码 换一张
取 消

关注公众号