When I create a new Win32 application, I notice the function:
LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
would receive message when somewhere call the function PostMessage or SendMessage, and I notice that the function WndProc can receive message because there is a function that register it:
ATOM MyRegisterClass(HINSTANCE hInstance)
{
WNDCLASSEX wcex;
wcex.cbSize = sizeof(WNDCLASSEX);
wcex.style = CS_HREDRAW | CS_VREDRAW;
wcex.lpfnWndProc = WndProc;
wcex.cbClsExtra = 0;
wcex.cbWndExtra = 0;
wcex.hInstance = hInstance;
wcex.hIcon = LoadIcon(hInstance, MAKEINTRESOURCE(IDI_SCREENCAPTURE));
wcex.hCursor = LoadCursor(NULL, IDC_ARROW);
wcex.hbrBackground = (HBRUSH)(COLOR_WINDOW+1);
wcex.lpszMenuName = MAKEINTRESOURCE(IDC_SCREENCAPTURE);
wcex.lpszClassName = szWindowClass;
wcex.hIconSm = LoadIcon(wcex.hInstance, MAKEINTRESOURCE(IDI_SMALL));
return RegisterClassEx(&wcex);
}
Notice: wcex.lpfnWndProc = WndProc;
I want to understand the mechanism of PostMessage() and how to receive it, so I created a C++ Console app to see if I can register the function WndProc, here is my attempting code:
LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{
int a = 1;//Break point here to see if it's call
return 0;
}
ATOM MyRegisterClass(HINSTANCE hInstance)
{
WNDCLASSEX wcex;
wcex.lpfnWndProc = WndProc;
wcex.hInstance = hInstance;
return RegisterClassEx(&wcex);
}
void main()
{
MyRegisterClass(GetModuleHandle(NULL));//(HINSTANCE)GetConsoleWindow()
PostMessage(GetConsoleWindow(), 132, 0, 0);
SYSTEMTIME st;
while (true)
{
GetSystemTime(&st);
printf("I'm wanting and waiting and waiting :(, The time is %I64u \n", st.wMilliseconds);
}
}
A window procedure can't receive messages unless its associated with a window. All you've done is created a window class. You still need to create a window of that class for your window procedure (WndProc) to receive messages.
Depending on the kind of message you want your windows procedure to receive you can create a hidden window that's not displayed on screen. If you need to handle certain messages, like keyboard and mouse events, that are directed at the console window then you can instead use SetConsoleMode and ReadConsoleInput to get these events. There's also SetConsoleCtrlHandler which lets you handle WM_QUERYENDSESSION events.
Microsoft has an example on MSDN that shows how to use ReadConsoleInput to handle certain console input events.