Thoughts start the win32 event loop without WndProc in a different way?

While messing with multithreaded, callbacks, win32 api functions and other nasty problems, I got an event with an idea. (Hehehe)

What if, instead of defining a global callback function (or static when designing a class), instead of DefWindowProc for lpfnWndProc assigned the value lpfnWndProc when registering a window class and then running the entire event loop in a separate thread?

This way, I don’t need to crack this problem when it implements a callback in the class and the main thread continues, freeing you from this loop left by God, allowing you to do anything, even open another window (yay!)

The "normal" way:

 LRESULT CALLBACK WndProc(...) { ... // process event information return DefWindowProc(...); } int CALLBACK WinMain(...) { ... // initialize whatever needs initializing :) WNDCLASSEX wc; ... wc.lpfnWndProc = WndProc; ... // register the class, create the window, etc... MSG msg; while(GetMessage(&msg, 0, 0, 0) != 0) { ... // TranslateMessage(&msg) if you want/need it DispatchMessage(&msg); // dispatches the message to WndProc } return static_cast<int>(msg.wParam); } 

My newfound amazing way:

 DWORD WINAPI MyAwesomeEventLoop(void* data) // must be static in a class { ... // do whatever you need with the data MSG msg; while(GetMessage(&msg, 0, 0, 0) != 0) { ... // TranslateMessage(&msg) if you want/need it ... // process event information // call PostQuitMessage(0) to leave the loop } return static_cast<DWORD>(msg.wParam); } int CALLBACK WndProc(...) { ... WNDCLASSEX wc; ... wc.lpfnWndProc = DefWindowProc; ... HANDLE threadHandle = 0; // use "this" as the 4th parameter when implementing in a class threadHandle = CreateThread(0, 0, MyAwesomeEventLoop, 0, 0, 0); ... // you are now free to do whatever you want! :) // waits untill the thread finishes // hopefully because PostQuitMessage(0) was called WaitForSingleObject(threadHandle, INFINITE); DWORD returnValue = 0; GetExitCodeThread(threadHandle, &returnValue); CloseHandle(threadHandle); ... return static_cast<int>(returnValue); } 

What do you guys think?

+4
source share
2 answers

GetMessage docs on MSDN:

http://msdn.microsoft.com/en-us/library/windows/desktop/ms644936(v=vs.85).aspx

Read the first sentence: "Gets a message from the message queue of the calling thread."

The message queue for the window is tied to the thread into which it was created. Since you created your window in the main thread, the event loop running in the new thread simply will not receive messages for this window. If you want to start the event loop in another thread, you must first create a thread, and then create a window in this thread.

+13
source

In fact, you are not buying anything, except that you now have window-specific event-handling code in the overall event loop, which is pretty ugly. If you need background work, use workflows. Store the graphical interface and event reactor inside the main thread and use callbacks as described.

And if you have a class whose instances handle windows, you should not make them global even in single-threaded code (or you will experience painful refactoring in the future).

+2
source

Source: https://habr.com/ru/post/1384454/


All Articles