UFO: Alien Invasion
Loading...
Searching...
No Matches
r_sdl.cpp
Go to the documentation of this file.
1
5
6/*
7Copyright (C) 1997-2001 Id Software, Inc.
8
9This program is free software; you can redistribute it and/or
10modify it under the terms of the GNU General Public License
11as published by the Free Software Foundation; either version 2
12of the License, or (at your option) any later version.
13
14This program is distributed in the hope that it will be useful,
15but WITHOUT ANY WARRANTY; without even the implied warranty of
16MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
17
18See the GNU General Public License for more details.
19
20You should have received a copy of the GNU General Public License
21along with this program; if not, write to the Free Software
22Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
23
24*/
25
26#include "r_local.h"
27#include "r_main.h"
28#include "r_sdl.h"
29#include "../../ports/system.h"
30#include "../client.h"
31
33
34static void R_SetSDLIcon (void)
35{
36#ifndef _WIN32
37#include "../../ports/linux/ufoicon.xbm"
38 SDL_Surface* icon = SDL_CreateRGBSurface(SDL_SWSURFACE, ufoicon_width, ufoicon_height, 8, 0, 0, 0, 0);
39 if (icon == nullptr)
40 return;
41 SDL_SetColorKey(icon, SDL_TRUE, 0);
42
43 Uint8 *ptr = (Uint8 *)icon->pixels;
44 for (unsigned int i = 0; i < sizeof(ufoicon_bits); i++) {
45 for (unsigned int mask = 1; mask != 0x100; mask <<= 1) {
46 *ptr = (ufoicon_bits[i] & mask) ? 1 : 0;
47 ptr++;
48 }
49 }
50
51 SDL_SetWindowIcon(cls.window, icon);
52 SDL_FreeSurface(icon);
53#endif
54}
55
56bool Rimp_Init (void)
57{
58 SDL_version version;
59 int attrValue;
60
61 Com_Printf("\n------- video initialization -------\n");
62
64
65 if (r_driver->string[0] != '\0') {
66 Com_Printf("I: using driver: %s\n", r_driver->string);
67 SDL_GL_LoadLibrary(r_driver->string);
68 }
69
70 Sys_Setenv("SDL_VIDEO_CENTERED", "1");
71 Sys_Setenv("SDL_VIDEO_ALLOW_SCREENSAVER", "0");
72
73 if (SDL_WasInit(SDL_INIT_VIDEO) == 0) {
74 if (SDL_Init(SDL_INIT_VIDEO) < 0)
75 Com_Error(ERR_FATAL, "Video SDL_Init failed: %s", SDL_GetError());
76 }
77
78 SDL_VERSION(&version)
79 Com_Printf("I: SDL version: %i.%i.%i\n", version.major, version.minor, version.patch);
80
81 r_sdl_config.desktopWidth = 1024;
82 r_sdl_config.desktopHeight = 768;
83
84 int selectedDisplay = 0; /* @todo Make selectedDisplay configurable */
85
86 const int displays = SDL_GetNumVideoDisplays();
87 Com_Printf("I: found %i display(s)\n", displays);
88
89 long posLeft = Cvar_GetValue("vid_left");
90 long posTop = Cvar_GetValue("vid_top");
91
92 for (int display = 0; display < displays; display++) {
93 if (SDL_GetDisplayName(display))
94 Com_Printf("I: display %i name: %s\n", display, SDL_GetDisplayName(display));
95
96 SDL_Rect displayBounds;
97 if (SDL_GetDisplayBounds(display, &displayBounds) == 0) {
98 Com_Printf("I: display %i bounds: x: %i, y: %i, w: %i, h: %i\n", display,
99 displayBounds.x, displayBounds.y, displayBounds.w, displayBounds.h);
100 if (posLeft >= displayBounds.x && posLeft < displayBounds.x + displayBounds.w
101 && posTop >= displayBounds.y && posTop < displayBounds.y + displayBounds.h)
102 selectedDisplay = display;
103 } else {
104 Com_Printf("W: failed to determine display %i bounds: %s\n", display, SDL_GetError());
105 }
106
107 SDL_DisplayMode displayMode;
108 if (SDL_GetDesktopDisplayMode(display, &displayMode) != -1) {
109 const char* name = SDL_GetPixelFormatName(displayMode.format);
110 Com_Printf("I: display %i current desktop mode: %dx%d@%dHz (%s)\n",
111 display, displayMode.w, displayMode.h, displayMode.refresh_rate, name);
112 if (display == selectedDisplay) {
113 r_sdl_config.desktopWidth = displayMode.w;
114 r_sdl_config.desktopHeight = displayMode.h;
115 }
116 } else {
117 Com_Printf("E: failed to get the desktop mode\n");
118 }
119 }
120
121 const int modes = SDL_GetNumDisplayModes(selectedDisplay);
122 if (modes > 0) {
123 r_sdl_config.modes = Mem_AllocTypeN(rect_t, modes);
124 for (int i = 0; i < modes; i++) {
125 SDL_DisplayMode displayMode;
126 SDL_GetDisplayMode(selectedDisplay, i, &displayMode);
127 r_sdl_config.modes[i][0] = displayMode.w;
128 r_sdl_config.modes[i][1] = displayMode.h;
129 }
130 }
131
132 const int videoDrivers = SDL_GetNumVideoDrivers();
133 for (int i = 0; i < videoDrivers; ++i) {
134 Com_Printf("I: available video driver: %s\n", SDL_GetVideoDriver(i));
135 }
136 Com_Printf("I: current video driver: %s\n", SDL_GetCurrentVideoDriver());
137
138 SDL_SetModState(KMOD_NONE);
139 SDL_StopTextInput();
140 if (r_sdl_config.numModes > 0) {
141 char buf[4096] = "";
142 Q_strcat(buf, sizeof(buf), "I: Available resolutions:");
143 for (int i = 0; i < r_sdl_config.numModes; i++) {
144 Q_strcat(buf, sizeof(buf), " %ix%i", r_sdl_config.modes[i][0], r_sdl_config.modes[i][1]);
145 }
146 Com_Printf("%s (%i)\n", buf, r_sdl_config.numModes);
147 }
148
149 if (!R_SetMode())
150 Com_Error(ERR_FATAL, "Video subsystem failed to initialize");
151
152 R_SetSDLIcon();
153
154 if (!SDL_GL_GetAttribute(SDL_GL_STENCIL_SIZE, &attrValue))
155 Com_Printf("I: got %d bits of stencil\n", attrValue);
156 if (!SDL_GL_GetAttribute(SDL_GL_DEPTH_SIZE, &attrValue))
157 Com_Printf("I: got %d bits of depth buffer\n", attrValue);
158 if (!SDL_GL_GetAttribute(SDL_GL_DOUBLEBUFFER, &attrValue))
159 Com_Printf("I: got double buffer\n");
160 if (!SDL_GL_GetAttribute(SDL_GL_RED_SIZE, &attrValue))
161 Com_Printf("I: got %d bits for red\n", attrValue);
162 if (!SDL_GL_GetAttribute(SDL_GL_GREEN_SIZE, &attrValue))
163 Com_Printf("I: got %d bits for green\n", attrValue);
164 if (!SDL_GL_GetAttribute(SDL_GL_BLUE_SIZE, &attrValue))
165 Com_Printf("I: got %d bits for blue\n", attrValue);
166 if (!SDL_GL_GetAttribute(SDL_GL_ALPHA_SIZE, &attrValue))
167 Com_Printf("I: got %d bits for alpha\n", attrValue);
168 if (!SDL_GL_GetAttribute(SDL_GL_MULTISAMPLESAMPLES, &attrValue))
169 Com_Printf("I: got multisample %s\n", attrValue != 0 ? "enabled" : "disabled");
170 if (!SDL_GL_GetAttribute(SDL_GL_MULTISAMPLEBUFFERS, &attrValue))
171 Com_Printf("I: got %d multisample buffers\n", attrValue);
172
173 return true;
174}
175
179bool R_InitGraphics (const viddefContext_t* context)
180{
181 SDL_GL_SetAttribute(SDL_GL_STENCIL_SIZE, 8);
182 SDL_GL_SetAttribute(SDL_GL_DEPTH_SIZE, 24);
183 SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER, 1);
184
185 if (context->multisample > 0) {
186 Com_Printf("I: set multisample buffers to %i\n", context->multisample);
187 SDL_GL_SetAttribute(SDL_GL_MULTISAMPLEBUFFERS, 1);
188 SDL_GL_SetAttribute(SDL_GL_MULTISAMPLESAMPLES, context->multisample);
189 } else {
190 Com_Printf("I: disable multisample buffers\n");
191 SDL_GL_SetAttribute(SDL_GL_MULTISAMPLEBUFFERS, 0);
192 SDL_GL_SetAttribute(SDL_GL_MULTISAMPLESAMPLES, 0);
193 }
194
195#ifdef GL_VERSION_ES_CM_1_0
196 /* Be sure to request GLES1 as we use GLES2 incompatible calls */
197 SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, SDL_GL_CONTEXT_PROFILE_ES);
198 SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, 1);
199#endif
200 /* valid values are between -1 and 1 */
201 const int i = std::min(1, std::max(-1, context->swapinterval));
202 Com_Printf("I: set swap control to %i\n", i);
203 SDL_GL_SetSwapInterval(i);
204 uint32_t flags = SDL_WINDOW_OPENGL | SDL_WINDOW_SHOWN;
205
206 if (context->fullscreen)
207 flags |= SDL_WINDOW_FULLSCREEN_DESKTOP;
208
209 cls.window = SDL_CreateWindow(
211 (context->left == VID_POS_UNSET) ? SDL_WINDOWPOS_CENTERED : context->left,
212 (context->top == VID_POS_UNSET) ? SDL_WINDOWPOS_CENTERED : context->top,
213 context->width,
214 context->height,
215 flags
216 );
217 if (!cls.window) {
218 const char* error = SDL_GetError();
219 Com_Printf("E: SDL_CreateWindow failed: %s\n", error);
220 SDL_ClearError();
221 return false;
222 }
223 cls.context = SDL_GL_CreateContext(cls.window);
224
225 SDL_ShowCursor(SDL_DISABLE);
226
227 return true;
228}
229
230void Rimp_Shutdown (void)
231{
232 SDL_DestroyWindow(cls.window);
233 SDL_GL_DeleteContext(cls.context);
234
235 /* SDL on Android does not support multiple video init/deinit yet, however calling SDL_SetVideoMode() multiple times works */
236#ifndef ANDROID
237 SDL_ShowCursor(SDL_ENABLE);
238
239 if (SDL_WasInit(SDL_INIT_EVERYTHING) == SDL_INIT_VIDEO)
240 SDL_Quit();
241 else
242 SDL_QuitSubSystem(SDL_INIT_VIDEO);
243#endif
244}
client_static_t cls
Definition cl_main.cpp:83
#define VID_POS_UNSET
Definition cl_video.h:37
Primary header for client.
void Com_Error(int code, const char *fmt,...)
Definition common.cpp:459
void Com_Printf(const char *const fmt,...)
Definition common.cpp:428
#define GAME_TITLE_LONG
Definition common.h:38
#define ERR_FATAL
Definition common.h:210
float Cvar_GetValue(const char *varName)
Returns the float value of a cvar.
Definition cvar.cpp:125
voidpf void * buf
Definition ioapi.h:42
#define Mem_AllocTypeN(type, n)
Definition mem.h:38
QGL_EXTERN GLint i
Definition r_gl.h:113
QGL_EXTERN GLuint GLsizei GLsizei GLint GLenum GLchar * name
Definition r_gl.h:110
local graphics definitions
cvar_t * r_driver
Definition r_main.cpp:86
bool R_SetMode(void)
Definition r_main.cpp:688
static void R_SetSDLIcon(void)
Definition r_sdl.cpp:34
#define ufoicon_height
void Rimp_Shutdown(void)
Definition r_sdl.cpp:230
bool R_InitGraphics(const viddefContext_t *context)
Init the SDL window.
Definition r_sdl.cpp:179
r_sdl_config_t r_sdl_config
Definition r_sdl.cpp:32
#define ufoicon_width
bool Rimp_Init(void)
Definition r_sdl.cpp:56
#define OBJZERO(obj)
Definition shared.h:178
void Q_strcat(char *dest, size_t destsize, const char *format,...)
Safely (without overflowing the destination buffer) concatenates two strings.
Definition shared.cpp:475
Contains the game screen context, everything that is needed to create the graphic context....
Definition cl_video.h:44
unsigned width
Definition cl_video.h:47
unsigned height
Definition cl_video.h:48
System specific stuff.
int Sys_Setenv(const char *name, const char *value)
set/unset environment variables (empty value removes it)