Reputation: 33
I am writing a quite simple WinAPI application. Just a window with single button in client area (this is minimum reproducible example). Button creation code is in WM_CREATE main window message handler:
case WM_CREATE:
hInst = ((LPCREATESTRUCT)lParam)->hInstance;
hwndButton = CreateWindowW(L"BUTTON", L"Start", WS_VISIBLE | WS_CHILD | BS_DEFPUSHBUTTON,
3, 30, 60, 30, hwnd, NULL, hInst, NULL);
break;
In real application I have to update window content when user moves mouse over window and when user resizes window. All update here is just filling client area with single color:
case WM_PAINT:
hdc = BeginPaint(hwnd, &ps);
FillRect(hdc, &ps.rcPaint, (HBRUSH) (COLOR_WINDOW + 10));
EndPaint(hwnd, &ps);
return 0
WM_size and WM_MOUSEMOVE message handlers just invalidate all client area:
case WM_SIZE:
InvalidateRect(hwnd, NULL, TRUE);
return 0;
case WM_MOUSEMOVE:
InvalidateRect(hwnd, NULL, TRUE);
break;
The problem is, behaviour of application differs in case of resizing window and in case of moving mouse pointer over it. In the first case, nothing happens except of window resizing - just as I want. But in second case, when mouse pointer moves over window, window begins to flicker. It's annoying. Moreover, button in client area also disappears - and appears again only after mouse pointer stops. This is absolutely unacceptable. What can I do to fix this situation?
Full text of program, if it will be useful:
#include <tchar.h>
#include <windows.h>
#if defined(UNICODE) && !defined(_UNICODE)
#define _UNICODE
#elif defined(_UNICODE) && !defined(UNICODE)
#define UNICODE
#endif
HINSTANCE hInst;
/* Make the class name into a global variable */
WCHAR szClassName[ ] = L"WindowsApp";
LRESULT CALLBACK WindowProcedure (HWND, UINT, WPARAM, LPARAM);
/*Application entry point. Function made from template. */
int WINAPI WinMain (HINSTANCE hThisInstance,
HINSTANCE hPrevInstance,
LPSTR lpszArgument,
int nCmdShow)
{
HWND hwnd, hWndToolbar; /* This is the handle for our window */
MSG messages; /* Here messages to the application are saved */
WNDCLASSEXW wincl; /* Data structure for the windowclass */
hInst = hThisInstance;
/* The Window structure */
wincl.hInstance = hThisInstance;
wincl.lpszClassName = szClassName;
wincl.lpfnWndProc = WindowProcedure; /* This function is called by windows */
wincl.style = CS_DBLCLKS; /* Catch double-clicks */
wincl.cbSize = sizeof (WNDCLASSEX);
/* Use default icon and mouse-pointer */
wincl.hIcon = NULL;
wincl.hIconSm = wincl.hIcon; //LoadIcon(NULL, IDI_APPLICATION);
wincl.hCursor = LoadCursor (NULL, IDC_ARROW);
wincl.lpszMenuName = NULL; /* No menu */
wincl.cbClsExtra = 0; /* No extra bytes after the window class */
wincl.cbWndExtra = 0; /* structure or the window instance */
/* Use Windows's default colour as the background of the window */
wincl.hbrBackground = (HBRUSH) COLOR_BACKGROUND;
/* Register the window class, and if it fails quit the program */
if (!RegisterClassExW (&wincl))
return 0;
/* The class is registered, let's create the program*/
hwnd = CreateWindowExW (
0, /* Extended possibilites for variation */
szClassName, /* Classname */
L"Check button", /* Title Text */
WS_OVERLAPPEDWINDOW, /* default window */
CW_USEDEFAULT, /* Windows decides the position */
CW_USEDEFAULT, /* where the window ends up on the screen */
CW_USEDEFAULT, /* The programs width */
CW_USEDEFAULT, /* and height in pixels */
HWND_DESKTOP, /* The window is a child-window to desktop */
NULL, /* Class menu used */
hThisInstance, /* Program Instance handler */
NULL /* No Window Creation data */
);
/* Make the window visible on the screen */
ShowWindow (hwnd, nCmdShow);
/* Run the message loop. It will run until GetMessage() returns 0 */
while (GetMessage (&messages, NULL, 0, 0))
{
/* Translate virtual-key messages into character messages */
TranslateMessage(&messages);
/* Send message to WindowProcedure */
DispatchMessage(&messages);
}
/* The program return-value is 0 - The value that PostQuitMessage() gave */
return messages.wParam;
}
/* Message handler: */
LRESULT CALLBACK WindowProcedure (HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
{
static HWND hwndButton;
PAINTSTRUCT ps;
HDC hdc;
switch (message) /* handle the messages */
{
case WM_CREATE:
hInst = ((LPCREATESTRUCT)lParam)->hInstance;
hwndButton = CreateWindowW(L"BUTTON", L"Start", WS_VISIBLE | WS_CHILD | BS_DEFPUSHBUTTON,
3, 30, 60, 30, hwnd, NULL, hInst, NULL);
break;
case WM_PAINT:
hdc = BeginPaint(hwnd, &ps);
FillRect(hdc, &ps.rcPaint, (HBRUSH) (COLOR_WINDOW + 10));
EndPaint(hwnd, &ps);
return 0;
case WM_SIZE:
InvalidateRect(hwnd, NULL, TRUE);
return 0;
case WM_MOUSEMOVE:
InvalidateRect(hwnd, NULL, TRUE);
break;
case WM_DESTROY:
PostQuitMessage (0); /* send a WM_QUIT to the message queue */
break;
default: /* for messages that we don't deal with */
return DefWindowProc (hwnd, message, wParam, lParam);
}
return 0;
}
Upvotes: 0
Views: 101