Mercurial > sdl-ios-xcode
comparison src/video/x11/SDL_x11modes.c @ 1768:814f9f2c7a33
Fixed bug #80
Date: 21 Apr 2003 17:20:20 +0100
From: Alan Swanson <swanson@uklinux.net>
Subject: [SDL] New XFree 4.3 Video Mode Patch
If you look at the unsorted list of modes returned by X, here's mine;
1280 x 1024 @ 85.0 >
1024 x 768 @ 100.3 > USER
800 x 600 @ 125.5 > SET
640 x 480 @ 124.9 >
1280 x 1024 @ 75.0 ]
1280 x 1024 @ 60.0 ]
1280 x 960 @ 85.0 ] X11
1280 x 960 @ 60.0 ] AUTO
1152 x 864 @ 75.0 ]=20
1152 x 768 @ 54.8 ]
960 x 720 @ 120.0 ]
...
640 x 400 @ 85.1 ] 256k
576 x 432 @ 150.0 ] 249k PIXEL
640 x 350 @ 85.1 ] 224k COUNT
576 x 384 @ 109.6 ] 221k
...
The user set modes come first followed by X set modes which are ordered
by decreasing number of pixels and refresh.
The reason why every other library or program not using SDL working is
due to SDL scanning the modes in reverse getting X11 provided modes
modes with the lowest refresh.
author | Sam Lantinga <slouken@libsdl.org> |
---|---|
date | Fri, 05 May 2006 05:50:26 +0000 |
parents | 410b1ed7fe28 |
children | 8d3ca155c396 |
comparison
equal
deleted
inserted
replaced
1767:ae9f6be81810 | 1768:814f9f2c7a33 |
---|---|
31 #include "SDL_x11video.h" | 31 #include "SDL_x11video.h" |
32 #include "SDL_x11wm_c.h" | 32 #include "SDL_x11wm_c.h" |
33 #include "SDL_x11modes_c.h" | 33 #include "SDL_x11modes_c.h" |
34 #include "SDL_x11image_c.h" | 34 #include "SDL_x11image_c.h" |
35 | 35 |
36 /*#define X11MODES_DEBUG*/ | |
37 | |
36 #define MAX(a, b) (a > b ? a : b) | 38 #define MAX(a, b) (a > b ? a : b) |
37 | 39 |
38 #if SDL_VIDEO_DRIVER_X11_XRANDR | 40 #if SDL_VIDEO_DRIVER_X11_XRANDR |
39 static int cmpmodelist(const void *va, const void *vb) | 41 static int cmpmodelist(const void *va, const void *vb) |
40 { | 42 { |
101 #if SDL_VIDEO_DRIVER_X11_VIDMODE | 103 #if SDL_VIDEO_DRIVER_X11_VIDMODE |
102 if ( use_vidmode ) { | 104 if ( use_vidmode ) { |
103 SDL_NAME(XF86VidModeModeLine) mode; | 105 SDL_NAME(XF86VidModeModeLine) mode; |
104 SDL_NAME(XF86VidModeModeInfo) **modes; | 106 SDL_NAME(XF86VidModeModeInfo) **modes; |
105 int i; | 107 int i; |
106 int best_width = 0, best_height = 0; | |
107 int nmodes; | 108 int nmodes; |
109 int best = -1; | |
108 | 110 |
109 if ( SDL_NAME(XF86VidModeGetModeLine)(SDL_Display, SDL_Screen, &i, &mode) && | 111 if ( SDL_NAME(XF86VidModeGetModeLine)(SDL_Display, SDL_Screen, &i, &mode) && |
110 SDL_NAME(XF86VidModeGetAllModeLines)(SDL_Display,SDL_Screen,&nmodes,&modes)){ | 112 SDL_NAME(XF86VidModeGetAllModeLines)(SDL_Display,SDL_Screen,&nmodes,&modes) ) { |
111 #ifdef X11MODES_DEBUG | |
112 printf("Available modes (unsorted):\n"); | |
113 for ( i = 0; i < nmodes; ++i ) { | |
114 printf("Mode %d: %d x %d @ %d\n", i, | |
115 modes[i]->hdisplay, modes[i]->vdisplay, | |
116 1000 * modes[i]->dotclock / (modes[i]->htotal * | |
117 modes[i]->vtotal) ); | |
118 } | |
119 #endif | |
120 for ( i = 0; i < nmodes ; i++ ) { | 113 for ( i = 0; i < nmodes ; i++ ) { |
121 if ( (modes[i]->hdisplay == width) && | 114 if ( (modes[i]->hdisplay == width) && |
122 (modes[i]->vdisplay == height) ) | 115 (modes[i]->vdisplay == height) ) { |
123 goto match; | 116 best = i; |
124 } | 117 break; |
125 qsort(modes, nmodes, sizeof *modes, cmpmodes); | 118 } |
126 for ( i = nmodes-1; i > 0 ; i-- ) { | 119 if ( modes[i]->hdisplay >= width && |
127 if ( ! best_width ) { | 120 modes[i]->vdisplay >= height ) { |
128 if ( (modes[i]->hdisplay >= width) && | 121 if ( best < 0 || |
129 (modes[i]->vdisplay >= height) ) { | 122 (modes[i]->hdisplay < modes[best]->hdisplay && |
130 best_width = modes[i]->hdisplay; | 123 modes[i]->vdisplay <= modes[best]->vdisplay) || |
131 best_height = modes[i]->vdisplay; | 124 (modes[i]->vdisplay < modes[best]->vdisplay && |
132 } | 125 modes[i]->hdisplay <= modes[best]->hdisplay) ) { |
133 } else { | 126 best = i; |
134 if ( (modes[i]->hdisplay != best_width) || | |
135 (modes[i]->vdisplay != best_height) ) { | |
136 i++; | |
137 break; | |
138 } | 127 } |
139 } | 128 } |
140 } | 129 } |
141 match: | 130 if ( best >= 0 && |
142 if ( (modes[i]->hdisplay != mode.hdisplay) || | 131 ((modes[best]->hdisplay != mode.hdisplay) || |
143 (modes[i]->vdisplay != mode.vdisplay) ) { | 132 (modes[best]->vdisplay != mode.vdisplay)) ) { |
144 SDL_NAME(XF86VidModeSwitchToMode)(SDL_Display, SDL_Screen, modes[i]); | 133 #ifdef X11MODES_DEBUG |
134 printf("Best Mode %d: %d x %d @ %d\n", best, | |
135 modes[best]->hdisplay, modes[best]->vdisplay, | |
136 (modes[best]->htotal && modes[best]->vtotal) ? (1000 * modes[best]->dotclock / (modes[best]->htotal * modes[best]->vtotal)) : 0 ); | |
137 #endif | |
138 SDL_NAME(XF86VidModeSwitchToMode)(SDL_Display, SDL_Screen, modes[best]); | |
145 } | 139 } |
146 XFree(modes); | 140 XFree(modes); |
147 } | 141 } |
148 } | 142 } |
149 #endif /* SDL_VIDEO_DRIVER_X11_VIDMODE */ | 143 #endif /* SDL_VIDEO_DRIVER_X11_VIDMODE */ |
150 | 144 |
151 /* XiG */ | 145 /* XiG */ |
152 #if SDL_VIDEO_DRIVER_X11_XME | 146 #if SDL_VIDEO_DRIVER_X11_XME |
153 #ifdef X11MODES_DEBUG | 147 if ( use_xme && SDL_modelist ) { |
154 fprintf(stderr, "XME: set_best_resolution(): w = %d, h = %d\n", | |
155 width, height); | |
156 #endif | |
157 if ( SDL_modelist ) { | |
158 int i; | 148 int i; |
159 | 149 |
150 #ifdef X11MODES_DEBUG | |
151 fprintf(stderr, "XME: set_best_resolution(): w = %d, h = %d\n", | |
152 width, height); | |
153 #endif | |
160 for ( i=0; SDL_modelist[i]; ++i ) { | 154 for ( i=0; SDL_modelist[i]; ++i ) { |
161 if ( (SDL_modelist[i]->w >= width) && | 155 if ( (SDL_modelist[i]->w >= width) && |
162 (SDL_modelist[i]->h >= height) ) { | 156 (SDL_modelist[i]->h >= height) ) { |
163 break; | 157 break; |
164 } | 158 } |
172 | 166 |
173 if ( (SDL_modelist[i]->w != w) || (SDL_modelist[i]->h != h) ) { | 167 if ( (SDL_modelist[i]->w != w) || (SDL_modelist[i]->h != h) ) { |
174 #ifdef X11MODES_DEBUG | 168 #ifdef X11MODES_DEBUG |
175 fprintf(stderr, "XME: set_best_resolution: " | 169 fprintf(stderr, "XME: set_best_resolution: " |
176 "XiGMiscChangeResolution: %d %d\n", | 170 "XiGMiscChangeResolution: %d %d\n", |
177 SDL_modelist[s]->w, SDL_modelist[s]->h); | 171 SDL_modelist[i]->w, SDL_modelist[i]->h); |
178 # endif | 172 #endif |
179 XiGMiscChangeResolution(SDL_Display, | 173 XiGMiscChangeResolution(SDL_Display, |
180 SDL_Screen, | 174 SDL_Screen, |
181 0, /* view */ | 175 0, /* view */ |
182 SDL_modelist[i]->w, | 176 SDL_modelist[i]->w, |
183 SDL_modelist[i]->h, | 177 SDL_modelist[i]->h, |
187 } | 181 } |
188 } | 182 } |
189 #endif /* SDL_VIDEO_DRIVER_X11_XME */ | 183 #endif /* SDL_VIDEO_DRIVER_X11_XME */ |
190 | 184 |
191 #if SDL_VIDEO_DRIVER_X11_XRANDR | 185 #if SDL_VIDEO_DRIVER_X11_XRANDR |
192 if ( use_xrandr ) { | 186 if ( use_xrandr && SDL_modelist ) { |
193 #ifdef X11MODES_DEBUG | 187 #ifdef X11MODES_DEBUG |
194 fprintf(stderr, "XRANDR: set_best_resolution(): w = %d, h = %d\n", | 188 fprintf(stderr, "XRANDR: set_best_resolution(): w = %d, h = %d\n", |
195 width, height); | 189 width, height); |
196 #endif | 190 #endif |
197 if ( SDL_modelist ) { | 191 int i, nsizes; |
198 int i, nsizes; | 192 XRRScreenSize *sizes; |
199 XRRScreenSize *sizes; | 193 |
200 | 194 /* find the smallest resolution that is at least as big as the user requested */ |
201 /* find the smallest resolution that is at least as big as the user requested */ | 195 sizes = XRRConfigSizes(screen_config, &nsizes); |
202 sizes = XRRConfigSizes(screen_config, &nsizes); | 196 for ( i = (nsizes-1); i >= 0; i-- ) { |
203 for ( i = (nsizes-1); i >= 0; i-- ) { | 197 if ( (SDL_modelist[i]->w >= width) && |
204 if ( (SDL_modelist[i]->w >= width) && | 198 (SDL_modelist[i]->h >= height) ) { |
205 (SDL_modelist[i]->h >= height) ) { | 199 break; |
206 break; | 200 } |
201 } | |
202 | |
203 if ( i >= 0 && SDL_modelist[i] ) { /* found one, lets try it */ | |
204 int w, h; | |
205 | |
206 /* check current mode so we can avoid uneccessary mode changes */ | |
207 get_real_resolution(this, &w, &h); | |
208 | |
209 if ( (SDL_modelist[i]->w != w) || (SDL_modelist[i]->h != h) ) { | |
210 int size_id; | |
211 | |
212 #ifdef X11MODES_DEBUG | |
213 fprintf(stderr, "XRANDR: set_best_resolution: " | |
214 "XXRSetScreenConfig: %d %d\n", | |
215 SDL_modelist[i]->w, SDL_modelist[i]->h); | |
216 #endif | |
217 | |
218 /* find the matching size entry index */ | |
219 for ( size_id = 0; size_id < nsizes; ++size_id ) { | |
220 if ( (sizes[size_id].width == SDL_modelist[i]->w) && | |
221 (sizes[size_id].height == SDL_modelist[i]->h) ) | |
222 break; | |
207 } | 223 } |
208 } | 224 |
209 | 225 XRRSetScreenConfig(SDL_Display, screen_config, SDL_Root, |
210 if ( i >= 0 && SDL_modelist[i] ) { /* found one, lets try it */ | 226 size_id, saved_rotation, CurrentTime); |
211 int w, h; | |
212 | |
213 /* check current mode so we can avoid uneccessary mode changes */ | |
214 get_real_resolution(this, &w, &h); | |
215 | |
216 if ( (SDL_modelist[i]->w != w) || (SDL_modelist[i]->h != h) ) { | |
217 int size_id; | |
218 | |
219 #ifdef X11MODES_DEBUG | |
220 fprintf(stderr, "XRANDR: set_best_resolution: " | |
221 "XXRSetScreenConfig: %d %d\n", | |
222 SDL_modelist[i]->w, SDL_modelist[i]->h); | |
223 #endif | |
224 | |
225 /* find the matching size entry index */ | |
226 for ( size_id = 0; size_id < nsizes; ++size_id ) { | |
227 if ( (sizes[size_id].width == SDL_modelist[i]->w) && | |
228 (sizes[size_id].height == SDL_modelist[i]->h) ) | |
229 break; | |
230 } | |
231 | |
232 XRRSetScreenConfig(SDL_Display, screen_config, SDL_Root, | |
233 size_id, saved_rotation, CurrentTime); | |
234 } | |
235 } | 227 } |
236 } | 228 } |
237 } | 229 } |
238 #endif /* SDL_VIDEO_DRIVER_X11_XRANDR */ | 230 #endif /* SDL_VIDEO_DRIVER_X11_XRANDR */ |
239 | |
240 } | 231 } |
241 | 232 |
242 static void get_real_resolution(_THIS, int* w, int* h) | 233 static void get_real_resolution(_THIS, int* w, int* h) |
243 { | 234 { |
244 #if SDL_VIDEO_DRIVER_X11_XME | 235 #if SDL_VIDEO_DRIVER_X11_XME |
641 (!use_xinerama || xinerama_info.screen_number == 0) && | 632 (!use_xinerama || xinerama_info.screen_number == 0) && |
642 CheckVidMode(this, &vm_major, &vm_minor) && | 633 CheckVidMode(this, &vm_major, &vm_minor) && |
643 SDL_NAME(XF86VidModeGetAllModeLines)(SDL_Display, SDL_Screen,&nmodes,&modes) ) | 634 SDL_NAME(XF86VidModeGetAllModeLines)(SDL_Display, SDL_Screen,&nmodes,&modes) ) |
644 { | 635 { |
645 #ifdef X11MODES_DEBUG | 636 #ifdef X11MODES_DEBUG |
646 printf("Available modes: (sorted)\n"); | 637 printf("VidMode modes: (unsorted)\n"); |
647 for ( i = 0; i < nmodes; ++i ) { | 638 for ( i = 0; i < nmodes; ++i ) { |
648 printf("Mode %d: %d x %d @ %d\n", i, | 639 printf("Mode %d: %d x %d @ %d\n", i, |
649 modes[i]->hdisplay, modes[i]->vdisplay, | 640 modes[i]->hdisplay, modes[i]->vdisplay, |
650 (modes[i]->htotal && modes[i]->vtotal) ? (1000 * modes[i]->dotclock / (modes[i]->htotal * modes[i]->vtotal)) : 0 ); | 641 (modes[i]->htotal && modes[i]->vtotal) ? (1000 * modes[i]->dotclock / (modes[i]->htotal * modes[i]->vtotal)) : 0 ); |
651 } | 642 } |
836 if ( use_xrandr ) { | 827 if ( use_xrandr ) { |
837 printf("XRandR is enabled\n"); | 828 printf("XRandR is enabled\n"); |
838 } | 829 } |
839 | 830 |
840 if ( use_vidmode ) { | 831 if ( use_vidmode ) { |
841 printf("XFree86 VidMode is enabled\n"); | 832 printf("VidMode is enabled\n"); |
842 } | 833 } |
843 | 834 |
844 if ( use_xme ) { | 835 if ( use_xme ) { |
845 printf("Xi Graphics XME fullscreen is enabled\n"); | 836 printf("Xi Graphics XME fullscreen is enabled\n"); |
846 } | 837 } |