aboutsummaryrefslogtreecommitdiffstats
path: root/code/sdl
diff options
context:
space:
mode:
Diffstat (limited to 'code/sdl')
-rw-r--r--code/sdl/sdl_glimp.c131
1 files changed, 93 insertions, 38 deletions
diff --git a/code/sdl/sdl_glimp.c b/code/sdl/sdl_glimp.c
index be2ab18..eeba074 100644
--- a/code/sdl/sdl_glimp.c
+++ b/code/sdl/sdl_glimp.c
@@ -44,6 +44,7 @@ Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
#include <stdarg.h>
#include <stdio.h>
#include <stdlib.h>
+#include <math.h>
#include "../renderer/tr_local.h"
#include "../client/client.h"
@@ -110,44 +111,79 @@ void GLimp_LogComment( char *comment )
{
}
-static void set_available_modes(void)
+/*
+===============
+GLimp_CompareModes
+===============
+*/
+static int GLimp_CompareModes( const void *a, const void *b )
{
- char buf[MAX_STRING_CHARS];
- SDL_Rect **modes;
- size_t len = 0;
- int i;
-
- modes = SDL_ListModes(NULL, SDL_OPENGL | SDL_FULLSCREEN);
-
- if (!modes)
- {
- ri.Printf( PRINT_WARNING, "Can't get list of available modes\n");
- return;
- }
-
- if (modes == (SDL_Rect **)-1)
- {
- ri.Printf( PRINT_ALL, "Display supports any resolution\n");
- return; // can set any resolution
- }
-
- for (i = 0; modes[i]; ++i)
- {
- if(snprintf(NULL, 0, "%ux%u ", modes[i]->w, modes[i]->h) < (int)sizeof(buf)-len)
- {
- len += sprintf(buf+len, "%ux%u ", modes[i]->w, modes[i]->h);
- }
- else
- {
- ri.Printf( PRINT_WARNING, "Skipping mode %ux%x, buffer too small\n", modes[i]->w, modes[i]->h);
- }
- }
- if(len)
- {
- buf[strlen(buf)-1] = 0;
- ri.Printf( PRINT_ALL, "Available modes: '%s'\n", buf);
- ri.Cvar_Set( "r_availableModes", buf );
- }
+ const float ASPECT_EPSILON = 0.001f;
+ SDL_Rect *modeA = *(SDL_Rect **)a;
+ SDL_Rect *modeB = *(SDL_Rect **)b;
+ float aspectDiffA = fabs( ( (float)modeA->w / (float)modeA->h ) - displayAspect );
+ float aspectDiffB = fabs( ( (float)modeB->w / (float)modeB->h ) - displayAspect );
+ float aspectDiffsDiff = aspectDiffA - aspectDiffB;
+
+ if( aspectDiffsDiff > ASPECT_EPSILON )
+ return 1;
+ else if( aspectDiffsDiff < -ASPECT_EPSILON )
+ return -1;
+ else
+ {
+ if( modeA->w == modeB->w )
+ return modeA->h - modeB->h;
+ else
+ return modeA->w - modeB->w;
+ }
+}
+
+/*
+===============
+GLimp_DetectAvailableModes
+===============
+*/
+static void GLimp_DetectAvailableModes(void)
+{
+ char buf[ MAX_STRING_CHARS ] = { 0 };
+ SDL_Rect **modes;
+ int numModes;
+ int i;
+
+ modes = SDL_ListModes( NULL, SDL_OPENGL | SDL_FULLSCREEN );
+
+ if( !modes )
+ {
+ ri.Printf( PRINT_WARNING, "Can't get list of available modes\n" );
+ return;
+ }
+
+ if( modes == (SDL_Rect **)-1 )
+ {
+ ri.Printf( PRINT_ALL, "Display supports any resolution\n" );
+ return; // can set any resolution
+ }
+
+ for( numModes = 0; modes[ numModes ]; numModes++ );
+
+ qsort( modes, numModes, sizeof( SDL_Rect* ), GLimp_CompareModes );
+
+ for( i = 0; i < numModes; i++ )
+ {
+ const char *newModeString = va( "%ux%u ", modes[ i ]->w, modes[ i ]->h );
+
+ if( strlen( newModeString ) < (int)sizeof( buf ) - strlen( buf ) )
+ Q_strcat( buf, sizeof( buf ), newModeString );
+ else
+ ri.Printf( PRINT_WARNING, "Skipping mode %ux%x, buffer too small\n", modes[i]->w, modes[i]->h );
+ }
+
+ if( *buf )
+ {
+ buf[ strlen( buf ) - 1 ] = 0;
+ ri.Printf( PRINT_ALL, "Available modes: '%s'\n", buf );
+ ri.Cvar_Set( "r_availableModes", buf );
+ }
}
/*
@@ -164,9 +200,28 @@ static int GLimp_SetMode( int mode, qboolean fullscreen )
int i = 0;
SDL_Surface *vidscreen = NULL;
Uint32 flags = SDL_OPENGL;
+ const SDL_VideoInfo *videoInfo;
ri.Printf( PRINT_ALL, "Initializing OpenGL display\n");
+ if( displayAspect == 0.0f )
+ {
+#if !SDL_VERSION_ATLEAST(1, 2, 10)
+ // 1.2.10 is needed to get the desktop resolution
+ displayAspect = 4.0f / 3.0f;
+#elif MINSDL_PATCH >= 10
+# error Ifdeffery no longer necessary, please remove
+#else
+ // Guess the display aspect ratio through the desktop resolution
+ // by assuming (relatively safely) that it is set at or close to
+ // the display's native aspect ratio
+ videoInfo = SDL_GetVideoInfo( );
+ displayAspect = (float)videoInfo->current_w / (float)videoInfo->current_h;
+#endif
+
+ ri.Printf( PRINT_ALL, "Estimated display aspect: %.3f\n", displayAspect );
+ }
+
ri.Printf (PRINT_ALL, "...setting mode %d:", mode );
if ( !R_GetModeInfo( &glConfig.vidWidth, &glConfig.vidHeight, &glConfig.windowAspect, mode ) )
@@ -315,7 +370,7 @@ static int GLimp_SetMode( int mode, qboolean fullscreen )
break;
}
- set_available_modes();
+ GLimp_DetectAvailableModes();
if (!vidscreen)
{