src/video/windib/SDL_dibvideo.c
author Sam Lantinga <slouken@libsdl.org>
Sun, 06 Oct 2002 20:31:34 +0000
changeset 515 230b156829ed
parent 514 1080bfc4aa96
child 766 ed57c876700d
permissions -rw-r--r--
*** empty log message ***
slouken@0
     1
/*
slouken@0
     2
    SDL - Simple DirectMedia Layer
slouken@0
     3
    Copyright (C) 1997, 1998, 1999  Sam Lantinga
slouken@0
     4
slouken@0
     5
    This library is free software; you can redistribute it and/or
slouken@0
     6
    modify it under the terms of the GNU Library General Public
slouken@0
     7
    License as published by the Free Software Foundation; either
slouken@0
     8
    version 2 of the License, or (at your option) any later version.
slouken@0
     9
slouken@0
    10
    This library is distributed in the hope that it will be useful,
slouken@0
    11
    but WITHOUT ANY WARRANTY; without even the implied warranty of
slouken@0
    12
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
slouken@0
    13
    Library General Public License for more details.
slouken@0
    14
slouken@0
    15
    You should have received a copy of the GNU Library General Public
slouken@0
    16
    License along with this library; if not, write to the Free
slouken@0
    17
    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
slouken@0
    18
slouken@0
    19
    Sam Lantinga
slouken@252
    20
    slouken@libsdl.org
slouken@0
    21
*/
slouken@0
    22
slouken@0
    23
#ifdef SAVE_RCSID
slouken@0
    24
static char rcsid =
slouken@0
    25
 "@(#) $Id$";
slouken@0
    26
#endif
slouken@0
    27
slouken@0
    28
#include <stdio.h>
slouken@0
    29
#include <stdlib.h>
slouken@0
    30
#include <malloc.h>
slouken@0
    31
#include <windows.h>
slouken@515
    32
#if defined(WIN32_PLATFORM_PSPC)
slouken@515
    33
#include <aygshell.h>                      // Add Pocket PC includes
slouken@515
    34
#pragma comment( lib, "aygshell" )         // Link Pocket PC library
slouken@514
    35
#endif
slouken@0
    36
slouken@0
    37
/* Not yet in the mingw32 cross-compile headers */
slouken@0
    38
#ifndef CDS_FULLSCREEN
slouken@0
    39
#define CDS_FULLSCREEN	4
slouken@0
    40
#endif
slouken@0
    41
slouken@0
    42
#include "SDL.h"
slouken@0
    43
#include "SDL_mutex.h"
slouken@0
    44
#include "SDL_syswm.h"
slouken@0
    45
#include "SDL_sysvideo.h"
slouken@0
    46
#include "SDL_sysevents.h"
slouken@0
    47
#include "SDL_events_c.h"
slouken@0
    48
#include "SDL_pixels_c.h"
slouken@0
    49
#include "SDL_dibvideo.h"
slouken@0
    50
#include "SDL_syswm_c.h"
slouken@0
    51
#include "SDL_sysmouse_c.h"
slouken@0
    52
#include "SDL_dibevents_c.h"
slouken@0
    53
#include "SDL_wingl_c.h"
slouken@0
    54
slouken@0
    55
#ifdef _WIN32_WCE
slouken@0
    56
#define NO_GETDIBITS
slouken@0
    57
#define NO_CHANGEDISPLAYSETTINGS
slouken@0
    58
#define NO_GAMMA_SUPPORT
slouken@0
    59
#endif
slouken@453
    60
#ifndef WS_MAXIMIZE
slouken@453
    61
#define WS_MAXIMIZE		0
slouken@453
    62
#endif
slouken@453
    63
#ifndef SWP_NOCOPYBITS
slouken@453
    64
#define SWP_NOCOPYBITS	0
slouken@453
    65
#endif
slouken@453
    66
#ifndef PC_NOCOLLAPSE
slouken@453
    67
#define PC_NOCOLLAPSE	0
slouken@453
    68
#endif
slouken@0
    69
slouken@0
    70
/* Initialization/Query functions */
slouken@0
    71
static int DIB_VideoInit(_THIS, SDL_PixelFormat *vformat);
slouken@0
    72
static SDL_Rect **DIB_ListModes(_THIS, SDL_PixelFormat *format, Uint32 flags);
slouken@0
    73
SDL_Surface *DIB_SetVideoMode(_THIS, SDL_Surface *current, int width, int height, int bpp, Uint32 flags);
slouken@0
    74
static int DIB_SetColors(_THIS, int firstcolor, int ncolors,
slouken@0
    75
			 SDL_Color *colors);
slouken@0
    76
static void DIB_CheckGamma(_THIS);
slouken@338
    77
void DIB_SwapGamma(_THIS);
slouken@338
    78
void DIB_QuitGamma(_THIS);
slouken@338
    79
int DIB_SetGammaRamp(_THIS, Uint16 *ramp);
slouken@338
    80
int DIB_GetGammaRamp(_THIS, Uint16 *ramp);
slouken@0
    81
static void DIB_VideoQuit(_THIS);
slouken@0
    82
slouken@0
    83
/* Hardware surface functions */
slouken@0
    84
static int DIB_AllocHWSurface(_THIS, SDL_Surface *surface);
slouken@0
    85
static int DIB_LockHWSurface(_THIS, SDL_Surface *surface);
slouken@0
    86
static void DIB_UnlockHWSurface(_THIS, SDL_Surface *surface);
slouken@0
    87
static void DIB_FreeHWSurface(_THIS, SDL_Surface *surface);
slouken@0
    88
slouken@0
    89
/* Windows message handling functions */
slouken@0
    90
static void DIB_RealizePalette(_THIS);
slouken@0
    91
static void DIB_PaletteChanged(_THIS, HWND window);
slouken@0
    92
static void DIB_WinPAINT(_THIS, HDC hdc);
slouken@0
    93
slouken@0
    94
/* helper fn */
slouken@0
    95
static int DIB_SussScreenDepth();
slouken@0
    96
slouken@0
    97
/* DIB driver bootstrap functions */
slouken@0
    98
slouken@0
    99
static int DIB_Available(void)
slouken@0
   100
{
slouken@0
   101
	return(1);
slouken@0
   102
}
slouken@0
   103
slouken@0
   104
static void DIB_DeleteDevice(SDL_VideoDevice *device)
slouken@0
   105
{
slouken@0
   106
	if ( device ) {
slouken@0
   107
		if ( device->hidden ) {
slouken@0
   108
			free(device->hidden);
slouken@0
   109
		}
slouken@0
   110
		if ( device->gl_data ) {
slouken@0
   111
			free(device->gl_data);
slouken@0
   112
		}
slouken@0
   113
		free(device);
slouken@0
   114
	}
slouken@0
   115
}
slouken@0
   116
slouken@0
   117
