I have made this event system to abstract platform code (currently win32 api). I built a simple event queueing system to dispatch the system messages, but my events aren’t responding in real time. My events seem to pile up and get all pushed at once when I am done.
example printing size: when resizing by dragging the window border, the Quest_Log function doesn’t print until I am done resize, only then it will print all the positions it should’ve printed while resizing.
#include "Quest.h"
int main(void) {
if(Quest_Init(QUEST_SUBSYSTEM_VIDEO) > 0) {
return 1;
}
Quest_Window *window = Quest_CreateWindow("Example", 100, 100, 640, 480, QUEST_WINDOW_DEFAULT);
if(window == NULL) {
return 2;
}
bool running = true;
while(running) {
Quest_Event event;
while(Quest_PollEvent(&event)) {
switch(event.type) {
case QUEST_QUIT:
running = false;
break;
case QUEST_WINDOW_RESIZING:
Quest_Log("Window resizing: %d;%d\n", event.window.width, event.window.height);
break;
default:
break;
}
}
}
Quest_DestroyWindow(window);
Quest_Shutdown();
return 0;
}
and here is how I am polling and pushing events:
#define QUEST_MAX_EVENTS 0xffffui16
static Quest_Event sQueue[QUEST_MAX_EVENTS] = {0};
static unsigned int Qsize = 0;
bool Quest_PollEvent(Quest_Event *event) {
MSG msg;
bool result = false;
if(PeekMessage(&msg, NULL, 0, 0, PM_REMOVE) > 0) {
if(msg.message == WM_QUIT) {
event->type = QUEST_QUIT;
result = true;
return result;
} else {
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}
if(Qsize > 0) {
*event = sQueue[0];
{
for(unsigned int i = 0; i < Qsize - 1; i++) {
sQueue[i] = sQueue[i + 1];
}
--Qsize;
}
result = true;
return result;
}
return result;
}
void Quest_PushEvent(const Quest_Event *event) {
if(Qsize < sizeof(sQueue) / sizeof(sQueue[0])) {
sQueue[Qsize++] = *event;
}
}
Basically this is the windowproc
LRESULT CALLBACK WindowProc(HWND hWnd, UINT uMsg, WPARAM wParam,LPARAM lParam) {
Quest_Event event;
memset(&event, 0x0000, sizeof(Quest_Event));
switch(uMsg) {
// other messages
case WM_SIZING: {
switch(wParam) {
case SIZE_MAXIMIZED:
event.type = QUEST_WINDOW_MAXIMIZE;
break;
case SIZE_MINIMIZED:
event.type = QUEST_WINDOW_MINIMIZE;
break;
case SIZE_RESTORED:
event.type = QUEST_WINDOW_RESIZE;
break;
default:
break;
}
event.window.width = LOWORD(lParam);
event.window.height = HIWORD(lParam);
} break;
default:
break;
}
Quest_PushEvent(&e);
return DefWindowProc(hWnd, uMsg, wParam, lParam);
WM_SIZE
is not sent until the window has finished being resized. You might be looking forWM_SIZING
instead, which is sent while the window is in the process of being resized.Both suggestion don’t change the outcome.
Also, inside of
Quest_PollEvent()
,while(Qsize > 0)
should beif(Qsize > 0)
instead, since you are processing only 1 queued event at a time. And,while(PeekMessage(...) > 0)
should probably beif(PeekMessage(...) > 0)
as well. Think of when a timer is running, for example. If you usewhile(PeekMesssage())
, you are handling multiple window messages at a time, and you might lag behind/never process your queued events in a timely manner.There is only 1
WM_SIZE
message per resize operation. But you claim there should be multiple positions printed. Where are those extra events actually coming from? Please provide a minimal reproducible example that shows everything you are doing/seeing.When I run it in C++ using std::thread to join the main loop to while(GetMessage) it prints continuously as I am resizing. but with this method using PeekMessage in the main loop in keeps the strings it should’ve printed until I finish resizing and then it prints everything to the console. Even WM_SIZING doesn’t print while resizing.
Show 11 more comments