Opengl SDL resize window

I have a project (nearly finished) in the works with OpenGL and SDL. Right now I’m trying to create an option so the user can resize the window either fullscreen/windowed mode and at different resolutions.

The problem is that I use SDL_SetVideoMode to set up the window, but when I try to call it again for a new resolution, the app crashes. I’ve been reading up that if you call SDL_SetVideoMode again you need to destroy the old SDL_Surface context and create a new one. Thats not a solution for me though, because whenever you destory the original SDL_Surface context, all my OpenGL textures get cleaned too. I’ve tried re-loading the textures after the resolution change, but its no good (my app dosn’t crash but the textues still don’t show).

I’m wondering what people here do to resize the window with SDL/OpenGL. How do you work your full/windowed screen option?

I’m been working on the problem for a while, then I let it sit on the backburner, but now my projects almost done and I need a solution.

BTW I’m on Windows and Mac.

I tried to reproduce your bug, when I resize I do the thing you write above and my texture are not cleaned.

Here is my test code:


#include <iostream>
#include <vector>

#include <GL/gl.h>
#include <GL/glu.h>

#include <SDL/SDL.h>

GLuint texID;

void display(void);
void init(void);
void reshape(GLsizei w,GLsizei h);

int main(int argc,char **argv)
{
  bool  done = false;
  bool fullscreen = false;
  
  SDL_Surface *surf;
  SDL_Event event;
  SDL_Init(SDL_INIT_VIDEO);
  
  SDL_GL_SetAttribute(SDL_GL_RED_SIZE,8);
  SDL_GL_SetAttribute(SDL_GL_GREEN_SIZE,8);
  SDL_GL_SetAttribute(SDL_GL_BLUE_SIZE,8);
  SDL_GL_SetAttribute(SDL_GL_ALPHA_SIZE,8);
  SDL_GL_SetAttribute(SDL_GL_DEPTH_SIZE,24);
  SDL_GL_SetAttribute(SDL_GL_STENCIL_SIZE,8);
  SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER,1);
  
  surf = SDL_SetVideoMode(512,512,32,SDL_OPENGL|SDL_RESIZABLE);
  
  init();
  
  while(!done)
  {
    SDL_PollEvent(&event);
    
    switch(event.type)
    {
      case SDL_KEYDOWN:
        switch(event.key.keysym.sym)
        {
          case SDLK_F1:
            SDL_WM_ToggleFullScreen(surf);
            fullscreen = !fullscreen;
            break;
          case SDLK_ESCAPE:
            done = true;
          default:
            break;
        }
        break;
        
      case SDL_VIDEORESIZE:
        
        SDL_FreeSurface(surf);
        surf = SDL_SetVideoMode(event.resize.w,event.resize.h,32,SDL_OPENGL|SDL_RESIZABLE);
        reshape(static_cast<GLsizei>(event.resize.w),static_cast<GLsizei>(event.resize.h));
        break;
        
      case SDL_QUIT:
        done = true;
        break;  
        
      default:
        break;
    }
    display();
  }
  
  if(fullscreen == true)
  {
    SDL_WM_ToggleFullScreen(surf);
  }
  
  SDL_Quit();
  
  return (EXIT_SUCCESS);
}


/*-----------------------------------------*/
void display(void)
{
  glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT|GL_STENCIL_BUFFER_BIT);
  glLoadIdentity();
  
  glEnable(GL_TEXTURE_2D);
  glBindTexture(GL_TEXTURE_2D,texID);
  glTexEnvi(GL_TEXTURE_ENV,GL_TEXTURE_ENV_MODE,GL_REPLACE);
  glScalef(0.5,0.5,0.5);
  glBegin(GL_TRIANGLE_STRIP);
  glColor4f(1.0,1.0,1.0,1.0);
  glTexCoord2f(0.0,0.0);
  glVertex4f(-1.0,-1.0,0.0,1.0);
  glTexCoord2f(1.0,0.0);
  glVertex4f(1.0,-1.0,0.0,1.0);
  glTexCoord2f(0.0,1.0);
  glVertex4f(-1.0,1.0,0.0,1.0);
  glTexCoord2f(1.0,1.0);
  glVertex4f(1.0,1.0,0.0,1.0);
  glEnd();
  
  glDisable(GL_TEXTURE_2D);
  SDL_GL_SwapBuffers();
}

/*-------------------------------------------------*/
void init(void)
{
  std::vector<GLubyte> texture_data;
  texture_data.resize(16);
  
  texture_data[0] = 255;texture_data[1] = 0;texture_data[2] = 0;texture_data[3] = 255;
  texture_data[4] = 0;texture_data[5] = 255;texture_data[6] = 0;texture_data[7] = 255;
  texture_data[8] = 0;texture_data[9] = 0;texture_data[10] = 255;texture_data[11] = 255;
  texture_data[12] = 255;texture_data[13] = 255;texture_data[14] = 0;texture_data[15] = 255;
  
  glEnable(GL_DEPTH_TEST);
  
  glEnable(GL_TEXTURE_2D);
  glGenTextures(1,&texID);
  glBindTexture(GL_TEXTURE_2D,texID);
  
  glTexImage2D(GL_TEXTURE_2D,0,GL_RGBA8,2,2,0,GL_RGBA,GL_UNSIGNED_BYTE,&texture_data[0]);
  glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_NEAREST);
  glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MAG_FILTER,GL_NEAREST);
  
  glDisable(GL_TEXTURE_2D);
}


/*------------------------------------------*/
void reshape(GLsizei w,GLsizei h)
{
  glViewport(0,0,w,h);
  glMatrixMode(GL_PROJECTION);
  glLoadIdentity();
  glOrtho(-1.0,1.0,-1.0,1.0,-1.0,1.0);
  glMatrixMode(GL_MODELVIEW);
 
}

I am under Linux. Try it to see if the simple texture disappear.

Thank you for your suggestion. I’ve tried your code but unfortunately, It is my understanding that SDL_WM_ToggleFullScreen only works on x11 machines http://sdl.beuc.net/sdl.wiki/SDL_WM_ToggleFullScreen

Even on my mac, which is x11/unix based, the SDL_WM_ToggleFullScreen command does not work, much less windows.

When I press F1 for full screen nothing happens and when I re-size the window the colored rectangle suddenly goes white.

Is there any other alternative to SDL_WM_ToggleFullScreen command?

Even on my mac, which is x11/unix based, the SDL_WM_ToggleFullScreen command does not work, much less windows.

I forget to read the entire doc before posting.

Is there any other alternative to SDL_WM_ToggleFullScreen command?

On the SDL web site they explain how to make a full screen window under Windows. I don’t know if it’s work for a mac.