static SDL_VideoDevice *DIB_CreateDevice(int devindex)
slouken@0
   118
{
slouken@0
   119
	SDL_VideoDevice *device;
slouken@0
   120
slouken@0
   121
	/* Initialize all variables that we clean on shutdown */
slouken@0
   122
	device = (SDL_VideoDevice *)malloc(sizeof(SDL_VideoDevice));
slouken@0
   123
	if ( device ) {
slouken@0
   124
		memset(device, 0, (sizeof *device));
slouken@0
   125
		device->hidden = (struct SDL_PrivateVideoData *)
slouken@0
   126
				malloc((sizeof *device->hidden));
slouken@0
   127
		device->gl_data = (struct SDL_PrivateGLData *)
slouken@0
   128
				malloc((sizeof *device->gl_data));
slouken@0
   129
	}
slouken@0
   130
	if ( (device == NULL) || (device->hidden == NULL) ||
slouken@0
   131
		                 (device->gl_data == NULL) ) {
slouken@0
   132
		SDL_OutOfMemory();
slouken@0
   133
		DIB_DeleteDevice(device);
slouken@0
   134
		return(NULL);
slouken@0
   135
	}
slouken@0
   136
	memset(device->hidden, 0, (sizeof *device->hidden));
slouken@0
   137
	memset(device->gl_data, 0, (sizeof *device->gl_data));
slouken@0
   138
slouken@0
   139
	/* Set the function pointers */
slouken@0
   140
	device->VideoInit = DIB_VideoInit;
slouken@0
   141
	device->ListModes = DIB_ListModes;
slouken@0
   142
	device->SetVideoMode = DIB_SetVideoMode;
slouken@0
   143
	device->UpdateMouse = WIN_UpdateMouse;
slouken@0
   144
	device->SetColors = DIB_SetColors;
slouken@0
   145
	device->UpdateRects = NULL;
slouken@0
   146
	device->VideoQuit = DIB_VideoQuit;
slouken@0
   147
	device->AllocHWSurface = DIB_AllocHWSurface;
slouken@0
   148
	device->CheckHWBlit = NULL;
slouken@0
   149
	device->FillHWRect = NULL;
slouken@0
   150
	device->SetHWColorKey = NULL;
slouken@0
   151
	device->SetHWAlpha = NULL;
slouken@0
   152
	device->LockHWSurface = DIB_LockHWSurface;
slouken@0
   153
	device->UnlockHWSurface = DIB_UnlockHWSurface;
slouken@0
   154
	device->FlipHWSurface = NULL;
slouken@0
   155
	device->FreeHWSurface = DIB_FreeHWSurface;
slouken@0
   156
	device->SetGammaRamp = DIB_SetGammaRamp;
slouken@0
   157
	device->GetGammaRamp = DIB_GetGammaRamp;
slouken@0
   158
#ifdef HAVE_OPENGL
slouken@453
   159
	device->GL_LoadLibrary = WIN_GL_LoadLibrary;
slouken@453
   160
	device->GL_GetProcAddress = WIN_GL_GetProcAddress;
slouken@453
   161
	device->GL_GetAttribute = WIN_GL_GetAttribute;
slouken@453
   162
	device->GL_MakeCurrent = WIN_GL_MakeCurrent;
slouken@453
   163
	device->GL_SwapBuffers = WIN_GL_SwapBuffers;
slouken@0
   164
#endif
slouken@0
   165
	device->SetCaption = WIN_SetWMCaption;
slouken@0
   166
	device->SetIcon = WIN_SetWMIcon;
slouken@0
   167
	device->IconifyWindow = WIN_IconifyWindow;
slouken@0
   168
	device->GrabInput = WIN_GrabInput;
slouken@0
   169
	device->GetWMInfo = WIN_GetWMInfo;
slouken@0
   170
	device->FreeWMCursor = WIN_FreeWMCursor;
slouken@0
   171
	device->CreateWMCursor = WIN_CreateWMCursor;
slouken@0
   172
	device->ShowWMCursor = WIN_ShowWMCursor;
slouken@0
   173
	device->WarpWMCursor = WIN_WarpWMCursor;
slouken@0
   174
	device->CheckMouseMode = WIN_CheckMouseMode;
slouken@0
   175
	device->InitOSKeymap = DIB_InitOSKeymap;
slouken@0
   176
	device->PumpEvents = DIB_PumpEvents;
slouken@0
   177
slouken@0
   178
	/* Set up the windows message handling functions */
slouken@0
   179
	WIN_RealizePalette = DIB_RealizePalette;
slouken@0
   180
	WIN_PaletteChanged = DIB_PaletteChanged;
slouken@0
   181
	WIN_WinPAINT = DIB_WinPAINT;
slouken@0
   182
	HandleMessage = DIB_HandleMessage;
slouken@0
   183
slouken@0
   184
	device->free = DIB_DeleteDevice;
slouken@0
   185
slouken@0
   186
	/* We're finally ready */
slouken@0
   187
	return device;
slouken@0
   188
}
slouken@0
   189
slouken@0
   190
VideoBootStrap WINDIB_bootstrap = {
slouken@0
   191
	"windib", "Win95/98/NT/2000 GDI",
slouken@0
   192
	DIB_Available, DIB_CreateDevice
slouken@0
   193
};
slouken@0
   194
slouken@0
   195
#ifndef NO_CHANGEDISPLAYSETTINGS
slouken@0
   196
slouken@0
   197
static int cmpmodes(const void *va, const void *vb)
slouken@0
   198
{
slouken@0
   199
    SDL_Rect *a = *(SDL_Rect **)va;
slouken@0
   200
    SDL_Rect *b = *(SDL_Rect **)vb;
slouken@0
   201
    if(a->w > b->w)
slouken@0
   202
        return -1;
slouken@0
   203
    return b->h - a->h;
slouken@0
   204
}
slouken@0
   205
slouken@0
   206
static int DIB_AddMode(_THIS, int bpp, int w, int h)
slouken@0
   207
{
slouken@0
   208
	SDL_Rect *mode;
slouken@0
   209
	int i, index;
slouken@0
   210
	int next_mode;
slouken@0
   211
slouken@0
   212
	/* Check to see if we already have this mode */
slouken@0
   213
	if ( bpp < 8 ) {  /* Not supported */
slouken@0
   214
		return(0);
slouken@0
   215
	}
slouken@0
   216
	index = ((bpp+7)/8)-1;
slouken@0
   217
	for ( i=0; i<SDL_nummodes[index]; ++i ) {
slouken@0
   218
		mode = SDL_modelist[index][i];
slouken@0
   219
		if ( (mode->w == w) && (mode->h == h) ) {
slouken@0
   220
			return(0);
slouken@0
   221
		}
slouken@0
   222
	}
slouken@0
   223
slouken@0
   224
	/* Set up the new video mode rectangle */
slouken@0
   225
	mode = (SDL_Rect *)malloc(sizeof *mode);
slouken@0
   226
	if ( mode == NULL ) {
slouken@0
   227
		SDL_OutOfMemory();
slouken@0
   228
		return(-1);
slouken@0
   229
	}
slouken@0
   230
	mode->x = 0;
slouken@0
   231
	mode->y = 0;
slouken@0
   232
	mode->w = w;
slouken@0
   233
	mode->h = h;
slouken@0
   234
slouken@0
   235
	/* Allocate the new list of modes, and fill in the new mode */
slouken@0
   236
	next_mode = SDL_nummodes[index];
slouken@0
   237
	SDL_modelist[index] = (SDL_Rect **)
slouken@0
   238
	       realloc(SDL_modelist[index], (1+next_mode+1)*sizeof(SDL_Rect *));
slouken@0
   239
	if ( SDL_modelist[index] == NULL ) {
slouken@0
   240
		SDL_OutOfMemory();
slouken@0
   241
		SDL_nummodes[index] = 0;
slouken@0
   242
		free(mode);
slouken@0
   243
		return(-1);
slouken@0
   244
	}
slouken@0
   245
	SDL_modelist[index][next_mode] = mode;
slouken@0
   246
	SDL_modelist[index][next_mode+1] = NULL;
slouken@0
   247
	SDL_nummodes[index]++;
slouken@0
   248
slouken@0
   249
	return(0);
slouken@0
   250
}
slouken@0
   251
