test/testgl.c
author Ryan C. Gordon <icculus@icculus.org>
Fri, 03 Jun 2011 16:03:10 -0400
changeset 5547 4ccecd0901e2
parent 5535 96594ac5fd1a
permissions -rw-r--r--
Assert code's stdio interface was reading from the wrong variable.

Thanks to Frank Zago for the catch.
     1 /*
     2   Copyright (C) 1997-2011 Sam Lantinga <slouken@libsdl.org>
     3 
     4   This software is provided 'as-is', without any express or implied
     5   warranty.  In no event will the authors be held liable for any damages
     6   arising from the use of this software.
     7 
     8   Permission is granted to anyone to use this software for any purpose,
     9   including commercial applications, and to alter it and redistribute it
    10   freely.
    11 */
    12 #include <stdlib.h>
    13 #include <stdio.h>
    14 #include <string.h>
    15 #include <math.h>
    16 
    17 #include "SDL.h"
    18 
    19 #ifdef __MACOS__
    20 #define HAVE_OPENGL
    21 #endif
    22 
    23 #ifdef HAVE_OPENGL
    24 
    25 #include "SDL_opengl.h"
    26 
    27 /* Undefine this if you want a flat cube instead of a rainbow cube */
    28 #define SHADED_CUBE
    29 
    30 /* Define this to be the name of the logo image to use with -logo */
    31 #define LOGO_FILE	"icon.bmp"
    32 
    33 static SDL_Surface *global_image = NULL;
    34 static GLuint global_texture = 0;
    35 static GLuint cursor_texture = 0;
    36 
    37 /**********************************************************************/
    38 
    39 void
    40 HotKey_ToggleFullScreen(void)
    41 {
    42     SDL_Surface *screen;
    43 
    44     screen = SDL_GetVideoSurface();
    45     if (SDL_WM_ToggleFullScreen(screen)) {
    46         printf("Toggled fullscreen mode - now %s\n",
    47                (screen->flags & SDL_FULLSCREEN) ? "fullscreen" : "windowed");
    48     } else {
    49         printf("Unable to toggle fullscreen mode\n");
    50     }
    51 }
    52 
    53 void
    54 HotKey_ToggleGrab(void)
    55 {
    56     SDL_GrabMode mode;
    57 
    58     printf("Ctrl-G: toggling input grab!\n");
    59     mode = SDL_WM_GrabInput(SDL_GRAB_QUERY);
    60     if (mode == SDL_GRAB_ON) {
    61         printf("Grab was on\n");
    62     } else {
    63         printf("Grab was off\n");
    64     }
    65     mode = SDL_WM_GrabInput(!mode);
    66     if (mode == SDL_GRAB_ON) {
    67         printf("Grab is now on\n");
    68     } else {
    69         printf("Grab is now off\n");
    70     }
    71 }
    72 
    73 void
    74 HotKey_Iconify(void)
    75 {
    76     printf("Ctrl-Z: iconifying window!\n");
    77     SDL_WM_IconifyWindow();
    78 }
    79 
    80 int
    81 HandleEvent(SDL_Event * event)
    82 {
    83     int done;
    84 
    85     done = 0;
    86     switch (event->type) {
    87     case SDL_ACTIVEEVENT:
    88         /* See what happened */
    89         printf("app %s ", event->active.gain ? "gained" : "lost");
    90         if (event->active.state & SDL_APPACTIVE) {
    91             printf("active ");
    92         } else if (event->active.state & SDL_APPMOUSEFOCUS) {
    93             printf("mouse ");
    94         } else if (event->active.state & SDL_APPINPUTFOCUS) {
    95             printf("input ");
    96         }
    97         printf("focus\n");
    98         break;
    99 
   100 
   101     case SDL_KEYDOWN:
   102         if (event->key.keysym.sym == SDLK_ESCAPE) {
   103             done = 1;
   104         }
   105         if ((event->key.keysym.sym == SDLK_g) &&
   106             (event->key.keysym.mod & KMOD_CTRL)) {
   107             HotKey_ToggleGrab();
   108         }
   109         if ((event->key.keysym.sym == SDLK_z) &&
   110             (event->key.keysym.mod & KMOD_CTRL)) {
   111             HotKey_Iconify();
   112         }
   113         if ((event->key.keysym.sym == SDLK_RETURN) &&
   114             (event->key.keysym.mod & KMOD_ALT)) {
   115             HotKey_ToggleFullScreen();
   116         }
   117         printf("key '%s' pressed\n", SDL_GetKeyName(event->key.keysym.sym));
   118         break;
   119     case SDL_QUIT:
   120         done = 1;
   121         break;
   122     }
   123     return (done);
   124 }
   125 
   126 void
   127 SDL_GL_Enter2DMode()
   128 {
   129     SDL_Surface *screen = SDL_GetVideoSurface();
   130 
   131     /* Note, there may be other things you need to change,
   132        depending on how you have your OpenGL state set up.
   133      */
   134     glPushAttrib(GL_ENABLE_BIT);
   135     glDisable(GL_DEPTH_TEST);
   136     glDisable(GL_CULL_FACE);
   137     glEnable(GL_TEXTURE_2D);
   138 
   139     /* This allows alpha blending of 2D textures with the scene */
   140     glEnable(GL_BLEND);
   141     glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
   142 
   143     glViewport(0, 0, screen->w, screen->h);
   144 
   145     glMatrixMode(GL_PROJECTION);
   146     glPushMatrix();
   147     glLoadIdentity();
   148 
   149     glOrtho(0.0, (GLdouble) screen->w, (GLdouble) screen->h, 0.0, 0.0, 1.0);
   150 
   151     glMatrixMode(GL_MODELVIEW);
   152     glPushMatrix();
   153     glLoadIdentity();
   154 
   155     glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_DECAL);
   156 }
   157 
   158 void
   159 SDL_GL_Leave2DMode()
   160 {
   161     glMatrixMode(GL_MODELVIEW);
   162     glPopMatrix();
   163 
   164     glMatrixMode(GL_PROJECTION);
   165     glPopMatrix();
   166 
   167     glPopAttrib();
   168 }
   169 
   170 /* Quick utility function for texture creation */
   171 static int
   172 power_of_two(int input)
   173 {
   174     int value = 1;
   175 
   176     while (value < input) {
   177         value <<= 1;
   178     }
   179     return value;
   180 }
   181 
   182 GLuint
   183 SDL_GL_LoadTexture(SDL_Surface * surface, GLfloat * texcoord)
   184 {
   185     GLuint texture;
   186     int w, h;
   187     SDL_Surface *image;
   188     SDL_Rect area;
   189     Uint32 saved_flags;
   190     Uint8 saved_alpha;
   191 
   192     /* Use the surface width and height expanded to powers of 2 */
   193     w = power_of_two(surface->w);
   194     h = power_of_two(surface->h);
   195     texcoord[0] = 0.0f;         /* Min X */
   196     texcoord[1] = 0.0f;         /* Min Y */
   197     texcoord[2] = (GLfloat) surface->w / w;     /* Max X */
   198     texcoord[3] = (GLfloat) surface->h / h;     /* Max Y */
   199 
   200     image = SDL_CreateRGBSurface(SDL_SWSURFACE, w, h, 32,
   201 #if SDL_BYTEORDER == SDL_LIL_ENDIAN     /* OpenGL RGBA masks */
   202                                  0x000000FF,
   203                                  0x0000FF00, 0x00FF0000, 0xFF000000
   204 #else
   205                                  0xFF000000,
   206                                  0x00FF0000, 0x0000FF00, 0x000000FF
   207 #endif
   208         );
   209     if (image == NULL) {
   210         return 0;
   211     }
   212 
   213     /* Save the alpha blending attributes */
   214     saved_flags = surface->flags & (SDL_SRCALPHA | SDL_RLEACCELOK);
   215     SDL_GetSurfaceAlphaMod(surface, &saved_alpha);
   216     if ((saved_flags & SDL_SRCALPHA) == SDL_SRCALPHA) {
   217         SDL_SetAlpha(surface, 0, 0);
   218     }
   219 
   220     /* Copy the surface into the GL texture image */
   221     area.x = 0;
   222     area.y = 0;
   223     area.w = surface->w;
   224     area.h = surface->h;
   225     SDL_BlitSurface(surface, &area, image, &area);
   226 
   227     /* Restore the alpha blending attributes */
   228     if ((saved_flags & SDL_SRCALPHA) == SDL_SRCALPHA) {
   229         SDL_SetAlpha(surface, saved_flags, saved_alpha);
   230     }
   231 
   232     /* Create an OpenGL texture for the image */
   233     glGenTextures(1, &texture);
   234     glBindTexture(GL_TEXTURE_2D, texture);
   235     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
   236     glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
   237     glTexImage2D(GL_TEXTURE_2D,
   238                  0,
   239                  GL_RGBA, w, h, 0, GL_RGBA, GL_UNSIGNED_BYTE, image->pixels);
   240     SDL_FreeSurface(image);     /* No longer needed */
   241 
   242     return texture;
   243 }
   244 
   245 void
   246 DrawLogoCursor(void)
   247 {
   248     static GLfloat texMinX, texMinY;
   249     static GLfloat texMaxX, texMaxY;
   250     static int w, h;
   251     int x, y;
   252 
   253     if (!cursor_texture) {
   254         SDL_Surface *image;
   255         GLfloat texcoord[4];
   256 
   257         /* Load the image (could use SDL_image library here) */
   258         image = SDL_LoadBMP(LOGO_FILE);
   259         if (image == NULL) {
   260             return;
   261         }
   262         w = image->w;
   263         h = image->h;
   264 
   265         /* Convert the image into an OpenGL texture */
   266         cursor_texture = SDL_GL_LoadTexture(image, texcoord);
   267 
   268         /* Make texture coordinates easy to understand */
   269         texMinX = texcoord[0];
   270         texMinY = texcoord[1];
   271         texMaxX = texcoord[2];
   272         texMaxY = texcoord[3];
   273 
   274         /* We don't need the original image anymore */
   275         SDL_FreeSurface(image);
   276 
   277         /* Make sure that the texture conversion is okay */
   278         if (!cursor_texture) {
   279             return;
   280         }
   281     }
   282 
   283     /* Move the image around */
   284     SDL_GetMouseState(&x, &y);
   285     x -= w / 2;
   286     y -= h / 2;
   287 
   288     /* Show the image on the screen */
   289     SDL_GL_Enter2DMode();
   290     glBindTexture(GL_TEXTURE_2D, cursor_texture);
   291     glBegin(GL_TRIANGLE_STRIP);
   292     glTexCoord2f(texMinX, texMinY);
   293     glVertex2i(x, y);
   294     glTexCoord2f(texMaxX, texMinY);
   295     glVertex2i(x + w, y);
   296     glTexCoord2f(texMinX, texMaxY);
   297     glVertex2i(x, y + h);
   298     glTexCoord2f(texMaxX, texMaxY);
   299     glVertex2i(x + w, y + h);
   300     glEnd();
   301     SDL_GL_Leave2DMode();
   302 }
   303 
   304 void
   305 DrawLogoTexture(void)
   306 {
   307     static GLfloat texMinX, texMinY;
   308     static GLfloat texMaxX, texMaxY;
   309     static int x = 0;
   310     static int y = 0;
   311     static int w, h;
   312     static int delta_x = 1;
   313     static int delta_y = 1;
   314 
   315     SDL_Surface *screen = SDL_GetVideoSurface();
   316 
   317     if (!global_texture) {
   318         SDL_Surface *image;
   319         GLfloat texcoord[4];
   320 
   321         /* Load the image (could use SDL_image library here) */
   322         image = SDL_LoadBMP(LOGO_FILE);
   323         if (image == NULL) {
   324             return;
   325         }
   326         w = image->w;
   327         h = image->h;
   328 
   329         /* Convert the image into an OpenGL texture */
   330         global_texture = SDL_GL_LoadTexture(image, texcoord);
   331 
   332         /* Make texture coordinates easy to understand */
   333         texMinX = texcoord[0];
   334         texMinY = texcoord[1];
   335         texMaxX = texcoord[2];
   336         texMaxY = texcoord[3];
   337 
   338         /* We don't need the original image anymore */
   339         SDL_FreeSurface(image);
   340 
   341         /* Make sure that the texture conversion is okay */
   342         if (!global_texture) {
   343             return;
   344         }
   345     }
   346 
   347     /* Move the image around */
   348     x += delta_x;
   349     if (x < 0) {
   350         x = 0;
   351         delta_x = -delta_x;
   352     } else if ((x + w) > screen->w) {
   353         x = screen->w - w;
   354         delta_x = -delta_x;
   355     }
   356     y += delta_y;
   357     if (y < 0) {
   358         y = 0;
   359         delta_y = -delta_y;
   360     } else if ((y + h) > screen->h) {
   361         y = screen->h - h;
   362         delta_y = -delta_y;
   363     }
   364 
   365     /* Show the image on the screen */
   366     SDL_GL_Enter2DMode();
   367     glBindTexture(GL_TEXTURE_2D, global_texture);
   368     glBegin(GL_TRIANGLE_STRIP);
   369     glTexCoord2f(texMinX, texMinY);
   370     glVertex2i(x, y);
   371     glTexCoord2f(texMaxX, texMinY);
   372     glVertex2i(x + w, y);
   373     glTexCoord2f(texMinX, texMaxY);
   374     glVertex2i(x, y + h);
   375     glTexCoord2f(texMaxX, texMaxY);
   376     glVertex2i(x + w, y + h);
   377     glEnd();
   378     SDL_GL_Leave2DMode();
   379 }
   380 
   381 int
   382 RunGLTest(int argc, char *argv[],
   383           int logo, int logocursor, int slowly, int bpp, float gamma,
   384           int noframe, int fsaa, int sync, int accel)
   385 {
   386     int i;
   387     int rgb_size[3];
   388     int w = 640;
   389     int h = 480;
   390     int done = 0;
   391     int frames;
   392     Uint32 start_time, this_time;
   393     float color[8][3] = { {1.0, 1.0, 0.0},
   394     {1.0, 0.0, 0.0},
   395     {0.0, 0.0, 0.0},
   396     {0.0, 1.0, 0.0},
   397     {0.0, 1.0, 1.0},
   398     {1.0, 1.0, 1.0},
   399     {1.0, 0.0, 1.0},
   400     {0.0, 0.0, 1.0}
   401     };
   402     float cube[8][3] = { {0.5, 0.5, -0.5},
   403     {0.5, -0.5, -0.5},
   404     {-0.5, -0.5, -0.5},
   405     {-0.5, 0.5, -0.5},
   406     {-0.5, 0.5, 0.5},
   407     {0.5, 0.5, 0.5},
   408     {0.5, -0.5, 0.5},
   409     {-0.5, -0.5, 0.5}
   410     };
   411     Uint32 video_flags;
   412     int value;
   413 
   414     if (SDL_Init(SDL_INIT_VIDEO) < 0) {
   415         fprintf(stderr, "Couldn't initialize SDL: %s\n", SDL_GetError());
   416         exit(1);
   417     }
   418 
   419     /* See if we should detect the display depth */
   420     if (bpp == 0) {
   421         if (SDL_GetVideoInfo()->vfmt->BitsPerPixel <= 8) {
   422             bpp = 8;
   423         } else {
   424             bpp = 16;           /* More doesn't seem to work */
   425         }
   426     }
   427 
   428     /* Set the flags we want to use for setting the video mode */
   429     video_flags = SDL_OPENGL;
   430     for (i = 1; argv[i]; ++i) {
   431         if (strcmp(argv[i], "-fullscreen") == 0) {
   432             video_flags |= SDL_FULLSCREEN;
   433         }
   434     }
   435 
   436     if (noframe) {
   437         video_flags |= SDL_NOFRAME;
   438     }
   439 
   440     /* Initialize the display */
   441     switch (bpp) {
   442     case 8:
   443         rgb_size[0] = 3;
   444         rgb_size[1] = 3;
   445         rgb_size[2] = 2;
   446         break;
   447     case 15:
   448     case 16:
   449         rgb_size[0] = 5;
   450         rgb_size[1] = 5;
   451         rgb_size[2] = 5;
   452         break;
   453     default:
   454         rgb_size[0] = 8;
   455         rgb_size[1] = 8;
   456         rgb_size[2] = 8;
   457         break;
   458     }
   459     SDL_GL_SetAttribute(SDL_GL_RED_SIZE, rgb_size[0]);
   460     SDL_GL_SetAttribute(SDL_GL_GREEN_SIZE, rgb_size[1]);
   461     SDL_GL_SetAttribute(SDL_GL_BLUE_SIZE, rgb_size[2]);
   462     SDL_GL_SetAttribute(SDL_GL_DEPTH_SIZE, 16);
   463     SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER, 1);
   464     if (fsaa) {
   465         SDL_GL_SetAttribute(SDL_GL_MULTISAMPLEBUFFERS, 1);
   466         SDL_GL_SetAttribute(SDL_GL_MULTISAMPLESAMPLES, fsaa);
   467     }
   468     if (accel >= 0) {
   469         SDL_GL_SetAttribute(SDL_GL_ACCELERATED_VISUAL, accel);
   470     }
   471     if (SDL_SetVideoMode(w, h, bpp, video_flags) == NULL) {
   472         fprintf(stderr, "Couldn't set GL mode: %s\n", SDL_GetError());
   473         SDL_Quit();
   474         exit(1);
   475     }
   476     if (sync) {
   477         SDL_GL_SetSwapInterval(1);
   478     } else {
   479         SDL_GL_SetSwapInterval(0);
   480     }
   481 
   482     printf("Screen BPP: %d\n", SDL_GetVideoSurface()->format->BitsPerPixel);
   483     printf("\n");
   484     printf("Vendor     : %s\n", glGetString(GL_VENDOR));
   485     printf("Renderer   : %s\n", glGetString(GL_RENDERER));
   486     printf("Version    : %s\n", glGetString(GL_VERSION));
   487     printf("Extensions : %s\n", glGetString(GL_EXTENSIONS));
   488     printf("\n");
   489 
   490     SDL_GL_GetAttribute(SDL_GL_RED_SIZE, &value);
   491     printf("SDL_GL_RED_SIZE: requested %d, got %d\n", rgb_size[0], value);
   492     SDL_GL_GetAttribute(SDL_GL_GREEN_SIZE, &value);
   493     printf("SDL_GL_GREEN_SIZE: requested %d, got %d\n", rgb_size[1], value);
   494     SDL_GL_GetAttribute(SDL_GL_BLUE_SIZE, &value);
   495     printf("SDL_GL_BLUE_SIZE: requested %d, got %d\n", rgb_size[2], value);
   496     SDL_GL_GetAttribute(SDL_GL_DEPTH_SIZE, &value);
   497     printf("SDL_GL_DEPTH_SIZE: requested %d, got %d\n", bpp, value);
   498     SDL_GL_GetAttribute(SDL_GL_DOUBLEBUFFER, &value);
   499     printf("SDL_GL_DOUBLEBUFFER: requested 1, got %d\n", value);
   500     if (fsaa) {
   501         SDL_GL_GetAttribute(SDL_GL_MULTISAMPLEBUFFERS, &value);
   502         printf("SDL_GL_MULTISAMPLEBUFFERS: requested 1, got %d\n", value);
   503         SDL_GL_GetAttribute(SDL_GL_MULTISAMPLESAMPLES, &value);
   504         printf("SDL_GL_MULTISAMPLESAMPLES: requested %d, got %d\n", fsaa,
   505                value);
   506     }
   507     if (accel >= 0) {
   508         SDL_GL_GetAttribute(SDL_GL_ACCELERATED_VISUAL, &value);
   509         printf("SDL_GL_ACCELERATED_VISUAL: requested %d, got %d\n", accel,
   510                value);
   511     }
   512     if (sync) {
   513         printf("Buffer swap interval: requested 1, got %d\n",
   514                SDL_GL_GetSwapInterval());
   515     }
   516 
   517     /* Set the window manager title bar */
   518     SDL_WM_SetCaption("SDL GL test", "testgl");
   519 
   520     /* Set the gamma for the window */
   521     if (gamma != 0.0) {
   522         SDL_SetGamma(gamma, gamma, gamma);
   523     }
   524 
   525     glViewport(0, 0, w, h);
   526     glMatrixMode(GL_PROJECTION);
   527     glLoadIdentity();
   528 
   529     glOrtho(-2.0, 2.0, -2.0, 2.0, -20.0, 20.0);
   530 
   531     glMatrixMode(GL_MODELVIEW);
   532     glLoadIdentity();
   533 
   534     glEnable(GL_DEPTH_TEST);
   535 
   536     glDepthFunc(GL_LESS);
   537 
   538     glShadeModel(GL_SMOOTH);
   539 
   540     /* Loop until done. */
   541     start_time = SDL_GetTicks();
   542     frames = 0;
   543     while (!done) {
   544         GLenum gl_error;
   545         char *sdl_error;
   546         SDL_Event event;
   547 
   548         /* Do our drawing, too. */
   549         glClearColor(0.0, 0.0, 0.0, 1.0);
   550         glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
   551 
   552         glBegin(GL_QUADS);
   553 
   554 #ifdef SHADED_CUBE
   555         glColor3fv(color[0]);
   556         glVertex3fv(cube[0]);
   557         glColor3fv(color[1]);
   558         glVertex3fv(cube[1]);
   559         glColor3fv(color[2]);
   560         glVertex3fv(cube[2]);
   561         glColor3fv(color[3]);
   562         glVertex3fv(cube[3]);
   563 
   564         glColor3fv(color[3]);
   565         glVertex3fv(cube[3]);
   566         glColor3fv(color[4]);
   567         glVertex3fv(cube[4]);
   568         glColor3fv(color[7]);
   569         glVertex3fv(cube[7]);
   570         glColor3fv(color[2]);
   571         glVertex3fv(cube[2]);
   572 
   573         glColor3fv(color[0]);
   574         glVertex3fv(cube[0]);
   575         glColor3fv(color[5]);
   576         glVertex3fv(cube[5]);
   577         glColor3fv(color[6]);
   578         glVertex3fv(cube[6]);
   579         glColor3fv(color[1]);
   580         glVertex3fv(cube[1]);
   581 
   582         glColor3fv(color[5]);
   583         glVertex3fv(cube[5]);
   584         glColor3fv(color[4]);
   585         glVertex3fv(cube[4]);
   586         glColor3fv(color[7]);
   587         glVertex3fv(cube[7]);
   588         glColor3fv(color[6]);
   589         glVertex3fv(cube[6]);
   590 
   591         glColor3fv(color[5]);
   592         glVertex3fv(cube[5]);
   593         glColor3fv(color[0]);
   594         glVertex3fv(cube[0]);
   595         glColor3fv(color[3]);
   596         glVertex3fv(cube[3]);
   597         glColor3fv(color[4]);
   598         glVertex3fv(cube[4]);
   599 
   600         glColor3fv(color[6]);
   601         glVertex3fv(cube[6]);
   602         glColor3fv(color[1]);
   603         glVertex3fv(cube[1]);
   604         glColor3fv(color[2]);
   605         glVertex3fv(cube[2]);
   606         glColor3fv(color[7]);
   607         glVertex3fv(cube[7]);
   608 #else /* flat cube */
   609         glColor3f(1.0, 0.0, 0.0);
   610         glVertex3fv(cube[0]);
   611         glVertex3fv(cube[1]);
   612         glVertex3fv(cube[2]);
   613         glVertex3fv(cube[3]);
   614 
   615         glColor3f(0.0, 1.0, 0.0);
   616         glVertex3fv(cube[3]);
   617         glVertex3fv(cube[4]);
   618         glVertex3fv(cube[7]);
   619         glVertex3fv(cube[2]);
   620 
   621         glColor3f(0.0, 0.0, 1.0);
   622         glVertex3fv(cube[0]);
   623         glVertex3fv(cube[5]);
   624         glVertex3fv(cube[6]);
   625         glVertex3fv(cube[1]);
   626 
   627         glColor3f(0.0, 1.0, 1.0);
   628         glVertex3fv(cube[5]);
   629         glVertex3fv(cube[4]);
   630         glVertex3fv(cube[7]);
   631         glVertex3fv(cube[6]);
   632 
   633         glColor3f(1.0, 1.0, 0.0);
   634         glVertex3fv(cube[5]);
   635         glVertex3fv(cube[0]);
   636         glVertex3fv(cube[3]);
   637         glVertex3fv(cube[4]);
   638 
   639         glColor3f(1.0, 0.0, 1.0);
   640         glVertex3fv(cube[6]);
   641         glVertex3fv(cube[1]);
   642         glVertex3fv(cube[2]);
   643         glVertex3fv(cube[7]);
   644 #endif /* SHADED_CUBE */
   645 
   646         glEnd();
   647 
   648         glMatrixMode(GL_MODELVIEW);
   649         glRotatef(5.0, 1.0, 1.0, 1.0);
   650 
   651         /* Draw 2D logo onto the 3D display */
   652         if (logo) {
   653             DrawLogoTexture();
   654         }
   655         if (logocursor) {
   656             DrawLogoCursor();
   657         }
   658 
   659         SDL_GL_SwapBuffers();
   660 
   661         /* Check for error conditions. */
   662         gl_error = glGetError();
   663 
   664         if (gl_error != GL_NO_ERROR) {
   665             fprintf(stderr, "testgl: OpenGL error: %d\n", gl_error);
   666         }
   667 
   668         sdl_error = (char *)SDL_GetError();
   669 
   670         if (sdl_error[0] != '\0') {
   671             fprintf(stderr, "testgl: SDL error '%s'\n", sdl_error);
   672             SDL_ClearError();
   673         }
   674 
   675         /* Allow the user to see what's happening */
   676         if (slowly) {
   677             SDL_Delay(20);
   678         }
   679 
   680         /* Check if there's a pending event. */
   681         while (SDL_PollEvent(&event)) {
   682             done |= HandleEvent(&event);
   683         }
   684         ++frames;
   685     }
   686 
   687     /* Print out the frames per second */
   688     this_time = SDL_GetTicks();
   689     if (this_time != start_time) {
   690         printf("%2.2f FPS\n",
   691                ((float) frames / (this_time - start_time)) * 1000.0);
   692     }
   693 
   694     if (global_image) {
   695         SDL_FreeSurface(global_image);
   696         global_image = NULL;
   697     }
   698     if (global_texture) {
   699         glDeleteTextures(1, &global_texture);
   700         global_texture = 0;
   701     }
   702     if (cursor_texture) {
   703         glDeleteTextures(1, &cursor_texture);
   704         cursor_texture = 0;
   705     }
   706 
   707     /* Destroy our GL context, etc. */
   708     SDL_Quit();
   709     return (0);
   710 }
   711 
   712 int
   713 main(int argc, char *argv[])
   714 {
   715     int i, logo, logocursor = 0;
   716     int numtests;
   717     int bpp = 0;
   718     int slowly;
   719     float gamma = 0.0;
   720     int noframe = 0;
   721     int fsaa = 0;
   722     int accel = -1;
   723     int sync = 0;
   724 
   725     logo = 0;
   726     slowly = 0;
   727     numtests = 1;
   728     for (i = 1; argv[i]; ++i) {
   729         if (strcmp(argv[i], "-twice") == 0) {
   730             ++numtests;
   731         }
   732         if (strcmp(argv[i], "-logo") == 0) {
   733             logo = 1;
   734         }
   735         if (strcmp(argv[i], "-logocursor") == 0) {
   736             logocursor = 1;
   737         }
   738         if (strcmp(argv[i], "-slow") == 0) {
   739             slowly = 1;
   740         }
   741         if (strcmp(argv[i], "-bpp") == 0) {
   742             bpp = atoi(argv[++i]);
   743         }
   744         if (strcmp(argv[i], "-gamma") == 0) {
   745             gamma = (float) atof(argv[++i]);
   746         }
   747         if (strcmp(argv[i], "-noframe") == 0) {
   748             noframe = 1;
   749         }
   750         if (strcmp(argv[i], "-fsaa") == 0) {
   751             ++fsaa;
   752         }
   753         if (strcmp(argv[i], "-accel") == 0) {
   754             accel = atoi(argv[++i]);
   755         }
   756         if (strcmp(argv[i], "-sync") == 0) {
   757             ++sync;
   758         }
   759         if (strncmp(argv[i], "-h", 2) == 0) {
   760             printf
   761                 ("Usage: %s [-twice] [-logo] [-logocursor] [-slow] [-bpp n] [-gamma n] [-noframe] [-fsaa] [-accel n] [-sync] [-fullscreen]\n",
   762                  argv[0]);
   763             exit(0);
   764         }
   765     }
   766     for (i = 0; i < numtests; ++i) {
   767         RunGLTest(argc, argv, logo, logocursor, slowly, bpp, gamma,
   768                   noframe, fsaa, sync, accel);
   769     }
   770     return 0;
   771 }
   772 
   773 #else /* HAVE_OPENGL */
   774 
   775 int
   776 main(int argc, char *argv[])
   777 {
   778     printf("No OpenGL support on this system\n");
   779     return 1;
   780 }
   781 
   782 #endif /* HAVE_OPENGL */