2010-11-18 57 views
2

J'essaie de convertir une surface SDL en une texture openGL en utilisant un extrait de code que j'ai trouvé sur Internet, après plusieurs heures de recherche, la plupart semblent utiliser les mêmes fonctions dans le même ordre, donc je suppose que je fais les choses correctement.White quad convertissant SDL_Surface à OPENGL_Texture

auto-Critisizing, je vais partager mon code un peu trop, j'aime garder les choses organisées, mais il peut y avoir quelque chose enterré dans un fichier que je ne vais pas dans beaucoup ...

Long et court, mon application est censée rendre 2 cubes, les faire pivoter tous les deux et permettre à l'un d'être déplacé.

Les cubes peuvent être créés avec une classe que j'ai écrite, il suffit de définir un et lui donner un nom de fichier, il doit charger cette texture et l'appliquer au cube lorsque la fonction show est appelée. Je l'ai fait fonctionner partiellement avec la bibliothèque SOIL, mais j'ai déplacé beaucoup de code vers SDL et je préfère utiliser IMG_Load à la place.

est ici le code

GLuint loadTexture(std::string filename) 
{ 
    GLuint texture; 
    if(SDL_Surface* surfaceTex = IMG_Load(filename.c_str())) 
    { 
     glPixelStorei(GL_UNPACK_ALIGNMENT,4); 
     glGenTextures(1,&texture); 
     glBindTexture(GL_TEXTURE_2D,texture); 
     SDL_PixelFormat *format = surfaceTex->format; 
     glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_NEAREST); 
     glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MAG_FILTER,GL_NEAREST); 
     if (format->Amask) 
     { 
      gluBuild2DMipmaps(GL_TEXTURE_2D,4,surfaceTex->w,surfaceTex->h,GL_RGBA,GL_UNSIGNED_BYTE,surfaceTex->pixels); 
     } 
     else 
     { 
      gluBuild2DMipmaps(GL_TEXTURE_2D,3,surfaceTex->w,surfaceTex->h,GL_RGBA,GL_UNSIGNED_BYTE,surfaceTex->pixels); 
     } 
     SDL_FreeSurface(surfaceTex); 
    } 
    else 
    { 
     log("Loading texture failed!",true); 
    } 
    return texture; 
} 

Je veux vraiment que le code soit portable entre les projets, donc je peux dire

Gluint Tex = loadTexture(filename); 

et la texture est prêt.

MISE À JOUR:

est ici la méthode d'exposition pour montrer un cube