slouken@0
   252
#endif /* !NO_CHANGEDISPLAYSETTINGS */
slouken@0
   253
slouken@0
   254
static HPALETTE DIB_CreatePalette(int bpp)
slouken@0
   255
{
slouken@0
   256
/*	RJR: March 28, 2000
slouken@0
   257
	moved palette creation here from "DIB_VideoInit" */
slouken@0
   258
slouken@0
   259
	HPALETTE handle = NULL;
slouken@0
   260
	
slouken@0
   261
	if ( bpp <= 8 )
slouken@0
   262
	{
slouken@0
   263
		LOGPALETTE *palette;
slouken@0
   264
		HDC hdc;
slouken@0
   265
		int ncolors;
slouken@0
   266
		int i;
slouken@0
   267
slouken@0
   268
		ncolors = 1;
slouken@0
   269
		for ( i=0; i<bpp; ++i ) {
slouken@0
   270
			ncolors *= 2;
slouken@0
   271
		}
slouken@0
   272
		palette = (LOGPALETTE *)malloc(sizeof(*palette)+
slouken@0
   273
					ncolors*sizeof(PALETTEENTRY));
slouken@0
   274
		palette->palVersion = 0x300;
slouken@0
   275
		palette->palNumEntries = ncolors;
slouken@0
   276
		hdc = GetDC(SDL_Window);
slouken@0
   277
		GetSystemPaletteEntries(hdc, 0, ncolors, palette->palPalEntry);
slouken@0
   278
		ReleaseDC(SDL_Window, hdc);
slouken@0
   279
		handle = CreatePalette(palette);
slouken@0
   280
		free(palette);
slouken@0
   281
	}
slouken@0
   282
	
slouken@0
   283
	return handle;
slouken@0
   284
}
slouken@0
   285
slouken@0
   286
int DIB_VideoInit(_THIS, SDL_PixelFormat *vformat)
slouken@0
   287
{
slouken@0
   288
#ifndef NO_CHANGEDISPLAYSETTINGS
slouken@0
   289
	int i;
slouken@0
   290
	DEVMODE settings;
slouken@0
   291
#endif
slouken@0
   292
slouken@0
   293
	/* Create the window */
slouken@0
   294
	if ( DIB_CreateWindow(this) < 0 ) {
slouken@0
   295
		return(-1);
slouken@0
   296
	}
slouken@169
   297
#ifndef DISABLE_AUDIO
slouken@0
   298
	DX5_SoundFocus(SDL_Window);
slouken@169
   299
#endif
slouken@0
   300
slouken@0
   301
	/* Determine the screen depth */
slouken@0
   302
	vformat->BitsPerPixel = DIB_SussScreenDepth();
slouken@0
   303
	switch (vformat->BitsPerPixel) {
slouken@0
   304
		case 15:
slouken@0
   305
			vformat->Rmask = 0x00007c00;
slouken@0
   306
			vformat->Gmask = 0x000003e0;
slouken@0
   307
			vformat->Bmask = 0x0000001f;
slouken@0
   308
			vformat->BitsPerPixel = 16;
slouken@0
   309
			break;
slouken@0
   310
		case 16:
slouken@0
   311
			vformat->Rmask = 0x0000f800;
slouken@0
   312
			vformat->Gmask = 0x000007e0;
slouken@0
   313
			vformat->Bmask = 0x0000001f;
slouken@0
   314
			break;
slouken@0
   315
		case 24:
slouken@0
   316
		case 32:
slouken@0
   317
			/* GDI defined as 8-8-8 */
slouken@0
   318
			vformat->Rmask = 0x00ff0000;
slouken@0
   319
			vformat->Gmask = 0x0000ff00;
slouken@0
   320
			vformat->Bmask = 0x000000ff;
slouken@0
   321
			break;
slouken@0
   322
		default:
slouken@0
   323
			break;
slouken@0
   324
	}
slouken@0
   325
slouken@0
   326
	/* See if gamma is supported on this screen */
slouken@0
   327
	DIB_CheckGamma(this);
slouken@0
   328
slouken@0
   329
#ifndef NO_CHANGEDISPLAYSETTINGS
slouken@0
   330
	/* Query for the list of available video modes */
slouken@0
   331
	for ( i=0; EnumDisplaySettings(NULL, i, &settings); ++i ) {
slouken@0
   332
		DIB_AddMode(this, settings.dmBitsPerPel,
slouken@0
   333
			settings.dmPelsWidth, settings.dmPelsHeight);
slouken@0
   334
	}
slouken@0
   335
	/* Sort the mode lists */
slouken@0
   336
	for ( i=0; i<NUM_MODELISTS; ++i ) {
slouken@0
   337
		if ( SDL_nummodes[i] > 0 ) {
slouken@0
   338
			qsort(SDL_modelist[i], SDL_nummodes[i], sizeof *SDL_modelist[i], cmpmodes);
slouken@0
   339
		}
slouken@0
   340
	}
slouken@0
   341
#endif /* !NO_CHANGEDISPLAYSETTINGS */
slouken@0
   342
slouken@0
   343
	/* Grab an identity palette if we are in a palettized mode */
slouken@0
   344
	if ( vformat->BitsPerPixel <= 8 ) {
slouken@0
   345
	/*	RJR: March 28, 2000
slouken@0
   346
		moved palette creation to "DIB_CreatePalette" */
slouken@0
   347
		screen_pal = DIB_CreatePalette(vformat->BitsPerPixel);
slouken@0
   348
	}
slouken@0
   349
slouken@0
   350
	/* Fill in some window manager capabilities */
slouken@0
   351
	this->info.wm_available = 1;
slouken@0
   352
slouken@0
   353
	/* We're done! */
slouken@0
   354
	return(0);
slouken@0
   355
}
slouken@0
   356
slouken@0
   357
/* We support any format at any dimension */
slouken@0
   358
SDL_Rect **DIB_ListModes(_THIS, SDL_PixelFormat *format, Uint32 flags)
slouken@0
   359
{
slouken@0
   360
#ifdef NO_CHANGEDISPLAYSETTINGS
slouken@0
   361
	return((SDL_Rect **)-1);
slouken@0
   362
#else
slouken@0
   363
	if ( (flags & SDL_FULLSCREEN) == SDL_FULLSCREEN ) {
slouken@0
   364
		return(SDL_modelist[((format->BitsPerPixel+7)/8)-1]);
slouken@0
   365
	} else {
slouken@0
   366
		return((SDL_Rect **)-1);
slouken@0
   367
	}
slouken@0
   368
#endif
slouken@0
   369
}
slouken@0
   370
slouken@0
   371
slouken@0
   372
/*
slouken@0
   373
  Helper fn to work out which screen depth windows is currently using.
slouken@0
   374
  15 bit mode is considered 555 format, 16 bit is 565.
slouken@0
   375
  returns 0 for unknown mode.
slouken@0
   376
  (Derived from code in sept 1999 Windows Developer Journal
slouken@0
   377
  http://www.wdj.com/code/archive.html)
slouken@0
   378
*/
slouken@0
   379
