From 6dd6408ce154b0e03d1e943cf6160b236c6bdeb4 Mon Sep 17 00:00:00 2001 From: Sam Lantinga Date: Mon, 16 Feb 2004 21:09:24 +0000 Subject: [PATCH] Added support for SDL_VIDEO_WINDOW_POS and SDL_VIDEO_CENTERED on Windows --- src/video/wincommon/SDL_lowvideo.h | 4 + src/video/wincommon/SDL_sysevents.c | 6 ++ src/video/windib/SDL_dibevents.c | 2 +- src/video/windib/SDL_dibvideo.c | 49 +++++++---- src/video/windx5/SDL_dx5events.c | 2 +- src/video/windx5/SDL_dx5video.c | 124 ++++++++++++++++++++-------- 6 files changed, 137 insertions(+), 50 deletions(-) diff --git a/src/video/wincommon/SDL_lowvideo.h b/src/video/wincommon/SDL_lowvideo.h index ddd464ab4..adcbc4155 100644 --- a/src/video/wincommon/SDL_lowvideo.h +++ b/src/video/wincommon/SDL_lowvideo.h @@ -83,6 +83,10 @@ extern HCURSOR SDL_hcursor; /* The bounds of the window in screen coordinates */ extern RECT SDL_bounds; +/* The position of the window in windowed mode */ +extern int SDL_windowX; +extern int SDL_windowY; + /* Flag -- SDL is performing a resize, rather than the user */ extern int SDL_resizing; diff --git a/src/video/wincommon/SDL_sysevents.c b/src/video/wincommon/SDL_sysevents.c index b673956bc..7c1f828c1 100644 --- a/src/video/wincommon/SDL_sysevents.c +++ b/src/video/wincommon/SDL_sysevents.c @@ -59,6 +59,8 @@ LPSTR SDL_Appname = NULL; HINSTANCE SDL_Instance = NULL; HWND SDL_Window = NULL; RECT SDL_bounds = {0, 0, 0, 0}; +int SDL_windowX = 0; +int SDL_windowY = 0; int SDL_resizing = 0; int mouse_relative = 0; int posted = 0; @@ -462,6 +464,10 @@ LONG CALLBACK WinMessage(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam) GetClientRect(SDL_Window, &SDL_bounds); ClientToScreen(SDL_Window, (LPPOINT)&SDL_bounds); ClientToScreen(SDL_Window, (LPPOINT)&SDL_bounds+1); + if ( SDL_bounds.left || SDL_bounds.top ) { + SDL_windowX = SDL_bounds.left; + SDL_windowY = SDL_bounds.top; + } w = SDL_bounds.right-SDL_bounds.left; h = SDL_bounds.bottom-SDL_bounds.top; if ( this->input_grab != SDL_GRAB_OFF ) { diff --git a/src/video/windib/SDL_dibevents.c b/src/video/windib/SDL_dibevents.c index fba57a4df..b86481ef8 100644 --- a/src/video/windib/SDL_dibevents.c +++ b/src/video/windib/SDL_dibevents.c @@ -379,7 +379,7 @@ int DIB_CreateWindow(_THIS) } else { SDL_Window = CreateWindow(SDL_Appname, SDL_Appname, (WS_OVERLAPPED|WS_CAPTION|WS_SYSMENU|WS_MINIMIZEBOX), - 0, 0, 0, 0, NULL, NULL, SDL_Instance, NULL); + CW_USEDEFAULT, CW_USEDEFAULT, 0, 0, NULL, NULL, SDL_Instance, NULL); if ( SDL_Window == NULL ) { SDL_SetError("Couldn't create window"); return(-1); diff --git a/src/video/windib/SDL_dibvideo.c b/src/video/windib/SDL_dibvideo.c index 1242b30c2..13db2a2cb 100644 --- a/src/video/windib/SDL_dibvideo.c +++ b/src/video/windib/SDL_dibvideo.c @@ -463,12 +463,8 @@ SDL_Surface *DIB_SetVideoMode(_THIS, SDL_Surface *current, HDC hdc; RECT bounds; int x, y; - BOOL was_visible; Uint32 Rmask, Gmask, Bmask; - /* See whether or not we should center the window */ - was_visible = IsWindowVisible(SDL_Window); - /* Clean up any GL context that may be hanging around */ if ( current->flags & SDL_OPENGL ) { WIN_GL_ShutDown(this); @@ -599,7 +595,7 @@ SDL_Surface *DIB_SetVideoMode(_THIS, SDL_Surface *current, } /* DJM: Don't piss of anyone who has setup his own window */ - if (!SDL_windowid) + if ( SDL_windowid == NULL ) SetWindowLong(SDL_Window, GWL_STYLE, style); /* Delete the old bitmap if necessary */ @@ -678,24 +674,47 @@ SDL_Surface *DIB_SetVideoMode(_THIS, SDL_Surface *current, if ( SDL_windowid == NULL ) { HWND top; UINT swp_flags; + const char *window = getenv("SDL_VIDEO_WINDOW_POS"); + const char *center = getenv("SDL_VIDEO_CENTERED"); + + if ( !SDL_windowX && !SDL_windowY ) { + if ( window ) { + if ( sscanf(window, "%d,%d", &x, &y) == 2 ) { + SDL_windowX = x; + SDL_windowY = y; + } + if ( strcmp(window, "center") == 0 ) { + center = window; + window = NULL; + } + } + } + swp_flags = (SWP_NOCOPYBITS | SWP_SHOWWINDOW); SDL_resizing = 1; - bounds.left = 0; - bounds.top = 0; - bounds.right = video->w; - bounds.bottom = video->h; + bounds.left = SDL_windowX; + bounds.top = SDL_windowY; + bounds.right = SDL_windowX+video->w; + bounds.bottom = SDL_windowY+video->h; AdjustWindowRectEx(&bounds, GetWindowLong(SDL_Window, GWL_STYLE), FALSE, 0); width = bounds.right-bounds.left; height = bounds.bottom-bounds.top; - x = (GetSystemMetrics(SM_CXSCREEN)-width)/2; - y = (GetSystemMetrics(SM_CYSCREEN)-height)/2; + if ( (flags & SDL_FULLSCREEN) ) { + x = (GetSystemMetrics(SM_CXSCREEN)-width)/2; + y = (GetSystemMetrics(SM_CYSCREEN)-height)/2; + } else if ( SDL_windowX || SDL_windowY || window ) { + x = bounds.left; + y = bounds.top; + } else if ( center ) { + x = (GetSystemMetrics(SM_CXSCREEN)-width)/2; + y = (GetSystemMetrics(SM_CYSCREEN)-height)/2; + } else { + x = y = -1; + swp_flags |= SWP_NOMOVE; + } if ( y < 0 ) { /* Cover up title bar for more client area */ y -= GetSystemMetrics(SM_CYCAPTION)/2; } - swp_flags = (SWP_NOCOPYBITS | SWP_FRAMECHANGED | SWP_SHOWWINDOW); - if ( was_visible && !(flags & SDL_FULLSCREEN) ) { - swp_flags |= SWP_NOMOVE; - } if ( flags & SDL_FULLSCREEN ) { top = HWND_TOPMOST; } else { diff --git a/src/video/windx5/SDL_dx5events.c b/src/video/windx5/SDL_dx5events.c index 9e2343629..c7acc8e9e 100644 --- a/src/video/windx5/SDL_dx5events.c +++ b/src/video/windx5/SDL_dx5events.c @@ -856,7 +856,7 @@ int DX5_CreateWindow(_THIS) } else { SDL_Window = CreateWindow(SDL_Appname, SDL_Appname, (WS_OVERLAPPED|WS_CAPTION|WS_SYSMENU|WS_MINIMIZEBOX), - 0, 0, 0, 0, NULL, NULL, SDL_Instance, NULL); + CW_USEDEFAULT, CW_USEDEFAULT, 0, 0, NULL, NULL, SDL_Instance, NULL); if ( SDL_Window == NULL ) { SDL_SetError("Couldn't create window"); return(-1); diff --git a/src/video/windx5/SDL_dx5video.c b/src/video/windx5/SDL_dx5video.c index 381bec3d2..4678c2818 100644 --- a/src/video/windx5/SDL_dx5video.c +++ b/src/video/windx5/SDL_dx5video.c @@ -1003,17 +1003,14 @@ SDL_Surface *DX5_SetVideoMode(_THIS, SDL_Surface *current, (WS_OVERLAPPED|WS_CAPTION|WS_SYSMENU|WS_MINIMIZEBOX); const DWORD resizestyle = (WS_THICKFRAME|WS_MAXIMIZEBOX); + int windowX, windowY; DDSURFACEDESC ddsd; LPDIRECTDRAWSURFACE dd_surface1; LPDIRECTDRAWSURFACE3 dd_surface3; - BOOL was_visible; #ifdef DDRAW_DEBUG fprintf(stderr, "Setting %dx%dx%d video mode\n", width, height, bpp); #endif - /* See whether or not we should center the window */ - was_visible = IsWindowVisible(SDL_Window); - /* Clean up any previous DirectDraw surfaces */ if ( current->hwdata ) { this->FreeHWSurface(this, current); @@ -1134,31 +1131,57 @@ SDL_Surface *DX5_SetVideoMode(_THIS, SDL_Surface *current, if (IsZoomed(SDL_Window)) style |= WS_MAXIMIZE; #endif } - SetWindowLong(SDL_Window, GWL_STYLE, style); + + /* DJM: Don't piss of anyone who has setup his own window */ + if ( SDL_windowid == NULL ) + SetWindowLong(SDL_Window, GWL_STYLE, style); /* Resize the window (copied from SDL WinDIB driver) */ if ( SDL_windowid == NULL ) { HWND top; UINT swp_flags; + const char *window = getenv("SDL_VIDEO_WINDOW_POS"); + const char *center = getenv("SDL_VIDEO_CENTERED"); + + if ( !SDL_windowX && !SDL_windowY ) { + if ( window ) { + if ( sscanf(window, "%d,%d", &x, &y) == 2 ) { + SDL_windowX = x; + SDL_windowY = y; + } + if ( strcmp(window, "center") == 0 ) { + center = window; + window = NULL; + } + } + } + swp_flags = (SWP_NOCOPYBITS | SWP_SHOWWINDOW); SDL_resizing = 1; - bounds.top = 0; - bounds.bottom = video->h; - bounds.left = 0; - bounds.right = video->w; + bounds.left = SDL_windowX; + bounds.top = SDL_windowY; + bounds.right = SDL_windowX+video->w; + bounds.bottom = SDL_windowY+video->h; AdjustWindowRectEx(&bounds, GetWindowLong(SDL_Window, GWL_STYLE), FALSE, 0); width = bounds.right-bounds.left; height = bounds.bottom-bounds.top; - x = (GetSystemMetrics(SM_CXSCREEN)-width)/2; - y = (GetSystemMetrics(SM_CYSCREEN)-height)/2; + if ( (flags & SDL_FULLSCREEN) ) { + x = (GetSystemMetrics(SM_CXSCREEN)-width)/2; + y = (GetSystemMetrics(SM_CYSCREEN)-height)/2; + } else if ( SDL_windowX || SDL_windowY || window ) { + x = bounds.left; + y = bounds.top; + } else if ( center ) { + x = (GetSystemMetrics(SM_CXSCREEN)-width)/2; + y = (GetSystemMetrics(SM_CYSCREEN)-height)/2; + } else { + x = y = -1; + swp_flags |= SWP_NOMOVE; + } if ( y < 0 ) { /* Cover up title bar for more client area */ y -= GetSystemMetrics(SM_CYCAPTION)/2; } - swp_flags = (SWP_NOCOPYBITS | SWP_FRAMECHANGED | SWP_SHOWWINDOW); - if ( was_visible && !(video->flags & SDL_FULLSCREEN) ) { - swp_flags |= SWP_NOMOVE; - } - if ( video->flags & SDL_FULLSCREEN ) { + if ( flags & SDL_FULLSCREEN ) { top = HWND_TOPMOST; } else { top = HWND_NOTOPMOST; @@ -1177,6 +1200,8 @@ SDL_Surface *DX5_SetVideoMode(_THIS, SDL_Surface *current, } /* Set the appropriate window style */ + windowX = SDL_windowX; + windowY = SDL_windowY; style = GetWindowLong(SDL_Window, GWL_STYLE); style &= ~(resizestyle|WS_MAXIMIZE); if ( (flags & SDL_FULLSCREEN) == SDL_FULLSCREEN ) { @@ -1197,7 +1222,9 @@ SDL_Surface *DX5_SetVideoMode(_THIS, SDL_Surface *current, if (IsZoomed(SDL_Window)) style |= WS_MAXIMIZE; #endif } - SetWindowLong(SDL_Window, GWL_STYLE, style); + /* DJM: Don't piss of anyone who has setup his own window */ + if ( SDL_windowid == NULL ) + SetWindowLong(SDL_Window, GWL_STYLE, style); /* Set DirectDraw sharing mode.. exclusive when fullscreen */ if ( (flags & SDL_FULLSCREEN) == SDL_FULLSCREEN ) { @@ -1210,18 +1237,26 @@ SDL_Surface *DX5_SetVideoMode(_THIS, SDL_Surface *current, SetDDerror("DirectDraw2::SetCooperativeLevel", result); return(NULL); } + SDL_windowX = windowX; + SDL_windowY = windowY; /* Set the display mode, if we are in fullscreen mode */ if ( (flags & SDL_FULLSCREEN) == SDL_FULLSCREEN ) { + RECT bounds; struct DX5EnumRect *rect; int maxRefreshRate; /* Cover up desktop during mode change */ SDL_resizing = 1; - SetWindowPos(SDL_Window, NULL, 0, 0, - GetSystemMetrics(SM_CXSCREEN), - GetSystemMetrics(SM_CYSCREEN), - (SWP_NOCOPYBITS | SWP_NOZORDER)); + bounds.left = 0; + bounds.top = 0; + bounds.right = GetSystemMetrics(SM_CXSCREEN); + bounds.bottom = GetSystemMetrics(SM_CYSCREEN); + AdjustWindowRectEx(&bounds, GetWindowLong(SDL_Window, GWL_STYLE), FALSE, 0); + SetWindowPos(SDL_Window, HWND_TOPMOST, + bounds.left, bounds.top, + bounds.right - bounds.left, + bounds.bottom - bounds.top, SWP_NOCOPYBITS); SDL_resizing = 0; ShowWindow(SDL_Window, SW_SHOW); while ( GetForegroundWindow() != SDL_Window ) { @@ -1485,6 +1520,8 @@ SDL_Surface *DX5_SetVideoMode(_THIS, SDL_Surface *current, RECT bounds; int x, y; UINT swp_flags; + const char *window = getenv("SDL_VIDEO_WINDOW_POS"); + const char *center = getenv("SDL_VIDEO_CENTERED"); /* Create and set a clipper on our primary surface */ if ( SDL_clipper == NULL ) { @@ -1516,26 +1553,47 @@ SDL_Surface *DX5_SetVideoMode(_THIS, SDL_Surface *current, return(NULL); } - /* Set the size of the window, centering and adjusting */ + if ( !SDL_windowX && !SDL_windowY ) { + if ( window ) { + if ( sscanf(window, "%d,%d", &x, &y) == 2 ) { + SDL_windowX = x; + SDL_windowY = y; + } + if ( strcmp(window, "center") == 0 ) { + center = window; + window = NULL; + } + } + } + swp_flags = SWP_NOCOPYBITS; + SDL_resizing = 1; - bounds.top = 0; - bounds.bottom = video->h; - bounds.left = 0; - bounds.right = video->w; + bounds.left = SDL_windowX; + bounds.top = SDL_windowY; + bounds.right = SDL_windowX+video->w; + bounds.bottom = SDL_windowY+video->h; AdjustWindowRectEx(&bounds, GetWindowLong(SDL_Window, GWL_STYLE), FALSE, 0); width = bounds.right-bounds.left; height = bounds.bottom-bounds.top; - x = (GetSystemMetrics(SM_CXSCREEN)-width)/2; - y = (GetSystemMetrics(SM_CYSCREEN)-height)/2; + if ( (flags & SDL_FULLSCREEN) ) { + x = (GetSystemMetrics(SM_CXSCREEN)-width)/2; + y = (GetSystemMetrics(SM_CYSCREEN)-height)/2; + } else if ( SDL_windowX || SDL_windowY || window ) { + x = bounds.left; + y = bounds.top; + } else if ( center ) { + x = (GetSystemMetrics(SM_CXSCREEN)-width)/2; + y = (GetSystemMetrics(SM_CYSCREEN)-height)/2; + } else { + x = y = -1; + swp_flags |= SWP_NOMOVE; + } if ( y < 0 ) { /* Cover up title bar for more client area */ y -= GetSystemMetrics(SM_CYCAPTION)/2; } - swp_flags = (SWP_NOCOPYBITS | SWP_NOZORDER); - if ( was_visible ) { - swp_flags |= SWP_NOMOVE; - } - SetWindowPos(SDL_Window, NULL, x, y, width, height, swp_flags); + SetWindowPos(SDL_Window, HWND_NOTOPMOST, x, y, width, height, swp_flags); SDL_resizing = 0; + } ShowWindow(SDL_Window, SW_SHOW); SetForegroundWindow(SDL_Window);