cubeTexture = loadTexture(filename); 
glLoadIdentity(); 
glTranslatef(xPos,yPos,zPos); 
xRotate = 1.0; 
yRotate = 1.0; 
zRotate = 1.0; 
glRotatef(angle,xRotate,yRotate,zRotate); 
glEnable(GL_TEXTURE_2D); 
glBindTexture(GL_TEXTURE_2D, cubeTexture); 
glBegin(GL_QUADS); 
    /* Top face */ 
    glNormal3f(0.0f,0.0f,1.0f); /* Top face normal */ 
    glTexCoord2f(0.0f, 0.0f); glVertex3f(Width,  Height, -Depth); /* top right */ 
    glTexCoord2f(1.0f, 0.0f); glVertex3f(-Width,  Height, -Depth); /* top left */ 
    glTexCoord2f(1.0f, 1.0f); glVertex3f(-Width,  Height,  Depth); /* bottom left */ 
    glTexCoord2f(0.0f, 1.0f); glVertex3f(Width,  Height,  Depth); /* bottom right */ 
    /* Bottom face */ 
    glNormal3f(0.0f,0.0f,-1.0f); /* Bottom face normal */ 
    glTexCoord2f(1.0f, 0.0f); glVertex3f(Width,  -Height,  Depth); /* top right */ 
    glTexCoord2f(1.0f, 1.0f); glVertex3f(-Width,  -Height,  Depth); /* top left */ 
    glTexCoord2f(0.0f, 1.0f); glVertex3f(-Width,  -Height, -Depth); /* bottom left */ 
    glTexCoord2f(0.0f, 0.0f); glVertex3f(Width,  -Height, -Depth); /* bottom right */ 
    /* Front face */ 
    glNormal3f(0.0f,1.0f,0.0f); /* Front face normal */ 
    glTexCoord2f(0.0f, 1.0f); glVertex3f(Width,  Height,  Depth); /* top right */ 
    glTexCoord2f(0.0f, 0.0f); glVertex3f(-Width,  Height,  Depth); /* top left */ 
    glTexCoord2f(1.0f, 0.0f); glVertex3f(-Width,  -Height,  Depth); /* bottom left */ 
    glTexCoord2f(1.0f, 1.0f); glVertex3f(Width,  -Height,  Depth); /* bottom right */ 
    /* Back face */ 
    glNormal3f(0.0f,-1.0f,0.0f); /* Back face normal */ 
    glTexCoord2f(1.0f, 1.0f); glVertex3f(Width,  -Height, -Depth); /* top right */ 
    glTexCoord2f(0.0f, 1.0f); glVertex3f(-Width,  -Height, -Depth); /* top left */ 
    glTexCoord2f(0.0f, 0.0f); glVertex3f(-Width,  Height, -Depth); /* bottom left */ 
    glTexCoord2f(1.0f, 0.0f); glVertex3f(Width,  Height, -Depth); /* bottom right */ 
    /* Left face */ 
    glNormal3f(-1.0f,0.0f,0.0f); /* Left face normal */ 
    glTexCoord2f(1.0f, 0.0f); glVertex3f(-Width,  Height,  Depth); /* top right */ 
    glTexCoord2f(1.0f, 1.0f); glVertex3f(-Width,  Height, -Depth); /* top left */ 
    glTexCoord2f(0.0f, 1.0f); glVertex3f(-Width,  -Height, -Depth); /* bottom left */ 
    glTexCoord2f(0.0f, 0.0f); glVertex3f(-Width,  -Height,  Depth); /* bottom right */ 
    /* Right face */ 
    glNormal3f(1.0f,0.0f,0.0f); /* Right face normal */ 
    glTexCoord2f(0.0f, 0.0f); glVertex3f(Width,  Height, -Depth); /* top right */ 
    glTexCoord2f(1.0f, 0.0f); glVertex3f(Width,  Height,  Depth); /* top left */ 
    glTexCoord2f(1.0f, 1.0f); glVertex3f(Width,  -Height,  Depth); /* bottom left */ 
    glTexCoord2f(0.0f, 1.0f); glVertex3f(Width,  -Height, -Depth); /* bottom right */ 

glEnd(); 

et ma fonction GL_INIT

glEnable(GL_TEXTURE_2D);   /* Enable Texture Mapping       */ 
    glShadeModel(GL_SMOOTH);   /* Enable smooth shading       */ 
    glClearColor(0.0f,0.0f,0.0f,0.0f); /* Set the background black       */ 
    glClearDepth(1.0f);     /* Set the depth buffer up       */ 
    glEnable(GL_DEPTH_TEST);   /* Set Depth testing up        */ 
    glDepthFunc(GL_LEQUAL);    /* Sets the type of depth testing to Less or Equal */ 
    glHint(GL_PERSPECTIVE_CORRECTION_HINT,GL_NICEST); /* Uses the nice perspective calcs */ 
    glLightfv(GL_LIGHT1,GL_AMBIENT,LightAmbient);  /* Sets up the ambient light  */ //test 
    glLightfv(GL_LIGHT1,GL_DIFFUSE,LightDiffuse);  /* Sets up the diffuse light  */ //test 
    glLightfv(GL_LIGHT1,GL_POSITION,LightPosition);  /* Sets up the light position  */ //test 
    glEnable(GL_LIGHT1);        /* Enable the first light   */ 

Répondre

1

Assurez-vous de glEnable(GL_TEXTURE_2D). En outre, votre deuxième appel gluBuild2DMipmaps() doit prendre GL_RGB, et non GL_RGBA. Sinon, il se termine après la fin de surfaceTex->pixels.

Essayez ceci:

#include <iostream> 

#include <SDL.h> 
#include <SDL_opengl.h> 
#include <SDL_image.h> 