static int DIB_SussScreenDepth()
slouken@0
   380
{
slouken@0
   381
#ifdef NO_GETDIBITS
slouken@0
   382
	int depth;
slouken@0
   383
	HDC hdc;
slouken@0
   384
slouken@0
   385
	hdc = GetDC(SDL_Window);
slouken@0
   386
	depth = GetDeviceCaps(hdc, PLANES) * GetDeviceCaps(hdc, BITSPIXEL);
slouken@0
   387
	ReleaseDC(SDL_Window, hdc);
slouken@112
   388
#ifndef _WIN32_WCE
slouken@112
   389
	// AFAIK 16 bit CE devices have indeed RGB 565
slouken@0
   390
	if ( depth == 16 ) {
slouken@0
   391
		depth = 15;	/* GDI defined as RGB 555 */
slouken@0
   392
	}
slouken@112
   393
#endif
slouken@0
   394
	return(depth);
slouken@0
   395
#else
slouken@0
   396
    int dib_size;
slouken@0
   397
    LPBITMAPINFOHEADER dib_hdr;
slouken@0
   398
    HDC hdc;
slouken@0
   399
    HBITMAP hbm;
slouken@0
   400
slouken@0
   401
    /* Allocate enough space for a DIB header plus palette (for
slouken@0
   402
     * 8-bit modes) or bitfields (for 16- and 32-bit modes)
slouken@0
   403
     */
slouken@0
   404
    dib_size = sizeof(BITMAPINFOHEADER) + 256 * sizeof (RGBQUAD);
slouken@0
   405
    dib_hdr = (LPBITMAPINFOHEADER) malloc(dib_size);
slouken@0
   406
    memset(dib_hdr, 0, dib_size);
slouken@0
   407
    dib_hdr->biSize = sizeof(BITMAPINFOHEADER);
slouken@0
   408
    
slouken@0
   409
    /* Get a device-dependent bitmap that's compatible with the
slouken@0
   410
       screen.
slouken@0
   411
     */
slouken@0
   412
    hdc = GetDC(NULL);
slouken@0
   413
    hbm = CreateCompatibleBitmap( hdc, 1, 1 );
slouken@0
   414
slouken@0
   415
    /* Convert the DDB to a DIB.  We need to call GetDIBits twice:
slouken@0
   416
     * the first call just fills in the BITMAPINFOHEADER; the 
slouken@0
   417
     * second fills in the bitfields or palette.
slouken@0
   418
     */
slouken@0
   419
    GetDIBits(hdc, hbm, 0, 1, NULL, (LPBITMAPINFO) dib_hdr, DIB_RGB_COLORS);
slouken@0
   420
    GetDIBits(hdc, hbm, 0, 1, NULL, (LPBITMAPINFO) dib_hdr, DIB_RGB_COLORS);
slouken@0
   421
    DeleteObject(hbm);
slouken@0
   422
    ReleaseDC(NULL, hdc);
slouken@0
   423
slouken@0
   424
    switch( dib_hdr->biBitCount )
slouken@0
   425
    {
slouken@0
   426
    case 8:     return 8;
slouken@0
   427
    case 24:    return 24;
slouken@0
   428
    case 32:    return 32;
slouken@0
   429
    case 16:
slouken@0
   430
        if( dib_hdr->biCompression == BI_BITFIELDS ) {
slouken@0
   431
            /* check the red mask */
slouken@0
   432
            switch( ((DWORD*)((char*)dib_hdr + dib_hdr->biSize))[0] ) {
slouken@0
   433
                case 0xf800: return 16;    /* 565 */
slouken@0
   434
                case 0x7c00: return 15;    /* 555 */
slouken@0
   435
            }
slouken@0
   436
        }
slouken@0
   437
    }
slouken@0
   438
    return 0;    /* poo. */
slouken@0
   439
#endif /* NO_GETDIBITS */
slouken@0
   440
}
slouken@0
   441
slouken@0
   442
slouken@0
   443
/* Various screen update functions available */
slouken@0
   444
static void DIB_NormalUpdate(_THIS, int numrects, SDL_Rect *rects);
slouken@0
   445
slouken@0
   446
SDL_Surface *DIB_SetVideoMode(_THIS, SDL_Surface *current,
slouken@0
   447
				int width, int height, int bpp, Uint32 flags)
