4 * Various freeglut initialization functions.
6 * Copyright (c) 1999-2000 Pawel W. Olszta. All Rights Reserved.
7 * Written by Pawel W. Olszta, <olszta@sourceforge.net>
8 * Creation date: Thu Dec 2 1999
10 * Permission is hereby granted, free of charge, to any person obtaining a
11 * copy of this software and associated documentation files (the "Software"),
12 * to deal in the Software without restriction, including without limitation
13 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
14 * and/or sell copies of the Software, and to permit persons to whom the
15 * Software is furnished to do so, subject to the following conditions:
17 * The above copyright notice and this permission notice shall be included
18 * in all copies or substantial portions of the Software.
20 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
21 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
22 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
23 * PAWEL W. OLSZTA BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
24 * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
25 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
32 #define G_LOG_DOMAIN "freeglut-init"
34 #include "../include/GL/freeglut.h"
35 #include "freeglut_internal.h"
38 * TODO BEFORE THE STABLE RELEASE:
40 * fgDeinitialize() -- Win32's OK, X11 needs the OS-specific
41 * deinitialization done
42 * glutInitDisplayString() -- display mode string parsing
44 * Wouldn't it be cool to use gettext() for error messages? I just love
45 * bash saying "nie znaleziono pliku" instead of "file not found" :)
46 * Is gettext easily portable?
49 /* -- GLOBAL VARIABLES ----------------------------------------------------- */
52 * A structure pointed by g_pDisplay holds all information
53 * regarding the display, screen, root window etc.
55 SFG_Display fgDisplay;
58 * The settings for the current freeglut session
60 SFG_State fgState = { { -1, -1, FALSE }, /* Position */
61 { 300, 300, TRUE }, /* Size */
62 GLUT_RGBA | GLUT_SINGLE | GLUT_DEPTH, /* DisplayMode */
63 FALSE, /* ForceDirectContext */
64 TRUE, /* TryDirectContext */
65 FALSE, /* ForceIconic */
66 FALSE, /* UseCurrentContext */
67 FALSE, /* GLDebugSwitch */
68 FALSE, /* XSyncSwitch */
69 TRUE, /* IgnoreKeyRepeat */
74 { 0, FALSE }, /* Time */
78 { NULL, NULL }, /* Timers */
79 NULL, /* IdleCallback */
80 FALSE, /* BuildingAMenu */
82 NULL, /* MenuStateCallback */
83 NULL, /* MenuStatusCallback */
84 { 640, 480, TRUE }, /* GameModeSize */
85 16, /* GameModeDepth */
86 72, /* GameModeRefresh */
87 GLUT_ACTION_EXIT, /* ActionOnWindowClose */
88 GLUT_EXEC_STATE_INIT /* ExecState */
92 /* -- PRIVATE FUNCTIONS ---------------------------------------------------- */
95 * A call to this function should initialize all the display stuff...
97 void fgInitialize( const char* displayName )
99 #if TARGET_HOST_UNIX_X11
100 fgDisplay.Display = XOpenDisplay( displayName );
102 if( fgDisplay.Display == NULL )
103 fgError( "failed to open display '%s'", XDisplayName( displayName ) );
105 if( !glXQueryExtension( fgDisplay.Display, NULL, NULL ) )
106 fgError( "OpenGL GLX extension not supported by display '%s'",
107 XDisplayName( displayName ) );
109 fgDisplay.Screen = DefaultScreen( fgDisplay.Display );
110 fgDisplay.RootWindow = RootWindow(
115 fgDisplay.ScreenWidth = DisplayWidth(
119 fgDisplay.ScreenHeight = DisplayHeight(
124 fgDisplay.ScreenWidthMM = DisplayWidthMM(
128 fgDisplay.ScreenHeightMM = DisplayHeightMM(
133 fgDisplay.Connection = ConnectionNumber( fgDisplay.Display );
136 * Create the window deletion atom
138 fgDisplay.DeleteWindow = XInternAtom(
144 #elif TARGET_HOST_WIN32
150 * What we need to do is to initialize the fgDisplay global structure here...
152 fgDisplay.Instance = GetModuleHandle( NULL );
154 atom = GetClassInfo( fgDisplay.Instance, "FREEGLUT", &wc );
157 ZeroMemory( &wc, sizeof(WNDCLASS) );
160 * Each of the windows should have its own device context...
163 wc.lpfnWndProc = fgWindowProc;
166 wc.hInstance = fgDisplay.Instance;
167 wc.hIcon = LoadIcon( fgDisplay.Instance, "GLUT_ICON" );
169 wc.hIcon = LoadIcon( NULL, IDI_WINLOGO );
171 wc.hCursor = LoadCursor( NULL, IDC_ARROW );
172 wc.hbrBackground = NULL;
173 wc.lpszMenuName = NULL;
174 wc.lpszClassName = "FREEGLUT";
177 * Register the window class
179 atom = RegisterClass( &wc );
184 * The screen dimensions can be obtained via GetSystemMetrics() calls
186 fgDisplay.ScreenWidth = GetSystemMetrics( SM_CXSCREEN );
187 fgDisplay.ScreenHeight = GetSystemMetrics( SM_CYSCREEN );
190 HWND desktop = GetDesktopWindow();
191 HDC context = GetDC( desktop );
193 fgDisplay.ScreenWidthMM = GetDeviceCaps( context, HORZSIZE );
194 fgDisplay.ScreenHeightMM = GetDeviceCaps( context, VERTSIZE );
196 ReleaseDC( desktop, context );
205 * Perform the freeglut deinitialization...
207 void fgDeinitialize( void )
211 if( !fgState.Time.Set )
213 fgWarning( "fgDeinitialize(): fgState.Timer is null => "
214 "no valid initialization has been performed" );
219 * If there was a menu created, destroy the rendering context
221 if( fgStructure.MenuContext )
223 free( fgStructure.MenuContext );
224 fgStructure.MenuContext = NULL;
227 fgDestroyStructure();
229 while( timer = (SFG_Timer *)fgState.Timers.First )
231 fgListRemove ( &fgState.Timers, &timer->Node );
237 fgState.Position.X = -1;
238 fgState.Position.Y = -1;
239 fgState.Position.Use = FALSE;
241 fgState.Size.X = 300;
242 fgState.Size.Y = 300;
243 fgState.Size.Use = TRUE;
245 fgState.DisplayMode = GLUT_RGBA | GLUT_SINGLE | GLUT_DEPTH;
247 fgState.ForceDirectContext = FALSE;
248 fgState.TryDirectContext = TRUE;
249 fgState.ForceIconic = FALSE;
250 fgState.UseCurrentContext = FALSE;
251 fgState.GLDebugSwitch = FALSE;
252 fgState.XSyncSwitch = FALSE;
253 fgState.ActionOnWindowClose = GLUT_ACTION_EXIT ;
254 fgState.ExecState = GLUT_EXEC_STATE_INIT ;
256 fgState.IgnoreKeyRepeat = TRUE;
258 fgState.GameModeSize.X = 640;
259 fgState.GameModeSize.Y = 480;
260 fgState.GameModeDepth = 16;
261 fgState.GameModeRefresh = 72;
263 fgState.Time.Set = FALSE;
265 fgState.Timers.First = fgState.Timers.Last = NULL;
266 fgState.IdleCallback = NULL;
267 fgState.MenuStateCallback = (FGCBmenuState)NULL;
268 fgState.MenuStatusCallback = (FGCBmenuStatus)NULL;
270 fgState.SwapCount = 0;
271 fgState.SwapTime = 0;
272 fgState.FPSInterval = 0;
274 if( fgState.ProgramName )
276 free( fgState.ProgramName );
277 fgState.ProgramName = NULL;
281 #if TARGET_HOST_UNIX_X11
284 * Make sure all X-client data we have created will be destroyed on
287 XSetCloseDownMode( fgDisplay.Display, DestroyAll );
290 * Close the display connection, destroying all windows we have
293 XCloseDisplay( fgDisplay.Display );
299 /* -- INTERFACE FUNCTIONS -------------------------------------------------- */
302 * Perform initialization. This usually happens on the program startup
303 * and restarting after glutMainLoop termination...
305 void FGAPIENTRY glutInit( int* pargc, char** argv )
307 char* displayName = NULL;
308 int i, j, argc = *pargc;
310 if (pargc && *pargc && argv && *argv && **argv)
311 fgState.ProgramName = strdup (*argv);
313 fgState.ProgramName = strdup ("");
314 if (!fgState.ProgramName)
315 fgError ("Could not allocate space for the program's name.");
317 if( fgState.Time.Set )
318 fgError( "illegal glutInit() reinitialization attemp" );
322 #if TARGET_HOST_UNIX_X11
323 gettimeofday(&fgState.Time.Value, NULL);
324 #elif TARGET_HOST_WIN32
325 fgState.Time.Value = timeGetTime();
327 fgState.Time.Set = TRUE;
329 /* check if GLUT_FPS env var is set */
331 const char *fps = getenv ( "GLUT_FPS" );
334 sscanf( fps, "%d", &fgState.FPSInterval );
335 if( fgState.FPSInterval <= 0 )
336 fgState.FPSInterval = 5000; /* 5000 milliseconds */
340 #if TARGET_HOST_WIN32
341 if( !getenv( "DISPLAY" ) )
342 displayName = strdup( "" );
345 displayName = strdup( getenv( "DISPLAY" ) );
347 fgError ("Could not allocate space for display name.");
349 for( i=1; i<argc; i++ )
351 if( strcmp( argv[ i ], "-display" ) == 0 )
354 fgError( "-display parameter must be followed by display name" );
358 displayName = strdup( argv[ i ] );
360 fgError( "Could not allocate space for display name (%s)",
363 argv[ i - 1 ] = NULL;
367 else if( strcmp( argv[ i ], "-geometry" ) == 0 )
373 fgError( "-geometry parameter must be followed by window "
374 "geometry settings" );
375 result = sscanf ( argv[i], "%dx%d+%d+%d", &x, &y, &w, &h );
386 fgDisplay.ScreenHeight + y - fgState.Size.Y;
388 fgState.Position.Y = y;
395 fgDisplay.ScreenWidth + x - fgState.Size.X;
397 fgState.Position.X = x;
400 argv[ i - 1 ] = NULL;
404 else if( strcmp( argv[ i ], "-direct" ) == 0)
406 if( fgState.TryDirectContext == FALSE )
407 fgError( "parameters ambiguity, -direct and -indirect "
408 "cannot be both specified" );
410 fgState.ForceDirectContext = TRUE;
414 else if( strcmp( argv[ i ], "-indirect" ) == 0 )
416 if( fgState.ForceDirectContext == TRUE )
417 fgError( "parameters ambiguity, -direct and -indirect "
418 "cannot be both specified" );
420 fgState.TryDirectContext = FALSE;
424 else if( strcmp( argv[ i ], "-iconic" ) == 0 )
426 fgState.ForceIconic = TRUE;
430 else if( strcmp( argv[ i ], "-gldebug" ) == 0 )
432 fgState.GLDebugSwitch = TRUE;
436 else if( strcmp( argv[ i ], "-sync" ) == 0 )
438 fgState.XSyncSwitch = TRUE;
448 for( i = 1; i < *pargc; i++, j++ )
450 if( argv[ i ] == NULL )
452 /* Guaranteed to end because there are "*pargc" arguments left */
453 while ( argv[j] == NULL )
460 * Have the display created now. As I am too lazy to implement
461 * the program arguments parsing, we will have the DISPLAY
462 * environment variable used for opening the X display:
464 * XXX The above comment is rather unclear. We have just
465 * XXX completed parsing of the program arguments for GLUT
466 * XXX parameters. We obviously canNOT parse the application-
467 * XXX specific parameters. Can someone re-write the above
470 fgInitialize( displayName );
473 * Check for the minus one settings for both position and size...
475 if( fgState.Position.X < 0 || fgState.Position.Y < 0 )
476 fgState.Position.Use = FALSE;
478 if( fgState.Size.X < 0 || fgState.Size.Y < 0 )
479 fgState.Size.Use = FALSE;
486 * Sets the default initial window position for new windows
488 void FGAPIENTRY glutInitWindowPosition( int x, int y )
490 if( (x >= 0) && (y >= 0) )
492 fgState.Position.X = x;
493 fgState.Position.Y = y;
494 fgState.Position.Use = TRUE;
498 fgState.Position.X = -1;
499 fgState.Position.Y = -1;
500 fgState.Position.Use = FALSE;
505 * Sets the default initial window size for new windows
507 void FGAPIENTRY glutInitWindowSize( int width, int height )
509 if( (width > 0) && (height > 0) )
511 fgState.Size.X = width;
512 fgState.Size.Y = height;
513 fgState.Size.Use = TRUE;
519 fgState.Size.Use = FALSE;
524 * Sets the default display mode for all new windows
526 void FGAPIENTRY glutInitDisplayMode( unsigned int displayMode )
529 * We will make use of this value when creating a new OpenGL context...
531 fgState.DisplayMode = displayMode;
535 /* -- INIT DISPLAY STRING PARSING ------------------------------------------ */
537 #if 0 /* FIXME: CJP */
539 * There is a discrete number of comparison operators we can encounter:
541 * comparison ::= "=" | "!=" | "<" | ">" | "<=" | ">=" | "~"
543 #define FG_NONE 0x0000
544 #define FG_EQUAL 0x0001
545 #define FG_NOT_EQUAL 0x0002
546 #define FG_LESS 0x0003
547 #define FG_MORE 0x0004
548 #define FG_LESS_OR_EQUAL 0x0005
549 #define FG_MORE_OR_EQUAL 0x0006
550 #define FG_CLOSEST 0x0007
553 * The caller can feed us with a number of capability tokens:
555 * capability ::= "alpha" | "acca" | "acc" | "blue" | "buffer" | "conformant" | "depth" | "double" |
556 * "green" | "index" | "num" | "red" | "rgba" | "rgb" | "luminance" | "stencil" |
557 * "single" | "stereo" | "samples" | "slow" | "win32pdf" | "xvisual" | "xstaticgray" |
558 * "xgrayscale" | "xstaticcolor" | "xpseudocolor" | "xtruecolor" | "xdirectcolor"
560 static gchar* g_Tokens[] =
562 "none", "alpha", "acca", "acc", "blue", "buffer", "conformant", "depth", "double", "green",
563 "index", "num", "red", "rgba", "rgb", "luminance", "stencil", "single", "stereo", "samples",
564 "slow", "win32pdf", "xvisual", "xstaticgray", "xgrayscale", "xstaticcolor", "xpseudocolor",
565 "xtruecolor", "xdirectcolor", NULL
569 * The structure to hold the parsed display string tokens
571 typedef struct tagSFG_Capability SFG_Capability;
572 struct tagSFG_Capability
574 gint capability; /* the capability token enumerator */
575 gint comparison; /* the comparison operator used */
576 gint value; /* the value we're comparing to */
580 * The scanner configuration for the init display string
582 static GScannerConfig fgInitDisplayStringScannerConfig =
584 ( " \t\r\n" ) /* cset_skip_characters */,
589 ) /* cset_identifier_first */,
597 ) /* cset_identifier_nth */,
598 ( "#\n" ) /* cpair_comment_single */,
599 FALSE /* case_sensitive */,
600 TRUE /* skip_comment_multi */,
601 TRUE /* skip_comment_single */,
602 TRUE /* scan_comment_multi */,
603 TRUE /* scan_identifier */,
604 FALSE /* scan_identifier_1char */,
605 FALSE /* scan_identifier_NULL */,
606 TRUE /* scan_symbols */,
607 FALSE /* scan_binary */,
608 TRUE /* scan_octal */,
609 TRUE /* scan_float */,
611 FALSE /* scan_hex_dollar */,
612 TRUE /* scan_string_sq */,
613 TRUE /* scan_string_dq */,
614 TRUE /* numbers_2_int */,
615 FALSE /* int_2_float */,
616 FALSE /* identifier_2_string */,
617 TRUE /* char_2_token */,
618 FALSE /* symbol_2_token */,
619 FALSE /* scope_0_fallback */,
623 * Sets the default display mode for all new windows using a string
625 void FGAPIENTRY glutInitDisplayString( char* displayMode )
628 * display_string ::= (switch)
629 * switch ::= capability [comparison value]
630 * comparison ::= "=" | "!=" | "<" | ">" | "<=" | ">=" | "~"
631 * capability ::= "alpha" | "acca" | "acc" | "blue" | "buffer" | "conformant" |
632 * "depth" | "double" | "green" | "index" | "num" | "red" | "rgba" |
633 * "rgb" | "luminance" | "stencil" | "single" | "stereo" |
634 * "samples" | "slow" | "win32pdf" | "xvisual" | "xstaticgray" |
635 * "xgrayscale" | "xstaticcolor" | "xpseudocolor" |
636 * "xtruecolor" | "xdirectcolor"
637 * value ::= 0..9 [value]
639 * The display string grammar. This should be EBNF, but I couldn't find the definitions so, to
640 * clarify: (expr) means 0 or more times the expression, [expr] means 0 or 1 times expr.
642 * Create a new GLib lexical analyzer to process the display mode string
644 GScanner* scanner = g_scanner_new( &fgInitDisplayStringScannerConfig );
649 * Fail if the display mode string is empty or the scanner failed to initialize
651 freeglut_return_if_fail( (scanner != NULL) && (strlen( displayMode ) > 0) );
654 * Set the scanner's input name (for debugging)
656 scanner->input_name = "glutInitDisplayString";
659 * Start the lexical analysis of the extensions string
661 g_scanner_input_text( scanner, displayMode, strlen( displayMode ) );
664 * While there are any more tokens to be checked...
666 while( !g_scanner_eof( scanner ) )
669 * Actually we're expecting only string tokens
671 GTokenType tokenType = g_scanner_get_next_token( scanner );
674 * We are looking for identifiers
676 if( tokenType == G_TOKEN_IDENTIFIER )
678 gchar* capability = NULL; /* the capability identifier string (always present) */
679 gint capID = 0; /* the capability identifier value (from g_Tokens) */
680 gint comparison = 0; /* the comparison operator value, see definitions */
681 gchar* valueString = NULL; /* if the previous one is present, this is needed */
682 gint value = 0; /* the integer value converted using a strtol call */
683 SFG_Capability* capStruct; /* the capability description structure */
686 * OK. The general rule of thumb that we always should be getting a capability identifier
687 * string (see the grammar description). If it is followed by a comparison identifier, then
688 * there must follow an integer value we're comparing the capability to...
690 * Have the current token analyzed with that in mind...
692 for( i=0; i<(gint) strlen( scanner->value.v_identifier ); i++ )
694 gchar c = scanner->value.v_identifier[ i ];
696 if( (c == '=') || (c == '!') || (c == '<') || (c == '>') || (c == '~') )
701 * Here we go with the length of the capability identifier string.
702 * In the worst of cases, it is as long as the token identifier.
704 capability = g_strndup( scanner->value.v_identifier, i );
707 * OK. Is there a chance for comparison and value identifiers to follow?
708 * Note: checking against i+1 as this handles two cases: single character
709 * comparison operator and first of value's digits, which must always be
710 * there, or the two-character comparison operators.
712 if( (i + 1) < (gint) strlen( scanner->value.v_identifier ) )
715 * Yeah, indeed, it is the i-th character to start the identifier, then.
717 gchar c1 = scanner->value.v_identifier[ i + 0 ];
718 gchar c2 = scanner->value.v_identifier[ i + 1 ];
720 if( (c1 == '=') ) { i += 1; comparison = FG_EQUAL; } else
721 if( (c1 == '!') && (c2 == '=') ) { i += 2; comparison = FG_NOT_EQUAL; } else
722 if( (c1 == '<') && (c2 == '=') ) { i += 2; comparison = FG_LESS_OR_EQUAL; } else
723 if( (c1 == '>') && (c2 == '=') ) { i += 2; comparison = FG_MORE_OR_EQUAL; } else
724 if( (c1 == '<') ) { i += 1; comparison = FG_LESS; } else
725 if( (c1 == '>') ) { i += 1; comparison = FG_MORE; } else
726 if( (c1 == '~') ) { i += 1; comparison = FG_CLOSEST; } else
727 g_warning( "invalid comparison operator in token `%s'", scanner->value.v_identifier );
731 * Grab the value string that must follow the comparison operator...
733 if( comparison != FG_NONE && i < (gint) strlen( scanner->value.v_identifier ) )
735 valueString = strdup( scanner->value.v_identifier + i );
737 fgError ("Could not allocate an internal string.");
741 * If there was a value string, convert it to integer...
743 if( comparison != FG_NONE && strlen( valueString ) > 0 )
744 value = strtol( valueString, NULL, 0 );
747 * Now we need to match the capability string and its ID
749 for( i=0; g_Tokens[ i ]!=NULL; i++ )
751 if( strcmp( capability, g_Tokens[ i ] ) == 0 )
754 * Looks like we've found the one we were looking for
762 * Create a new capability description structure
764 capStruct = g_new0( SFG_Capability, 1 );
767 * Fill in the cap's values, as we have parsed it:
769 capStruct->capability = capID;
770 capStruct->comparison = comparison;
771 capStruct->value = value;
774 * Add the new capabaility to the caps list
776 caps = g_list_append( caps, capStruct );
779 * Clean up the local mess and keep rolling on
781 g_free( valueString );
782 g_free( capability );
787 * Now that we have converted the string into somewhat more machine-friendly
788 * form, proceed with matching the frame buffer configuration...
790 * The caps list could be passed to a function that would try finding the closest
791 * matching pixel format, visual, frame buffer configuration or whatever. It would
792 * be good to convert the glutInitDisplayMode() to use the same method.
795 g_message( "found %i capability preferences", g_list_length( caps ) );
797 g_message( "token `%s': cap: %i, com: %i, val: %i",
798 scanner->value.v_identifier,
799 capStruct->capability,
800 capStruct->comparison,
806 * Free the capabilities we have parsed
808 for( i=0; i<(gint) g_list_length( caps ); i++ )
809 g_free( g_list_nth( caps, i )->data );
812 * Destroy the capabilities list itself
817 * Free the lexical scanner now...
819 g_scanner_destroy( scanner );
823 #define NUM_TOKENS 28
824 static char* Tokens[] =
826 "alpha", "acca", "acc", "blue", "buffer", "conformant", "depth", "double", "green",
827 "index", "num", "red", "rgba", "rgb", "luminance", "stencil", "single", "stereo", "samples",
828 "slow", "win32pdf", "xvisual", "xstaticgray", "xgrayscale", "xstaticcolor", "xpseudocolor",
829 "xtruecolor", "xdirectcolor"
832 static int TokenLengths[] =
834 5, 4, 3, 4, 6, 10, 5, 6, 5,
835 5, 3, 3, 4, 3, 9, 7, 6, 6, 7,
836 4, 8, 7, 11, 10, 12, 12,
840 void FGAPIENTRY glutInitDisplayString( const char* displayMode )
842 int glut_state_flag = 0 ;
844 * Unpack a lot of options from a character string. The options are delimited by blanks or tabs.
847 int len = strlen ( displayMode ) ;
848 char *buffer = (char *)malloc ( (len+1) * sizeof(char) ) ;
849 memcpy ( buffer, displayMode, len ) ;
852 token = strtok ( buffer, " \t" ) ;
859 for ( i = 0; i < NUM_TOKENS; i++ )
861 if ( strncmp ( token, Tokens[i], TokenLengths[i] ) == 0 ) break ;
866 case 0 : /* "alpha": Alpha color buffer precision in bits */
867 glut_state_flag |= GLUT_ALPHA ; /* Somebody fix this for me! */
870 case 1 : /* "acca": Red, green, blue, and alpha accumulation buffer precision in bits */
873 case 2 : /* "acc": Red, green, and blue accumulation buffer precision in bits with zero bits alpha */
874 glut_state_flag |= GLUT_ACCUM ; /* Somebody fix this for me! */
877 case 3 : /* "blue": Blue color buffer precision in bits */
880 case 4 : /* "buffer": Number of bits in the color index color buffer */
883 case 5 : /* "conformant": Boolean indicating if the frame buffer configuration is conformant or not */
886 case 6 : /* "depth": Number of bits of precsion in the depth buffer */
887 glut_state_flag |= GLUT_DEPTH ; /* Somebody fix this for me! */
890 case 7 : /* "double": Boolean indicating if the color buffer is double buffered */
891 glut_state_flag |= GLUT_DOUBLE ;
894 case 8 : /* "green": Green color buffer precision in bits */
897 case 9 : /* "index": Boolean if the color model is color index or not */
898 glut_state_flag |= GLUT_INDEX ;
901 case 10 : /* "num": A special capability name indicating where the value represents the Nth frame buffer configuration matching the description string */
904 case 11 : /* "red": Red color buffer precision in bits */
907 case 12 : /* "rgba": Number of bits of red, green, blue, and alpha in the RGBA color buffer */
908 glut_state_flag |= GLUT_RGBA ; /* Somebody fix this for me! */
911 case 13 : /* "rgb": Number of bits of red, green, and blue in the RGBA color buffer with zero bits alpha */
912 glut_state_flag |= GLUT_RGB ; /* Somebody fix this for me! */
915 case 14 : /* "luminance": Number of bits of red in the RGBA and zero bits of green, blue (alpha not specified) of color buffer precision */
916 glut_state_flag |= GLUT_LUMINANCE ; /* Somebody fix this for me! */
919 case 15 : /* "stencil": Number of bits in the stencil buffer */
920 glut_state_flag |= GLUT_STENCIL ; /* Somebody fix this for me! */
923 case 16 : /* "single": Boolean indicate the color buffer is single buffered */
924 glut_state_flag |= GLUT_SINGLE ;
927 case 17 : /* "stereo": Boolean indicating the color buffer supports OpenGL-style stereo */
928 glut_state_flag |= GLUT_STEREO ;
931 case 18 : /* "samples": Indicates the number of multisamples to use based on GLX's SGIS_multisample extension (for antialiasing) */
932 glut_state_flag |= GLUT_MULTISAMPLE ; /* Somebody fix this for me! */
935 case 19 : /* "slow": Boolean indicating if the frame buffer configuration is slow or not */
938 case 20 : /* "win32pdf": matches the Win32 Pixel Format Descriptor by number */
939 #if TARGET_HOST_WIN32
943 case 21 : /* "xvisual": matches the X visual ID by number */
944 #if TARGET_HOST_UNIX_X11
948 case 22 : /* "xstaticgray": boolean indicating if the frame buffer configuration's X visual is of type StaticGray */
949 #if TARGET_HOST_UNIX_X11
953 case 23 : /* "xgrayscale": boolean indicating if the frame buffer configuration's X visual is of type GrayScale */
954 #if TARGET_HOST_UNIX_X11
958 case 24 : /* "xstaticcolor": boolean indicating if the frame buffer configuration's X visual is of type StaticColor */
959 #if TARGET_HOST_UNIX_X11
963 case 25 : /* "xpseudocolor": boolean indicating if the frame buffer configuration's X visual is of type PseudoColor */
964 #if TARGET_HOST_UNIX_X11
968 case 26 : /* "xtruecolor": boolean indicating if the frame buffer configuration's X visual is of type TrueColor */
969 #if TARGET_HOST_UNIX_X11
973 case 27 : /* "xdirectcolor": boolean indicating if the frame buffer configuration's X visual is of type DirectColor */
974 #if TARGET_HOST_UNIX_X11
978 case 28 : /* Unrecognized */
979 printf ( "WARNING - Display string token not recognized: %s\n", token ) ;
983 token = strtok ( NULL, " \t" ) ;
989 * We will make use of this value when creating a new OpenGL context...
991 fgState.DisplayMode = glut_state_flag;
994 /*** END OF FILE ***/