/
SDL_ph_video.c
653 lines (569 loc) · 19.6 KB
1
2
/*
SDL - Simple DirectMedia Layer
3
Copyright (C) 1997-2006 Sam Lantinga
4
5
This library is free software; you can redistribute it and/or
6
modify it under the terms of the GNU Lesser General Public
7
License as published by the Free Software Foundation; either
8
version 2.1 of the License, or (at your option) any later version.
9
10
11
12
This library is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13
Lesser General Public License for more details.
14
15
16
17
You should have received a copy of the GNU Lesser General Public
License along with this library; if not, write to the Free Software
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
18
19
Sam Lantinga
20
slouken@libsdl.org
21
22
23
24
25
26
*/
#include <unistd.h>
#include <sys/ioctl.h>
#include "SDL.h"
27
28
#include "SDL_stdlib.h"
#include "SDL_string.h"
29
30
31
32
33
34
35
36
37
38
39
40
41
42
#include "SDL_error.h"
#include "SDL_timer.h"
#include "SDL_thread.h"
#include "SDL_video.h"
#include "SDL_mouse.h"
#include "SDL_endian.h"
#include "SDL_sysvideo.h"
#include "SDL_pixels_c.h"
#include "SDL_events_c.h"
#include "SDL_ph_video.h"
#include "SDL_ph_modes_c.h"
#include "SDL_ph_image_c.h"
#include "SDL_ph_events_c.h"
#include "SDL_ph_mouse_c.h"
43
#include "SDL_ph_wm_c.h"
44
#include "SDL_ph_gl.h"
45
46
47
#include "SDL_phyuv_c.h"
#include "blank_cursor.h"
48
49
50
static int ph_VideoInit(_THIS, SDL_PixelFormat *vformat);
static SDL_Surface *ph_SetVideoMode(_THIS, SDL_Surface *current, int width, int height, int bpp, Uint32 flags);
static int ph_SetColors(_THIS, int firstcolor, int ncolors, SDL_Color *colors);
51
52
static void ph_VideoQuit(_THIS);
static void ph_DeleteDevice(SDL_VideoDevice *device);
53
54
55
static int phstatus=-1;
56
57
static int ph_Available(void)
{
58
if (phstatus!=0)
59
{
60
61
62
63
64
65
66
67
68
phstatus=PtInit(NULL);
if (phstatus==0)
{
return 1;
}
else
{
return 0;
}
69
}
70
return 1;
71
72
}
73
static SDL_VideoDevice* ph_CreateDevice(int devindex)
74
{
75
SDL_VideoDevice* device;
76
77
/* Initialize all variables that we clean on shutdown */
78
device = (SDL_VideoDevice *)SDL_malloc(sizeof(SDL_VideoDevice));
79
80
if (device)
{
81
82
SDL_memset(device, 0, (sizeof *device));
device->hidden = (struct SDL_PrivateVideoData*)SDL_malloc((sizeof *device->hidden));
83
84
device->gl_data = NULL;
}
85
86
if ((device == NULL) || (device->hidden == NULL))
{
87
88
SDL_OutOfMemory();
ph_DeleteDevice(device);
89
return NULL;
90
}
91
SDL_memset(device->hidden, 0, (sizeof *device->hidden));
92
93
/* Set the driver flags */
94
device->handles_any_size = 1;
95
96
/* Set the function pointers */
97
device->CreateYUVOverlay = ph_CreateYUVOverlay;
98
99
100
device->VideoInit = ph_VideoInit;
device->ListModes = ph_ListModes;
device->SetVideoMode = ph_SetVideoMode;
101
device->ToggleFullScreen = ph_ToggleFullScreen;
102
device->UpdateMouse = ph_UpdateMouse;
103
device->SetColors = ph_SetColors;
104
device->UpdateRects = NULL; /* set up in ph_SetupUpdateFunction */
105
106
device->VideoQuit = ph_VideoQuit;
device->AllocHWSurface = ph_AllocHWSurface;
107
108
109
110
device->CheckHWBlit = ph_CheckHWBlit;
device->FillHWRect = ph_FillHWRect;
device->SetHWColorKey = ph_SetHWColorKey;
device->SetHWAlpha = ph_SetHWAlpha;
111
112
113
114
device->LockHWSurface = ph_LockHWSurface;
device->UnlockHWSurface = ph_UnlockHWSurface;
device->FlipHWSurface = ph_FlipHWSurface;
device->FreeHWSurface = ph_FreeHWSurface;
115
device->SetCaption = ph_SetCaption;
116
device->SetIcon = NULL;
117
device->IconifyWindow = ph_IconifyWindow;
118
device->GrabInput = ph_GrabInput;
119
device->GetWMInfo = ph_GetWMInfo;
120
121
122
123
device->FreeWMCursor = ph_FreeWMCursor;
device->CreateWMCursor = ph_CreateWMCursor;
device->ShowWMCursor = ph_ShowWMCursor;
device->WarpWMCursor = ph_WarpWMCursor;
124
device->MoveWMCursor = NULL;
125
126
127
128
device->CheckMouseMode = ph_CheckMouseMode;
device->InitOSKeymap = ph_InitOSKeymap;
device->PumpEvents = ph_PumpEvents;
129
130
/* OpenGL support. */
#ifdef HAVE_OPENGL
131
device->GL_MakeCurrent = ph_GL_MakeCurrent;
132
device->GL_SwapBuffers = ph_GL_SwapBuffers;
133
device->GL_GetAttribute = ph_GL_GetAttribute;
134
135
device->GL_LoadLibrary = ph_GL_LoadLibrary;
device->GL_GetProcAddress = ph_GL_GetProcAddress;
136
#else
137
device->GL_MakeCurrent = NULL;
138
device->GL_SwapBuffers = NULL;
139
device->GL_GetAttribute = NULL;
140
141
device->GL_LoadLibrary = NULL;
device->GL_GetProcAddress = NULL;
142
#endif /* HAVE_OPENGL */
143
144
device->free = ph_DeleteDevice;
145
146
147
148
return device;
}
149
VideoBootStrap ph_bootstrap = {
150
151
"photon", "QNX Photon video output",
ph_Available, ph_CreateDevice
152
153
154
155
};
static void ph_DeleteDevice(SDL_VideoDevice *device)
{
156
157
158
159
if (device)
{
if (device->hidden)
{
160
SDL_free(device->hidden);
161
162
device->hidden = NULL;
}
163
164
if (device->gl_data)
{
165
SDL_free(device->gl_data);
166
167
device->gl_data = NULL;
}
168
SDL_free(device);
169
170
171
172
device = NULL;
}
}
173
174
175
176
static PtWidget_t *ph_CreateWindow(_THIS)
{
PtWidget_t *widget;
177
widget = PtCreateWidget(PtWindow, NULL, 0, NULL);
178
179
180
181
182
183
184
185
return widget;
}
static int ph_SetupWindow(_THIS, int w, int h, int flags)
{
PtArg_t args[32];
PhPoint_t pos = {0, 0};
186
PhDim_t* olddim;
187
PhDim_t dim = {w, h};
188
PhRect_t desktopextent;
189
int nargs = 0;
190
191
192
const char* windowpos;
const char* iscentered;
int x, y;
193
194
195
196
197
198
199
/* check if window size has been changed by Window Manager */
PtGetResource(window, Pt_ARG_DIM, &olddim, 0);
if ((olddim->w!=w) || (olddim->h!=h))
{
PtSetArg(&args[nargs++], Pt_ARG_DIM, &dim, 0);
}
200
201
202
if ((flags & SDL_RESIZABLE) == SDL_RESIZABLE)
{
203
204
205
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_MANAGED_FLAGS, Pt_FALSE, Ph_WM_CLOSE);
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_MANAGED_FLAGS, Pt_TRUE, Ph_WM_MAX | Ph_WM_RESTORE | Ph_WM_RESIZE);
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_NOTIFY_FLAGS, Pt_TRUE, Ph_WM_RESIZE | Ph_WM_MOVE | Ph_WM_CLOSE | Ph_WM_MAX | Ph_WM_RESTORE);
206
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_RENDER_FLAGS, Pt_TRUE, Ph_WM_RENDER_RESIZE | Ph_WM_RENDER_MAX | Ph_WM_RENDER_COLLAPSE | Ph_WM_RENDER_RETURN);
207
PtSetArg(&args[nargs++], Pt_ARG_RESIZE_FLAGS, Pt_TRUE, Pt_RESIZE_XY_AS_REQUIRED);
208
209
210
}
else
{
211
212
213
214
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_MANAGED_FLAGS, Pt_FALSE, Ph_WM_RESIZE | Ph_WM_MAX | Ph_WM_RESTORE | Ph_WM_CLOSE);
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_NOTIFY_FLAGS, Pt_FALSE, Ph_WM_RESIZE | Ph_WM_MAX | Ph_WM_RESTORE);
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_NOTIFY_FLAGS, Pt_TRUE, Ph_WM_MOVE | Ph_WM_CLOSE);
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_RENDER_FLAGS, Pt_FALSE, Ph_WM_RENDER_RESIZE | Ph_WM_RENDER_MAX | Ph_WM_RENDER_COLLAPSE | Ph_WM_RENDER_RETURN);
215
PtSetArg(&args[nargs++], Pt_ARG_RESIZE_FLAGS, Pt_FALSE, Pt_RESIZE_XY_AS_REQUIRED);
216
217
218
219
}
if (((flags & SDL_NOFRAME)==SDL_NOFRAME) || ((flags & SDL_FULLSCREEN)==SDL_FULLSCREEN))
{
220
221
222
223
224
225
226
227
228
if ((flags & SDL_RESIZABLE) != SDL_RESIZABLE)
{
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_RENDER_FLAGS, Pt_FALSE, Pt_TRUE);
}
else
{
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_RENDER_FLAGS, Pt_FALSE, Pt_TRUE);
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_RENDER_FLAGS, Pt_TRUE, Ph_WM_RENDER_RESIZE | Ph_WM_RENDER_BORDER);
}
229
230
231
232
}
else
{
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_RENDER_FLAGS, Pt_TRUE, Ph_WM_RENDER_BORDER | Ph_WM_RENDER_TITLE |
233
Ph_WM_RENDER_CLOSE | Ph_WM_RENDER_MENU | Ph_WM_RENDER_MIN);
234
235
}
236
if ((flags & SDL_FULLSCREEN) == SDL_FULLSCREEN)
237
238
{
PtSetArg(&args[nargs++], Pt_ARG_POS, &pos, 0);
239
PtSetArg(&args[nargs++], Pt_ARG_BASIC_FLAGS, Pt_TRUE, Pt_BASIC_PREVENT_FILL);
240
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_MANAGED_FLAGS, Pt_TRUE, Ph_WM_FFRONT | Ph_WM_MAX | Ph_WM_TOFRONT | Ph_WM_CONSWITCH);
241
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_STATE, Pt_TRUE, Ph_WM_STATE_ISFRONT | Ph_WM_STATE_ISFOCUS | Ph_WM_STATE_ISALTKEY);
242
243
244
}
else
{
245
246
247
248
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_MANAGED_FLAGS, Pt_FALSE, Ph_WM_FFRONT | Ph_WM_CONSWITCH);
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_STATE, Pt_FALSE, Ph_WM_STATE_ISFRONT);
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_STATE, Pt_TRUE, Ph_WM_STATE_ISALTKEY);
249
250
251
252
253
254
255
256
if ((flags & SDL_HWSURFACE) == SDL_HWSURFACE)
{
PtSetArg(&args[nargs++], Pt_ARG_BASIC_FLAGS, Pt_TRUE, Pt_BASIC_PREVENT_FILL);
}
else
{
PtSetArg(&args[nargs++], Pt_ARG_FILL_COLOR, Pg_BLACK, 0);
}
257
if (!currently_maximized)
258
{
259
260
windowpos = SDL_getenv("SDL_VIDEO_WINDOW_POS");
iscentered = SDL_getenv("SDL_VIDEO_CENTERED");
261
262
if ((iscentered) || ((windowpos) && (SDL_strcmp(windowpos, "center")==0)))
263
{
264
265
PhWindowQueryVisible(Ph_QUERY_CONSOLE, 0, 0, &desktopextent);
if (desktop_mode.width>w)
266
{
267
268
269
270
271
pos.x = (desktop_mode.width - w)/2;
}
if (desktop_mode.height>h)
{
pos.y = (desktop_mode.height - h)/2;
272
273
}
274
275
276
277
278
279
280
281
pos.x+=desktopextent.ul.x;
pos.y+=desktopextent.ul.y;
PtSetArg(&args[nargs++], Pt_ARG_POS, &pos, 0);
}
else
{
if (windowpos)
{
282
if (SDL_sscanf(windowpos, "%d,%d", &x, &y) == 2)
283
284
285
286
287
288
289
290
291
292
293
294
{
if ((x<desktop_mode.width) && (y<desktop_mode.height))
{
PhWindowQueryVisible(Ph_QUERY_CONSOLE, 0, 0, &desktopextent);
pos.x=x+desktopextent.ul.x;
pos.y=y+desktopextent.ul.y;
}
PtSetArg(&args[nargs++], Pt_ARG_POS, &pos, 0);
}
}
}
}
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
/* if window is maximized render it as maximized */
if (currently_maximized)
{
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_STATE, Pt_TRUE, Ph_WM_STATE_ISMAX);
}
else
{
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_STATE, Pt_FALSE, Ph_WM_STATE_ISMAX);
}
/* do not grab the keyboard by default */
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_STATE, Pt_FALSE, Ph_WM_STATE_ISALTKEY);
/* bring the focus to the window */
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_STATE, Pt_TRUE, Ph_WM_STATE_ISFOCUS);
312
/* allow to catch hide event */
313
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_MANAGED_FLAGS, Pt_TRUE, Ph_WM_HIDE);
314
PtSetArg(&args[nargs++], Pt_ARG_WINDOW_NOTIFY_FLAGS, Pt_TRUE, Ph_WM_HIDE);
315
316
317
318
}
PtSetResources(window, nargs, args);
PtRealizeWidget(window);
319
PtWindowToFront(window);
320
321
322
323
324
325
#if 0 /* FIXME */
PtGetResource(window, Pt_ARG_POS, &olddim, 0);
fprintf(stderr, "POSITION: %d, %d\n", olddim->w, olddim->h);
#endif
326
327
328
return 0;
}
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
static const struct ColourMasks* ph_GetColourMasks(int bpp)
{
/* The alpha mask doesn't appears to be needed */
static const struct ColourMasks phColorMasks[5] = {
/* 8 bit */ {0, 0, 0, 0, 8},
/* 15 bit ARGB */ {0x7C00, 0x03E0, 0x001F, 0x8000, 15},
/* 16 bit RGB */ {0xF800, 0x07E0, 0x001F, 0x0000, 16},
/* 24 bit RGB */ {0xFF0000, 0x00FF00, 0x0000FF, 0x000000, 24},
/* 32 bit ARGB */ {0x00FF0000, 0x0000FF00, 0x000000FF, 0xFF000000, 32},
};
switch (bpp)
{
case 8:
return &phColorMasks[0];
case 15:
return &phColorMasks[1];
case 16:
return &phColorMasks[2];
case 24:
return &phColorMasks[3];
case 32:
return &phColorMasks[4];
}
return NULL;
}
356
static int ph_VideoInit(_THIS, SDL_PixelFormat* vformat)
357
{
358
PgHWCaps_t hwcaps;
359
int i;
360
361
window=NULL;
362
desktoppal=SDLPH_PAL_NONE;
363
364
365
#ifdef HAVE_OPENGL
oglctx=NULL;
366
oglbuffers=NULL;
367
368
oglflags=0;
oglbpp=0;
369
#endif /* HAVE_OPENGL */
370
371
372
old_video_mode=-1;
old_refresh_rate=-1;
373
374
if (NULL == (event = SDL_malloc(EVENT_SIZE)))
375
{
376
377
SDL_OutOfMemory();
return -1;
378
}
379
SDL_memset(event, 0x00, EVENT_SIZE);
380
381
382
383
window = ph_CreateWindow(this);
if (window == NULL)
{
384
SDL_SetError("ph_VideoInit(): Couldn't create video window !\n");
385
386
387
return -1;
}
388
389
390
391
392
393
394
/* Create the blank cursor */
SDL_BlankCursor = this->CreateWMCursor(this, blank_cdata, blank_cmask,
(int)BLANK_CWIDTH, (int)BLANK_CHEIGHT,
(int)BLANK_CHOTX, (int)BLANK_CHOTY);
if (SDL_BlankCursor == NULL)
{
395
return -1;
396
397
}
398
if (PgGetGraphicsHWCaps(&hwcaps) < 0)
399
{
400
401
402
SDL_SetError("ph_VideoInit(): GetGraphicsHWCaps function failed !\n");
this->FreeWMCursor(this, SDL_BlankCursor);
return -1;
403
404
}
405
if (PgGetVideoModeInfo(hwcaps.current_video_mode, &desktop_mode) < 0)
406
{
407
408
409
SDL_SetError("ph_VideoInit(): PgGetVideoModeInfo function failed !\n");
this->FreeWMCursor(this, SDL_BlankCursor);
return -1;
410
411
412
}
/* We need to return BytesPerPixel as it in used by CreateRGBsurface */
413
414
415
vformat->BitsPerPixel = desktop_mode.bits_per_pixel;
vformat->BytesPerPixel = desktop_mode.bytes_per_scanline/desktop_mode.width;
desktopbpp = desktop_mode.bits_per_pixel;
416
417
418
/* save current palette */
if (desktopbpp==8)
419
{
420
421
PgGetPalette(savedpal);
PgGetPalette(syspalph);
422
}
423
424
425
426
427
428
429
430
else
{
for(i=0; i<_Pg_MAX_PALETTE; i++)
{
savedpal[i]=PgRGB(0, 0, 0);
syspalph[i]=PgRGB(0, 0, 0);
}
}
431
432
currently_fullscreen = 0;
433
currently_hided = 0;
434
currently_maximized = 0;
435
436
437
438
439
440
441
442
443
current_overlay = NULL;
OCImage.direct_context = NULL;
OCImage.offscreen_context = NULL;
OCImage.offscreen_backcontext = NULL;
OCImage.oldDC = NULL;
OCImage.CurrentFrameData = NULL;
OCImage.FrameData0 = NULL;
OCImage.FrameData1 = NULL;
444
videomode_emulatemode = 0;
445
446
this->info.wm_available = 1;
447
448
ph_UpdateHWInfo(this);
449
450
451
452
return 0;
}
453
static SDL_Surface* ph_SetVideoMode(_THIS, SDL_Surface *current, int width, int height, int bpp, Uint32 flags)
454
{
455
const struct ColourMasks* mask;
456
457
458
459
/* Lock the event thread, in multi-threading environments */
SDL_Lock_EventThread();
460
461
current->flags = flags;
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
/* if we do not have desired fullscreen mode, then fallback into window mode */
if (((current->flags & SDL_FULLSCREEN) == SDL_FULLSCREEN) && (ph_GetVideoMode(width, height, bpp)==0))
{
current->flags &= ~SDL_FULLSCREEN;
current->flags &= ~SDL_NOFRAME;
current->flags &= ~SDL_RESIZABLE;
}
ph_SetupWindow(this, width, height, current->flags);
mask = ph_GetColourMasks(bpp);
if (mask != NULL)
{
SDL_ReallocFormat(current, mask->bpp, mask->red, mask->green, mask->blue, 0);
}
else
{
SDL_SetError("ph_SetVideoMode(): desired bpp is not supported by photon !\n");
return NULL;
}
482
483
if ((current->flags & SDL_OPENGL)==SDL_OPENGL)
484
{
485
486
487
#if !defined(HAVE_OPENGL)
/* if no built-in OpenGL support */
SDL_SetError("ph_SetVideoMode(): no OpenGL support, you need to recompile SDL.\n");
488
current->flags &= ~SDL_OPENGL;
489
return NULL;
490
#endif /* HAVE_OPENGL */
491
}
492
493
else
{
494
495
/* Initialize internal variables */
if ((current->flags & SDL_FULLSCREEN) == SDL_FULLSCREEN)
496
{
497
498
499
500
if (bpp==8)
{
desktoppal=SDLPH_PAL_SYSTEM;
}
501
502
current->flags &= ~SDL_RESIZABLE; /* no resize for Direct Context */
503
current->flags |= SDL_HWSURFACE;
504
}
505
506
else
{
507
/* remove this if we'll have support for the non-fullscreen sw/hw+doublebuf one day */
508
509
510
511
current->flags &= ~SDL_DOUBLEBUF;
/* Use offscreen memory if SDL_HWSURFACE flag is set */
if ((current->flags & SDL_HWSURFACE) == SDL_HWSURFACE)
512
{
513
514
515
516
if (desktopbpp!=bpp)
{
current->flags &= ~SDL_HWSURFACE;
}
517
}
518
519
520
521
522
523
/* using palette emulation code in window mode */
if (bpp==8)
{
if (desktopbpp>=15)
{
524
desktoppal = SDLPH_PAL_EMULATE;
525
526
527
}
else
{
528
desktoppal = SDLPH_PAL_SYSTEM;
529
530
531
}
}
else
532
{
533
desktoppal = SDLPH_PAL_NONE;
534
}
535
}
536
537
538
539
}
current->w = width;
current->h = height;
540
541
542
543
544
if (desktoppal==SDLPH_PAL_SYSTEM)
{
current->flags|=SDL_HWPALETTE;
}
545
546
547
/* Must call at least once for setup image planes */
if (ph_SetupUpdateFunction(this, current, current->flags)==-1)
548
{
549
/* Error string was filled in the ph_SetupUpdateFunction() */
550
551
return NULL;
}
552
553
554
555
556
557
/* finish window drawing, if we are not in fullscreen, of course */
if ((current->flags & SDL_FULLSCREEN) != SDL_FULLSCREEN)
{
PtFlush();
}
558
559
560
561
else
{
PgFlush();
}
562
563
564
visualbpp=bpp;
565
ph_UpdateHWInfo(this);
566
567
568
SDL_Unlock_EventThread();
569
/* We've done! */
570
return (current);
571
572
573
574
}
static void ph_VideoQuit(_THIS)
{
575
576
/* restore palette */
if (desktopbpp==8)
577
{
578
579
580
PgSetPalette(syspalph, 0, -1, 0, 0, 0);
PgSetPalette(savedpal, 0, 0, _Pg_MAX_PALETTE, Pg_PALSET_GLOBAL | Pg_PALSET_FORCE_EXPOSE, 0);
PgFlush();
581
}
582
583
584
ph_DestroyImage(this, SDL_VideoSurface);
585
586
587
588
589
590
591
if (window)
{
PtUnrealizeWidget(window);
PtDestroyWidget(window);
window=NULL;
}
592
593
if (event!=NULL)
{
594
SDL_free(event);
595
596
event=NULL;
}
597
}
598
599
600
static int ph_SetColors(_THIS, int firstcolor, int ncolors, SDL_Color *colors)
{
601
int i;
602
603
604
605
606
SDL_Rect updaterect;
updaterect.x = updaterect.y = 0;
updaterect.w = this->screen->w;
updaterect.h = this->screen->h;
607
608
609
610
611
612
613
614
/* palette emulation code, using palette of the PhImage_t struct */
if (desktoppal==SDLPH_PAL_EMULATE)
{
if ((SDL_Image) && (SDL_Image->palette))
{
for (i=firstcolor; i<firstcolor+ncolors; i++)
{
615
616
syspalph[i] = PgRGB(colors[i-firstcolor].r, colors[i-firstcolor].g, colors[i-firstcolor].b);
SDL_Image->palette[i] = syspalph[i];
617
}
618
619
620
/* image needs to be redrawn */
this->UpdateRects(this, 1, &updaterect);
621
}
622
}
623
624
625
else
{
if (desktoppal==SDLPH_PAL_SYSTEM)
626
{
627
628
for (i=firstcolor; i<firstcolor+ncolors; i++)
{
629
syspalph[i] = PgRGB(colors[i-firstcolor].r, colors[i-firstcolor].g, colors[i-firstcolor].b);
630
631
632
633
}
if ((this->screen->flags & SDL_FULLSCREEN) != SDL_FULLSCREEN)
{
634
/* window mode must use soft palette */
635
PgSetPalette(&syspalph[firstcolor], 0, firstcolor, ncolors, Pg_PALSET_GLOBAL, 0);
636
637
/* image needs to be redrawn */
this->UpdateRects(this, 1, &updaterect);
638
639
640
641
}
else
{
/* fullscreen mode must use hardware palette */
642
PgSetPalette(&syspalph[firstcolor], 0, firstcolor, ncolors, Pg_PALSET_GLOBAL, 0);
643
}
644
}
645
else
646
{
647
/* SDLPH_PAL_NONE do nothing */
648
}
649
650
651
}
return 1;
652
}