slouken@0
   448
{
slouken@0
   449
	SDL_Surface *video;
slouken@0
   450
	Uint32 prev_flags;
slouken@0
   451
	DWORD style;
slouken@0
   452
	const DWORD directstyle =
slouken@0
   453
			(WS_POPUP);
slouken@0
   454
	const DWORD windowstyle = 
slouken@0
   455
			(WS_OVERLAPPED|WS_CAPTION|WS_SYSMENU|WS_MINIMIZEBOX);
slouken@0
   456
	const DWORD resizestyle =
slouken@0
   457
			(WS_THICKFRAME|WS_MAXIMIZEBOX);
slouken@0
   458
	int binfo_size;
slouken@0
   459
	BITMAPINFO *binfo;
slouken@0
   460
	HDC hdc;
slouken@0
   461
	RECT bounds;
slouken@0
   462
	int x, y;
slouken@0
   463
	BOOL was_visible;
slouken@0
   464
	Uint32 Rmask, Gmask, Bmask;
slouken@0
   465
slouken@0
   466
	/* See whether or not we should center the window */
slouken@0
   467
	was_visible = IsWindowVisible(SDL_Window);
slouken@0
   468
slouken@0
   469
	/* Clean up any GL context that may be hanging around */
slouken@0
   470
	if ( current->flags & SDL_OPENGL ) {
slouken@0
   471
		WIN_GL_ShutDown(this);
slouken@0
   472
	}
slouken@0
   473
slouken@0
   474
	/* Recalculate the bitmasks if necessary */
slouken@0
   475
	if ( bpp == current->format->BitsPerPixel ) {
slouken@0
   476
		video = current;
slouken@0
   477
	} else {
slouken@0
   478
		switch (bpp) {
slouken@0
   479
			case 15:
slouken@0
   480
			case 16:
slouken@0
   481
				if ( DIB_SussScreenDepth() == 15 ) {
slouken@0
   482
					/* 5-5-5 */
slouken@0
   483
					Rmask = 0x00007c00;
slouken@0
   484
					Gmask = 0x000003e0;
slouken@0
   485
					Bmask = 0x0000001f;
slouken@0
   486
				} else {
slouken@0
   487
					/* 5-6-5 */
slouken@0
   488
					Rmask = 0x0000f800;
slouken@0
   489
					Gmask = 0x000007e0;
slouken@0
   490
					Bmask = 0x0000001f;
slouken@0
   491
				}
slouken@0
   492
				break;
slouken@0
   493
			case 24:
slouken@0
   494
			case 32:
slouken@0
   495
				/* GDI defined as 8-8-8 */
slouken@0
   496
				Rmask = 0x00ff0000;
slouken@0
   497
				Gmask = 0x0000ff00;
slouken@0
   498
				Bmask = 0x000000ff;
slouken@0
   499
				break;
slouken@0
   500
			default:
slouken@0
   501
				Rmask = 0x00000000;
slouken@0
   502
				Gmask = 0x00000000;
slouken@0
   503
				Bmask = 0x00000000;
slouken@0
   504
				break;
slouken@0
   505
		}
slouken@0
   506
		video = SDL_CreateRGBSurface(SDL_SWSURFACE,
slouken@0
   507
					0, 0, bpp, Rmask, Gmask, Bmask, 0);
slouken@0
   508
		if ( video == NULL ) {
slouken@0
   509
			SDL_OutOfMemory();
slouken@0
   510
			return(NULL);
slouken@0
   511
		}
slouken@0
   512
	}
slouken@0
   513
slouken@0
   514
	/* Fill in part of the video surface */
slouken@0
   515
	prev_flags = video->flags;
slouken@0
   516
	video->flags = 0;	/* Clear flags */
slouken@0
   517
	video->w = width;
slouken@0
   518
	video->h = height;
slouken@0
   519
	video->pitch = SDL_CalculatePitch(video);
slouken@0
   520
slouken@515
   521
#ifdef WIN32_PLATFORM_PSPC
slouken@514
   522
	 /* Stuff to hide that $#!^%#$ WinCE taskbar in fullscreen... */
slouken@514
   523
	if ( flags & SDL_FULLSCREEN ) {
slouken@514
   524
		if ( !(prev_flags & SDL_FULLSCREEN) ) {
slouken@514
   525
			SHFullScreen(SDL_Window, SHFS_HIDETASKBAR);
slouken@514
   526
			SHFullScreen(SDL_Window, SHFS_HIDESIPBUTTON);
slouken@514
   527
			ShowWindow(FindWindow(TEXT("HHTaskBar"),NULL),SW_HIDE);
slouken@514
   528
		}
slouken@514
   529
		video->flags |= SDL_FULLSCREEN;
slouken@514
   530
	} else {
slouken@514
   531
		if ( prev_flags & SDL_FULLSCREEN ) {
slouken@514
   532
			SHFullScreen(SDL_Window, SHFS_SHOWTASKBAR);
slouken@514
   533
			SHFullScreen(SDL_Window, SHFS_SHOWSIPBUTTON);
slouken@514
   534
			ShowWindow(FindWindow(TEXT("HHTaskBar"),NULL),SW_SHOWNORMAL);
slouken@514
   535
		}
slouken@514
   536
	}
slouken@514
   537
#endif
slouken@0
   538
#ifndef NO_CHANGEDISPLAYSETTINGS
slouken@0
   539
	/* Set fullscreen mode if appropriate */
slouken@0
   540
	if ( (flags & SDL_FULLSCREEN) == SDL_FULLSCREEN ) {
slouken@0
   541
		DEVMODE settings;
slouken@0
   542
slouken@0
   543
		memset(&settings, 0, sizeof(DEVMODE));
slouken@0
   544
		settings.dmSize = sizeof(DEVMODE);
slouken@0
   545
		settings.dmBitsPerPel = video->format->BitsPerPixel;
slouken@0
   546
		settings.dmPelsWidth = width;
slouken@0
   547
		settings.dmPelsHeight = height;
slouken@0
   548
		settings.dmFields = DM_PELSWIDTH | DM_PELSHEIGHT | DM_BITSPERPEL;
slouken@0
   549
		if ( ChangeDisplaySettings(&settings, CDS_FULLSCREEN) == DISP_CHANGE_SUCCESSFUL ) {
slouken@0
   550
			video->flags |= SDL_FULLSCREEN;
slouken@304
   551
			SDL_fullscreen_mode = settings;
slouken@0
   552
		}
slouken@0
   553
	}
slouken@0
   554
#endif /* !NO_CHANGEDISPLAYSETTINGS */
slouken@0
   555
slouken@45
   556
	/* Reset the palette and create a new one if necessary */
slouken@45
   557
	if ( screen_pal != NULL ) {
slouken@45
   558
	/*	RJR: March 28, 2000
slouken@45
   559
		delete identity palette if switching from a palettized mode */
slouken@45
   560
		DeleteObject(screen_pal);
slouken@45
   561
		screen_pal = NULL;
slouken@45
   562
	}
slouken@45
   563
	if ( bpp <= 8 )
slouken@45
   564
	{
slouken@45
   565
	/*	RJR: March 28, 2000
slouken@45
   566
		create identity palette switching to a palettized mode */
slouken@45
   567
		screen_pal = DIB_CreatePalette(bpp);
slouken@45
   568
	}
slouken@45
   569
slouken@0
   570
	style = GetWindowLong(SDL_Window, GWL_STYLE);
slouken@0
   571
	style &= ~(resizestyle|WS_MAXIMIZE);
slouken@0
   572
	if ( (video->flags & SDL_FULLSCREEN) == SDL_FULLSCREEN ) {
slouken@0
   573
		style &= ~windowstyle;
slouken@0
   574
		style |= directstyle;
slouken@0
   575
	} else {
slouken@0
   576
#ifndef NO_CHANGEDISPLAYSETTINGS
slouken@0
   577
		if ( (prev_flags & SDL_FULLSCREEN) == SDL_FULLSCREEN ) {
slouken@0
   578
			ChangeDisplaySettings(NULL, 0);
slouken@0
   579
		}
slouken@0
   580
#endif
slouken@0
   581
		if ( flags & SDL_NOFRAME ) {
slouken@0
   582
			style &= ~windowstyle;
slouken@0
   583
			style |= directstyle;
slouken@0
   584
			video->flags |= SDL_NOFRAME;
slouken@0
   585
		} else {
slouken@0
   586
			style &= ~directstyle;
slouken@0
   587
			style |= windowstyle;
slouken@0
   588
			if ( flags & SDL_RESIZABLE ) {
slouken@0
   589
				style |= resizestyle;
slouken@0
   590
				video->flags |= SDL_RESIZABLE;
slouken@0
   591
			}
slouken@0
   592
		}
slouken@453
   593
#if WS_MAXIMIZE
slouken@0
   594
		if (IsZoomed(SDL_Window)) style |= WS_MAXIMIZE;
slouken@36
   595
#endif
slouken@0
   596
	}
slouken@145
   597
slouken@448
   598
	/* DJM: Don't piss of anyone who has setup his own window */
slouken@448
   599
	if (!SDL_windowid)
slouken@448
   600
		SetWindowLong(SDL_Window, GWL_STYLE, style);
slouken@0
   601
slouken@0
   602
	/* Delete the old bitmap if necessary */
slouken@0
   603
	if ( screen_bmp != NULL ) {
slouken@0
   604
		DeleteObject(screen_bmp);
slouken@0
   605
	}
slouken@0
   606
	if ( ! (flags & SDL_OPENGL) ) {
slouken@0
   607
		BOOL is16bitmode = (video->format->BytesPerPixel == 2);
slouken@0
   608
slouken@0
   609
		/* Suss out the bitmap info header */
slouken@0
   610
		binfo_size = sizeof(*binfo);
slouken@0
   611
		if( is16bitmode ) {
slouken@0
   612
			/* 16bit modes, palette area used for rgb bitmasks */
slouken@0
   613
			binfo_size += 3*sizeof(DWORD);
slouken@0
   614
		} else if ( video->format->palette ) {
slouken@0
   615
			binfo_size += video->format->palette->ncolors *
slouken@0
   616
							sizeof(RGBQUAD);
slouken@0
   617
		}
slouken@0
   618
		binfo = (BITMAPINFO *)malloc(binfo_size);
slouken@0
   619
		if ( ! binfo ) {
slouken@0
   620
			if ( video != current ) {
slouken@0
   621
				SDL_FreeSurface(video);
slouken@0
   622
			}
slouken@0
   623
			SDL_OutOfMemory();
slouken@0
   624
			return(NULL);
slouken@0
   625
		}
slouken@0
   626
slouken@0
   627
		binfo->bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
slouken@0
   628
		binfo->bmiHeader.biWidth = video->w;
slouken@0
   629
		binfo->bmiHeader.biHeight = -video->h;	/* -ve for topdown bitmap */
slouken@0
   630
		binfo->bmiHeader.biPlanes = 1;
slouken@0
   631
		binfo->bmiHeader.biSizeImage = video->h * video->pitch;
slouken@0
   632
		binfo->bmiHeader.biXPelsPerMeter = 0;
slouken@0
   633
		binfo->bmiHeader.biYPelsPerMeter = 0;
slouken@0
   634
		binfo->bmiHeader.biClrUsed = 0;
slouken@0
   635
		binfo->bmiHeader.biClrImportant = 0;
slouken@0
   636
		binfo->bmiHeader.biBitCount = video->format->BitsPerPixel;
slouken@0
   637
slouken@0
   638
		if ( is16bitmode ) {
slouken@0
   639
			/* BI_BITFIELDS tells CreateDIBSection about the rgb masks in the palette */
slouken@0
   640
			binfo->bmiHeader.biCompression = BI_BITFIELDS;
slouken@0
   641
			((Uint32*)binfo->bmiColors)[0] = video->format->Rmask;
slouken@0
   642
			((Uint32*)binfo->bmiColors)[1] = video->format->Gmask;
slouken@0
   643
			((Uint32*)binfo->bmiColors)[2] = video->format->Bmask;
slouken@0
   644
		} else {
slouken@0
   645
			binfo->bmiHeader.biCompression = BI_RGB;	/* BI_BITFIELDS for 565 vs 555 */
slouken@0
   646
			if ( video->format->palette ) {
slouken@0
   647
				memset(binfo->bmiColors, 0,
slouken@0
   648
					video->format->palette->ncolors*sizeof(RGBQUAD));
slouken@0
   649
			}
slouken@0
   650
		}
slouken@0
   651
slouken@0
   652
		/* Create the offscreen bitmap buffer */
slouken@0
   653
		hdc = GetDC(SDL_Window);
slouken@0
   654
		screen_bmp = CreateDIBSection(hdc, binfo, DIB_RGB_COLORS,
slouken@0
   655
					(void **)(&video->pixels), NULL, 0);
slouken@0
   656
		ReleaseDC(SDL_Window, hdc);
slouken@0
   657
		free(binfo);
slouken@0
   658
		if ( screen_bmp == NULL ) {
slouken@0
   659
			if ( video != current ) {
slouken@0
   660
				SDL_FreeSurface(video);
slouken@0
   661
			}
slouken@0
   662
			SDL_SetError("Couldn't create DIB section");
slouken@0
   663
			return(NULL);
slouken@0
   664
		}
slouken@0
   665
		this->UpdateRects = DIB_NormalUpdate;
slouken@0
   666
slouken@0
   667
		/* Set video surface flags */
slouken@0
   668
		if ( bpp <= 8 ) {
slouken@0
   669
			/* BitBlt() maps colors for us */
slouken@0
   670
			video->flags |= SDL_HWPALETTE;
slouken@0
   671
		}
slouken@0
   672
	}
slouken@0
   673
slouken@0
   674
	/* Resize the window */
slouken@0
   675
	if ( SDL_windowid == NULL ) {
slouken@448
   676
		HWND top;
slouken@0
   677
		UINT swp_flags;
slouken@0
   678
slouken@0
   679
		SDL_resizing = 1;
slouken@0
   680
		bounds.left = 0;
slouken@0
   681
		bounds.top = 0;
slouken@0
   682
		bounds.right = video->w;
slouken@0
   683
		bounds.bottom = video->h;
slouken@453
   684
		AdjustWindowRectEx(&bounds, GetWindowLong(SDL_Window, GWL_STYLE), FALSE, 0);
slouken@0
   685
		width = bounds.right-bounds.left;
slouken@0
   686
		height = bounds.bottom-bounds.top;
slouken@0
   687
		x = (GetSystemMetrics(SM_CXSCREEN)-width)/2;
slouken@0
   688
		y = (GetSystemMetrics(SM_CYSCREEN)-height)/2;
slouken@0
   689
		if ( y < 0 ) { /* Cover up title bar for more client area */
slouken@0
   690
			y -= GetSystemMetrics(SM_CYCAPTION)/2;
slouken@0
   691
		}
slouken@448
   692
		swp_flags = (SWP_NOCOPYBITS | SWP_FRAMECHANGED | SWP_SHOWWINDOW);
slouken@0
   693
		if ( was_visible && !(flags & SDL_FULLSCREEN) ) {
slouken@0
   694
			swp_flags |= SWP_NOMOVE;
slouken@0
   695
		}
slouken@448
   696
		if ( flags & SDL_FULLSCREEN ) {
slouken@448
   697
			top = HWND_TOPMOST;
slouken@448
   698
		} else {
slouken@448
   699
			top = HWND_NOTOPMOST;
slouken@448
   700
		}
slouken@448
   701
		SetWindowPos(SDL_Window, top, x, y, width, height, swp_flags);
slouken@0
   702
		SDL_resizing = 0;
slouken@0
   703
		SetForegroundWindow(SDL_Window);
slouken@0
   704
	}
slouken@0
   705
slouken@0
   706
	/* Set up for OpenGL */
slouken@0
   707
	if ( flags & SDL_OPENGL ) {
slouken@0
   708
		if ( WIN_GL_SetupWindow(this) < 0 ) {
slouken@0
   709
			return(NULL);
slouken@0
   710
		}
slouken@0
   711
		video->flags |= SDL_OPENGL;
slouken@0
   712
	}
slouken@36
   713
slouken@0
   714
	/* We're live! */
slouken@0
   715
	return(video);
slouken@0
   716
}
slouken@0
   717
