1 /*
2 Simple DirectMedia Layer
3 Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
4
5 This software is provided 'as-is', without any express or implied
6 warranty. In no event will the authors be held liable for any damages
7 arising from the use of this software.
8
9 Permission is granted to anyone to use this software for any purpose,
10 including commercial applications, and to alter it and redistribute it
11 freely, subject to the following restrictions:
12
13 1. The origin of this software must not be misrepresented; you must not
14 claim that you wrote the original software. If you use this software
15 in a product, an acknowledgment in the product documentation would be
16 appreciated but is not required.
17 2. Altered source versions must be plainly marked as such, and must not be
18 misrepresented as being the original software.
19 3. This notice may not be removed or altered from any source distribution.
20 */
21
22 /* Ported from original test\common.c file. */
23
24 #include "SDL_config.h"
25 #include "SDL_test.h"
26
27 #include <stdio.h>
28
29 #define VIDEO_USAGE \
30 "[--video driver] [--renderer driver] [--gldebug] [--info all|video|modes|render|event] [--log all|error|system|audio|video|render|input] [--display N] [--fullscreen | --fullscreen-desktop | --windows N] [--title title] [--icon icon.bmp] [--center | --position X,Y] [--geometry WxH] [--min-geometry WxH] [--max-geometry WxH] [--logical WxH] [--scale N] [--depth N] [--refresh R] [--vsync] [--noframe] [--resize] [--minimize] [--maximize] [--grab] [--allow-highdpi]"
31
32 #define AUDIO_USAGE \
33 "[--rate N] [--format U8|S8|U16|U16LE|U16BE|S16|S16LE|S16BE] [--channels N] [--samples N]"
34
35 SDLTest_CommonState *
SDLTest_CommonCreateState(char ** argv,Uint32 flags)36 SDLTest_CommonCreateState(char **argv, Uint32 flags)
37 {
38 SDLTest_CommonState *state = (SDLTest_CommonState *)SDL_calloc(1, sizeof(*state));
39 if (!state) {
40 SDL_OutOfMemory();
41 return NULL;
42 }
43
44 /* Initialize some defaults */
45 state->argv = argv;
46 state->flags = flags;
47 state->window_title = argv[0];
48 state->window_flags = 0;
49 state->window_x = SDL_WINDOWPOS_UNDEFINED;
50 state->window_y = SDL_WINDOWPOS_UNDEFINED;
51 state->window_w = DEFAULT_WINDOW_WIDTH;
52 state->window_h = DEFAULT_WINDOW_HEIGHT;
53 state->num_windows = 1;
54 state->audiospec.freq = 22050;
55 state->audiospec.format = AUDIO_S16;
56 state->audiospec.channels = 2;
57 state->audiospec.samples = 2048;
58
59 /* Set some very sane GL defaults */
60 state->gl_red_size = 3;
61 state->gl_green_size = 3;
62 state->gl_blue_size = 2;
63 state->gl_alpha_size = 0;
64 state->gl_buffer_size = 0;
65 state->gl_depth_size = 16;
66 state->gl_stencil_size = 0;
67 state->gl_double_buffer = 1;
68 state->gl_accum_red_size = 0;
69 state->gl_accum_green_size = 0;
70 state->gl_accum_blue_size = 0;
71 state->gl_accum_alpha_size = 0;
72 state->gl_stereo = 0;
73 state->gl_multisamplebuffers = 0;
74 state->gl_multisamplesamples = 0;
75 state->gl_retained_backing = 1;
76 state->gl_accelerated = -1;
77 state->gl_debug = 0;
78
79 return state;
80 }
81
82 int
SDLTest_CommonArg(SDLTest_CommonState * state,int index)83 SDLTest_CommonArg(SDLTest_CommonState * state, int index)
84 {
85 char **argv = state->argv;
86
87 if (SDL_strcasecmp(argv[index], "--video") == 0) {
88 ++index;
89 if (!argv[index]) {
90 return -1;
91 }
92 state->videodriver = argv[index];
93 return 2;
94 }
95 if (SDL_strcasecmp(argv[index], "--renderer") == 0) {
96 ++index;
97 if (!argv[index]) {
98 return -1;
99 }
100 state->renderdriver = argv[index];
101 return 2;
102 }
103 if (SDL_strcasecmp(argv[index], "--gldebug") == 0) {
104 state->gl_debug = 1;
105 return 1;
106 }
107 if (SDL_strcasecmp(argv[index], "--info") == 0) {
108 ++index;
109 if (!argv[index]) {
110 return -1;
111 }
112 if (SDL_strcasecmp(argv[index], "all") == 0) {
113 state->verbose |=
114 (VERBOSE_VIDEO | VERBOSE_MODES | VERBOSE_RENDER |
115 VERBOSE_EVENT);
116 return 2;
117 }
118 if (SDL_strcasecmp(argv[index], "video") == 0) {
119 state->verbose |= VERBOSE_VIDEO;
120 return 2;
121 }
122 if (SDL_strcasecmp(argv[index], "modes") == 0) {
123 state->verbose |= VERBOSE_MODES;
124 return 2;
125 }
126 if (SDL_strcasecmp(argv[index], "render") == 0) {
127 state->verbose |= VERBOSE_RENDER;
128 return 2;
129 }
130 if (SDL_strcasecmp(argv[index], "event") == 0) {
131 state->verbose |= VERBOSE_EVENT;
132 return 2;
133 }
134 return -1;
135 }
136 if (SDL_strcasecmp(argv[index], "--log") == 0) {
137 ++index;
138 if (!argv[index]) {
139 return -1;
140 }
141 if (SDL_strcasecmp(argv[index], "all") == 0) {
142 SDL_LogSetAllPriority(SDL_LOG_PRIORITY_VERBOSE);
143 return 2;
144 }
145 if (SDL_strcasecmp(argv[index], "error") == 0) {
146 SDL_LogSetPriority(SDL_LOG_CATEGORY_ERROR, SDL_LOG_PRIORITY_VERBOSE);
147 return 2;
148 }
149 if (SDL_strcasecmp(argv[index], "system") == 0) {
150 SDL_LogSetPriority(SDL_LOG_CATEGORY_SYSTEM, SDL_LOG_PRIORITY_VERBOSE);
151 return 2;
152 }
153 if (SDL_strcasecmp(argv[index], "audio") == 0) {
154 SDL_LogSetPriority(SDL_LOG_CATEGORY_AUDIO, SDL_LOG_PRIORITY_VERBOSE);
155 return 2;
156 }
157 if (SDL_strcasecmp(argv[index], "video") == 0) {
158 SDL_LogSetPriority(SDL_LOG_CATEGORY_VIDEO, SDL_LOG_PRIORITY_VERBOSE);
159 return 2;
160 }
161 if (SDL_strcasecmp(argv[index], "render") == 0) {
162 SDL_LogSetPriority(SDL_LOG_CATEGORY_RENDER, SDL_LOG_PRIORITY_VERBOSE);
163 return 2;
164 }
165 if (SDL_strcasecmp(argv[index], "input") == 0) {
166 SDL_LogSetPriority(SDL_LOG_CATEGORY_INPUT, SDL_LOG_PRIORITY_VERBOSE);
167 return 2;
168 }
169 return -1;
170 }
171 if (SDL_strcasecmp(argv[index], "--display") == 0) {
172 ++index;
173 if (!argv[index]) {
174 return -1;
175 }
176 state->display = SDL_atoi(argv[index]);
177 if (SDL_WINDOWPOS_ISUNDEFINED(state->window_x)) {
178 state->window_x = SDL_WINDOWPOS_UNDEFINED_DISPLAY(state->display);
179 state->window_y = SDL_WINDOWPOS_UNDEFINED_DISPLAY(state->display);
180 }
181 if (SDL_WINDOWPOS_ISCENTERED(state->window_x)) {
182 state->window_x = SDL_WINDOWPOS_CENTERED_DISPLAY(state->display);
183 state->window_y = SDL_WINDOWPOS_CENTERED_DISPLAY(state->display);
184 }
185 return 2;
186 }
187 if (SDL_strcasecmp(argv[index], "--fullscreen") == 0) {
188 state->window_flags |= SDL_WINDOW_FULLSCREEN;
189 state->num_windows = 1;
190 return 1;
191 }
192 if (SDL_strcasecmp(argv[index], "--fullscreen-desktop") == 0) {
193 state->window_flags |= SDL_WINDOW_FULLSCREEN_DESKTOP;
194 state->num_windows = 1;
195 return 1;
196 }
197 if (SDL_strcasecmp(argv[index], "--allow-highdpi") == 0) {
198 state->window_flags |= SDL_WINDOW_ALLOW_HIGHDPI;
199 return 1;
200 }
201 if (SDL_strcasecmp(argv[index], "--windows") == 0) {
202 ++index;
203 if (!argv[index] || !SDL_isdigit(*argv[index])) {
204 return -1;
205 }
206 if (!(state->window_flags & SDL_WINDOW_FULLSCREEN)) {
207 state->num_windows = SDL_atoi(argv[index]);
208 }
209 return 2;
210 }
211 if (SDL_strcasecmp(argv[index], "--title") == 0) {
212 ++index;
213 if (!argv[index]) {
214 return -1;
215 }
216 state->window_title = argv[index];
217 return 2;
218 }
219 if (SDL_strcasecmp(argv[index], "--icon") == 0) {
220 ++index;
221 if (!argv[index]) {
222 return -1;
223 }
224 state->window_icon = argv[index];
225 return 2;
226 }
227 if (SDL_strcasecmp(argv[index], "--center") == 0) {
228 state->window_x = SDL_WINDOWPOS_CENTERED;
229 state->window_y = SDL_WINDOWPOS_CENTERED;
230 return 1;
231 }
232 if (SDL_strcasecmp(argv[index], "--position") == 0) {
233 char *x, *y;
234 ++index;
235 if (!argv[index]) {
236 return -1;
237 }
238 x = argv[index];
239 y = argv[index];
240 while (*y && *y != ',') {
241 ++y;
242 }
243 if (!*y) {
244 return -1;
245 }
246 *y++ = '\0';
247 state->window_x = SDL_atoi(x);
248 state->window_y = SDL_atoi(y);
249 return 2;
250 }
251 if (SDL_strcasecmp(argv[index], "--geometry") == 0) {
252 char *w, *h;
253 ++index;
254 if (!argv[index]) {
255 return -1;
256 }
257 w = argv[index];
258 h = argv[index];
259 while (*h && *h != 'x') {
260 ++h;
261 }
262 if (!*h) {
263 return -1;
264 }
265 *h++ = '\0';
266 state->window_w = SDL_atoi(w);
267 state->window_h = SDL_atoi(h);
268 return 2;
269 }
270 if (SDL_strcasecmp(argv[index], "--min-geometry") == 0) {
271 char *w, *h;
272 ++index;
273 if (!argv[index]) {
274 return -1;
275 }
276 w = argv[index];
277 h = argv[index];
278 while (*h && *h != 'x') {
279 ++h;
280 }
281 if (!*h) {
282 return -1;
283 }
284 *h++ = '\0';
285 state->window_minW = SDL_atoi(w);
286 state->window_minH = SDL_atoi(h);
287 return 2;
288 }
289 if (SDL_strcasecmp(argv[index], "--max-geometry") == 0) {
290 char *w, *h;
291 ++index;
292 if (!argv[index]) {
293 return -1;
294 }
295 w = argv[index];
296 h = argv[index];
297 while (*h && *h != 'x') {
298 ++h;
299 }
300 if (!*h) {
301 return -1;
302 }
303 *h++ = '\0';
304 state->window_maxW = SDL_atoi(w);
305 state->window_maxH = SDL_atoi(h);
306 return 2;
307 }
308 if (SDL_strcasecmp(argv[index], "--logical") == 0) {
309 char *w, *h;
310 ++index;
311 if (!argv[index]) {
312 return -1;
313 }
314 w = argv[index];
315 h = argv[index];
316 while (*h && *h != 'x') {
317 ++h;
318 }
319 if (!*h) {
320 return -1;
321 }
322 *h++ = '\0';
323 state->logical_w = SDL_atoi(w);
324 state->logical_h = SDL_atoi(h);
325 return 2;
326 }
327 if (SDL_strcasecmp(argv[index], "--scale") == 0) {
328 ++index;
329 if (!argv[index]) {
330 return -1;
331 }
332 state->scale = (float)SDL_atof(argv[index]);
333 return 2;
334 }
335 if (SDL_strcasecmp(argv[index], "--depth") == 0) {
336 ++index;
337 if (!argv[index]) {
338 return -1;
339 }
340 state->depth = SDL_atoi(argv[index]);
341 return 2;
342 }
343 if (SDL_strcasecmp(argv[index], "--refresh") == 0) {
344 ++index;
345 if (!argv[index]) {
346 return -1;
347 }
348 state->refresh_rate = SDL_atoi(argv[index]);
349 return 2;
350 }
351 if (SDL_strcasecmp(argv[index], "--vsync") == 0) {
352 state->render_flags |= SDL_RENDERER_PRESENTVSYNC;
353 return 1;
354 }
355 if (SDL_strcasecmp(argv[index], "--noframe") == 0) {
356 state->window_flags |= SDL_WINDOW_BORDERLESS;
357 return 1;
358 }
359 if (SDL_strcasecmp(argv[index], "--resize") == 0) {
360 state->window_flags |= SDL_WINDOW_RESIZABLE;
361 return 1;
362 }
363 if (SDL_strcasecmp(argv[index], "--minimize") == 0) {
364 state->window_flags |= SDL_WINDOW_MINIMIZED;
365 return 1;
366 }
367 if (SDL_strcasecmp(argv[index], "--maximize") == 0) {
368 state->window_flags |= SDL_WINDOW_MAXIMIZED;
369 return 1;
370 }
371 if (SDL_strcasecmp(argv[index], "--grab") == 0) {
372 state->window_flags |= SDL_WINDOW_INPUT_GRABBED;
373 return 1;
374 }
375 if (SDL_strcasecmp(argv[index], "--rate") == 0) {
376 ++index;
377 if (!argv[index]) {
378 return -1;
379 }
380 state->audiospec.freq = SDL_atoi(argv[index]);
381 return 2;
382 }
383 if (SDL_strcasecmp(argv[index], "--format") == 0) {
384 ++index;
385 if (!argv[index]) {
386 return -1;
387 }
388 if (SDL_strcasecmp(argv[index], "U8") == 0) {
389 state->audiospec.format = AUDIO_U8;
390 return 2;
391 }
392 if (SDL_strcasecmp(argv[index], "S8") == 0) {
393 state->audiospec.format = AUDIO_S8;
394 return 2;
395 }
396 if (SDL_strcasecmp(argv[index], "U16") == 0) {
397 state->audiospec.format = AUDIO_U16;
398 return 2;
399 }
400 if (SDL_strcasecmp(argv[index], "U16LE") == 0) {
401 state->audiospec.format = AUDIO_U16LSB;
402 return 2;
403 }
404 if (SDL_strcasecmp(argv[index], "U16BE") == 0) {
405 state->audiospec.format = AUDIO_U16MSB;
406 return 2;
407 }
408 if (SDL_strcasecmp(argv[index], "S16") == 0) {
409 state->audiospec.format = AUDIO_S16;
410 return 2;
411 }
412 if (SDL_strcasecmp(argv[index], "S16LE") == 0) {
413 state->audiospec.format = AUDIO_S16LSB;
414 return 2;
415 }
416 if (SDL_strcasecmp(argv[index], "S16BE") == 0) {
417 state->audiospec.format = AUDIO_S16MSB;
418 return 2;
419 }
420 return -1;
421 }
422 if (SDL_strcasecmp(argv[index], "--channels") == 0) {
423 ++index;
424 if (!argv[index]) {
425 return -1;
426 }
427 state->audiospec.channels = (Uint8) SDL_atoi(argv[index]);
428 return 2;
429 }
430 if (SDL_strcasecmp(argv[index], "--samples") == 0) {
431 ++index;
432 if (!argv[index]) {
433 return -1;
434 }
435 state->audiospec.samples = (Uint16) SDL_atoi(argv[index]);
436 return 2;
437 }
438 if ((SDL_strcasecmp(argv[index], "-h") == 0)
439 || (SDL_strcasecmp(argv[index], "--help") == 0)) {
440 /* Print the usage message */
441 return -1;
442 }
443 if (SDL_strcmp(argv[index], "-NSDocumentRevisionsDebugMode") == 0) {
444 /* Debug flag sent by Xcode */
445 return 2;
446 }
447 return 0;
448 }
449
450 const char *
SDLTest_CommonUsage(SDLTest_CommonState * state)451 SDLTest_CommonUsage(SDLTest_CommonState * state)
452 {
453 switch (state->flags & (SDL_INIT_VIDEO | SDL_INIT_AUDIO)) {
454 case SDL_INIT_VIDEO:
455 return VIDEO_USAGE;
456 case SDL_INIT_AUDIO:
457 return AUDIO_USAGE;
458 case (SDL_INIT_VIDEO | SDL_INIT_AUDIO):
459 return VIDEO_USAGE " " AUDIO_USAGE;
460 default:
461 return "";
462 }
463 }
464
465 static void
SDLTest_PrintRendererFlag(Uint32 flag)466 SDLTest_PrintRendererFlag(Uint32 flag)
467 {
468 switch (flag) {
469 case SDL_RENDERER_PRESENTVSYNC:
470 fprintf(stderr, "PresentVSync");
471 break;
472 case SDL_RENDERER_ACCELERATED:
473 fprintf(stderr, "Accelerated");
474 break;
475 default:
476 fprintf(stderr, "0x%8.8x", flag);
477 break;
478 }
479 }
480
481 static void
SDLTest_PrintPixelFormat(Uint32 format)482 SDLTest_PrintPixelFormat(Uint32 format)
483 {
484 switch (format) {
485 case SDL_PIXELFORMAT_UNKNOWN:
486 fprintf(stderr, "Unknwon");
487 break;
488 case SDL_PIXELFORMAT_INDEX1LSB:
489 fprintf(stderr, "Index1LSB");
490 break;
491 case SDL_PIXELFORMAT_INDEX1MSB:
492 fprintf(stderr, "Index1MSB");
493 break;
494 case SDL_PIXELFORMAT_INDEX4LSB:
495 fprintf(stderr, "Index4LSB");
496 break;
497 case SDL_PIXELFORMAT_INDEX4MSB:
498 fprintf(stderr, "Index4MSB");
499 break;
500 case SDL_PIXELFORMAT_INDEX8:
501 fprintf(stderr, "Index8");
502 break;
503 case SDL_PIXELFORMAT_RGB332:
504 fprintf(stderr, "RGB332");
505 break;
506 case SDL_PIXELFORMAT_RGB444:
507 fprintf(stderr, "RGB444");
508 break;
509 case SDL_PIXELFORMAT_RGB555:
510 fprintf(stderr, "RGB555");
511 break;
512 case SDL_PIXELFORMAT_BGR555:
513 fprintf(stderr, "BGR555");
514 break;
515 case SDL_PIXELFORMAT_ARGB4444:
516 fprintf(stderr, "ARGB4444");
517 break;
518 case SDL_PIXELFORMAT_ABGR4444:
519 fprintf(stderr, "ABGR4444");
520 break;
521 case SDL_PIXELFORMAT_ARGB1555:
522 fprintf(stderr, "ARGB1555");
523 break;
524 case SDL_PIXELFORMAT_ABGR1555:
525 fprintf(stderr, "ABGR1555");
526 break;
527 case SDL_PIXELFORMAT_RGB565:
528 fprintf(stderr, "RGB565");
529 break;
530 case SDL_PIXELFORMAT_BGR565:
531 fprintf(stderr, "BGR565");
532 break;
533 case SDL_PIXELFORMAT_RGB24:
534 fprintf(stderr, "RGB24");
535 break;
536 case SDL_PIXELFORMAT_BGR24:
537 fprintf(stderr, "BGR24");
538 break;
539 case SDL_PIXELFORMAT_RGB888:
540 fprintf(stderr, "RGB888");
541 break;
542 case SDL_PIXELFORMAT_BGR888:
543 fprintf(stderr, "BGR888");
544 break;
545 case SDL_PIXELFORMAT_ARGB8888:
546 fprintf(stderr, "ARGB8888");
547 break;
548 case SDL_PIXELFORMAT_RGBA8888:
549 fprintf(stderr, "RGBA8888");
550 break;
551 case SDL_PIXELFORMAT_ABGR8888:
552 fprintf(stderr, "ABGR8888");
553 break;
554 case SDL_PIXELFORMAT_BGRA8888:
555 fprintf(stderr, "BGRA8888");
556 break;
557 case SDL_PIXELFORMAT_ARGB2101010:
558 fprintf(stderr, "ARGB2101010");
559 break;
560 case SDL_PIXELFORMAT_YV12:
561 fprintf(stderr, "YV12");
562 break;
563 case SDL_PIXELFORMAT_IYUV:
564 fprintf(stderr, "IYUV");
565 break;
566 case SDL_PIXELFORMAT_YUY2:
567 fprintf(stderr, "YUY2");
568 break;
569 case SDL_PIXELFORMAT_UYVY:
570 fprintf(stderr, "UYVY");
571 break;
572 case SDL_PIXELFORMAT_YVYU:
573 fprintf(stderr, "YVYU");
574 break;
575 case SDL_PIXELFORMAT_NV12:
576 fprintf(stderr, "NV12");
577 break;
578 case SDL_PIXELFORMAT_NV21:
579 fprintf(stderr, "NV21");
580 break;
581 default:
582 fprintf(stderr, "0x%8.8x", format);
583 break;
584 }
585 }
586
587 static void
SDLTest_PrintRenderer(SDL_RendererInfo * info)588 SDLTest_PrintRenderer(SDL_RendererInfo * info)
589 {
590 int i, count;
591
592 fprintf(stderr, " Renderer %s:\n", info->name);
593
594 fprintf(stderr, " Flags: 0x%8.8X", info->flags);
595 fprintf(stderr, " (");
596 count = 0;
597 for (i = 0; i < sizeof(info->flags) * 8; ++i) {
598 Uint32 flag = (1 << i);
599 if (info->flags & flag) {
600 if (count > 0) {
601 fprintf(stderr, " | ");
602 }
603 SDLTest_PrintRendererFlag(flag);
604 ++count;
605 }
606 }
607 fprintf(stderr, ")\n");
608
609 fprintf(stderr, " Texture formats (%d): ", info->num_texture_formats);
610 for (i = 0; i < (int) info->num_texture_formats; ++i) {
611 if (i > 0) {
612 fprintf(stderr, ", ");
613 }
614 SDLTest_PrintPixelFormat(info->texture_formats[i]);
615 }
616 fprintf(stderr, "\n");
617
618 if (info->max_texture_width || info->max_texture_height) {
619 fprintf(stderr, " Max Texture Size: %dx%d\n",
620 info->max_texture_width, info->max_texture_height);
621 }
622 }
623
624 static SDL_Surface *
SDLTest_LoadIcon(const char * file)625 SDLTest_LoadIcon(const char *file)
626 {
627 SDL_Surface *icon;
628
629 /* Load the icon surface */
630 icon = SDL_LoadBMP(file);
631 if (icon == NULL) {
632 fprintf(stderr, "Couldn't load %s: %s\n", file, SDL_GetError());
633 return (NULL);
634 }
635
636 if (icon->format->palette) {
637 /* Set the colorkey */
638 SDL_SetColorKey(icon, 1, *((Uint8 *) icon->pixels));
639 }
640
641 return (icon);
642 }
643
644 SDL_bool
SDLTest_CommonInit(SDLTest_CommonState * state)645 SDLTest_CommonInit(SDLTest_CommonState * state)
646 {
647 int i, j, m, n, w, h;
648 SDL_DisplayMode fullscreen_mode;
649
650 if (state->flags & SDL_INIT_VIDEO) {
651 if (state->verbose & VERBOSE_VIDEO) {
652 n = SDL_GetNumVideoDrivers();
653 if (n == 0) {
654 fprintf(stderr, "No built-in video drivers\n");
655 } else {
656 fprintf(stderr, "Built-in video drivers:");
657 for (i = 0; i < n; ++i) {
658 if (i > 0) {
659 fprintf(stderr, ",");
660 }
661 fprintf(stderr, " %s", SDL_GetVideoDriver(i));
662 }
663 fprintf(stderr, "\n");
664 }
665 }
666 if (SDL_VideoInit(state->videodriver) < 0) {
667 fprintf(stderr, "Couldn't initialize video driver: %s\n",
668 SDL_GetError());
669 return SDL_FALSE;
670 }
671 if (state->verbose & VERBOSE_VIDEO) {
672 fprintf(stderr, "Video driver: %s\n",
673 SDL_GetCurrentVideoDriver());
674 }
675
676 /* Upload GL settings */
677 SDL_GL_SetAttribute(SDL_GL_RED_SIZE, state->gl_red_size);
678 SDL_GL_SetAttribute(SDL_GL_GREEN_SIZE, state->gl_green_size);
679 SDL_GL_SetAttribute(SDL_GL_BLUE_SIZE, state->gl_blue_size);
680 SDL_GL_SetAttribute(SDL_GL_ALPHA_SIZE, state->gl_alpha_size);
681 SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER, state->gl_double_buffer);
682 SDL_GL_SetAttribute(SDL_GL_BUFFER_SIZE, state->gl_buffer_size);
683 SDL_GL_SetAttribute(SDL_GL_DEPTH_SIZE, state->gl_depth_size);
684 SDL_GL_SetAttribute(SDL_GL_STENCIL_SIZE, state->gl_stencil_size);
685 SDL_GL_SetAttribute(SDL_GL_ACCUM_RED_SIZE, state->gl_accum_red_size);
686 SDL_GL_SetAttribute(SDL_GL_ACCUM_GREEN_SIZE, state->gl_accum_green_size);
687 SDL_GL_SetAttribute(SDL_GL_ACCUM_BLUE_SIZE, state->gl_accum_blue_size);
688 SDL_GL_SetAttribute(SDL_GL_ACCUM_ALPHA_SIZE, state->gl_accum_alpha_size);
689 SDL_GL_SetAttribute(SDL_GL_STEREO, state->gl_stereo);
690 SDL_GL_SetAttribute(SDL_GL_MULTISAMPLEBUFFERS, state->gl_multisamplebuffers);
691 SDL_GL_SetAttribute(SDL_GL_MULTISAMPLESAMPLES, state->gl_multisamplesamples);
692 if (state->gl_accelerated >= 0) {
693 SDL_GL_SetAttribute(SDL_GL_ACCELERATED_VISUAL,
694 state->gl_accelerated);
695 }
696 SDL_GL_SetAttribute(SDL_GL_RETAINED_BACKING, state->gl_retained_backing);
697 if (state->gl_major_version) {
698 SDL_GL_SetAttribute(SDL_GL_CONTEXT_MAJOR_VERSION, state->gl_major_version);
699 SDL_GL_SetAttribute(SDL_GL_CONTEXT_MINOR_VERSION, state->gl_minor_version);
700 }
701 if (state->gl_debug) {
702 SDL_GL_SetAttribute(SDL_GL_CONTEXT_FLAGS, SDL_GL_CONTEXT_DEBUG_FLAG);
703 }
704 if (state->gl_profile_mask) {
705 SDL_GL_SetAttribute(SDL_GL_CONTEXT_PROFILE_MASK, state->gl_profile_mask);
706 }
707
708 if (state->verbose & VERBOSE_MODES) {
709 SDL_Rect bounds;
710 SDL_DisplayMode mode;
711 int bpp;
712 Uint32 Rmask, Gmask, Bmask, Amask;
713 #if SDL_VIDEO_DRIVER_WINDOWS
714 int adapterIndex = 0;
715 int outputIndex = 0;
716 #endif
717 n = SDL_GetNumVideoDisplays();
718 fprintf(stderr, "Number of displays: %d\n", n);
719 for (i = 0; i < n; ++i) {
720 fprintf(stderr, "Display %d: %s\n", i, SDL_GetDisplayName(i));
721
722 SDL_zero(bounds);
723 SDL_GetDisplayBounds(i, &bounds);
724 fprintf(stderr, "Bounds: %dx%d at %d,%d\n", bounds.w, bounds.h, bounds.x, bounds.y);
725
726 SDL_GetDesktopDisplayMode(i, &mode);
727 SDL_PixelFormatEnumToMasks(mode.format, &bpp, &Rmask, &Gmask,
728 &Bmask, &Amask);
729 fprintf(stderr,
730 " Current mode: %dx%d@%dHz, %d bits-per-pixel (%s)\n",
731 mode.w, mode.h, mode.refresh_rate, bpp,
732 SDL_GetPixelFormatName(mode.format));
733 if (Rmask || Gmask || Bmask) {
734 fprintf(stderr, " Red Mask = 0x%.8x\n", Rmask);
735 fprintf(stderr, " Green Mask = 0x%.8x\n", Gmask);
736 fprintf(stderr, " Blue Mask = 0x%.8x\n", Bmask);
737 if (Amask)
738 fprintf(stderr, " Alpha Mask = 0x%.8x\n", Amask);
739 }
740
741 /* Print available fullscreen video modes */
742 m = SDL_GetNumDisplayModes(i);
743 if (m == 0) {
744 fprintf(stderr, "No available fullscreen video modes\n");
745 } else {
746 fprintf(stderr, " Fullscreen video modes:\n");
747 for (j = 0; j < m; ++j) {
748 SDL_GetDisplayMode(i, j, &mode);
749 SDL_PixelFormatEnumToMasks(mode.format, &bpp, &Rmask,
750 &Gmask, &Bmask, &Amask);
751 fprintf(stderr,
752 " Mode %d: %dx%d@%dHz, %d bits-per-pixel (%s)\n",
753 j, mode.w, mode.h, mode.refresh_rate, bpp,
754 SDL_GetPixelFormatName(mode.format));
755 if (Rmask || Gmask || Bmask) {
756 fprintf(stderr, " Red Mask = 0x%.8x\n",
757 Rmask);
758 fprintf(stderr, " Green Mask = 0x%.8x\n",
759 Gmask);
760 fprintf(stderr, " Blue Mask = 0x%.8x\n",
761 Bmask);
762 if (Amask)
763 fprintf(stderr,
764 " Alpha Mask = 0x%.8x\n",
765 Amask);
766 }
767 }
768 }
769
770 #if SDL_VIDEO_DRIVER_WINDOWS
771 /* Print the D3D9 adapter index */
772 adapterIndex = SDL_Direct3D9GetAdapterIndex( i );
773 fprintf( stderr, "D3D9 Adapter Index: %d", adapterIndex );
774
775 /* Print the DXGI adapter and output indices */
776 SDL_DXGIGetOutputInfo(i, &adapterIndex, &outputIndex);
777 fprintf( stderr, "DXGI Adapter Index: %d Output Index: %d", adapterIndex, outputIndex );
778 #endif
779 }
780 }
781
782 if (state->verbose & VERBOSE_RENDER) {
783 SDL_RendererInfo info;
784
785 n = SDL_GetNumRenderDrivers();
786 if (n == 0) {
787 fprintf(stderr, "No built-in render drivers\n");
788 } else {
789 fprintf(stderr, "Built-in render drivers:\n");
790 for (i = 0; i < n; ++i) {
791 SDL_GetRenderDriverInfo(i, &info);
792 SDLTest_PrintRenderer(&info);
793 }
794 }
795 }
796
797 SDL_zero(fullscreen_mode);
798 switch (state->depth) {
799 case 8:
800 fullscreen_mode.format = SDL_PIXELFORMAT_INDEX8;
801 break;
802 case 15:
803 fullscreen_mode.format = SDL_PIXELFORMAT_RGB555;
804 break;
805 case 16:
806 fullscreen_mode.format = SDL_PIXELFORMAT_RGB565;
807 break;
808 case 24:
809 fullscreen_mode.format = SDL_PIXELFORMAT_RGB24;
810 break;
811 default:
812 fullscreen_mode.format = SDL_PIXELFORMAT_RGB888;
813 break;
814 }
815 fullscreen_mode.refresh_rate = state->refresh_rate;
816
817 state->windows =
818 (SDL_Window **) SDL_malloc(state->num_windows *
819 sizeof(*state->windows));
820 state->renderers =
821 (SDL_Renderer **) SDL_malloc(state->num_windows *
822 sizeof(*state->renderers));
823 state->targets =
824 (SDL_Texture **) SDL_malloc(state->num_windows *
825 sizeof(*state->targets));
826 if (!state->windows || !state->renderers) {
827 fprintf(stderr, "Out of memory!\n");
828 return SDL_FALSE;
829 }
830 for (i = 0; i < state->num_windows; ++i) {
831 char title[1024];
832
833 if (state->num_windows > 1) {
834 SDL_snprintf(title, SDL_arraysize(title), "%s %d",
835 state->window_title, i + 1);
836 } else {
837 SDL_strlcpy(title, state->window_title, SDL_arraysize(title));
838 }
839 state->windows[i] =
840 SDL_CreateWindow(title, state->window_x, state->window_y,
841 state->window_w, state->window_h,
842 state->window_flags);
843 if (!state->windows[i]) {
844 fprintf(stderr, "Couldn't create window: %s\n",
845 SDL_GetError());
846 return SDL_FALSE;
847 }
848 if (state->window_minW || state->window_minH) {
849 SDL_SetWindowMinimumSize(state->windows[i], state->window_minW, state->window_minH);
850 }
851 if (state->window_maxW || state->window_maxH) {
852 SDL_SetWindowMaximumSize(state->windows[i], state->window_maxW, state->window_maxH);
853 }
854 SDL_GetWindowSize(state->windows[i], &w, &h);
855 if (!(state->window_flags & SDL_WINDOW_RESIZABLE) &&
856 (w != state->window_w || h != state->window_h)) {
857 printf("Window requested size %dx%d, got %dx%d\n", state->window_w, state->window_h, w, h);
858 state->window_w = w;
859 state->window_h = h;
860 }
861 if (SDL_SetWindowDisplayMode(state->windows[i], &fullscreen_mode) < 0) {
862 fprintf(stderr, "Can't set up fullscreen display mode: %s\n",
863 SDL_GetError());
864 return SDL_FALSE;
865 }
866
867 if (state->window_icon) {
868 SDL_Surface *icon = SDLTest_LoadIcon(state->window_icon);
869 if (icon) {
870 SDL_SetWindowIcon(state->windows[i], icon);
871 SDL_FreeSurface(icon);
872 }
873 }
874
875 SDL_ShowWindow(state->windows[i]);
876
877 state->renderers[i] = NULL;
878 state->targets[i] = NULL;
879
880 if (!state->skip_renderer
881 && (state->renderdriver
882 || !(state->window_flags & SDL_WINDOW_OPENGL))) {
883 m = -1;
884 if (state->renderdriver) {
885 SDL_RendererInfo info;
886 n = SDL_GetNumRenderDrivers();
887 for (j = 0; j < n; ++j) {
888 SDL_GetRenderDriverInfo(j, &info);
889 if (SDL_strcasecmp(info.name, state->renderdriver) ==
890 0) {
891 m = j;
892 break;
893 }
894 }
895 if (m == -1) {
896 fprintf(stderr,
897 "Couldn't find render driver named %s",
898 state->renderdriver);
899 return SDL_FALSE;
900 }
901 }
902 state->renderers[i] = SDL_CreateRenderer(state->windows[i],
903 m, state->render_flags);
904 if (!state->renderers[i]) {
905 fprintf(stderr, "Couldn't create renderer: %s\n",
906 SDL_GetError());
907 return SDL_FALSE;
908 }
909 if (state->logical_w && state->logical_h) {
910 SDL_RenderSetLogicalSize(state->renderers[i], state->logical_w, state->logical_h);
911 } else if (state->scale) {
912 SDL_RenderSetScale(state->renderers[i], state->scale, state->scale);
913 }
914 if (state->verbose & VERBOSE_RENDER) {
915 SDL_RendererInfo info;
916
917 fprintf(stderr, "Current renderer:\n");
918 SDL_GetRendererInfo(state->renderers[i], &info);
919 SDLTest_PrintRenderer(&info);
920 }
921 }
922 }
923 }
924
925 if (state->flags & SDL_INIT_AUDIO) {
926 if (state->verbose & VERBOSE_AUDIO) {
927 n = SDL_GetNumAudioDrivers();
928 if (n == 0) {
929 fprintf(stderr, "No built-in audio drivers\n");
930 } else {
931 fprintf(stderr, "Built-in audio drivers:");
932 for (i = 0; i < n; ++i) {
933 if (i > 0) {
934 fprintf(stderr, ",");
935 }
936 fprintf(stderr, " %s", SDL_GetAudioDriver(i));
937 }
938 fprintf(stderr, "\n");
939 }
940 }
941 if (SDL_AudioInit(state->audiodriver) < 0) {
942 fprintf(stderr, "Couldn't initialize audio driver: %s\n",
943 SDL_GetError());
944 return SDL_FALSE;
945 }
946 if (state->verbose & VERBOSE_VIDEO) {
947 fprintf(stderr, "Audio driver: %s\n",
948 SDL_GetCurrentAudioDriver());
949 }
950
951 if (SDL_OpenAudio(&state->audiospec, NULL) < 0) {
952 fprintf(stderr, "Couldn't open audio: %s\n", SDL_GetError());
953 return SDL_FALSE;
954 }
955 }
956
957 return SDL_TRUE;
958 }
959
960 static const char *
ControllerAxisName(const SDL_GameControllerAxis axis)961 ControllerAxisName(const SDL_GameControllerAxis axis)
962 {
963 switch (axis)
964 {
965 #define AXIS_CASE(ax) case SDL_CONTROLLER_AXIS_##ax: return #ax
966 AXIS_CASE(INVALID);
967 AXIS_CASE(LEFTX);
968 AXIS_CASE(LEFTY);
969 AXIS_CASE(RIGHTX);
970 AXIS_CASE(RIGHTY);
971 AXIS_CASE(TRIGGERLEFT);
972 AXIS_CASE(TRIGGERRIGHT);
973 #undef AXIS_CASE
974 default: return "???";
975 }
976 }
977
978 static const char *
ControllerButtonName(const SDL_GameControllerButton button)979 ControllerButtonName(const SDL_GameControllerButton button)
980 {
981 switch (button)
982 {
983 #define BUTTON_CASE(btn) case SDL_CONTROLLER_BUTTON_##btn: return #btn
984 BUTTON_CASE(INVALID);
985 BUTTON_CASE(A);
986 BUTTON_CASE(B);
987 BUTTON_CASE(X);
988 BUTTON_CASE(Y);
989 BUTTON_CASE(BACK);
990 BUTTON_CASE(GUIDE);
991 BUTTON_CASE(START);
992 BUTTON_CASE(LEFTSTICK);
993 BUTTON_CASE(RIGHTSTICK);
994 BUTTON_CASE(LEFTSHOULDER);
995 BUTTON_CASE(RIGHTSHOULDER);
996 BUTTON_CASE(DPAD_UP);
997 BUTTON_CASE(DPAD_DOWN);
998 BUTTON_CASE(DPAD_LEFT);
999 BUTTON_CASE(DPAD_RIGHT);
1000 #undef BUTTON_CASE
1001 default: return "???";
1002 }
1003 }
1004
1005 static void
SDLTest_PrintEvent(SDL_Event * event)1006 SDLTest_PrintEvent(SDL_Event * event)
1007 {
1008 if ((event->type == SDL_MOUSEMOTION) || (event->type == SDL_FINGERMOTION)) {
1009 /* Mouse and finger motion are really spammy */
1010 return;
1011 }
1012
1013 switch (event->type) {
1014 case SDL_WINDOWEVENT:
1015 switch (event->window.event) {
1016 case SDL_WINDOWEVENT_SHOWN:
1017 SDL_Log("SDL EVENT: Window %d shown", event->window.windowID);
1018 break;
1019 case SDL_WINDOWEVENT_HIDDEN:
1020 SDL_Log("SDL EVENT: Window %d hidden", event->window.windowID);
1021 break;
1022 case SDL_WINDOWEVENT_EXPOSED:
1023 SDL_Log("SDL EVENT: Window %d exposed", event->window.windowID);
1024 break;
1025 case SDL_WINDOWEVENT_MOVED:
1026 SDL_Log("SDL EVENT: Window %d moved to %d,%d",
1027 event->window.windowID, event->window.data1,
1028 event->window.data2);
1029 break;
1030 case SDL_WINDOWEVENT_RESIZED:
1031 SDL_Log("SDL EVENT: Window %d resized to %dx%d",
1032 event->window.windowID, event->window.data1,
1033 event->window.data2);
1034 break;
1035 case SDL_WINDOWEVENT_SIZE_CHANGED:
1036 SDL_Log("SDL EVENT: Window %d changed size to %dx%d",
1037 event->window.windowID, event->window.data1,
1038 event->window.data2);
1039 break;
1040 case SDL_WINDOWEVENT_MINIMIZED:
1041 SDL_Log("SDL EVENT: Window %d minimized", event->window.windowID);
1042 break;
1043 case SDL_WINDOWEVENT_MAXIMIZED:
1044 SDL_Log("SDL EVENT: Window %d maximized", event->window.windowID);
1045 break;
1046 case SDL_WINDOWEVENT_RESTORED:
1047 SDL_Log("SDL EVENT: Window %d restored", event->window.windowID);
1048 break;
1049 case SDL_WINDOWEVENT_ENTER:
1050 SDL_Log("SDL EVENT: Mouse entered window %d",
1051 event->window.windowID);
1052 break;
1053 case SDL_WINDOWEVENT_LEAVE:
1054 SDL_Log("SDL EVENT: Mouse left window %d", event->window.windowID);
1055 break;
1056 case SDL_WINDOWEVENT_FOCUS_GAINED:
1057 SDL_Log("SDL EVENT: Window %d gained keyboard focus",
1058 event->window.windowID);
1059 break;
1060 case SDL_WINDOWEVENT_FOCUS_LOST:
1061 SDL_Log("SDL EVENT: Window %d lost keyboard focus",
1062 event->window.windowID);
1063 break;
1064 case SDL_WINDOWEVENT_CLOSE:
1065 SDL_Log("SDL EVENT: Window %d closed", event->window.windowID);
1066 break;
1067 case SDL_WINDOWEVENT_TAKE_FOCUS:
1068 SDL_Log("SDL EVENT: Window %d take focus", event->window.windowID);
1069 break;
1070 case SDL_WINDOWEVENT_HIT_TEST:
1071 SDL_Log("SDL EVENT: Window %d hit test", event->window.windowID);
1072 break;
1073 default:
1074 SDL_Log("SDL EVENT: Window %d got unknown event %d",
1075 event->window.windowID, event->window.event);
1076 break;
1077 }
1078 break;
1079 case SDL_KEYDOWN:
1080 SDL_Log("SDL EVENT: Keyboard: key pressed in window %d: scancode 0x%08X = %s, keycode 0x%08X = %s",
1081 event->key.windowID,
1082 event->key.keysym.scancode,
1083 SDL_GetScancodeName(event->key.keysym.scancode),
1084 event->key.keysym.sym, SDL_GetKeyName(event->key.keysym.sym));
1085 break;
1086 case SDL_KEYUP:
1087 SDL_Log("SDL EVENT: Keyboard: key released in window %d: scancode 0x%08X = %s, keycode 0x%08X = %s",
1088 event->key.windowID,
1089 event->key.keysym.scancode,
1090 SDL_GetScancodeName(event->key.keysym.scancode),
1091 event->key.keysym.sym, SDL_GetKeyName(event->key.keysym.sym));
1092 break;
1093 case SDL_TEXTINPUT:
1094 SDL_Log("SDL EVENT: Keyboard: text input \"%s\" in window %d",
1095 event->text.text, event->text.windowID);
1096 break;
1097 case SDL_MOUSEMOTION:
1098 SDL_Log("SDL EVENT: Mouse: moved to %d,%d (%d,%d) in window %d",
1099 event->motion.x, event->motion.y,
1100 event->motion.xrel, event->motion.yrel,
1101 event->motion.windowID);
1102 break;
1103 case SDL_MOUSEBUTTONDOWN:
1104 SDL_Log("SDL EVENT: Mouse: button %d pressed at %d,%d with click count %d in window %d",
1105 event->button.button, event->button.x, event->button.y, event->button.clicks,
1106 event->button.windowID);
1107 break;
1108 case SDL_MOUSEBUTTONUP:
1109 SDL_Log("SDL EVENT: Mouse: button %d released at %d,%d with click count %d in window %d",
1110 event->button.button, event->button.x, event->button.y, event->button.clicks,
1111 event->button.windowID);
1112 break;
1113 case SDL_MOUSEWHEEL:
1114 SDL_Log("SDL EVENT: Mouse: wheel scrolled %d in x and %d in y (reversed: %d) in window %d",
1115 event->wheel.x, event->wheel.y, event->wheel.direction, event->wheel.windowID);
1116 break;
1117 case SDL_JOYDEVICEADDED:
1118 SDL_Log("SDL EVENT: Joystick index %d attached",
1119 event->jdevice.which);
1120 break;
1121 case SDL_JOYDEVICEREMOVED:
1122 SDL_Log("SDL EVENT: Joystick %d removed",
1123 event->jdevice.which);
1124 break;
1125 case SDL_JOYBALLMOTION:
1126 SDL_Log("SDL EVENT: Joystick %d: ball %d moved by %d,%d",
1127 event->jball.which, event->jball.ball, event->jball.xrel,
1128 event->jball.yrel);
1129 break;
1130 case SDL_JOYHATMOTION:
1131 {
1132 const char *position = "UNKNOWN";
1133 switch (event->jhat.value) {
1134 case SDL_HAT_CENTERED:
1135 position = "CENTER";
1136 break;
1137 case SDL_HAT_UP:
1138 position = "UP";
1139 break;
1140 case SDL_HAT_RIGHTUP:
1141 position = "RIGHTUP";
1142 break;
1143 case SDL_HAT_RIGHT:
1144 position = "RIGHT";
1145 break;
1146 case SDL_HAT_RIGHTDOWN:
1147 position = "RIGHTDOWN";
1148 break;
1149 case SDL_HAT_DOWN:
1150 position = "DOWN";
1151 break;
1152 case SDL_HAT_LEFTDOWN:
1153 position = "LEFTDOWN";
1154 break;
1155 case SDL_HAT_LEFT:
1156 position = "LEFT";
1157 break;
1158 case SDL_HAT_LEFTUP:
1159 position = "LEFTUP";
1160 break;
1161 }
1162 SDL_Log("SDL EVENT: Joystick %d: hat %d moved to %s", event->jhat.which,
1163 event->jhat.hat, position);
1164 }
1165 break;
1166 case SDL_JOYBUTTONDOWN:
1167 SDL_Log("SDL EVENT: Joystick %d: button %d pressed",
1168 event->jbutton.which, event->jbutton.button);
1169 break;
1170 case SDL_JOYBUTTONUP:
1171 SDL_Log("SDL EVENT: Joystick %d: button %d released",
1172 event->jbutton.which, event->jbutton.button);
1173 break;
1174 case SDL_CONTROLLERDEVICEADDED:
1175 SDL_Log("SDL EVENT: Controller index %d attached",
1176 event->cdevice.which);
1177 break;
1178 case SDL_CONTROLLERDEVICEREMOVED:
1179 SDL_Log("SDL EVENT: Controller %d removed",
1180 event->cdevice.which);
1181 break;
1182 case SDL_CONTROLLERAXISMOTION:
1183 SDL_Log("SDL EVENT: Controller %d axis %d ('%s') value: %d",
1184 event->caxis.which,
1185 event->caxis.axis,
1186 ControllerAxisName((SDL_GameControllerAxis)event->caxis.axis),
1187 event->caxis.value);
1188 break;
1189 case SDL_CONTROLLERBUTTONDOWN:
1190 SDL_Log("SDL EVENT: Controller %d button %d ('%s') down",
1191 event->cbutton.which, event->cbutton.button,
1192 ControllerButtonName((SDL_GameControllerButton)event->cbutton.button));
1193 break;
1194 case SDL_CONTROLLERBUTTONUP:
1195 SDL_Log("SDL EVENT: Controller %d button %d ('%s') up",
1196 event->cbutton.which, event->cbutton.button,
1197 ControllerButtonName((SDL_GameControllerButton)event->cbutton.button));
1198 break;
1199 case SDL_CLIPBOARDUPDATE:
1200 SDL_Log("SDL EVENT: Clipboard updated");
1201 break;
1202
1203 case SDL_FINGERDOWN:
1204 case SDL_FINGERUP:
1205 SDL_Log("SDL EVENT: Finger: %s touch=%ld, finger=%ld, x=%f, y=%f, dx=%f, dy=%f, pressure=%f",
1206 (event->type == SDL_FINGERDOWN) ? "down" : "up",
1207 (long) event->tfinger.touchId,
1208 (long) event->tfinger.fingerId,
1209 event->tfinger.x, event->tfinger.y,
1210 event->tfinger.dx, event->tfinger.dy, event->tfinger.pressure);
1211 break;
1212 case SDL_DOLLARGESTURE:
1213 SDL_Log("SDL_EVENT: Dollar gesture detect: %"SDL_PRIs64, (Sint64) event->dgesture.gestureId);
1214 break;
1215 case SDL_DOLLARRECORD:
1216 SDL_Log("SDL_EVENT: Dollar gesture record: %"SDL_PRIs64, (Sint64) event->dgesture.gestureId);
1217 break;
1218 case SDL_MULTIGESTURE:
1219 SDL_Log("SDL_EVENT: Multi gesture fingers: %d", event->mgesture.numFingers);
1220 break;
1221
1222 case SDL_RENDER_DEVICE_RESET:
1223 SDL_Log("SDL EVENT: render device reset");
1224 break;
1225 case SDL_RENDER_TARGETS_RESET:
1226 SDL_Log("SDL EVENT: render targets reset");
1227 break;
1228
1229 case SDL_QUIT:
1230 SDL_Log("SDL EVENT: Quit requested");
1231 break;
1232 case SDL_USEREVENT:
1233 SDL_Log("SDL EVENT: User event %d", event->user.code);
1234 break;
1235 default:
1236 SDL_Log("Unknown event %04x", event->type);
1237 break;
1238 }
1239 }
1240
1241 static void
SDLTest_ScreenShot(SDL_Renderer * renderer)1242 SDLTest_ScreenShot(SDL_Renderer *renderer)
1243 {
1244 SDL_Rect viewport;
1245 SDL_Surface *surface;
1246
1247 if (!renderer) {
1248 return;
1249 }
1250
1251 SDL_RenderGetViewport(renderer, &viewport);
1252 surface = SDL_CreateRGBSurface(0, viewport.w, viewport.h, 24,
1253 #if SDL_BYTEORDER == SDL_LIL_ENDIAN
1254 0x00FF0000, 0x0000FF00, 0x000000FF,
1255 #else
1256 0x000000FF, 0x0000FF00, 0x00FF0000,
1257 #endif
1258 0x00000000);
1259 if (!surface) {
1260 fprintf(stderr, "Couldn't create surface: %s\n", SDL_GetError());
1261 return;
1262 }
1263
1264 if (SDL_RenderReadPixels(renderer, NULL, surface->format->format,
1265 surface->pixels, surface->pitch) < 0) {
1266 fprintf(stderr, "Couldn't read screen: %s\n", SDL_GetError());
1267 SDL_free(surface);
1268 return;
1269 }
1270
1271 if (SDL_SaveBMP(surface, "screenshot.bmp") < 0) {
1272 fprintf(stderr, "Couldn't save screenshot.bmp: %s\n", SDL_GetError());
1273 SDL_free(surface);
1274 return;
1275 }
1276 }
1277
1278 static void
FullscreenTo(int index,int windowId)1279 FullscreenTo(int index, int windowId)
1280 {
1281 Uint32 flags;
1282 struct SDL_Rect rect = { 0, 0, 0, 0 };
1283 SDL_Window *window = SDL_GetWindowFromID(windowId);
1284 if (!window) {
1285 return;
1286 }
1287
1288 SDL_GetDisplayBounds( index, &rect );
1289
1290 flags = SDL_GetWindowFlags(window);
1291 if (flags & SDL_WINDOW_FULLSCREEN) {
1292 SDL_SetWindowFullscreen( window, SDL_FALSE );
1293 SDL_Delay( 15 );
1294 }
1295
1296 SDL_SetWindowPosition( window, rect.x, rect.y );
1297 SDL_SetWindowFullscreen( window, SDL_TRUE );
1298 }
1299
1300 void
SDLTest_CommonEvent(SDLTest_CommonState * state,SDL_Event * event,int * done)1301 SDLTest_CommonEvent(SDLTest_CommonState * state, SDL_Event * event, int *done)
1302 {
1303 int i;
1304 static SDL_MouseMotionEvent lastEvent;
1305
1306 if (state->verbose & VERBOSE_EVENT) {
1307 SDLTest_PrintEvent(event);
1308 }
1309
1310 switch (event->type) {
1311 case SDL_WINDOWEVENT:
1312 switch (event->window.event) {
1313 case SDL_WINDOWEVENT_CLOSE:
1314 {
1315 SDL_Window *window = SDL_GetWindowFromID(event->window.windowID);
1316 if (window) {
1317 for (i = 0; i < state->num_windows; ++i) {
1318 if (window == state->windows[i]) {
1319 if (state->targets[i]) {
1320 SDL_DestroyTexture(state->targets[i]);
1321 state->targets[i] = NULL;
1322 }
1323 if (state->renderers[i]) {
1324 SDL_DestroyRenderer(state->renderers[i]);
1325 state->renderers[i] = NULL;
1326 }
1327 SDL_DestroyWindow(state->windows[i]);
1328 state->windows[i] = NULL;
1329 break;
1330 }
1331 }
1332 }
1333 }
1334 break;
1335 }
1336 break;
1337 case SDL_KEYDOWN: {
1338 SDL_bool withControl = !!(event->key.keysym.mod & KMOD_CTRL);
1339 SDL_bool withShift = !!(event->key.keysym.mod & KMOD_SHIFT);
1340 SDL_bool withAlt = !!(event->key.keysym.mod & KMOD_ALT);
1341
1342 switch (event->key.keysym.sym) {
1343 /* Add hotkeys here */
1344 case SDLK_PRINTSCREEN: {
1345 SDL_Window *window = SDL_GetWindowFromID(event->key.windowID);
1346 if (window) {
1347 for (i = 0; i < state->num_windows; ++i) {
1348 if (window == state->windows[i]) {
1349 SDLTest_ScreenShot(state->renderers[i]);
1350 }
1351 }
1352 }
1353 }
1354 break;
1355 case SDLK_EQUALS:
1356 if (withControl) {
1357 /* Ctrl-+ double the size of the window */
1358 SDL_Window *window = SDL_GetWindowFromID(event->key.windowID);
1359 if (window) {
1360 int w, h;
1361 SDL_GetWindowSize(window, &w, &h);
1362 SDL_SetWindowSize(window, w*2, h*2);
1363 }
1364 }
1365 break;
1366 case SDLK_MINUS:
1367 if (withControl) {
1368 /* Ctrl-- half the size of the window */
1369 SDL_Window *window = SDL_GetWindowFromID(event->key.windowID);
1370 if (window) {
1371 int w, h;
1372 SDL_GetWindowSize(window, &w, &h);
1373 SDL_SetWindowSize(window, w/2, h/2);
1374 }
1375 }
1376 break;
1377 case SDLK_o:
1378 if (withControl) {
1379 /* Ctrl-O (or Ctrl-Shift-O) changes window opacity. */
1380 SDL_Window *window = SDL_GetWindowFromID(event->key.windowID);
1381 if (window) {
1382 float opacity;
1383 if (SDL_GetWindowOpacity(window, &opacity) == 0) {
1384 if (withShift) {
1385 opacity += 0.20f;
1386 } else {
1387 opacity -= 0.20f;
1388 }
1389 SDL_SetWindowOpacity(window, opacity);
1390 }
1391 }
1392 }
1393 break;
1394
1395 case SDLK_c:
1396 if (withControl) {
1397 /* Ctrl-C copy awesome text! */
1398 SDL_SetClipboardText("SDL rocks!\nYou know it!");
1399 printf("Copied text to clipboard\n");
1400 }
1401 if (withAlt) {
1402 /* Alt-C toggle a render clip rectangle */
1403 for (i = 0; i < state->num_windows; ++i) {
1404 int w, h;
1405 if (state->renderers[i]) {
1406 SDL_Rect clip;
1407 SDL_GetWindowSize(state->windows[i], &w, &h);
1408 SDL_RenderGetClipRect(state->renderers[i], &clip);
1409 if (SDL_RectEmpty(&clip)) {
1410 clip.x = w/4;
1411 clip.y = h/4;
1412 clip.w = w/2;
1413 clip.h = h/2;
1414 SDL_RenderSetClipRect(state->renderers[i], &clip);
1415 } else {
1416 SDL_RenderSetClipRect(state->renderers[i], NULL);
1417 }
1418 }
1419 }
1420 }
1421 if (withShift) {
1422 SDL_Window *current_win = SDL_GetKeyboardFocus();
1423 if (current_win) {
1424 const SDL_bool shouldCapture = (SDL_GetWindowFlags(current_win) & SDL_WINDOW_MOUSE_CAPTURE) == 0;
1425 const int rc = SDL_CaptureMouse(shouldCapture);
1426 SDL_Log("%sapturing mouse %s!\n", shouldCapture ? "C" : "Unc", (rc == 0) ? "succeeded" : "failed");
1427 }
1428 }
1429 break;
1430 case SDLK_v:
1431 if (withControl) {
1432 /* Ctrl-V paste awesome text! */
1433 char *text = SDL_GetClipboardText();
1434 if (*text) {
1435 printf("Clipboard: %s\n", text);
1436 } else {
1437 printf("Clipboard is empty\n");
1438 }
1439 SDL_free(text);
1440 }
1441 break;
1442 case SDLK_g:
1443 if (withControl) {
1444 /* Ctrl-G toggle grab */
1445 SDL_Window *window = SDL_GetWindowFromID(event->key.windowID);
1446 if (window) {
1447 SDL_SetWindowGrab(window, !SDL_GetWindowGrab(window) ? SDL_TRUE : SDL_FALSE);
1448 }
1449 }
1450 break;
1451 case SDLK_m:
1452 if (withControl) {
1453 /* Ctrl-M maximize */
1454 SDL_Window *window = SDL_GetWindowFromID(event->key.windowID);
1455 if (window) {
1456 Uint32 flags = SDL_GetWindowFlags(window);
1457 if (flags & SDL_WINDOW_MAXIMIZED) {
1458 SDL_RestoreWindow(window);
1459 } else {
1460 SDL_MaximizeWindow(window);
1461 }
1462 }
1463 }
1464 break;
1465 case SDLK_r:
1466 if (withControl) {
1467 /* Ctrl-R toggle mouse relative mode */
1468 SDL_SetRelativeMouseMode(!SDL_GetRelativeMouseMode() ? SDL_TRUE : SDL_FALSE);
1469 }
1470 break;
1471 case SDLK_z:
1472 if (withControl) {
1473 /* Ctrl-Z minimize */
1474 SDL_Window *window = SDL_GetWindowFromID(event->key.windowID);
1475 if (window) {
1476 SDL_MinimizeWindow(window);
1477 }
1478 }
1479 break;
1480 case SDLK_RETURN:
1481 if (withControl) {
1482 /* Ctrl-Enter toggle fullscreen */
1483 SDL_Window *window = SDL_GetWindowFromID(event->key.windowID);
1484 if (window) {
1485 Uint32 flags = SDL_GetWindowFlags(window);
1486 if (flags & SDL_WINDOW_FULLSCREEN) {
1487 SDL_SetWindowFullscreen(window, SDL_FALSE);
1488 } else {
1489 SDL_SetWindowFullscreen(window, SDL_WINDOW_FULLSCREEN);
1490 }
1491 }
1492 } else if (withAlt) {
1493 /* Alt-Enter toggle fullscreen desktop */
1494 SDL_Window *window = SDL_GetWindowFromID(event->key.windowID);
1495 if (window) {
1496 Uint32 flags = SDL_GetWindowFlags(window);
1497 if (flags & SDL_WINDOW_FULLSCREEN) {
1498 SDL_SetWindowFullscreen(window, SDL_FALSE);
1499 } else {
1500 SDL_SetWindowFullscreen(window, SDL_WINDOW_FULLSCREEN_DESKTOP);
1501 }
1502 }
1503 } else if (withShift) {
1504 /* Shift-Enter toggle fullscreen desktop / fullscreen */
1505 SDL_Window *window = SDL_GetWindowFromID(event->key.windowID);
1506 if (window) {
1507 Uint32 flags = SDL_GetWindowFlags(window);
1508 if ((flags & SDL_WINDOW_FULLSCREEN_DESKTOP) == SDL_WINDOW_FULLSCREEN_DESKTOP) {
1509 SDL_SetWindowFullscreen(window, SDL_WINDOW_FULLSCREEN);
1510 } else {
1511 SDL_SetWindowFullscreen(window, SDL_WINDOW_FULLSCREEN_DESKTOP);
1512 }
1513 }
1514 }
1515
1516 break;
1517 case SDLK_b:
1518 if (withControl) {
1519 /* Ctrl-B toggle window border */
1520 SDL_Window *window = SDL_GetWindowFromID(event->key.windowID);
1521 if (window) {
1522 const Uint32 flags = SDL_GetWindowFlags(window);
1523 const SDL_bool b = ((flags & SDL_WINDOW_BORDERLESS) != 0) ? SDL_TRUE : SDL_FALSE;
1524 SDL_SetWindowBordered(window, b);
1525 }
1526 }
1527 break;
1528 case SDLK_a:
1529 if (withControl) {
1530 /* Ctrl-A reports absolute mouse position. */
1531 int x, y;
1532 const Uint32 mask = SDL_GetGlobalMouseState(&x, &y);
1533 SDL_Log("ABSOLUTE MOUSE: (%d, %d)%s%s%s%s%s\n", x, y,
1534 (mask & SDL_BUTTON_LMASK) ? " [LBUTTON]" : "",
1535 (mask & SDL_BUTTON_MMASK) ? " [MBUTTON]" : "",
1536 (mask & SDL_BUTTON_RMASK) ? " [RBUTTON]" : "",
1537 (mask & SDL_BUTTON_X1MASK) ? " [X2BUTTON]" : "",
1538 (mask & SDL_BUTTON_X2MASK) ? " [X2BUTTON]" : "");
1539 }
1540 break;
1541 case SDLK_0:
1542 if (withControl) {
1543 SDL_Window *window = SDL_GetWindowFromID(event->key.windowID);
1544 SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_INFORMATION, "Test Message", "You're awesome!", window);
1545 }
1546 break;
1547 case SDLK_1:
1548 if (withControl) {
1549 FullscreenTo(0, event->key.windowID);
1550 }
1551 break;
1552 case SDLK_2:
1553 if (withControl) {
1554 FullscreenTo(1, event->key.windowID);
1555 }
1556 break;
1557 case SDLK_ESCAPE:
1558 *done = 1;
1559 break;
1560 case SDLK_SPACE:
1561 {
1562 char message[256];
1563 SDL_Window *window = SDL_GetWindowFromID(event->key.windowID);
1564
1565 SDL_snprintf(message, sizeof(message), "(%i, %i), rel (%i, %i)\n", lastEvent.x, lastEvent.y, lastEvent.xrel, lastEvent.yrel);
1566 SDL_ShowSimpleMessageBox(SDL_MESSAGEBOX_INFORMATION, "Last mouse position", message, window);
1567 break;
1568 }
1569 default:
1570 break;
1571 }
1572 break;
1573 }
1574 case SDL_QUIT:
1575 *done = 1;
1576 break;
1577 case SDL_MOUSEMOTION:
1578 lastEvent = event->motion;
1579 break;
1580 }
1581 }
1582
1583 void
SDLTest_CommonQuit(SDLTest_CommonState * state)1584 SDLTest_CommonQuit(SDLTest_CommonState * state)
1585 {
1586 int i;
1587
1588 SDL_free(state->windows);
1589 if (state->targets) {
1590 for (i = 0; i < state->num_windows; ++i) {
1591 if (state->targets[i]) {
1592 SDL_DestroyTexture(state->targets[i]);
1593 }
1594 }
1595 SDL_free(state->targets);
1596 }
1597 if (state->renderers) {
1598 for (i = 0; i < state->num_windows; ++i) {
1599 if (state->renderers[i]) {
1600 SDL_DestroyRenderer(state->renderers[i]);
1601 }
1602 }
1603 SDL_free(state->renderers);
1604 }
1605 if (state->flags & SDL_INIT_VIDEO) {
1606 SDL_VideoQuit();
1607 }
1608 if (state->flags & SDL_INIT_AUDIO) {
1609 SDL_AudioQuit();
1610 }
1611 SDL_free(state);
1612 SDL_Quit();
1613 }
1614
1615 /* vi: set ts=4 sw=4 expandtab: */
1616