From 4e739d91bb24ca646ca1b3382cf430064b361286 Mon Sep 17 00:00:00 2001
From: Frank Praznik <[EMAIL REDACTED]>
Date: Wed, 16 Oct 2024 15:04:03 -0400
Subject: [PATCH] Flush old size, move, and exposure events from the queue
SDL2 removed old size, move, and exposure events from the queue to prevent the queue from overflowing, and a side effect was that this prevented clients from operating on old size and position data. Replicate this behavior in sdl2-compat, as it is relied upon in some cases.
---
src/sdl2_compat.c | 59 +++++++++++++++++++++++++++++++++++++++++++++++
1 file changed, 59 insertions(+)
diff --git a/src/sdl2_compat.c b/src/sdl2_compat.c
index 21c7b965..b8771628 100644
--- a/src/sdl2_compat.c
+++ b/src/sdl2_compat.c
@@ -1565,6 +1565,47 @@ WindowEventType3To2(Uint32 event_type3)
}
}
+typedef struct RemovePendingSizeChangedAndResizedEvents_Data
+{
+ const SDL2_Event *new_event;
+ bool saw_resized;
+} RemovePendingSizeChangedAndResizedEvents_Data;
+
+static int SDLCALL
+RemovePendingSizeChangedAndResizedEvents(void *userdata, SDL2_Event *event)
+{
+ RemovePendingSizeChangedAndResizedEvents_Data *resizedata = (RemovePendingSizeChangedAndResizedEvents_Data *)userdata;
+ const SDL2_Event *new_event = resizedata->new_event;
+
+ if (event->type == SDL2_WINDOWEVENT &&
+ (event->window.event == SDL_WINDOWEVENT_SIZE_CHANGED ||
+ event->window.event == SDL_WINDOWEVENT_RESIZED) &&
+ event->window.windowID == new_event->window.windowID) {
+
+ if (event->window.event == SDL_WINDOWEVENT_RESIZED) {
+ resizedata->saw_resized = true;
+ }
+
+ /* We're about to post a new size event, drop the old one */
+ return 0;
+ }
+ return 1;
+}
+
+static int SDLCALL
+RemoveSupercededWindowEvents(void *userdata, SDL2_Event *event)
+{
+ SDL2_Event *new_event = (SDL2_Event *)userdata;
+
+ if (event->type == SDL2_WINDOWEVENT &&
+ event->window.type == new_event->window.type &&
+ event->window.windowID == new_event->window.windowID) {
+ /* We're about to post a new move event, drop the old one */
+ return 0;
+ }
+ return 1;
+}
+
static bool SDLCALL
EventFilter3to2(void *userdata, SDL_Event *event3)
{
@@ -1647,6 +1688,24 @@ EventFilter3to2(void *userdata, SDL_Event *event3)
event2.window.padding3 = 0;
event2.window.data1 = event3->window.data1;
event2.window.data2 = event3->window.data2;
+
+ /* Fixes queue overflow with resize events that aren't processed */
+ if (event2.window.event == SDL_WINDOWEVENT_SIZE_CHANGED) {
+ RemovePendingSizeChangedAndResizedEvents_Data resizedata = {
+ &event2,
+ false
+ };
+ SDL_FilterEvents(RemovePendingSizeChangedAndResizedEvents, &resizedata);
+ if (resizedata.saw_resized) { /* if there was a pending resize, make sure one at the new dimensions remains. */
+ event2.window.event = SDL_WINDOWEVENT_RESIZED;
+ SDL_PushEvent(&event2);
+ event2.window.event = SDL_WINDOWEVENT_SIZE_CHANGED; /* then push the actual event next. */
+ }
+ } else if (event2.window.event == SDL_WINDOWEVENT_MOVED || event2.window.event == SDL_WINDOWEVENT_EXPOSED) {
+ /* Flush old move and exposure events */
+ SDL_FilterEvents(RemoveSupercededWindowEvents, &event2);
+ }
+
SDL_PushEvent(&event2);
}
break;