slouken@0
   718
/* We don't actually allow hardware surfaces in the DIB driver */
slouken@0
   719
static int DIB_AllocHWSurface(_THIS, SDL_Surface *surface)
slouken@0
   720
{
slouken@0
   721
	return(-1);
slouken@0
   722
}
slouken@0
   723
static void DIB_FreeHWSurface(_THIS, SDL_Surface *surface)
slouken@0
   724
{
slouken@0
   725
	return;
slouken@0
   726
}
slouken@0
   727
static int DIB_LockHWSurface(_THIS, SDL_Surface *surface)
slouken@0
   728
{
slouken@0
   729
	return(0);
slouken@0
   730
}
slouken@0
   731
static void DIB_UnlockHWSurface(_THIS, SDL_Surface *surface)
slouken@0
   732
{
slouken@0
   733
	return;
slouken@0
   734
}
slouken@0
   735
slouken@0
   736
static void DIB_NormalUpdate(_THIS, int numrects, SDL_Rect *rects)
slouken@0
   737
{
slouken@0
   738
	HDC hdc, mdc;
slouken@0
   739
	int i;
slouken@0
   740
slouken@0
   741
	hdc = GetDC(SDL_Window);
slouken@0
   742
	if ( screen_pal ) {
slouken@0
   743
		SelectPalette(hdc, screen_pal, FALSE);
slouken@0
   744
	}
slouken@0
   745
	mdc = CreateCompatibleDC(hdc);
slouken@0
   746
	SelectObject(mdc, screen_bmp);
slouken@0
   747
	for ( i=0; i<numrects; ++i ) {
slouken@0
   748
		BitBlt(hdc, rects[i].x, rects[i].y, rects[i].w, rects[i].h,
slouken@0
   749
					mdc, rects[i].x, rects[i].y, SRCCOPY);
slouken@0
   750
	}
slouken@0
   751
	DeleteDC(mdc);
slouken@0
   752
	ReleaseDC(SDL_Window, hdc);
slouken@0
   753
}
slouken@0
   754
