1- // Copyright (C) 2005 - 2025 Settlers Freaks (sf-team at siedler25.org)
1+ // Copyright (C) 2005 - 2026 Settlers Freaks (sf-team at siedler25.org)
22//
33// SPDX-License-Identifier: GPL-2.0-or-later
44
55#include " VideoSDL2.h"
6+ #include " RTTR_Assert.h"
67#include " driver/Interface.h"
78#include " driver/VideoDriverLoaderInterface.h"
89#include " driver/VideoInterface.h"
3132# include < gl4esinit.h>
3233#endif
3334
34- #define CHECK_SDL (call ) \
35- ([&]() -> bool { \
36- if ((call) < 0 ) \
37- { \
38- PrintError (SDL_GetError ()); \
39- return false ; \
40- } \
41- return true ; \
42- })()
35+ // / Check that the (SDL) call returns success or print the error
36+ // / Can be used in conditions: if(CHECK_SDL(SDL_Foo()))
37+ #define CHECK_SDL (call ) ((call) >= 0 || (PrintError(), false ))
4338
4439namespace {
40+
4541template <typename T>
4642struct SDLMemoryDeleter
4743{
@@ -102,7 +98,7 @@ bool VideoSDL2::Initialize()
10298 SDL_SetHint (SDL_HINT_TOUCH_MOUSE_EVENTS, " 0" );
10399 if (SDL_InitSubSystem (SDL_INIT_VIDEO) < 0 )
104100 {
105- PrintError (SDL_GetError () );
101+ PrintError ();
106102 return false ;
107103 }
108104
@@ -156,37 +152,53 @@ bool VideoSDL2::CreateScreen(const std::string& title, const VideoMode& size, Di
156152 CHECK_SDL (SDL_GL_SetAttribute (SDL_GL_DOUBLEBUFFER, 1 ));
157153
158154 const int wndPos = SDL_WINDOWPOS_CENTERED;
159- const auto fullscreen = (displayMode & DisplayMode::Fullscreen) != DisplayMode::None;
160- const auto resizable = (displayMode & DisplayMode::Resizable) != DisplayMode::None;
155+ const auto fullscreen = displayMode == DisplayMode::Fullscreen;
161156 const auto requestedSize = fullscreen ? FindClosestVideoMode (size) : size;
162- const unsigned commonFlags = SDL_WINDOW_OPENGL | (resizable ? SDL_WINDOW_RESIZABLE : 0 );
163- const unsigned fullscreenFlag = (fullscreen ? SDL_WINDOW_FULLSCREEN : 0 );
157+ const unsigned commonFlags = SDL_WINDOW_OPENGL;
164158 // TODO: Fix GUI scaling with High DPI support enabled.
165159 // See https://github.com/Return-To-The-Roots/s25client/issues/1621
166160 // commonFlags |= SDL_WINDOW_ALLOW_HIGHDPI;
167161
162+ const unsigned windowTypeFlag =
163+ fullscreen ? SDL_WINDOW_FULLSCREEN :
164+ (displayMode == DisplayMode::BorderlessWindow ? SDL_WINDOW_BORDERLESS : SDL_WINDOW_RESIZABLE);
165+
168166 window = SDL_CreateWindow (title.c_str (), wndPos, wndPos, requestedSize.width , requestedSize.height ,
169- commonFlags | fullscreenFlag );
167+ commonFlags | windowTypeFlag );
170168
171- // Fallback to non-fullscreen
172- if (!window && fullscreen)
169+ if (!window)
173170 {
174- window = SDL_CreateWindow (title.c_str (), wndPos, wndPos, requestedSize.width , requestedSize.height ,
175- commonFlags | SDL_WINDOW_RESIZABLE);
171+ PrintError ();
172+ // Fallback to borderless fullscreen
173+ if (fullscreen)
174+ {
175+ SDL_DisplayMode dskSize;
176+ if (!CHECK_SDL (SDL_GetDesktopDisplayMode (0 , &dskSize)))
177+ {
178+ dskSize.w = size.width ;
179+ dskSize.h = size.height ;
180+ }
181+ window = SDL_CreateWindow (title.c_str (), wndPos, wndPos, dskSize.w , dskSize.h ,
182+ commonFlags | SDL_WINDOW_BORDERLESS);
183+ }
184+ // No borderless -> Resizable
185+ if (!window)
186+ {
187+ window = SDL_CreateWindow (title.c_str (), wndPos, wndPos, size.width , size.height ,
188+ commonFlags | SDL_WINDOW_RESIZABLE);
189+ }
176190 }
177191
178192 if (!window)
179193 {
180- PrintError (SDL_GetError () );
194+ PrintError ();
181195 return false ;
182196 }
183197
184- const auto flags = SDL_GetWindowFlags (window);
185- SetFullscreenFlag ((flags & SDL_WINDOW_FULLSCREEN) != 0 );
186- SetResizableFlag ((flags & SDL_WINDOW_RESIZABLE) != 0 );
198+ UpdateCurrentDisplayMode ();
187199 UpdateCurrentSizes ();
188200
189- if (! IsFullscreen () )
201+ if (displayMode_ != DisplayMode::Fullscreen )
190202 MoveWindowToCenter ();
191203
192204 SDL_Surface* iconSurf =
@@ -196,7 +208,7 @@ bool VideoSDL2::CreateScreen(const std::string& title, const VideoMode& size, Di
196208 SDL_SetWindowIcon (window, iconSurf);
197209 SDL_FreeSurface (iconSurf);
198210 } else
199- PrintError (SDL_GetError () );
211+ PrintError ();
200212
201213 context = SDL_GL_CreateContext (window);
202214
@@ -216,27 +228,27 @@ bool VideoSDL2::ResizeScreen(const VideoMode& newSize, DisplayMode displayMode)
216228 if (!initialized)
217229 return false ;
218230
219- const auto fullscreen = (displayMode & DisplayMode::Fullscreen) != DisplayMode::None;
220- const auto resizable = (displayMode & DisplayMode::Resizable) != DisplayMode::None;
221-
222- if (IsFullscreen () != fullscreen)
223- {
224- SDL_SetWindowFullscreen (window, fullscreen ? SDL_WINDOW_FULLSCREEN : 0 );
225- SetFullscreenFlag ((SDL_GetWindowFlags (window) & SDL_WINDOW_FULLSCREEN) != 0 );
226- if (!IsFullscreen ())
227- MoveWindowToCenter ();
228- }
229-
230231 if (displayMode_ != displayMode)
231232 {
232- if (!IsFullscreen ())
233- SDL_SetWindowResizable (window, static_cast <SDL_bool>(resizable));
234- SetResizableFlag ((SDL_GetWindowFlags (window) & SDL_WINDOW_RESIZABLE) != 0 );
235- }
233+ if (displayMode_ == DisplayMode::Fullscreen || displayMode == DisplayMode::Fullscreen)
234+ {
235+ if (!CHECK_SDL (
236+ SDL_SetWindowFullscreen (window, (displayMode == DisplayMode::Fullscreen) ? SDL_WINDOW_FULLSCREEN : 0 )))
237+ {
238+ if (displayMode == DisplayMode::Fullscreen)
239+ displayMode = DisplayMode::BorderlessWindow;
240+ }
241+ }
242+ SDL_SetWindowResizable (window, static_cast <SDL_bool>(displayMode == DisplayMode::Windowed));
243+ SDL_SetWindowBordered (window, static_cast <SDL_bool>(displayMode != DisplayMode::BorderlessWindow));
236244
245+ UpdateCurrentDisplayMode ();
246+ if (displayMode_ != DisplayMode::Fullscreen)
247+ MoveWindowToCenter ();
248+ }
237249 if (newSize != GetWindowSize ())
238250 {
239- if (IsFullscreen () )
251+ if (displayMode_ == DisplayMode::Fullscreen )
240252 {
241253 auto const targetMode = FindClosestVideoMode (newSize);
242254 SDL_DisplayMode target;
@@ -247,22 +259,22 @@ bool VideoSDL2::ResizeScreen(const VideoMode& newSize, DisplayMode displayMode)
247259 target.driverdata = nullptr ; // initialize to 0
248260 // Explicitly change the window size to avoid a bug with SDL reporting the wrong size until alt+tab
249261 SDL_SetWindowSize (window, target.w , target.h );
250- if (SDL_SetWindowDisplayMode (window, &target) < 0 )
251- {
252- PrintError (SDL_GetError ());
262+ if (!CHECK_SDL (SDL_SetWindowDisplayMode (window, &target)))
253263 return false ;
254- }
255264 } else
256- {
257265 SDL_SetWindowSize (window, newSize.width , newSize.height );
258- }
259266 UpdateCurrentSizes ();
260267 }
261268
262269 return true ;
263270}
264271
265- void VideoSDL2::PrintError (const std::string& msg) const
272+ void VideoSDL2::PrintError ()
273+ {
274+ PrintError (SDL_GetError ());
275+ }
276+
277+ void VideoSDL2::PrintError (const std::string& msg)
266278{
267279 boost::nowide::cerr << msg << std::endl;
268280}
@@ -320,7 +332,7 @@ bool VideoSDL2::MessageLoop()
320332 {
321333 case SDL_WINDOWEVENT_RESIZED:
322334 {
323- SetFullscreenFlag (( SDL_GetWindowFlags (window) & SDL_WINDOW_FULLSCREEN) != 0 );
335+ UpdateCurrentDisplayMode ( );
324336 VideoMode newSize (ev.window .data1 , ev.window .data2 );
325337 if (newSize != GetWindowSize ())
326338 {
@@ -515,7 +527,7 @@ void VideoSDL2::ListVideoModes(std::vector<VideoMode>& video_modes) const
515527 {
516528 SDL_DisplayMode mode;
517529 if (SDL_GetDisplayMode (display, i, &mode) != 0 )
518- PrintError (SDL_GetError () );
530+ PrintError ();
519531 else
520532 {
521533 VideoMode vm (mode.w , mode.h );
@@ -577,3 +589,15 @@ void VideoSDL2::MoveWindowToCenter()
577589 }
578590 SDL_SetWindowPosition (window, SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED);
579591}
592+
593+ void VideoSDL2::UpdateCurrentDisplayMode ()
594+ {
595+ RTTR_Assert (window);
596+ const auto flags = SDL_GetWindowFlags (window);
597+ if (flags & SDL_WINDOW_FULLSCREEN)
598+ displayMode_ = DisplayMode::Fullscreen;
599+ else if ((flags & SDL_WINDOW_BORDERLESS) != 0 )
600+ displayMode_ = DisplayMode::BorderlessWindow;
601+ else
602+ displayMode_ = DisplayMode::Windowed;
603+ }
0 commit comments