using namespace std; 

GLuint loadTexture(std::string filename) 
{ 
    GLuint texture; 
    if(SDL_Surface* surfaceTex = IMG_Load(filename.c_str())) 
    { 
     glPixelStorei(GL_UNPACK_ALIGNMENT,4); 
     glGenTextures(1,&texture); 
     glBindTexture(GL_TEXTURE_2D,texture); 
     SDL_PixelFormat *format = surfaceTex->format; 
     glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_NEAREST); 
     glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MAG_FILTER,GL_NEAREST); 
     if (format->Amask) 
     { 
      gluBuild2DMipmaps(GL_TEXTURE_2D,4,surfaceTex->w,surfaceTex->h,GL_RGBA,GL_UNSIGNED_BYTE,surfaceTex->pixels); 
     } 
     else 
     { 
      gluBuild2DMipmaps(GL_TEXTURE_2D,3,surfaceTex->w,surfaceTex->h,GL_RGB,GL_UNSIGNED_BYTE,surfaceTex->pixels); 
     } 
     SDL_FreeSurface(surfaceTex); 
    } 
    else 
    { 
     return 0; 
    } 
    return texture; 
} 


int main(int argc, char* argv[]) 
{ 
    _putenv("SDL_VIDEO_CENTERED=1"); 

    SDL_Init(SDL_INIT_EVERYTHING); 

    int win_w = 800; 
    int win_h = 600; 
    SDL_Surface* display = SDL_SetVideoMode(win_w, win_h, 32, SDL_OPENGL); 

    GLuint tex = loadTexture("concrete.png"); 

    bool running = true; 
    while(running) 
    { 
     // handle all pending events 
     SDL_Event event; 
     while(SDL_PollEvent(&event)) 
     { 
      switch (event.type) 
      { 
       case SDL_KEYDOWN: 
        if(event.key.keysym.sym == SDLK_ESCAPE) 
         running = false; 
        break; 
       case SDL_QUIT: 
        running = false; 
        break; 
       default: 
        break; 
      } 
     } 

     glClearColor(0.0f, 0.0f, 0.0f, 0.0f); 
     glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); 

     glMatrixMode(GL_PROJECTION); 
     glLoadIdentity(); 
     glOrtho(0, win_w, 0, win_h, -10.0, 10.0); 
     glMatrixMode(GL_MODELVIEW); 
     glLoadIdentity(); 

     glEnable(GL_TEXTURE_2D); 
     glBindTexture(GL_TEXTURE_2D, tex); 

     glPushMatrix(); 
     glScalef(200,200,200); 
     glBegin(GL_TRIANGLES); 
     glTexCoord2f(0,0); 
     glVertex2f(0,0); 
     glTexCoord2f(1,0); 
     glVertex2f(1,0); 
     glTexCoord2f(1,1); 
     glVertex2f(1,1); 
     glEnd(); 
     glPopMatrix(); 

     SDL_GL_SwapBuffers(); 
     SDL_Delay(1); 
    } 

    SDL_Quit(); 

    return 0; 
} 

concrete.png:

concrete.png

+0

encore une fois, pas de chance, j'ai posté un peu plus de mon code afin que vous puissiez avoir une meilleure idée de ce que je fais. Essayer de rendre ce code un peu trop modulaire je pense ... – sudorossy

+0

@ashrossy: Donc le programme et l'image que j'ai posté ne fonctionnent pas quand vous le construisez sur votre système? – genpfault

+0

Non, Segfault. Je ne suis pas génial avec le débogueur, mais c'est apparemment le second gluBuild2DMipmaps. – sudorossy

0
+0

où exactement dois-je mettre dans mon code? Merci d'avance. – sudorossy

+0

Là où vous avez 'glPixelStorei (GL_UNPACK_ALIGNMENT, 4)'. – genpfault

+0

J'ai remplacé gluBuild2DMipmaps avec glTexImage2D et pas de chance. J'ai même remplacé la fonction par celle d'un portage SDL des tutoriels de Nehe. Pas de chance. Je suppose maintenant qu'il y a plus à ce problème qu'un simple chargement d'image. – sudorossy