slouken@0
   755
int DIB_SetColors(_THIS, int firstcolor, int ncolors, SDL_Color *colors)
slouken@0
   756
{
slouken@0
   757
	RGBQUAD *pal;
slouken@0
   758
	int i;
slouken@36
   759
#ifndef _WIN32_WCE
slouken@0
   760
	HDC hdc, mdc;
slouken@36
   761
#else
slouken@36
   762
	HDC hdc;
slouken@36
   763
#endif
slouken@0
   764
slouken@0
   765
	/* Update the display palette */
slouken@0
   766
	hdc = GetDC(SDL_Window);
slouken@0
   767
	if ( screen_pal ) {
slouken@0
   768
		PALETTEENTRY *entries;
slouken@0
   769
slouken@0
   770
		entries = (PALETTEENTRY *)alloca(ncolors*sizeof(PALETTEENTRY));
slouken@0
   771
		for ( i=0; i<ncolors; ++i ) {
slouken@0
   772
			entries[i].peRed   = colors[i].r;
slouken@0
   773
			entries[i].peGreen = colors[i].g;
slouken@0
   774
			entries[i].peBlue  = colors[i].b;
slouken@0
   775
			entries[i].peFlags = PC_NOCOLLAPSE;
slouken@0
   776
		}
slouken@0
   777
		SetPaletteEntries(screen_pal, firstcolor, ncolors, entries);
slouken@0
   778
		SelectPalette(hdc, screen_pal, FALSE);
slouken@0
   779
		RealizePalette(hdc);
slouken@0
   780
	}
slouken@0
   781
slouken@0
   782
	/* Copy palette colors into DIB palette */
slouken@0
   783
	pal = (RGBQUAD *)alloca(ncolors*sizeof(RGBQUAD));
slouken@0
   784
	for ( i=0; i<ncolors; ++i ) {
slouken@0
   785
		pal[i].rgbRed = colors[i].r;
slouken@0
   786
		pal[i].rgbGreen = colors[i].g;
slouken@0
   787
		pal[i].rgbBlue = colors[i].b;
slouken@0
   788
		pal[i].rgbReserved = 0;
slouken@0
   789
	}
slouken@0
   790
slouken@0
   791
	/* Set the DIB palette and update the display */
slouken@36
   792
#ifndef _WIN32_WCE
slouken@0
   793
	mdc = CreateCompatibleDC(hdc);
slouken@0
   794
	SelectObject(mdc, screen_bmp);
slouken@0
   795
	SetDIBColorTable(mdc, firstcolor, ncolors, pal);
slouken@0
   796
	BitBlt(hdc, 0, 0, this->screen->w, this->screen->h,
slouken@0
   797
	       mdc, 0, 0, SRCCOPY);
slouken@0
   798
	DeleteDC(mdc);
slouken@36
   799
#endif
slouken@0
   800
	ReleaseDC(SDL_Window, hdc);
slouken@0
   801
	return(1);
slouken@0
   802
}
slouken@0
   803
slouken@0
   804
static void DIB_CheckGamma(_THIS)
slouken@0
   805
{
slouken@0
   806
#ifndef NO_GAMMA_SUPPORT
slouken@0
   807
	HDC hdc;
slouken@0
   808
	WORD ramp[3*256];
slouken@0
   809
slouken@0
   810
	/* If we fail to get gamma, disable gamma control */
slouken@0
   811
	hdc = GetDC(SDL_Window);
slouken@0
   812
	if ( ! GetDeviceGammaRamp(hdc, ramp) ) {
slouken@0
   813
		this->GetGammaRamp = NULL;
slouken@0
   814
		this->SetGammaRamp = NULL;
slouken@0
   815
	}
slouken@0
   816
	ReleaseDC(SDL_Window, hdc);
slouken@0
   817
#endif /* !NO_GAMMA_SUPPORT */
slouken@0
   818
}
slouken@338
   819
void DIB_SwapGamma(_THIS)
slouken@0
   820
{
slouken@0
   821
#ifndef NO_GAMMA_SUPPORT
slouken@0
   822
	HDC hdc;
slouken@0
   823
slouken@0
   824
	if ( gamma_saved ) {
slouken@0
   825
		hdc = GetDC(SDL_Window);
slouken@0
   826
		if ( SDL_GetAppState() & SDL_APPINPUTFOCUS ) {
slouken@0
   827
			/* About to leave active state, restore gamma */
slouken@0
   828
			SetDeviceGammaRamp(hdc, gamma_saved);
slouken@0
   829
		} else {
slouken@0
   830
			/* About to enter active state, set game gamma */
slouken@0
   831
			GetDeviceGammaRamp(hdc, gamma_saved);
slouken@0
   832
			SetDeviceGammaRamp(hdc, this->gamma);
slouken@0
   833
		}
slouken@0
   834
		ReleaseDC(SDL_Window, hdc);
slouken@0
   835
	}
slouken@0
   836
#endif /* !NO_GAMMA_SUPPORT */
slouken@0
   837
}
slouken@338
   838
void DIB_QuitGamma(_THIS)
slouken@0
   839
{
slouken@0
   840
#ifndef NO_GAMMA_SUPPORT
slouken@0
   841
	if ( gamma_saved ) {
slouken@0
   842
		/* Restore the original gamma if necessary */
slouken@0
   843
		if ( SDL_GetAppState() & SDL_APPINPUTFOCUS ) {
slouken@0
   844
			HDC hdc;
slouken@0
   845
slouken@0
   846
			hdc = GetDC(SDL_Window);
slouken@0
   847
			SetDeviceGammaRamp(hdc, gamma_saved);
slouken@0
   848
			ReleaseDC(SDL_Window, hdc);
slouken@0
   849
		}
slouken@0
   850
slouken@0
   851
		/* Free the saved gamma memory */
slouken@0
   852
		free(gamma_saved);
slouken@0
   853
		gamma_saved = 0;
slouken@0
   854
	}
slouken@0
   855
#endif /* !NO_GAMMA_SUPPORT */
slouken@0
   856
}
slouken@0
   857
slouken@338
   858
