SDL2 support, if USE_SDL2 defined.

git-svn-id: svn+ssh://svn.code.sf.net/p/quakespasm/code/trunk@987 af15c1b1-3010-417e-b628-4374ebc0bcbd
This commit is contained in:
ewasylishen 2014-09-05 19:34:43 +00:00
parent 7a762fbb66
commit 5e8102e1e6
16 changed files with 719 additions and 75 deletions

View file

@ -20,7 +20,11 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
#import "AppController.h"
#import "ScreenInfo.h"
#if defined(SDL_FRAMEWORK) || defined(NO_SDL_CONFIG)
#if defined(USE_SDL2)
#import <SDL2/SDL.h>
#else
#import <SDL/SDL.h>
#endif
#else
#import "SDL.h"
#endif
@ -60,6 +64,21 @@ NSString *FQPrefScreenModeKey = @"ScreenMode";
if (SDL_InitSubSystem(SDL_INIT_VIDEO) == -1)
return self;
#if defined(USE_SDL2)
{
const int sdlmodes = SDL_GetNumDisplayModes(0);
for (i = 0; i < sdlmodes; i++)
{
SDL_DisplayMode mode;
if (SDL_GetDisplayMode(0, i, &mode) == 0)
{
info = [[ScreenInfo alloc] initWithWidth:mode.w height:mode.h bpp:SDL_BITSPERPIXEL(mode.format)];
[screenModes addObject:info];
[info release];
}
}
}
#else
flags = SDL_OPENGL | SDL_FULLSCREEN;
format.palette = NULL;
@ -76,6 +95,7 @@ NSString *FQPrefScreenModeKey = @"ScreenMode";
[info release];
}
}
#endif
SDL_QuitSubSystem(SDL_INIT_VIDEO);

View file

@ -20,7 +20,11 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
#import "SDLApplication.h"
#if defined(SDL_FRAMEWORK) || defined(NO_SDL_CONFIG)
#if defined(USE_SDL2)
#import <SDL2/SDL.h>
#else
#import <SDL/SDL.h>
#endif
#else
#import "SDL.h"
#endif

View file

@ -6,7 +6,11 @@
*/
#if defined(SDL_FRAMEWORK) || defined(NO_SDL_CONFIG)
#if defined(USE_SDL2)
#import <SDL2/SDL.h>
#else
#import <SDL/SDL.h>
#endif
#else
#import "SDL.h"
#endif

View file

@ -26,7 +26,11 @@
#if defined(SDL_FRAMEWORK) || defined(NO_SDL_CONFIG)
#if defined(USE_SDL2)
#include <SDL2/SDL.h>
#else
#include <SDL/SDL.h>
#endif
#else
#include "SDL.h"
#endif
@ -35,7 +39,7 @@
/* SDL dropped support for
cd audio since v1.3.0 */
#warning SDL CDAudio support disabled
#pragma message ( "SDL CDAudio support disabled" )
#include "cd_null.c"
#else /* SDL_INIT_CDROM */

View file

