From 6534345d9abaf3a1c18f4a1a7ab7117f9e6d67f3 Mon Sep 17 00:00:00 2001
From: Sam Lantinga <[EMAIL REDACTED]>
Date: Mon, 24 Nov 2025 12:47:05 -0800
Subject: [PATCH] Only process events for the window being created at creation
time
Fixes https://github.com/libsdl-org/SDL/issues/14524
---
src/video/windows/SDL_windowsevents.c | 20 ++++++++++++++++++++
src/video/windows/SDL_windowsevents.h | 1 +
src/video/windows/SDL_windowsopengl.c | 8 ++++----
src/video/windows/SDL_windowswindow.c | 2 +-
4 files changed, 26 insertions(+), 5 deletions(-)
diff --git a/src/video/windows/SDL_windowsevents.c b/src/video/windows/SDL_windowsevents.c
index 2ad327441b808..f347e6dd93fd3 100644
--- a/src/video/windows/SDL_windowsevents.c
+++ b/src/video/windows/SDL_windowsevents.c
@@ -2556,6 +2556,26 @@ void WIN_SendWakeupEvent(SDL_VideoDevice *_this, SDL_Window *window)
PostMessage(data->hwnd, data->videodata->_SDL_WAKEUP, 0, 0);
}
+// Simplified event pump for using when creating and destroying windows
+void WIN_PumpEventsForHWND(SDL_VideoDevice *_this, HWND hwnd)
+{
+ MSG msg;
+
+ if (g_WindowsEnableMessageLoop) {
+ SDL_processing_messages = true;
+
+ while (PeekMessage(&msg, hwnd, 0, 0, PM_REMOVE)) {
+ WIN_SetMessageTick(msg.time);
+
+ // Always translate the message in case it's a non-SDL window (e.g. with Qt integration)
+ TranslateMessage(&msg);
+ DispatchMessage(&msg);
+ }
+
+ SDL_processing_messages = false;
+ }
+}
+
void WIN_PumpEvents(SDL_VideoDevice *_this)
{
MSG msg;
diff --git a/src/video/windows/SDL_windowsevents.h b/src/video/windows/SDL_windowsevents.h
index 78a92208312e2..0955df0666411 100644
--- a/src/video/windows/SDL_windowsevents.h
+++ b/src/video/windows/SDL_windowsevents.h
@@ -33,6 +33,7 @@ extern LRESULT CALLBACK WIN_DefWindowProc(HWND hwnd, UINT msg, WPARAM wParam, LP
extern void WIN_PollRawInput(SDL_VideoDevice *_this, Uint64 poll_start);
extern void WIN_CheckKeyboardAndMouseHotplug(SDL_VideoDevice *_this, bool initial_check);
extern void WIN_PumpEvents(SDL_VideoDevice *_this);
+extern void WIN_PumpEventsForHWND(SDL_VideoDevice *_this, HWND hwnd);
extern void WIN_SendWakeupEvent(SDL_VideoDevice *_this, SDL_Window *window);
extern int WIN_WaitEventTimeout(SDL_VideoDevice *_this, Sint64 timeoutNS);
diff --git a/src/video/windows/SDL_windowsopengl.c b/src/video/windows/SDL_windowsopengl.c
index 57629c2b13327..ef97e8149ead1 100644
--- a/src/video/windows/SDL_windowsopengl.c
+++ b/src/video/windows/SDL_windowsopengl.c
@@ -429,7 +429,7 @@ void WIN_GL_InitExtensions(SDL_VideoDevice *_this)
if (!hwnd) {
return;
}
- WIN_PumpEvents(_this);
+ WIN_PumpEventsForHWND(_this, hwnd);
hdc = GetDC(hwnd);
@@ -527,7 +527,7 @@ void WIN_GL_InitExtensions(SDL_VideoDevice *_this)
_this->gl_data->wglDeleteContext(hglrc);
ReleaseDC(hwnd, hdc);
DestroyWindow(hwnd);
- WIN_PumpEvents(_this);
+ WIN_PumpEventsForHWND(_this, hwnd);
}
static int WIN_GL_ChoosePixelFormatARB(SDL_VideoDevice *_this, int *iAttribs, float *fAttribs)
@@ -542,7 +542,7 @@ static int WIN_GL_ChoosePixelFormatARB(SDL_VideoDevice *_this, int *iAttribs, fl
hwnd =
CreateWindow(SDL_Appname, SDL_Appname, (WS_POPUP | WS_DISABLED), 0, 0,
10, 10, NULL, NULL, SDL_Instance, NULL);
- WIN_PumpEvents(_this);
+ WIN_PumpEventsForHWND(_this, hwnd);
hdc = GetDC(hwnd);
@@ -573,7 +573,7 @@ static int WIN_GL_ChoosePixelFormatARB(SDL_VideoDevice *_this, int *iAttribs, fl
}
ReleaseDC(hwnd, hdc);
DestroyWindow(hwnd);
- WIN_PumpEvents(_this);
+ WIN_PumpEventsForHWND(_this, hwnd);
return pixel_format;
}
diff --git a/src/video/windows/SDL_windowswindow.c b/src/video/windows/SDL_windowswindow.c
index 542c29f510156..d8413c4f32b39 100644
--- a/src/video/windows/SDL_windowswindow.c
+++ b/src/video/windows/SDL_windowswindow.c
@@ -722,7 +722,7 @@ bool WIN_CreateWindow(SDL_VideoDevice *_this, SDL_Window *window, SDL_Properties
WIN_UpdateDarkModeForHWND(hwnd);
- WIN_PumpEvents(_this);
+ WIN_PumpEventsForHWND(_this, hwnd);
if (!SetupWindowData(_this, window, hwnd, parent)) {
DestroyWindow(hwnd);