int DIB_SetGammaRamp(_THIS, Uint16 *ramp)
slouken@0
   859
{
slouken@338
   860
#ifdef NO_GAMMA_SUPPORT
slouken@338
   861
	SDL_SetError("SDL compiled without gamma ramp support");
slouken@338
   862
	return -1;
slouken@338
   863
#else
slouken@0
   864
	HDC hdc;
slouken@0
   865
	BOOL succeeded;
slouken@0
   866
slouken@0
   867
	/* Set the ramp for the display */
slouken@0
   868
	if ( ! gamma_saved ) {
slouken@0
   869
		gamma_saved = (WORD *)malloc(3*256*sizeof(*gamma_saved));
slouken@0
   870
		if ( ! gamma_saved ) {
slouken@0
   871
			SDL_OutOfMemory();
slouken@0
   872
			return -1;
slouken@0
   873
		}
slouken@0
   874
		hdc = GetDC(SDL_Window);
slouken@0
   875
		GetDeviceGammaRamp(hdc, gamma_saved);
slouken@0
   876
		ReleaseDC(SDL_Window, hdc);
slouken@0
   877
	}
slouken@0
   878
	if ( SDL_GetAppState() & SDL_APPINPUTFOCUS ) {
slouken@0
   879
		hdc = GetDC(SDL_Window);
slouken@0
   880
		succeeded = SetDeviceGammaRamp(hdc, ramp);
slouken@0
   881
		ReleaseDC(SDL_Window, hdc);
slouken@0
   882
	} else {
slouken@0
   883
		succeeded = TRUE;
slouken@0
   884
	}
slouken@0
   885
	return succeeded ? 0 : -1;
slouken@338
   886
#endif /* !NO_GAMMA_SUPPORT */
slouken@0
   887
}
slouken@0
   888
slouken@338
   889
int DIB_GetGammaRamp(_THIS, Uint16 *ramp)
slouken@0
   890
{
slouken@338
   891
#ifdef NO_GAMMA_SUPPORT
slouken@338
   892
	SDL_SetError("SDL compiled without gamma ramp support");
slouken@338
   893
	return -1;
slouken@338
   894
#else
slouken@0
   895
	HDC hdc;
slouken@0
   896
	BOOL succeeded;
slouken@0
   897
slouken@0
   898
	/* Get the ramp from the display */
slouken@0
   899
	hdc = GetDC(SDL_Window);
slouken@0
   900
	succeeded = GetDeviceGammaRamp(hdc, ramp);
slouken@0
   901
	ReleaseDC(SDL_Window, hdc);
slouken@0
   902
	return succeeded ? 0 : -1;
slouken@338
   903
#endif /* !NO_GAMMA_SUPPORT */
slouken@0
   904
}
slouken@0
   905
slouken@442
   906
static void FlushMessageQueue()
slouken@442
   907
{
slouken@442
   908
	MSG  msg;
slouken@442
   909
	while ( PeekMessage(&msg, NULL, 0, 0, PM_REMOVE) ) {
slouken@442
   910
		if ( msg.message == WM_QUIT ) break;
slouken@442
   911
		TranslateMessage( &msg );
slouken@442
   912
		DispatchMessage( &msg );
slouken@442
   913
	}
slouken@442
   914
}
slouken@442
   915
slouken@0
   916
void DIB_VideoQuit(_THIS)
slouken@0
   917
{
slouken@0
   918
	/* Destroy the window and everything associated with it */
slouken@0
   919
	if ( SDL_Window ) {
slouken@0
   920
		/* Delete the screen bitmap (also frees screen->pixels) */
slouken@0
   921
		if ( this->screen ) {
slouken@515
   922
#ifdef WIN32_PLATFORM_PSPC
slouken@515
   923
			if ( this->screen->flags & SDL_FULLSCREEN ) {
slouken@515
   924
				/* Unhide taskbar, etc. */
slouken@515
   925
				SHFullScreen(SDL_Window, SHFS_SHOWTASKBAR);
slouken@515
   926
				SHFullScreen(SDL_Window, SHFS_SHOWSIPBUTTON);
slouken@515
   927
				ShowWindow(FindWindow(TEXT("HHTaskBar"),NULL),SW_SHOWNORMAL);
slouken@515
   928
			}
slouken@515
   929
#endif
slouken@0
   930
#ifndef NO_CHANGEDISPLAYSETTINGS
slouken@0
   931
			if ( this->screen->flags & SDL_FULLSCREEN ) {
slouken@0
   932
				ChangeDisplaySettings(NULL, 0);
slouken@376
   933
				ShowWindow(SDL_Window, SW_HIDE);
slouken@0
   934
			}
slouken@0
   935
#endif
slouken@0
   936
			if ( this->screen->flags & SDL_OPENGL ) {
slouken@0
   937
				WIN_GL_ShutDown(this);
slouken@0
   938
			}
slouken@0
   939
			this->screen->pixels = NULL;
slouken@0
   940
		}
slouken@0
   941
		if ( screen_bmp ) {
slouken@0
   942
			DeleteObject(screen_bmp);
slouken@0
   943
			screen_bmp = NULL;
slouken@0
   944
		}
slouken@0
   945
		if ( screen_icn ) {
slouken@0
   946
			DestroyIcon(screen_icn);
slouken@0
   947
			screen_icn = NULL;
slouken@0
   948
		}
slouken@0
   949
		DIB_QuitGamma(this);
slouken@0
   950
		DIB_DestroyWindow(this);
slouken@442
   951
		FlushMessageQueue();
slouken@0
   952
slouken@0
   953
		SDL_Window = NULL;
slouken@0
   954
	}
slouken@0
   955
}
slouken@0
   956
slouken@0
   957
/* Exported for the windows message loop only */
slouken@0
   958
static void DIB_FocusPalette(_THIS, int foreground)
slouken@0
   959
{
slouken@0
   960
	if ( screen_pal != NULL ) {
slouken@0
   961
		HDC hdc;
slouken@0
   962
slouken@0
   963
		hdc = GetDC(SDL_Window);
slouken@0
   964
		SelectPalette(hdc, screen_pal, FALSE);
slouken@0
   965
		if ( RealizePalette(hdc) )
slouken@0
   966
			InvalidateRect(SDL_Window, NULL, FALSE);
slouken@0
   967
		ReleaseDC(SDL_Window, hdc);
slouken@0
   968
	}
slouken@0
   969
}
slouken@0
   970
static void DIB_RealizePalette(_THIS)
slouken@0
   971
{
slouken@0
   972
	DIB_FocusPalette(this, 1);
slouken@0
   973
}
slouken@0
   974
static void DIB_PaletteChanged(_THIS, HWND window)
slouken@0
   975
{
slouken@0
   976
	if ( window != SDL_Window ) {
slouken@0
   977
		DIB_FocusPalette(this, 0);
slouken@0
   978
	}
slouken@0
   979
}
slouken@0
   980
slouken@0
   981
/* Exported for the windows message loop only */
slouken@0
   982
static void DIB_WinPAINT(_THIS, HDC hdc)
slouken@0
   983
{
slouken@0
   984
	HDC mdc;
slouken@0
   985
slouken@0
   986
	if ( screen_pal ) {
slouken@0
   987
		SelectPalette(hdc, screen_pal, FALSE);
slouken@0
   988
	}
slouken@0
   989
	mdc = CreateCompatibleDC(hdc);
slouken@0
   990
	SelectObject(mdc, screen_bmp);
slouken@0
   991
	BitBlt(hdc, 0, 0, SDL_VideoSurface->w, SDL_VideoSurface->h,
slouken@0
   992
							mdc, 0, 0, SRCCOPY);
slouken@0
   993
	DeleteDC(mdc);
slouken@0
   994
}
slouken@0
   995
slouken@0
   996
/* Stub in case DirectX isn't available */
slouken@0
   997
#ifndef ENABLE_DIRECTX
slouken@0
   998
void DX5_SoundFocus(HWND hwnd)
slouken@0
   999
{
slouken@0
  1000
	return;
slouken@0
  1001
}
slouken@0
  1002
#endif