@ -27,7 +27,11 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
#include "bgmusic.h"
#include "resource.h"
#if defined(SDL_FRAMEWORK) || defined(NO_SDL_CONFIG)
#if defined(USE_SDL2)
#include <SDL2/SDL.h>
#else
#include <SDL/SDL.h>
#endif
#else
#include "SDL.h"
#endif
@ -58,7 +62,12 @@ static int nummodes;
static qboolean vid_initialized = false;
#if defined(USE_SDL2)
static SDL_Window *draw_context;
static SDL_GLContext gl_context;
#else
static SDL_Surface *draw_context;
#endif
static qboolean vid_locked = false; //johnfitz
static qboolean vid_changed = false;
@ -130,10 +139,6 @@ static void VID_Gamma_SetGamma (void)
{
if (draw_context && gammaworks)
{
#if USE_GAMMA_RAMPS
if (SDL_SetGammaRamp(vid_gamma_red, vid_gamma_green, vid_gamma_blue) == -1)
Con_Printf ("VID_Gamma_SetGamma: failed on SDL_SetGammaRamp\n");
#else
float value;
if (vid_gamma.value > (1.0f / GAMMA_MAX))
@ -141,8 +146,17 @@ static void VID_Gamma_SetGamma (void)
else
value = GAMMA_MAX;
#if defined(USE_SDL2)
if (SDL_SetWindowBrightness(draw_context, value) != 0)
Con_Printf ("VID_Gamma_SetGamma: failed on SDL_SetWindowBrightness\n");
#else
#if USE_GAMMA_RAMPS
if (SDL_SetGammaRamp(vid_gamma_red, vid_gamma_green, vid_gamma_blue) == -1)
Con_Printf ("VID_Gamma_SetGamma: failed on SDL_SetGammaRamp\n");
#else
if (SDL_SetGamma(value,value,value) == -1)
Con_Printf ("VID_Gamma_SetGamma: failed on SDL_SetGamma\n");
#endif
#endif
}
}
@ -156,12 +170,17 @@ static void VID_Gamma_Restore (void)
{
if (draw_context && gammaworks)
{
#if defined(USE_SDL2)
if (SDL_SetWindowBrightness(draw_context, 1) != 0)
Con_Printf ("VID_Gamma_Restore: failed on SDL_SetWindowBrightness\n");
#else
#if USE_GAMMA_RAMPS
if (SDL_SetGammaRamp(vid_sysgamma_red, vid_sysgamma_green, vid_sysgamma_blue) == -1)
Con_Printf ("VID_Gamma_Restore: failed on SDL_SetGammaRamp\n");
#else
if (SDL_SetGamma(1, 1, 1) == -1)
Con_Printf ("VID_Gamma_Restore: failed on SDL_SetGamma\n");
#endif
#endif
}
}
@ -204,12 +223,16 @@ VID_Gamma_Init -- call on init
*/
static void VID_Gamma_Init (void)
{
#if defined(USE_SDL2)
gammaworks = (SDL_SetWindowBrightness(draw_context, 1) == 0);
#else
#if USE_GAMMA_RAMPS
gammaworks = (SDL_GetGammaRamp(vid_sysgamma_red, vid_sysgamma_green, vid_sysgamma_blue) == 0);
if (gammaworks)
gammaworks = (SDL_SetGammaRamp(vid_sysgamma_red, vid_sysgamma_green, vid_sysgamma_blue) == 0);
#else
gammaworks = (SDL_SetGamma(1, 1, 1) == 0);
#endif
#endif
if (!gammaworks)
@ -219,6 +242,161 @@ static void VID_Gamma_Init (void)
Cvar_SetCallback (&vid_gamma, VID_Gamma_f);
}
/*
======================
VID_GetCurrentWidth
======================
*/
static int VID_GetCurrentWidth (void)
{
#if defined(USE_SDL2)
int w = 0, h = 0;
SDL_GetWindowSize(draw_context, &w, &h);
return w;
#else
return draw_context->w;
#endif
}
/*
=======================
VID_GetCurrentHeight
=======================
*/
static int VID_GetCurrentHeight (void)
{
#if defined(USE_SDL2)
int w=0, h=0;
SDL_GetWindowSize(draw_context, &w, &h);
return h;
#else
return draw_context->h;
#endif
}
/*
====================
VID_GetCurrentBPP
====================
*/
static int VID_GetCurrentBPP (void)
{
#if defined(USE_SDL2)
const Uint32 pixelFormat = SDL_GetWindowPixelFormat(draw_context);
return SDL_BITSPERPIXEL(pixelFormat);
#else
return draw_context->format->BitsPerPixel;
#endif
}
/*
====================
VID_GetFullscreen
====================
*/
static qboolean VID_GetFullscreen (void)
{
#if defined(USE_SDL2)
return (SDL_GetWindowFlags(draw_context) & SDL_WINDOW_FULLSCREEN) != 0;
#else
return (draw_context->flags & SDL_FULLSCREEN) != 0;
#endif
}
/*
====================
VID_GetVSync
====================
*/
static qboolean VID_GetVSync (void)
{
#if defined(USE_SDL2)
return SDL_GL_GetSwapInterval() == 1;
#else
int swap_control;
if (SDL_GL_GetAttribute(SDL_GL_SWAP_CONTROL, &swap_control) == 0)
return swap_control > 0;
return false;
#endif
}
/*
====================
VID_GetWindow
used by pl_win.c
====================
*/
void *VID_GetWindow (void)
{
#if defined(USE_SDL2)
return draw_context;
#else
return NULL;
#endif
}
/*
====================
VID_HasMouseOrInputFocus
====================
*/
qboolean VID_HasMouseOrInputFocus (void)
{
#if defined(USE_SDL2)
return (SDL_GetWindowFlags(draw_context) & (SDL_WINDOW_MOUSE_FOCUS | SDL_WINDOW_INPUT_FOCUS)) != 0;
#else
return (SDL_GetAppState() & (SDL_APPMOUSEFOCUS | SDL_APPINPUTFOCUS)) != 0;
#endif
}
/*
====================
VID_IsMinimized
====================
*/
qboolean VID_IsMinimized (void)
{
#if defined(USE_SDL2)
return !(SDL_GetWindowFlags(draw_context) & SDL_WINDOW_SHOWN);
#else
/* SDL_APPACTIVE in SDL 1.x means "not minimized" */
return !(SDL_GetAppState() & SDL_APPACTIVE);
#endif
}
#if defined(USE_SDL2)
/*
================
VID_SDL2_GetDisplayMode
Returns a pointer to a statically allocated SDL_DisplayMode structure
if there is one with the requested params on the default display.
Otherwise returns NULL.
This is passed to SDL_SetWindowDisplayMode to specify a pixel format
with the requested bpp. If we didn't care about bpp we could just pass NULL.
================
*/
static SDL_DisplayMode *VID_SDL2_GetDisplayMode(int width, int height, int bpp)
{
static SDL_DisplayMode mode;
const int sdlmodes = SDL_GetNumDisplayModes(0);
int i;
for (i = 0; i < sdlmodes; i++)
{
if (SDL_GetDisplayMode(0, i, &mode) == 0
&& mode.w == width && mode.h == height
&& SDL_BITSPERPIXEL(mode.format) == bpp)
{
return &mode;
}
}
return NULL;
}
#endif
/*
================
VID_ValidMode
@ -226,18 +404,24 @@ VID_ValidMode
*/
static qboolean VID_ValidMode (int width, int height, int bpp, qboolean fullscreen)
{
Uint32 flags = DEFAULT_SDL_FLAGS;
if (width < 320)
return false;
if (height < 200)
return false;
if (fullscreen)
flags |= SDL_FULLSCREEN;
#if defined(USE_SDL2)
if (fullscreen && VID_SDL2_GetDisplayMode(width, height, bpp) == NULL)
bpp = 0;
#else
{
Uint32 flags = DEFAULT_SDL_FLAGS;
if (fullscreen)
flags |= SDL_FULLSCREEN;
bpp = SDL_VideoModeOK(width, height, bpp, flags);
bpp = SDL_VideoModeOK(width, height, bpp, flags);
}
#endif
switch (bpp)
{
@ -260,14 +444,11 @@ VID_SetMode
static int VID_SetMode (int width, int height, int bpp, qboolean fullscreen)
{
int temp;
Uint32 flags = DEFAULT_SDL_FLAGS;
Uint32 flags;
char caption[50];
int depthbits;
int fsaa_obtained;
if (fullscreen)
flags |= SDL_FULLSCREEN;
// so Con_Printfs don't mess us up by forcing vid and snd updates
temp = scr_disabled_for_loading;
scr_disabled_for_loading = true;
@ -275,15 +456,6 @@ static int VID_SetMode (int width, int height, int bpp, qboolean fullscreen)
CDAudio_Pause ();
BGM_Pause ();
//
// swap control (the "before SDL_SetVideoMode" part)
//
gl_swap_control = true;
if (SDL_GL_SetAttribute(SDL_GL_SWAP_CONTROL, (vid_vsync.value) ? 1 : 0) == -1)
gl_swap_control = false;
bpp = SDL_VideoModeOK(width, height, bpp, flags);
//
// z-buffer depth
//
@ -298,6 +470,71 @@ static int VID_SetMode (int width, int height, int bpp, qboolean fullscreen)
SDL_GL_SetAttribute(SDL_GL_MULTISAMPLEBUFFERS, fsaa > 0 ? 1 : 0);
SDL_GL_SetAttribute(SDL_GL_MULTISAMPLESAMPLES, fsaa);
q_snprintf(caption, sizeof(caption), "QuakeSpasm %1.2f.%d", (float)FITZQUAKE_VERSION, QUAKESPASM_VER_PATCH);
#if defined(USE_SDL2)
/* Create the window if needed, hidden */
if (!draw_context)
{
flags = SDL_WINDOW_OPENGL | SDL_WINDOW_HIDDEN;
draw_context = SDL_CreateWindow (caption, SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, width, height, flags);
if (!draw_context)
Sys_Error ("Couldn't create window");
gl_context = SDL_GL_CreateContext (draw_context);
if (!gl_context) { // scale back fsaa
SDL_GL_SetAttribute(SDL_GL_MULTISAMPLEBUFFERS, 0);
SDL_GL_SetAttribute(SDL_GL_MULTISAMPLESAMPLES, 0);
gl_context = SDL_GL_CreateContext (draw_context);
}
if (!gl_context) { // scale back SDL_GL_DEPTH_SIZE
SDL_GL_SetAttribute(SDL_GL_DEPTH_SIZE, 16);
gl_context = SDL_GL_CreateContext (draw_context);
if (!gl_context)
Sys_Error ("Couldn't craete GL context");
}
}
/* Ensure the window is not fullscreen */
if (VID_GetFullscreen ())
{
if (SDL_SetWindowFullscreen (draw_context, 0) != 0)
Sys_Error("Couldn't set fullscreen state mode");
}
/* Set window size and display mode */
SDL_SetWindowSize (draw_context, width, height);
SDL_SetWindowPosition (draw_context, SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED);
SDL_SetWindowDisplayMode (draw_context, VID_SDL2_GetDisplayMode(width, height, bpp));
/* Make window fullscreen if needed, and show the window */
if (fullscreen)
{
if (SDL_SetWindowFullscreen (draw_context, SDL_WINDOW_FULLSCREEN) != 0)
Sys_Error ("Couldn't set fullscreen state mode");
}
SDL_ShowWindow (draw_context);
gl_swap_control = true;
if (SDL_GL_SetSwapInterval ((vid_vsync.value) ? 1 : 0) == -1)
gl_swap_control = false;
#else /* !defined(USE_SDL2) */
flags = DEFAULT_SDL_FLAGS;
if (fullscreen)
flags |= SDL_FULLSCREEN;
//
// swap control (the "before SDL_SetVideoMode" part)
//
gl_swap_control = true;
if (SDL_GL_SetAttribute(SDL_GL_SWAP_CONTROL, (vid_vsync.value) ? 1 : 0) == -1)
gl_swap_control = false;
bpp = SDL_VideoModeOK(width, height, bpp, flags);
draw_context = SDL_SetVideoMode(width, height, bpp, flags);
if (!draw_context) { // scale back fsaa
SDL_GL_SetAttribute(SDL_GL_MULTISAMPLEBUFFERS, 0);
@ -311,11 +548,11 @@ static int VID_SetMode (int width, int height, int bpp, qboolean fullscreen)
Sys_Error ("Couldn't set video mode");
}
q_snprintf(caption, sizeof(caption), "QuakeSpasm %1.2f.%d", (float)FITZQUAKE_VERSION, QUAKESPASM_VER_PATCH);
SDL_WM_SetCaption(caption, caption);
#endif
vid.width = draw_context->w;
vid.height = draw_context->h;
vid.width = VID_GetCurrentWidth();
vid.height = VID_GetCurrentHeight();
vid.conwidth = vid.width & 0xFFFFFFF8;
vid.conheight = vid.conwidth * vid.height / vid.width;
vid.numpages = 2;
@ -328,7 +565,7 @@ static int VID_SetMode (int width, int height, int bpp, qboolean fullscreen)
if (SDL_GL_GetAttribute(SDL_GL_MULTISAMPLESAMPLES, &fsaa_obtained) == -1)
fsaa_obtained = 0;
modestate = draw_context->flags & SDL_FULLSCREEN ? MS_FULLSCREEN : MS_WINDOWED;
modestate = VID_GetFullscreen() ? MS_FULLSCREEN : MS_WINDOWED;
CDAudio_Resume ();
BGM_Resume ();
@ -338,9 +575,9 @@ static int VID_SetMode (int width, int height, int bpp, qboolean fullscreen)
ClearAllStates ();
Con_SafePrintf ("Video mode %dx%dx%d (%d-bit z-buffer, %dx FSAA) initialized\n",
draw_context->w,
draw_context->h,
draw_context->format->BitsPerPixel,
VID_GetCurrentWidth(),
VID_GetCurrentHeight(),
VID_GetCurrentBPP(),
depthbits,
fsaa_obtained);
@ -437,10 +674,10 @@ static void VID_Test (void)
//
// now try the switch
//
old_width = draw_context->w;
old_height = draw_context->h;
old_bpp = draw_context->format->BitsPerPixel;
old_fullscreen = draw_context->flags & SDL_FULLSCREEN ? true : false;
old_width = VID_GetCurrentWidth();
old_height = VID_GetCurrentHeight();
old_bpp = VID_GetCurrentBPP();
old_fullscreen = VID_GetFullscreen() ? true : false;
VID_Restart ();
@ -619,11 +856,19 @@ static void GL_CheckExtensions (void)
{
Con_Warning ("vertical sync not supported (SDL_GL_SetAttribute failed)\n");
}
#if defined(USE_SDL2)
else if ((swap_control = SDL_GL_GetSwapInterval()) == -1)
{
gl_swap_control = false;
Con_Warning ("vertical sync not supported (SDL_GL_GetSwapInterval failed)\n");
}
#else
else if (SDL_GL_GetAttribute(SDL_GL_SWAP_CONTROL, &swap_control) == -1)
{
gl_swap_control = false;
Con_Warning ("vertical sync not supported (SDL_GL_GetAttribute failed)\n");
}
#endif
else if ((vid_vsync.value && swap_control != 1) || (!vid_vsync.value && swap_control != 0))
{
gl_swap_control = false;
@ -766,7 +1011,13 @@ GL_EndRendering
void GL_EndRendering (void)
{
if (!scr_skipupdate)
{
#if defined(USE_SDL2)
SDL_GL_SwapWindow(draw_context);
#else
SDL_GL_SwapBuffers();
#endif
}
}
@ -778,6 +1029,9 @@ void VID_Shutdown (void)
SDL_QuitSubSystem(SDL_INIT_VIDEO);
draw_context = NULL;
#if defined(USE_SDL2)
gl_context = NULL;
#endif
PL_VID_Shutdown();
}
@ -821,10 +1075,10 @@ static void VID_DescribeCurrentMode_f (void)
{
if (draw_context)
Con_Printf("%dx%dx%d %s\n",
draw_context->w,
draw_context->h,
draw_context->format->BitsPerPixel,
draw_context->flags & SDL_FULLSCREEN ? "fullscreen" : "windowed");
VID_GetCurrentWidth(),
VID_GetCurrentHeight(),
VID_GetCurrentBPP(),
VID_GetFullscreen() ? "fullscreen" : "windowed");
}
/*
@ -880,6 +1134,26 @@ VID_InitModelist
*/
static void VID_InitModelist (void)
{
#if defined(USE_SDL2)
const int sdlmodes = SDL_GetNumDisplayModes(0);
int i;
nummodes = 0;
for (i = 0; i < sdlmodes; i++)
{
if (nummodes >= MAX_MODE_LIST)
break;
SDL_DisplayMode mode;
if (SDL_GetDisplayMode(0, i, &mode) == 0)
{
modelist[nummodes].width = mode.w;
modelist[nummodes].height = mode.h;
modelist[nummodes].bpp = SDL_BITSPERPIXEL(mode.format);
nummodes++;
}
}
#else
SDL_PixelFormat format;
SDL_Rect **modes;
Uint32 flags;
@ -931,6 +1205,7 @@ static void VID_InitModelist (void)
if (nummodes == originalnummodes)
Con_SafePrintf ("No fullscreen DIB modes found\n");
#endif
}
/*
@ -941,8 +1216,7 @@ VID_Init
void VID_Init (void)
{
static char vid_center[] = "SDL_VIDEO_CENTERED=center";
const SDL_VideoInfo *info;
int p, width, height, bpp;
int p, width, height, bpp, display_width, display_height, display_bpp;
qboolean fullscreen;
const char *read_vars[] = { "vid_fullscreen",
"vid_width",
@ -976,8 +1250,26 @@ void VID_Init (void)
if (SDL_InitSubSystem(SDL_INIT_VIDEO) == -1)
Sys_Error("Could not initialize SDL Video");
info = SDL_GetVideoInfo();
Cvar_SetValueQuick (&vid_bpp, (float)info->vfmt->BitsPerPixel);
#if defined(USE_SDL2)
{
SDL_DisplayMode mode;
if (SDL_GetDesktopDisplayMode(0, &mode) != 0)
Sys_Error("Could not get desktop display mode");
display_width = mode.w;
display_height = mode.h;
display_bpp = SDL_BITSPERPIXEL(mode.format);
}
#else
{
const SDL_VideoInfo *info = SDL_GetVideoInfo();
display_width = info->current_w;
display_height = info->current_h;
display_bpp = info->vfmt->BitsPerPixel;
}
#endif
Cvar_SetValueQuick (&vid_bpp, (float)display_bpp);
if (CFG_OpenConfig("config.cfg") == 0)
{
@ -996,9 +1288,9 @@ void VID_Init (void)
if (COM_CheckParm("-current"))
{
width = info->current_w;
height = info->current_h;
bpp = info->vfmt->BitsPerPixel;
width = display_width;
height = display_height;
bpp = display_bpp;
fullscreen = true;
}
else
@ -1047,7 +1339,7 @@ void VID_Init (void)
{
width = 640;
height = 480;
bpp = info->vfmt->BitsPerPixel;
bpp = display_bpp;
fullscreen = false;
}
@ -1085,16 +1377,24 @@ void VID_Init (void)
void VID_Toggle (void)
{
static qboolean vid_toggle_works = true;
qboolean toggleWorked;
S_ClearBuffer ();
if (!vid_toggle_works)
goto vrestart;
if (SDL_WM_ToggleFullScreen(draw_context) == 1)
#if defined(USE_SDL2)
toggleWorked = SDL_SetWindowFullscreen(draw_context, VID_GetFullscreen() ? 0 : SDL_WINDOW_FULLSCREEN) == 0;
#else
toggleWorked = SDL_WM_ToggleFullScreen(draw_context) == 1;
#endif
if (toggleWorked)
{
Sbar_Changed (); // Sbar seems to need refreshing
modestate = draw_context->flags & SDL_FULLSCREEN ? MS_FULLSCREEN : MS_WINDOWED;
modestate = VID_GetFullscreen() ? MS_FULLSCREEN : MS_WINDOWED;
VID_SyncCvars();
@ -1112,7 +1412,7 @@ void VID_Toggle (void)
vid_toggle_works = false;
Con_DPrintf ("SDL_WM_ToggleFullScreen failed, attempting VID_Restart\n");
vrestart:
Cvar_SetQuick (&vid_fullscreen, draw_context-> flags & SDL_FULLSCREEN ? "0" : "1");
Cvar_SetQuick (&vid_fullscreen, VID_GetFullscreen() ? "0" : "1");
Cbuf_AddText ("vid_restart\n");
}
}
@ -1124,17 +1424,13 @@ VID_SyncCvars -- johnfitz -- set vid cvars to match current video mode
*/
void VID_SyncCvars (void)
{
int swap_control;
if (draw_context)
{
Cvar_SetValueQuick (&vid_width, draw_context->w);
Cvar_SetValueQuick (&vid_height, draw_context->h);
Cvar_SetValueQuick (&vid_bpp, draw_context->format->BitsPerPixel);
Cvar_SetQuick (&vid_fullscreen, draw_context->flags & SDL_FULLSCREEN ? "1" : "0");
if (SDL_GL_GetAttribute(SDL_GL_SWAP_CONTROL, &swap_control) == 0)
Cvar_SetQuick (&vid_vsync, (swap_control > 0)? "1" : "0");
Cvar_SetValueQuick (&vid_width, VID_GetCurrentWidth());
Cvar_SetValueQuick (&vid_height, VID_GetCurrentHeight());
Cvar_SetValueQuick (&vid_bpp, VID_GetCurrentBPP());
Cvar_SetQuick (&vid_fullscreen, VID_GetFullscreen() ? "1" : "0");
Cvar_SetQuick (&vid_vsync, VID_GetVSync() ? "1" : "0");
}
vid_changed = false;

View file

@ -22,7 +22,11 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
#include "quakedef.h"
#if defined(SDL_FRAMEWORK) || defined(NO_SDL_CONFIG)
#if defined(USE_SDL2)
#include <SDL2/SDL.h>
#else
#include <SDL/SDL.h>
#endif
#else
#include "SDL.h"
#endif
@ -74,6 +78,39 @@ static int FilterMouseEvents (const SDL_Event *event)
return 1;
}
static int FilterMouseEvents_SDL2 (void *userdata, SDL_Event *event)
{
return FilterMouseEvents (event);
}
static void IN_BeginIgnoringMouseEvents()
{
#if defined(USE_SDL2)
SDL_EventFilter currentFilter = NULL;
void *currentUserdata = NULL;
SDL_GetEventFilter(&currentFilter, &currentUserdata);
if (currentFilter != FilterMouseEvents_SDL2)
SDL_SetEventFilter(FilterMouseEvents_SDL2, NULL);
#else
if (SDL_GetEventFilter() != FilterMouseEvents)
SDL_SetEventFilter(FilterMouseEvents);
#endif
}
static void IN_EndIgnoringMouseEvents()
{
#if defined(USE_SDL2)
SDL_EventFilter currentFilter;
void *currentUserdata;
if (SDL_GetEventFilter(&currentFilter, &currentUserdata) == SDL_TRUE)
SDL_SetEventFilter(NULL, NULL);
#else
if (SDL_GetEventFilter() != NULL)
SDL_SetEventFilter(NULL);
#endif
}
#ifdef MACOS_X_ACCELERATION_HACK
static cvar_t in_disablemacosxmouseaccel = {"in_disablemacosxmouseaccel", "1", CVAR_ARCHIVE};
static double originalMouseSpeed = -1.0;
@ -155,6 +192,12 @@ void IN_Activate (void)
IN_DisableOSXMouseAccel();
#endif
#if defined(USE_SDL2)
if (SDL_SetRelativeMouseMode(SDL_TRUE) != 0)
{
Con_Printf("WARNING: SDL_SetRelativeMouseMode(SDL_TRUE) failed.\n");
}
#else
if (SDL_WM_GrabInput(SDL_GRAB_QUERY) != SDL_GRAB_ON)
{
SDL_WM_GrabInput(SDL_GRAB_ON);
@ -168,9 +211,9 @@ void IN_Activate (void)
if (SDL_ShowCursor(SDL_QUERY) != SDL_DISABLE)
Con_Printf("WARNING: SDL_ShowCursor(SDL_DISABLE) failed.\n");
}
#endif
if (SDL_GetEventFilter() != NULL)
SDL_SetEventFilter(NULL);
IN_EndIgnoringMouseEvents();
total_dx = 0;
total_dy = 0;
@ -188,6 +231,9 @@ void IN_Deactivate (qboolean free_cursor)
if (free_cursor)
{
#if defined(USE_SDL2)
SDL_SetRelativeMouseMode(SDL_FALSE);
#else
if (SDL_WM_GrabInput(SDL_GRAB_QUERY) != SDL_GRAB_OFF)
{
SDL_WM_GrabInput(SDL_GRAB_OFF);
@ -201,25 +247,27 @@ void IN_Deactivate (qboolean free_cursor)
if (SDL_ShowCursor(SDL_QUERY) != SDL_ENABLE)
Con_Printf("WARNING: SDL_ShowCursor(SDL_ENABLE) failed.\n");
}
#endif
}
/* discard all mouse events when input is deactivated */
if (SDL_GetEventFilter() != FilterMouseEvents)
SDL_SetEventFilter(FilterMouseEvents);
IN_BeginIgnoringMouseEvents();
}
void IN_Init (void)
{
prev_gamekey = ((key_dest == key_game && !con_forcedup) || m_keys_bind_grab);
#if !defined(USE_SDL2)
SDL_EnableUNICODE (!prev_gamekey);
if (SDL_EnableKeyRepeat(SDL_DEFAULT_REPEAT_DELAY, SDL_DEFAULT_REPEAT_INTERVAL) == -1)
Con_Printf("Warning: SDL_EnableKeyRepeat() failed.\n");
#endif
if (safemode || COM_CheckParm("-nomouse"))
{
no_mouse = true;
/* discard all mouse events when input is deactivated */
SDL_SetEventFilter(FilterMouseEvents);
IN_BeginIgnoringMouseEvents();
}
#ifdef MACOS_X_ACCELERATION_HACK
@ -307,10 +355,146 @@ void IN_UpdateForKeydest (void)
{
prev_gamekey = gamekey;
Key_ClearStates();
#if !defined(USE_SDL2)
SDL_EnableUNICODE(!gamekey);
#else
if (gamekey)
SDL_StopTextInput();
else
SDL_StartTextInput();
#endif
}
}
#if defined(USE_SDL2)
static qboolean IN_SDL2_QuakeKeyHandledAsTextInput(int qkey)
{
return (qkey >= 32 && qkey <= 126) && qkey != '`';
}
static inline int IN_SDL2_ScancodeToQuakeKey(SDL_Scancode scancode)
{
switch (scancode)
{
case SDL_SCANCODE_TAB: return K_TAB;
case SDL_SCANCODE_RETURN: return K_ENTER;
case SDL_SCANCODE_RETURN2: return K_ENTER;
case SDL_SCANCODE_ESCAPE: return K_ESCAPE;
case SDL_SCANCODE_SPACE: return K_SPACE;
case SDL_SCANCODE_A: return 'a';
case SDL_SCANCODE_B: return 'b';
case SDL_SCANCODE_C: return 'c';
case SDL_SCANCODE_D: return 'd';
case SDL_SCANCODE_E: return 'e';
case SDL_SCANCODE_F: return 'f';
case SDL_SCANCODE_G: return 'g';
case SDL_SCANCODE_H: return 'h';
case SDL_SCANCODE_I: return 'i';
case SDL_SCANCODE_J: return 'j';
case SDL_SCANCODE_K: return 'k';
case SDL_SCANCODE_L: return 'l';
case SDL_SCANCODE_M: return 'm';
case SDL_SCANCODE_N: return 'n';
case SDL_SCANCODE_O: return 'o';
case SDL_SCANCODE_P: return 'p';
case SDL_SCANCODE_Q: return 'q';
case SDL_SCANCODE_R: return 'r';
case SDL_SCANCODE_S: return 's';
case SDL_SCANCODE_T: return 't';
case SDL_SCANCODE_U: return 'u';
case SDL_SCANCODE_V: return 'v';
case SDL_SCANCODE_W: return 'w';
case SDL_SCANCODE_X: return 'x';
case SDL_SCANCODE_Y: return 'y';
case SDL_SCANCODE_Z: return 'z';
case SDL_SCANCODE_1: return '1';
case SDL_SCANCODE_2: return '2';
case SDL_SCANCODE_3: return '3';
case SDL_SCANCODE_4: return '4';
case SDL_SCANCODE_5: return '5';
case SDL_SCANCODE_6: return '6';
case SDL_SCANCODE_7: return '7';
case SDL_SCANCODE_8: return '8';
case SDL_SCANCODE_9: return '9';
case SDL_SCANCODE_0: return '0';
case SDL_SCANCODE_MINUS: return '-';
case SDL_SCANCODE_EQUALS: return '=';
case SDL_SCANCODE_LEFTBRACKET: return '[';
case SDL_SCANCODE_RIGHTBRACKET: return ']';
case SDL_SCANCODE_BACKSLASH: return '\\';
case SDL_SCANCODE_NONUSHASH: return '#';
case SDL_SCANCODE_SEMICOLON: return ';';
case SDL_SCANCODE_APOSTROPHE: return '\'';
case SDL_SCANCODE_GRAVE: return '`';
case SDL_SCANCODE_COMMA: return ',';
case SDL_SCANCODE_PERIOD: return '.';
case SDL_SCANCODE_SLASH: return '/';
case SDL_SCANCODE_NONUSBACKSLASH: return '\\';
case SDL_SCANCODE_BACKSPACE: return K_BACKSPACE;
case SDL_SCANCODE_UP: return K_UPARROW;
case SDL_SCANCODE_DOWN: return K_DOWNARROW;
case SDL_SCANCODE_LEFT: return K_LEFTARROW;
case SDL_SCANCODE_RIGHT: return K_RIGHTARROW;
case SDL_SCANCODE_LALT: return K_ALT;
case SDL_SCANCODE_RALT: return K_ALT;
case SDL_SCANCODE_LCTRL: return K_CTRL;
case SDL_SCANCODE_RCTRL: return K_CTRL;
case SDL_SCANCODE_LSHIFT: return K_SHIFT;
case SDL_SCANCODE_RSHIFT: return K_SHIFT;
case SDL_SCANCODE_F1: return K_F1;
case SDL_SCANCODE_F2: return K_F2;
case SDL_SCANCODE_F3: return K_F3;
case SDL_SCANCODE_F4: return K_F4;
case SDL_SCANCODE_F5: return K_F5;
case SDL_SCANCODE_F6: return K_F6;
case SDL_SCANCODE_F7: return K_F7;
case SDL_SCANCODE_F8: return K_F8;
case SDL_SCANCODE_F9: return K_F9;
case SDL_SCANCODE_F10: return K_F10;
case SDL_SCANCODE_F11: return K_F11;
case SDL_SCANCODE_F12: return K_F12;
case SDL_SCANCODE_INSERT: return K_INS;
case SDL_SCANCODE_DELETE: return K_DEL;
case SDL_SCANCODE_PAGEDOWN: return K_PGDN;
case SDL_SCANCODE_PAGEUP: return K_PGUP;
case SDL_SCANCODE_HOME: return K_HOME;
case SDL_SCANCODE_END: return K_END;
case SDL_SCANCODE_NUMLOCKCLEAR: return K_KP_NUMLOCK;
case SDL_SCANCODE_KP_DIVIDE: return K_KP_SLASH;
case SDL_SCANCODE_KP_MULTIPLY: return K_KP_STAR;
case SDL_SCANCODE_KP_MINUS: return K_KP_MINUS;
case SDL_SCANCODE_KP_7: return K_KP_HOME;
case SDL_SCANCODE_KP_8: return K_KP_UPARROW;
case SDL_SCANCODE_KP_9: return K_KP_PGUP;
case SDL_SCANCODE_KP_PLUS: return K_KP_PLUS;
case SDL_SCANCODE_KP_4: return K_KP_LEFTARROW;
case SDL_SCANCODE_KP_5: return K_KP_5;
case SDL_SCANCODE_KP_6: return K_KP_RIGHTARROW;
case SDL_SCANCODE_KP_1: return K_KP_END;
case SDL_SCANCODE_KP_2: return K_KP_DOWNARROW;
case SDL_SCANCODE_KP_3: return K_KP_PGDN;
case SDL_SCANCODE_KP_ENTER: return K_KP_ENTER;
case SDL_SCANCODE_KP_0: return K_KP_INS;
case SDL_SCANCODE_KP_PERIOD: return K_KP_DEL;
case SDL_SCANCODE_LGUI: return K_COMMAND;
case SDL_SCANCODE_RGUI: return K_COMMAND;
case SDL_SCANCODE_PAUSE: return K_PAUSE;
default: return 0;
}
}
#endif
void IN_SendKeyEvents (void)
{
SDL_Event event;
@ -320,6 +504,14 @@ void IN_SendKeyEvents (void)
{
switch (event.type)
{
#if defined(USE_SDL2)
case SDL_WINDOWEVENT:
if (event.window.event == SDL_WINDOWEVENT_FOCUS_GAINED)
S_UnblockSound();
else if (event.window.event == SDL_WINDOWEVENT_FOCUS_LOST)
S_BlockSound();
break;
#else
case SDL_ACTIVEEVENT:
if (event.active.state & (SDL_APPINPUTFOCUS|SDL_APPACTIVE))
{
@ -328,7 +520,27 @@ void IN_SendKeyEvents (void)
else S_BlockSound();
}
break;
#endif
#if defined(USE_SDL2)
case SDL_TEXTINPUT:
// SDL2: We use SDL_TEXTINPUT for typing in the console / chat.
// SDL2 uses the local keyboard layout and handles modifiers
// (shift for uppercase, etc.) for us.
{
char *ch;
for (ch = event.text.text; *ch != '\0'; ch++)
{
int qkey = *ch;
if (IN_SDL2_QuakeKeyHandledAsTextInput(qkey) && !gamekey)
{
Key_Event (qkey, true, false);
Key_Event (qkey, false, false);
}
}
}
break;
#endif
case SDL_KEYDOWN:
if ((event.key.keysym.sym == SDLK_RETURN) &&
(event.key.keysym.mod & KMOD_ALT))
@ -344,6 +556,20 @@ void IN_SendKeyEvents (void)
}
/* fallthrough */
case SDL_KEYUP:
#if defined(USE_SDL2)
// SDL2: in gamekey mode, we interpret the keyboard as the US
// layout, so keybindings are based on key position, not the label
// on the key cap.
sym = IN_SDL2_ScancodeToQuakeKey(event.key.keysym.scancode);
if (gamekey || !IN_SDL2_QuakeKeyHandledAsTextInput(sym))
{
state = event.key.state;
Key_Event (sym, state, true);
}
break;
#else
sym = event.key.keysym.sym;
state = event.key.state;
modstate = SDL_GetModState();
@ -569,9 +795,9 @@ void IN_SendKeyEvents (void)
sym = 0;
break;
}
Key_Event (sym, state);
Key_Event (sym, state, true);
break;
#endif
case SDL_MOUSEBUTTONDOWN:
case SDL_MOUSEBUTTONUP:
if (event.button.button < 1 ||
@ -581,9 +807,24 @@ void IN_SendKeyEvents (void)
event.button.button);
break;
}
Key_Event(buttonremap[event.button.button - 1], event.button.state == SDL_PRESSED);
Key_Event(buttonremap[event.button.button - 1], event.button.state == SDL_PRESSED, true);
break;
#if defined(USE_SDL2)
case SDL_MOUSEWHEEL:
if (event.wheel.y > 0)
{
Key_Event(K_MWHEELUP, false, true);
Key_Event(K_MWHEELUP, true, true);
}
else if (event.wheel.y < 0)
{
Key_Event(K_MWHEELDOWN, false, true);
Key_Event(K_MWHEELDOWN, true, true);
}
break;
#endif
case SDL_MOUSEMOTION:
IN_MouseMove(event.motion.xrel, event.motion.yrel);
break;

View file

@ -888,9 +888,14 @@ Key_Event
Called by the system between frames for both key up and key down events
Should NOT be called during an interrupt!
If interpret_shift is true, and the shift key is currently down, handles
mapping to the shifted version of a key following the US keyboard layout
(e.g. '5' -> '%'). We pass false for SDL_TEXTINPUT events; SDL has already
processed the shift mapping for these.
===================
*/
void Key_Event (int key, qboolean down)
void Key_Event (int key, qboolean down, qboolean interpret_shift)
{
char *kb;
char cmd[1024];
@ -1001,7 +1006,7 @@ void Key_Event (int key, qboolean down)
if (!down)
return; // other systems only care about key down events
if (shift_down)
if (shift_down && interpret_shift)
key = keyshift[key];
switch (key_dest)
@ -1034,7 +1039,7 @@ void Key_ClearStates (void)
for (i = 0; i < 256; i++)
{
if (keydown[i])
Key_Event (i, false);
Key_Event (i, false, true);
}
}

View file

@ -164,7 +164,7 @@ void Key_Init (void);
void Key_ClearStates (void);
void Key_UpdateForDest (void);
void Key_Event (int key, qboolean down);
void Key_Event (int key, qboolean down, qboolean interpret_shift);
void Key_SetBinding (int keynum, const char *binding);
const char *Key_KeynumToString (int keynum);

View file

@ -22,12 +22,27 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
#include "quakedef.h"
#if defined(SDL_FRAMEWORK) || defined(NO_SDL_CONFIG)
#if defined(USE_SDL2)
#include <SDL2/SDL.h>
#else
#include <SDL/SDL.h>
#endif
#else
#include "SDL.h"
#endif
#include <stdio.h>
#if defined(USE_SDL2)
/* need at least SDL_2.0.0 */
#define SDL_MIN_X 2
#define SDL_MIN_Y 0
#define SDL_MIN_Z 0
#define SDL_REQUIREDVERSION (SDL_VERSIONNUM(SDL_MIN_X,SDL_MIN_Y,SDL_MIN_Z))
#define SDL_NEW_VERSION_REJECT (SDL_VERSIONNUM(3,0,0))
#else
/* need at least SDL_1.2.10 */
#define SDL_MIN_X 1
#define SDL_MIN_Y 2
@ -36,9 +51,17 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
/* reject 1.3.0 and newer at runtime. */
#define SDL_NEW_VERSION_REJECT (SDL_VERSIONNUM(1,3,0))
#endif
static void Sys_CheckSDL (void)
{
#if defined(USE_SDL2)
SDL_version v;
SDL_version *sdl_version = &v;
SDL_GetVersion(&v);
#else
const SDL_version *sdl_version = SDL_Linked_Version();
#endif
Sys_Printf("Found SDL version %i.%i.%i\n",sdl_version->major,sdl_version->minor,sdl_version->patch);
if (SDL_VERSIONNUM(sdl_version->major,sdl_version->minor,sdl_version->patch) < SDL_REQUIREDVERSION)
@ -59,7 +82,12 @@ static void Sys_CheckSDL (void)
#endif
static quakeparms_t parms;
static Uint8 appState;
// On OS X we call SDL_main from the launcher, but SDL2 doesn't redefine main
// as SDL_main on OS X anymore, so we do it ourselves.
#if defined(USE_SDL2) && defined(__APPLE__)
#define main SDL_main
#endif
int main(int argc, char *argv[])
{
@ -128,14 +156,13 @@ int main(int argc, char *argv[])
else
while (1)
{
appState = SDL_GetAppState();
/* If we have no input focus at all, sleep a bit */
if ( !(appState & (SDL_APPMOUSEFOCUS | SDL_APPINPUTFOCUS)) || cl.paused)
if ( !VID_HasMouseOrInputFocus() || cl.paused)
{
SDL_Delay(16);
}
/* If we're minimised, sleep a bit more */
if ( !(appState & SDL_APPACTIVE) )
if ( VID_IsMinimized() )
{
scr_skipupdate = 1;
SDL_Delay(32);

View file

@ -47,8 +47,13 @@ void PL_SetWindowIcon (void)
return;
/* make pure magenta (#ff00ff) tranparent */
colorkey = SDL_MapRGB(icon->format, 255, 0, 255);
#if defined(USE_SDL2)
SDL_SetColorKey(icon, SDL_TRUE, colorkey);
SDL_SetWindowIcon(VID_GetWindow(), icon);
#else
SDL_SetColorKey(icon, SDL_SRCCOLORKEY, colorkey);
SDL_WM_SetIcon(icon, NULL);
#endif
SDL_FreeSurface(icon);
}

View file

@ -22,7 +22,11 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
#include "quakedef.h"
#if defined(SDL_FRAMEWORK) || defined(NO_SDL_CONFIG)
#if defined(USE_SDL2)
#include <SDL2/SDL.h>
#else
#include <SDL/SDL.h>
#endif
#else
#include "SDL.h"
#endif

View file

@ -46,10 +46,17 @@ void PL_SetWindowIcon (void)
SDL_VERSION(&wminfo.version);
#if defined(USE_SDL2)
if (SDL_GetWindowWMInfo(VID_GetWindow(), &wminfo) != SDL_TRUE)
return; /* wrong SDL version */
hwnd = wminfo.info.win.window;
#else
if (SDL_GetWMInfo(&wminfo) != 1)
return; /* wrong SDL version */
hwnd = wminfo.window;
#endif
#ifdef _WIN64
SetClassLongPtr(hwnd, GCLP_HICON, (LONG_PTR) icon);
#else

View file

@ -212,8 +212,13 @@ typedef struct
#include "platform.h"
#if defined(SDL_FRAMEWORK) || defined(NO_SDL_CONFIG)
#if defined(USE_SDL2)
#include <SDL2/SDL.h>
#include <SDL2/SDL_opengl.h>
#else
#include <SDL/SDL.h>
#include <SDL/SDL_opengl.h>
#endif
#else
#include "SDL.h"
#include "SDL_opengl.h"

View file

@ -24,7 +24,11 @@
#include "quakedef.h"
#if defined(SDL_FRAMEWORK) || defined(NO_SDL_CONFIG)
#if defined(USE_SDL2)
#include <SDL2/SDL.h>
#else
#include <SDL/SDL.h>
#endif
#else
#include "SDL.h"
#endif
@ -150,8 +154,18 @@ qboolean SNDDMA_Init (dma_t *dma)
Con_Printf ("SDL audio spec : %d Hz, %d samples, %d channels\n",
obtained.freq, obtained.samples, obtained.channels);
#if defined(USE_SDL2)
{
const char *driver = SDL_GetCurrentAudioDriver();
const char *device = SDL_GetAudioDeviceName(0, SDL_FALSE);
q_snprintf(drivername, sizeof(drivername), "%s - %s",
driver != NULL ? driver : "(UNKNOWN)",
device != NULL ? device : "(UNKNOWN)");
}
#else
if (SDL_AudioDriverName(drivername, sizeof(drivername)) == NULL)
strcpy(drivername, "(UNKNOWN)");
#endif
buffersize = shm->samples * (shm->samplebits / 8);
Con_Printf ("SDL audio driver: %s, %d bytes buffer\n", drivername, buffersize);

View file

@ -31,7 +31,11 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
#include <time.h>
#if defined(SDL_FRAMEWORK) || defined(NO_SDL_CONFIG)
#if defined(USE_SDL2)
#include <SDL2/SDL.h>
#else
#include <SDL/SDL.h>
#endif
#else
#include "SDL.h"
#endif

View file

@ -83,5 +83,9 @@ void VID_SyncCvars (void);
void VID_Toggle (void);
void *VID_GetWindow (void);
qboolean VID_HasMouseOrInputFocus (void);
qboolean VID_IsMinimized (void);
#endif /* __VID_DEFS_H */