From f355c7f2172a0f07181529f68ecd2aa44bc37cf5 Mon Sep 17 00:00:00 2001
From: Sam Lantinga <[EMAIL REDACTED]>
Date: Tue, 25 Mar 2025 08:32:26 -0700
Subject: [PATCH] Allow the progress API to be used on all platforms
It's visually only hooked up on Windows for now, but the API will be internally consistent on all platforms.
---
src/test/SDL_test_common.c | 29 ++++++++++++--
src/video/SDL_sysvideo.h | 8 ++--
src/video/SDL_video.c | 40 +++++++++----------
src/video/windows/SDL_windowsevents.c | 5 +--
src/video/windows/SDL_windowsvideo.c | 5 +--
src/video/windows/SDL_windowswindow.c | 55 +++------------------------
src/video/windows/SDL_windowswindow.h | 8 +---
7 files changed, 60 insertions(+), 90 deletions(-)
diff --git a/src/test/SDL_test_common.c b/src/test/SDL_test_common.c
index 7e46991d49acb..5f1ab6b920f62 100644
--- a/src/test/SDL_test_common.c
+++ b/src/test/SDL_test_common.c
@@ -2457,20 +2457,42 @@ SDL_AppResult SDLTest_CommonEventMainCallbacks(SDLTest_CommonState *state, const
break;
case SDLK_P:
if (withAlt) {
- /* Ctrl-P Cycle through progress states */
+ /* Alt-P cycle through progress states */
SDL_Window *window = SDL_GetWindowFromEvent(event);
if (window) {
- float progress_state = SDL_GetWindowProgressState(window);
+ const char *name;
+ SDL_ProgressState progress_state = SDL_GetWindowProgressState(window);
progress_state += 1;
if (progress_state > SDL_PROGRESS_STATE_ERROR) {
progress_state = SDL_PROGRESS_STATE_NONE;
}
+ switch (progress_state) {
+ case SDL_PROGRESS_STATE_NONE:
+ name = "NONE";
+ break;
+ case SDL_PROGRESS_STATE_INDETERMINATE:
+ name = "INDETERMINATE";
+ break;
+ case SDL_PROGRESS_STATE_NORMAL:
+ name = "NORMAL";
+ break;
+ case SDL_PROGRESS_STATE_PAUSED:
+ name = "PAUSED";
+ break;
+ case SDL_PROGRESS_STATE_ERROR:
+ name = "ERROR";
+ break;
+ default:
+ name = "UNKNOWN";
+ break;
+ }
+ SDL_Log("Setting progress state to %s", name);
SDL_SetWindowProgressState(window, progress_state);
}
}
else if (withControl)
{
- /* Alt-P Increase progress value */
+ /* Ctrl-P increase progress value */
SDL_Window *window = SDL_GetWindowFromEvent(event);
if (window) {
float progress_value = SDL_GetWindowProgressValue(window);
@@ -2479,6 +2501,7 @@ SDL_AppResult SDLTest_CommonEventMainCallbacks(SDLTest_CommonState *state, const
} else {
progress_value += 0.1f;
}
+ SDL_Log("Setting progress value to %.1f", progress_value);
SDL_SetWindowProgressValue(window, progress_value);
}
}
diff --git a/src/video/SDL_sysvideo.h b/src/video/SDL_sysvideo.h
index b46e12227a030..5fe87a86d8b50 100644
--- a/src/video/SDL_sysvideo.h
+++ b/src/video/SDL_sysvideo.h
@@ -123,6 +123,9 @@ struct SDL_Window
SDL_HitTest hit_test;
void *hit_test_data;
+ SDL_ProgressState progress_state;
+ float progress_value;
+
SDL_PropertiesID props;
int num_renderers;
@@ -303,10 +306,7 @@ struct SDL_VideoDevice
void (*OnWindowEnter)(SDL_VideoDevice *_this, SDL_Window *window);
bool (*UpdateWindowShape)(SDL_VideoDevice *_this, SDL_Window *window, SDL_Surface *shape);
bool (*FlashWindow)(SDL_VideoDevice *_this, SDL_Window *window, SDL_FlashOperation operation);
- bool (*SetWindowProgressState)(SDL_VideoDevice *_this, SDL_Window *window, SDL_ProgressState state);
- SDL_ProgressState (*GetWindowProgressState)(SDL_VideoDevice *_this, SDL_Window *window);
- bool (*SetWindowProgressValue)(SDL_VideoDevice *_this, SDL_Window *window, float value);
- float (*GetWindowProgressValue)(SDL_VideoDevice *_this, SDL_Window *window);
+ bool (*ApplyWindowProgress)(SDL_VideoDevice *_this, SDL_Window *window);
bool (*SetWindowFocusable)(SDL_VideoDevice *_this, SDL_Window *window, bool focusable);
bool (*SyncWindow)(SDL_VideoDevice *_this, SDL_Window *window);
diff --git a/src/video/SDL_video.c b/src/video/SDL_video.c
index a5d1f3554a121..a9d91a479c63b 100644
--- a/src/video/SDL_video.c
+++ b/src/video/SDL_video.c
@@ -3930,23 +3930,23 @@ bool SDL_SetWindowProgressState(SDL_Window *window, SDL_ProgressState state)
return SDL_InvalidParamError("state");
}
- if (_this->SetWindowProgressState) {
- return _this->SetWindowProgressState(_this, window, state);
+ window->progress_state = state;
+
+ if (_this->ApplyWindowProgress) {
+ if (!_this->ApplyWindowProgress(_this, window)) {
+ return false;
+ }
}
- return SDL_Unsupported();
+ return true;
}
SDL_ProgressState SDL_GetWindowProgressState(SDL_Window *window)
{
- CHECK_WINDOW_MAGIC(window, false);
- CHECK_WINDOW_NOT_POPUP(window, false);
-
- if (_this->GetWindowProgressState) {
- return _this->GetWindowProgressState(_this, window);
- }
+ CHECK_WINDOW_MAGIC(window, SDL_PROGRESS_STATE_INVALID);
+ CHECK_WINDOW_NOT_POPUP(window, SDL_PROGRESS_STATE_INVALID);
- return SDL_Unsupported();
+ return window->progress_state;
}
bool SDL_SetWindowProgressValue(SDL_Window *window, float value)
@@ -3956,23 +3956,23 @@ bool SDL_SetWindowProgressValue(SDL_Window *window, float value)
value = SDL_clamp(value, 0.0f, 1.f);
- if (_this->SetWindowProgressValue) {
- return _this->SetWindowProgressValue(_this, window, value);
+ window->progress_value = value;
+
+ if (_this->ApplyWindowProgress) {
+ if (!_this->ApplyWindowProgress(_this, window)) {
+ return false;
+ }
}
- return SDL_Unsupported();
+ return true;
}
float SDL_GetWindowProgressValue(SDL_Window *window)
{
- CHECK_WINDOW_MAGIC(window, false);
- CHECK_WINDOW_NOT_POPUP(window, false);
-
- if (_this->GetWindowProgressValue) {
- return _this->GetWindowProgressValue(_this, window);
- }
+ CHECK_WINDOW_MAGIC(window, -1.0f);
+ CHECK_WINDOW_NOT_POPUP(window, -1.0f);
- return SDL_Unsupported();
+ return window->progress_value;
}
void SDL_OnWindowShown(SDL_Window *window)
diff --git a/src/video/windows/SDL_windowsevents.c b/src/video/windows/SDL_windowsevents.c
index bc11457ccfb06..dce81ba015bbf 100644
--- a/src/video/windows/SDL_windowsevents.c
+++ b/src/video/windows/SDL_windowsevents.c
@@ -2437,9 +2437,8 @@ LRESULT CALLBACK WIN_WindowProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lPara
#ifdef HAVE_SHOBJIDL_CORE_H
if (msg == data->videodata->WM_TASKBAR_BUTTON_CREATED) {
- SDL_Window *window = data->window;
- window->internal->taskbar_button_created = true;
- WIN_ApplyWindowProgress(window);
+ data->taskbar_button_created = true;
+ WIN_ApplyWindowProgress(SDL_GetVideoDevice(), data->window);
}
#endif
diff --git a/src/video/windows/SDL_windowsvideo.c b/src/video/windows/SDL_windowsvideo.c
index 71bc520d487c7..bdfde9ce3404f 100644
--- a/src/video/windows/SDL_windowsvideo.c
+++ b/src/video/windows/SDL_windowsvideo.c
@@ -272,10 +272,7 @@ static SDL_VideoDevice *WIN_CreateDevice(void)
device->SetWindowHitTest = WIN_SetWindowHitTest;
device->AcceptDragAndDrop = WIN_AcceptDragAndDrop;
device->FlashWindow = WIN_FlashWindow;
- device->SetWindowProgressState = WIN_SetWindowProgressState;
- device->GetWindowProgressState = WIN_GetWindowProgressState;
- device->SetWindowProgressValue = WIN_SetWindowProgressValue;
- device->GetWindowProgressValue = WIN_GetWindowProgressValue;
+ device->ApplyWindowProgress = WIN_ApplyWindowProgress;
device->ShowWindowSystemMenu = WIN_ShowWindowSystemMenu;
device->SetWindowFocusable = WIN_SetWindowFocusable;
device->UpdateWindowShape = WIN_UpdateWindowShape;
diff --git a/src/video/windows/SDL_windowswindow.c b/src/video/windows/SDL_windowswindow.c
index 755b191053788..3eca533a37d5a 100644
--- a/src/video/windows/SDL_windowswindow.c
+++ b/src/video/windows/SDL_windowswindow.c
@@ -2245,11 +2245,9 @@ bool WIN_FlashWindow(SDL_VideoDevice *_this, SDL_Window *window, SDL_FlashOperat
return true;
}
-bool WIN_ApplyWindowProgress(SDL_Window* window)
+bool WIN_ApplyWindowProgress(SDL_VideoDevice *_this, SDL_Window* window)
{
-#ifndef HAVE_SHOBJIDL_CORE_H
- return false;
-#else
+#ifdef HAVE_SHOBJIDL_CORE_H
SDL_WindowData *data = window->internal;
if (!data->taskbar_button_created) {
return true;
@@ -2261,7 +2259,7 @@ bool WIN_ApplyWindowProgress(SDL_Window* window)
}
TBPFLAG tbpFlags;
- switch (data->progress_state) {
+ switch (window->progress_state) {
case SDL_PROGRESS_STATE_NONE:
tbpFlags = TBPF_NOPROGRESS;
break;
@@ -2286,55 +2284,14 @@ bool WIN_ApplyWindowProgress(SDL_Window* window)
return WIN_SetErrorFromHRESULT("ITaskbarList3::SetProgressState()", ret);
}
- if (data->progress_state >= SDL_PROGRESS_STATE_NORMAL) {
- ret = taskbar_list->lpVtbl->SetProgressValue(taskbar_list, data->hwnd, (ULONGLONG)(data->progress_value * 10000.f), 10000);
+ if (window->progress_state >= SDL_PROGRESS_STATE_NORMAL) {
+ ret = taskbar_list->lpVtbl->SetProgressValue(taskbar_list, data->hwnd, (ULONGLONG)(window->progress_value * 10000.f), 10000);
if (FAILED(ret)) {
return WIN_SetErrorFromHRESULT("ITaskbarList3::SetProgressValue()", ret);
}
}
-
- return true;
-#endif
-}
-
-bool WIN_SetWindowProgressState(SDL_VideoDevice *_this, SDL_Window *window, SDL_ProgressState state)
-{
-#ifndef HAVE_SHOBJIDL_CORE_H
- return SDL_Unsupported();
-#else
- window->internal->progress_state = state;
- return WIN_ApplyWindowProgress(window);
-#endif
-}
-
-SDL_ProgressState WIN_GetWindowProgressState(SDL_VideoDevice *_this, SDL_Window *window)
-{
-#ifndef HAVE_SHOBJIDL_CORE_H
- SDL_Unsupported();
- return SDL_PROGRESS_STATE_INVALID;
-#else
- return window->internal->progress_state;
-#endif // HAVE_SHOBJIDL_CORE_H
-}
-
-bool WIN_SetWindowProgressValue(SDL_VideoDevice *_this, SDL_Window *window, float value)
-{
-#ifndef HAVE_SHOBJIDL_CORE_H
- return SDL_Unsupported();
-#else
- window->internal->progress_value = value;
- return WIN_ApplyWindowProgress(window);
#endif
-}
-
-float WIN_GetWindowProgressValue(SDL_VideoDevice *_this, SDL_Window *window)
-{
-#ifndef HAVE_SHOBJIDL_CORE_H
- SDL_Unsupported();
- return -1.0f;
-#else
- return window->internal->progress_value;
-#endif // HAVE_SHOBJIDL_CORE_H
+ return true;
}
void WIN_ShowWindowSystemMenu(SDL_Window *window, int x, int y)
diff --git a/src/video/windows/SDL_windowswindow.h b/src/video/windows/SDL_windowswindow.h
index 449abfe54d162..d23d83c04e46b 100644
--- a/src/video/windows/SDL_windowswindow.h
+++ b/src/video/windows/SDL_windowswindow.h
@@ -94,8 +94,6 @@ struct SDL_WindowData
SDL_Window *keyboard_focus;
SDL_WindowEraseBackgroundMode hint_erase_background_mode;
bool taskbar_button_created;
- SDL_ProgressState progress_state;
- float progress_value;
struct SDL_VideoData *videodata;
#ifdef SDL_VIDEO_OPENGL_EGL
EGLSurface egl_surface;
@@ -136,11 +134,7 @@ extern void WIN_UnclipCursorForWindow(SDL_Window *window);
extern bool WIN_SetWindowHitTest(SDL_Window *window, bool enabled);
extern void WIN_AcceptDragAndDrop(SDL_Window *window, bool accept);
extern bool WIN_FlashWindow(SDL_VideoDevice *_this, SDL_Window *window, SDL_FlashOperation operation);
-extern bool WIN_ApplyWindowProgress(SDL_Window *window);
-extern bool WIN_SetWindowProgressState(SDL_VideoDevice *_this, SDL_Window *window, SDL_ProgressState state);
-extern SDL_ProgressState WIN_GetWindowProgressState(SDL_VideoDevice *_this, SDL_Window *window);
-extern bool WIN_SetWindowProgressValue(SDL_VideoDevice *_this, SDL_Window *window, float value);
-extern float WIN_GetWindowProgressValue(SDL_VideoDevice *_this, SDL_Window *window);
+extern bool WIN_ApplyWindowProgress(SDL_VideoDevice *_this, SDL_Window *window);
extern void WIN_UpdateDarkModeForHWND(HWND hwnd);
extern bool WIN_SetWindowPositionInternal(SDL_Window *window, UINT flags, SDL_WindowRect rect_type);
extern void WIN_ShowWindowSystemMenu(SDL_Window *window, int x, int y);