|
|
1.1 root 1: /*
2: Hatari - resolution.c
3:
4: This file is distributed under the GNU Public License, version 2 or at
5: your option any later version. Read the file gpl.txt for details.
6:
7: SDL resolution limitation and selection routines.
8: */
9: const char Resolution_fileid[] = "Hatari resolution.c : " __DATE__ " " __TIME__;
10:
11: #include <SDL.h>
12: #include "main.h"
13: #include "configuration.h"
14: #include "resolution.h"
15: #include "screen.h"
16:
17: #define RESOLUTION_DEBUG 0
18:
19: #if RESOLUTION_DEBUG
20: #define Dprintf(a) printf a
21: #else
22: #define Dprintf(a)
23: #endif
24:
1.1.1.2 root 25: static int DesktopWidth, DesktopHeight;
26:
27: /**
28: * Initilizes resolution settings (gets current desktop
29: * resolution, sets max Falcon/TT Videl zooming resolution).
30: */
31: void Resolution_Init(void)
32: {
33: /* Needs to be called after SDL video and configuration
34: * initialization, but before Hatari Screen init is called
35: * for the first time!
36: */
37: const SDL_VideoInfo* info = SDL_GetVideoInfo();
38: if (info->current_w >= 640 && info->current_h >= 400) {
39: DesktopWidth = info->current_w;
40: DesktopHeight = info->current_h;
41: } else {
42: /* target 800x600 screen with statusbar out of screen */
43: DesktopWidth = 2*(48+320+48);
44: DesktopHeight = 2*NUM_VISIBLE_LINES+24;
45: fprintf(stderr, "WARNING: invalid desktop size %dx%d, defaulting to %dx%d!\n",
46: info->current_w, info->current_h, DesktopWidth, DesktopHeight);
47: }
48: /* if user hasn't set own max zoom size, use desktop size */
49: if (!(ConfigureParams.Screen.nMaxWidth &&
50: ConfigureParams.Screen.nMaxHeight)) {
51: ConfigureParams.Screen.nMaxWidth = DesktopWidth;
52: ConfigureParams.Screen.nMaxHeight = DesktopHeight;
53: }
54: Dprintf(("Desktop resolution: %dx%d\n",DesktopWidth, DesktopHeight));
55: Dprintf(("Configured Max res: %dx%d\n",ConfigureParams.Screen.nMaxWidth,ConfigureParams.Screen.nMaxHeight));
56: }
57:
58: /**
59: * Get current desktop resolution
60: */
61: void Resolution_GetDesktopSize(int *width, int *height)
62: {
1.1.1.3 ! root 63: Dprintf(("resolution: limit to desktop size\n"));
1.1.1.2 root 64: *width = DesktopWidth;
65: *height = DesktopHeight;
66: }
1.1 root 67:
68: /**
1.1.1.3 ! root 69: * Get max resolution
! 70: */
! 71: static void Resolution_GetMaxSize(int *width, int *height)
! 72: {
! 73: Dprintf(("resolution: force to specified max size\n"));
! 74: *width = ConfigureParams.Screen.nMaxWidth;
! 75: *height = ConfigureParams.Screen.nMaxHeight;
! 76: }
! 77:
! 78: /**
1.1 root 79: * Select best resolution from given SDL video modes.
80: * - If width and height are given, select the smallest mode larger
81: * or equal to requested size
82: * - Otherwise select the largest available mode
83: * return true for success and false if no matching mode was found.
84: */
85: static bool Resolution_Select(SDL_Rect **modes, int *width, int *height)
86: {
87: #define TOO_LARGE 0x7fff
88: int i, bestw, besth;
89:
90: if (!(*width && *height)) {
91: /* search the largest mode (prefer wider ones) */
92: for (i = 0; modes[i]; i++) {
93: if ((modes[i]->w > *width) && (modes[i]->h >= *height)) {
94: *width = modes[i]->w;
95: *height = modes[i]->h;
96: }
97: }
1.1.1.2 root 98: Dprintf(("resolution: largest found video mode: %dx%d\n",*width,*height));
1.1 root 99: return true;
100: }
101:
102: /* Search the smallest mode larger or equal to requested size */
103: bestw = TOO_LARGE;
104: besth = TOO_LARGE;
105: for (i = 0; modes[i]; i++) {
106: if ((modes[i]->w >= *width) && (modes[i]->h >= *height)) {
107: if ((modes[i]->w < bestw) || (modes[i]->h < besth)) {
108: bestw = modes[i]->w;
109: besth = modes[i]->h;
110: }
111: }
112: }
113: if (bestw == TOO_LARGE || besth == TOO_LARGE) {
114: return false;
115: }
116: *width = bestw;
117: *height = besth;
1.1.1.2 root 118: Dprintf(("resolution: video mode found: %dx%d\n",*width,*height));
1.1 root 119: return true;
120: #undef TOO_LARGE
121: }
122:
123:
124: /**
125: * Search video mode size that best suits the given width/height/bpp
126: * constraints and set them into given arguments. With zeroed arguments,
127: * return largest video mode.
128: */
129: void Resolution_Search(int *width, int *height, int *bpp)
130: {
131: SDL_Rect **modes;
132: SDL_PixelFormat pixelformat;
133: Uint32 modeflags;
134:
135: /* Search in available modes the best suited */
1.1.1.2 root 136: Dprintf(("resolution: video mode asked: %dx%dx%d\n",
1.1 root 137: *width, *height, *bpp));
1.1.1.3 ! root 138:
1.1 root 139: modeflags = 0 /*SDL_HWSURFACE | SDL_HWPALETTE*/;
1.1.1.3 ! root 140:
1.1.1.2 root 141: if (bInFullScreen) {
142: /* resolution change not allowed? */
143: if (ConfigureParams.Screen.bKeepResolution) {
144: Resolution_GetDesktopSize(width, height);
145: return;
146: }
1.1 root 147: modeflags |= SDL_FULLSCREEN;
1.1.1.2 root 148: }
1.1.1.3 ! root 149: if (ConfigureParams.Screen.bForceMax) {
! 150: /* force given max size */
! 151: Resolution_GetMaxSize(width, height);
! 152: return;
! 153: }
! 154:
! 155: /* Read available video modes */
1.1 root 156:
157: /*--- Search a video mode with asked bpp ---*/
158: if (*bpp != 0) {
159: pixelformat.BitsPerPixel = *bpp;
160: modes = SDL_ListModes(&pixelformat, modeflags);
161: if ((modes != (SDL_Rect **) 0) && (modes != (SDL_Rect **) -1)) {
1.1.1.2 root 162: Dprintf(("resolution: searching a good video mode (given bpp)\n"));
1.1 root 163: if (Resolution_Select(modes, width, height)) {
1.1.1.2 root 164: Dprintf(("resolution: video mode selected: %dx%dx%d\n",
1.1 root 165: *width, *height, *bpp));
166: return;
167: }
168: }
169: }
170:
171: /*--- Search a video mode with any bpp ---*/
172: modes = SDL_ListModes(NULL, modeflags);
173: if ((modes != (SDL_Rect **) 0) && (modes != (SDL_Rect **) -1)) {
1.1.1.2 root 174: Dprintf(("resolution: searching a good video mode (any bpp)\n"));
1.1 root 175: if (Resolution_Select(modes, width, height)) {
1.1.1.2 root 176: Dprintf(("resolution: video mode selected: %dx%dx%d\n",
1.1 root 177: *width, *height, *bpp));
178: return;
179: }
180: }
181:
182: if (modes == (SDL_Rect **) 0) {
183: fprintf(stderr, "WARNING: No suitable video modes available!\n");
184: }
185:
186: if (modes == (SDL_Rect **) -1) {
187: /* Any mode available */
1.1.1.2 root 188: Dprintf(("resolution: All resolutions available.\n"));
1.1 root 189: }
190:
1.1.1.2 root 191: Dprintf(("resolution: video mode selected: %dx%dx%d\n",
1.1 root 192: *width, *height, *bpp));
193: }
194:
195:
196: /**
1.1.1.2 root 197: * Set given width & height arguments to maximum size allowed in the
198: * configuration, or if that's too large for the requested bit depth,
199: * to the largest available video mode size.
1.1 root 200: */
201: void Resolution_GetLimits(int *width, int *height, int *bpp)
202: {
203: *width = *height = 0;
204: /* constrain max size to what HW/SDL offers */
1.1.1.2 root 205: Dprintf(("resolution: request limits for: %dx%dx%d\n", *width, *height, *bpp));
1.1 root 206: Resolution_Search(width, height, bpp);
1.1.1.3 ! root 207:
1.1.1.2 root 208: if (bInFullScreen && ConfigureParams.Screen.bKeepResolution) {
209: /* resolution change not allowed */
210: Resolution_GetDesktopSize(width, height);
211: return;
212: }
1.1.1.3 ! root 213: if (ConfigureParams.Screen.bForceMax) {
! 214: /* force given max window size */
! 215: Resolution_GetMaxSize(width, height);
! 216: return;
! 217: }
! 218:
1.1.1.2 root 219: if (!(*width && *height) ||
1.1 root 220: (ConfigureParams.Screen.nMaxWidth < *width &&
221: ConfigureParams.Screen.nMaxHeight < *height)) {
1.1.1.2 root 222: Dprintf(("resolution: limit to user configured max\n"));
1.1 root 223: *width = ConfigureParams.Screen.nMaxWidth;
224: *height = ConfigureParams.Screen.nMaxHeight;
225: }
226: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.