Annotation of quake2/win32/rw_dib.c, revision 1.1.1.2

1.1       root        1: /*
1.1.1.2 ! root        2: Copyright (C) 1997-2001 Id Software, Inc.
        !             3: 
        !             4: This program is free software; you can redistribute it and/or
        !             5: modify it under the terms of the GNU General Public License
        !             6: as published by the Free Software Foundation; either version 2
        !             7: of the License, or (at your option) any later version.
        !             8: 
        !             9: This program is distributed in the hope that it will be useful,
        !            10: but WITHOUT ANY WARRANTY; without even the implied warranty of
        !            11: MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  
        !            12: 
        !            13: See the GNU General Public License for more details.
        !            14: 
        !            15: You should have received a copy of the GNU General Public License
        !            16: along with this program; if not, write to the Free Software
        !            17: Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
        !            18: 
        !            19: */
        !            20: /*
1.1       root       21: ** RW_DIB.C
                     22: **
                     23: ** This handles DIB section management under Windows.
                     24: **
                     25: */
                     26: #include "..\ref_soft\r_local.h"
                     27: #include "rw_win.h"
                     28: 
                     29: #ifndef _WIN32
                     30: #  error You should not be trying to compile this file on this platform
                     31: #endif
                     32: 
                     33: static qboolean s_systemcolors_saved;
                     34: 
                     35: static HGDIOBJ previously_selected_GDI_obj;
                     36: 
                     37: static int s_syspalindices[] = 
                     38: {
                     39:   COLOR_ACTIVEBORDER,
                     40:   COLOR_ACTIVECAPTION,
                     41:   COLOR_APPWORKSPACE,
                     42:   COLOR_BACKGROUND,
                     43:   COLOR_BTNFACE,
                     44:   COLOR_BTNSHADOW,
                     45:   COLOR_BTNTEXT,
                     46:   COLOR_CAPTIONTEXT,
                     47:   COLOR_GRAYTEXT,
                     48:   COLOR_HIGHLIGHT,
                     49:   COLOR_HIGHLIGHTTEXT,
                     50:   COLOR_INACTIVEBORDER,
                     51: 
                     52:   COLOR_INACTIVECAPTION,
                     53:   COLOR_MENU,
                     54:   COLOR_MENUTEXT,
                     55:   COLOR_SCROLLBAR,
                     56:   COLOR_WINDOW,
                     57:   COLOR_WINDOWFRAME,
                     58:   COLOR_WINDOWTEXT
                     59: };
                     60: 
                     61: #define NUM_SYS_COLORS ( sizeof( s_syspalindices ) / sizeof( int ) )
                     62: 
                     63: static int s_oldsyscolors[NUM_SYS_COLORS];
                     64: 
                     65: typedef struct dibinfo
                     66: {
                     67:        BITMAPINFOHEADER        header;
                     68:        RGBQUAD                         acolors[256];
                     69: } dibinfo_t;
                     70: 
                     71: typedef struct
                     72: {
                     73:        WORD palVersion;
                     74:        WORD palNumEntries;
                     75:        PALETTEENTRY palEntries[256];
                     76: } identitypalette_t;
                     77: 
                     78: static identitypalette_t s_ipal;
                     79: 
                     80: static void DIB_SaveSystemColors( void );
                     81: static void DIB_RestoreSystemColors( void );
                     82: 
                     83: /*
                     84: ** DIB_Init
                     85: **
                     86: ** Builds our DIB section
                     87: */
                     88: qboolean DIB_Init( unsigned char **ppbuffer, int *ppitch )
                     89: {
                     90:        dibinfo_t   dibheader;
                     91:        BITMAPINFO *pbmiDIB = ( BITMAPINFO * ) &dibheader;
                     92:        int i;
                     93: 
                     94:        memset( &dibheader, 0, sizeof( dibheader ) );
                     95: 
                     96:        /*
                     97:        ** grab a DC
                     98:        */
                     99:        if ( !sww_state.hDC )
                    100:        {
                    101:                if ( ( sww_state.hDC = GetDC( sww_state.hWnd ) ) == NULL )
                    102:                        return false;
                    103:        }
                    104: 
                    105:        /*
                    106:        ** figure out if we're running in an 8-bit display mode
                    107:        */
                    108:        if ( GetDeviceCaps( sww_state.hDC, RASTERCAPS ) & RC_PALETTE )
                    109:        {
                    110:                sww_state.palettized = true;
                    111: 
                    112:                // save system colors
                    113:                if ( !s_systemcolors_saved )
                    114:                {
                    115:                        DIB_SaveSystemColors();
                    116:                        s_systemcolors_saved = true;
                    117:                }
                    118:        }
                    119:        else
                    120:        {
                    121:                sww_state.palettized = false;
                    122:        }
                    123: 
                    124:        /*
                    125:        ** fill in the BITMAPINFO struct
                    126:        */
                    127:        pbmiDIB->bmiHeader.biSize          = sizeof(BITMAPINFOHEADER);
                    128:        pbmiDIB->bmiHeader.biWidth         = vid.width;
                    129:        pbmiDIB->bmiHeader.biHeight        = vid.height;
                    130:        pbmiDIB->bmiHeader.biPlanes        = 1;
                    131:        pbmiDIB->bmiHeader.biBitCount      = 8;
                    132:        pbmiDIB->bmiHeader.biCompression   = BI_RGB;
                    133:        pbmiDIB->bmiHeader.biSizeImage     = 0;
                    134:        pbmiDIB->bmiHeader.biXPelsPerMeter = 0;
                    135:        pbmiDIB->bmiHeader.biYPelsPerMeter = 0;
                    136:        pbmiDIB->bmiHeader.biClrUsed       = 256;
                    137:        pbmiDIB->bmiHeader.biClrImportant  = 256;
                    138: 
                    139:        /*
                    140:        ** fill in the palette
                    141:        */
                    142:        for ( i = 0; i < 256; i++ )
                    143:        {
                    144:                dibheader.acolors[i].rgbRed   = ( d_8to24table[i] >> 0 )  & 0xff;
                    145:                dibheader.acolors[i].rgbGreen = ( d_8to24table[i] >> 8 )  & 0xff;
                    146:                dibheader.acolors[i].rgbBlue  = ( d_8to24table[i] >> 16 ) & 0xff;
                    147:        }
                    148: 
                    149:        /*
                    150:        ** create the DIB section
                    151:        */
                    152:        sww_state.hDIBSection = CreateDIBSection( sww_state.hDC,
                    153:                                                     pbmiDIB,
                    154:                                                                                         DIB_RGB_COLORS,
                    155:                                                                                         &sww_state.pDIBBase,
                    156:                                                                                         NULL,
                    157:                                                                                         0 );
                    158: 
                    159:        if ( sww_state.hDIBSection == NULL )
                    160:        {
                    161:                ri.Con_Printf( PRINT_ALL, "DIB_Init() - CreateDIBSection failed\n" );
                    162:                goto fail;
                    163:        }
                    164: 
                    165:        if ( pbmiDIB->bmiHeader.biHeight > 0 )
                    166:     {
                    167:                // bottom up
                    168:                *ppbuffer       = sww_state.pDIBBase + ( vid.height - 1 ) * vid.width;
                    169:                *ppitch         = -vid.width;
                    170:     }
                    171:     else
                    172:     {
                    173:                // top down
                    174:                *ppbuffer       = sww_state.pDIBBase;
                    175:                *ppitch         = vid.width;
                    176:     }
                    177: 
                    178:        /*
                    179:        ** clear the DIB memory buffer
                    180:        */
                    181:        memset( sww_state.pDIBBase, 0xff, vid.width * vid.height );
                    182: 
                    183:        if ( ( sww_state.hdcDIBSection = CreateCompatibleDC( sww_state.hDC ) ) == NULL )
                    184:        {
                    185:                ri.Con_Printf( PRINT_ALL, "DIB_Init() - CreateCompatibleDC failed\n" );
                    186:                goto fail;
                    187:        }
                    188:        if ( ( previously_selected_GDI_obj = SelectObject( sww_state.hdcDIBSection, sww_state.hDIBSection ) ) == NULL )
                    189:        {
                    190:                ri.Con_Printf( PRINT_ALL, "DIB_Init() - SelectObject failed\n" );
                    191:                goto fail;
                    192:        }
                    193: 
                    194:        return true;
                    195: 
                    196: fail:
                    197:        DIB_Shutdown();
                    198:        return false;
                    199:        
                    200: }
                    201: 
                    202: /*
                    203: ** DIB_SetPalette
                    204: **
                    205: ** Sets the color table in our DIB section, and also sets the system palette
                    206: ** into an identity mode if we're running in an 8-bit palettized display mode.
                    207: **
                    208: ** The palette is expected to be 1024 bytes, in the format:
                    209: **
                    210: ** R = offset 0
                    211: ** G = offset 1
                    212: ** B = offset 2
                    213: ** A = offset 3
                    214: */
                    215: void DIB_SetPalette( const unsigned char *_pal )
                    216: {
                    217:        const unsigned char *pal = _pal;
                    218:        LOGPALETTE              *pLogPal = ( LOGPALETTE * ) &s_ipal;
                    219:        RGBQUAD                 colors[256];
                    220:        int                             i;
                    221:        int                             ret;
                    222:        HDC                             hDC = sww_state.hDC;
                    223: 
                    224:        /*
                    225:        ** set the DIB color table
                    226:        */
                    227:        if ( sww_state.hdcDIBSection )
                    228:        {
                    229:                for ( i = 0; i < 256; i++, pal += 4 )
                    230:                {
                    231:                        colors[i].rgbRed   = pal[0];
                    232:                        colors[i].rgbGreen = pal[1];
                    233:                        colors[i].rgbBlue  = pal[2];
                    234:                        colors[i].rgbReserved = 0;
                    235:                }
                    236: 
                    237:                colors[0].rgbRed = 0;
                    238:                colors[0].rgbGreen = 0;
                    239:                colors[0].rgbBlue = 0;
                    240: 
                    241:                colors[255].rgbRed = 0xff;
                    242:                colors[255].rgbGreen = 0xff;
                    243:                colors[255].rgbBlue = 0xff;
                    244: 
                    245:                if ( SetDIBColorTable( sww_state.hdcDIBSection, 0, 256, colors ) == 0 )
                    246:                {
                    247:                        ri.Con_Printf( PRINT_ALL, "DIB_SetPalette() - SetDIBColorTable failed\n" );
                    248:                }
                    249:        }
                    250: 
                    251:        /*
                    252:        ** for 8-bit color desktop modes we set up the palette for maximum
                    253:        ** speed by going into an identity palette mode.
                    254:        */
                    255:        if ( sww_state.palettized )
                    256:        {
                    257:                int i;
                    258:                HPALETTE hpalOld;
                    259: 
                    260:                if ( SetSystemPaletteUse( hDC, SYSPAL_NOSTATIC ) == SYSPAL_ERROR )
                    261:                {
                    262:                        ri.Sys_Error( ERR_FATAL, "DIB_SetPalette() - SetSystemPaletteUse() failed\n" );
                    263:                }
                    264: 
                    265:                /*
                    266:                ** destroy our old palette
                    267:                */
                    268:                if ( sww_state.hPal )
                    269:                {
                    270:                        DeleteObject( sww_state.hPal );
                    271:                        sww_state.hPal = 0;
                    272:                }
                    273: 
                    274:                /*
                    275:                ** take up all physical palette entries to flush out anything that's currently
                    276:                ** in the palette
                    277:                */
                    278:                pLogPal->palVersion             = 0x300;
                    279:                pLogPal->palNumEntries  = 256;
                    280: 
                    281:                for ( i = 0, pal = _pal; i < 256; i++, pal += 4 )
                    282:                {
                    283:                        pLogPal->palPalEntry[i].peRed   = pal[0];
                    284:                        pLogPal->palPalEntry[i].peGreen = pal[1];
                    285:                        pLogPal->palPalEntry[i].peBlue  = pal[2];
                    286:                        pLogPal->palPalEntry[i].peFlags = PC_RESERVED | PC_NOCOLLAPSE;
                    287:                }
                    288:                pLogPal->palPalEntry[0].peRed           = 0;
                    289:                pLogPal->palPalEntry[0].peGreen         = 0;
                    290:                pLogPal->palPalEntry[0].peBlue          = 0;
                    291:                pLogPal->palPalEntry[0].peFlags         = 0;
                    292:                pLogPal->palPalEntry[255].peRed         = 0xff;
                    293:                pLogPal->palPalEntry[255].peGreen       = 0xff;
                    294:                pLogPal->palPalEntry[255].peBlue        = 0xff;
                    295:                pLogPal->palPalEntry[255].peFlags       = 0;
                    296: 
                    297:                if ( ( sww_state.hPal = CreatePalette( pLogPal ) ) == NULL )
                    298:                {
                    299:                        ri.Sys_Error( ERR_FATAL, "DIB_SetPalette() - CreatePalette failed(%x)\n", GetLastError() );
                    300:                }
                    301: 
                    302:                if ( ( hpalOld = SelectPalette( hDC, sww_state.hPal, FALSE ) ) == NULL )
                    303:                {
                    304:                        ri.Sys_Error( ERR_FATAL, "DIB_SetPalette() - SelectPalette failed(%x)\n",GetLastError() );
                    305:                }
                    306: 
                    307:                if ( sww_state.hpalOld == NULL )
                    308:                        sww_state.hpalOld = hpalOld;
                    309: 
                    310:                if ( ( ret = RealizePalette( hDC ) ) != pLogPal->palNumEntries ) 
                    311:                {
                    312:                        ri.Sys_Error( ERR_FATAL, "DIB_SetPalette() - RealizePalette set %d entries\n", ret );
                    313:                }
                    314:        }
                    315: }
                    316: 
                    317: /*
                    318: ** DIB_Shutdown
                    319: */
                    320: void DIB_Shutdown( void )
                    321: {
                    322:        if ( sww_state.palettized && s_systemcolors_saved )
                    323:                DIB_RestoreSystemColors();
                    324: 
                    325:        if ( sww_state.hPal )
                    326:        {
                    327:                DeleteObject( sww_state.hPal );
                    328:                sww_state.hPal = 0;
                    329:        }
                    330: 
                    331:        if ( sww_state.hpalOld )
                    332:        {
                    333:                SelectPalette( sww_state.hDC, sww_state.hpalOld, FALSE );
                    334:                RealizePalette( sww_state.hDC );
                    335:                sww_state.hpalOld = NULL;
                    336:        }
                    337: 
                    338:        if ( sww_state.hdcDIBSection )
                    339:        {
                    340:                SelectObject( sww_state.hdcDIBSection, previously_selected_GDI_obj );
                    341:                DeleteDC( sww_state.hdcDIBSection );
                    342:                sww_state.hdcDIBSection = NULL;
                    343:        }
                    344: 
                    345:        if ( sww_state.hDIBSection )
                    346:        {
                    347:                DeleteObject( sww_state.hDIBSection );
                    348:                sww_state.hDIBSection = NULL;
                    349:                sww_state.pDIBBase = NULL;
                    350:        }
                    351: 
                    352:        if ( sww_state.hDC )
                    353:        {
                    354:                ReleaseDC( sww_state.hWnd, sww_state.hDC );
                    355:                sww_state.hDC = 0;
                    356:        }
                    357: }
                    358: 
                    359: 
                    360: /*
                    361: ** DIB_Save/RestoreSystemColors
                    362: */
                    363: static void DIB_RestoreSystemColors( void )
                    364: {
                    365:     SetSystemPaletteUse( sww_state.hDC, SYSPAL_STATIC );
                    366:     SetSysColors( NUM_SYS_COLORS, s_syspalindices, s_oldsyscolors );
                    367: }
                    368: 
                    369: static void DIB_SaveSystemColors( void )
                    370: {
                    371:        int i;
                    372: 
                    373:        for ( i = 0; i < NUM_SYS_COLORS; i++ )
                    374:                s_oldsyscolors[i] = GetSysColor( s_syspalindices[i] );
                    375: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.