1
$\begingroup$

I know there are tons of questions about it, but I found nothing useful so far so, here I am.

I'm trying to render a texture which is attached to a wavefront .obj mesh. I continued to fail (somehow, it was like textures were not correctly loaded), so I wrote a simple example code to see where I was wrong. The sample code follows, and the texture is "correctly" loaded and rendered. However, there are some problems in the render itself: the image is incomplete / blurry / repeated / distorted. I will also post the expected result and the actual result.

Working on Linux Ubuntu 14.04, OpenGL 3.0 Mesa 10.5.9. Any idea of what is happening?

Texture (copyright Angryfly @ Turbosquid) and result on the right: enter image description here

Sample code:

#include <math.h>
#include <GL/gl.h>
#include <GL/glu.h>
#include <SDL2/SDL.h>
#include <SDL2/SDL_image.h>
#include<iostream>

int main(int argc, char* argv[]) {
    SDL_Init( SDL_INIT_VIDEO );
    SDL_GL_SetAttribute( SDL_GL_DEPTH_SIZE, 16 );
    SDL_GL_SetAttribute( SDL_GL_DOUBLEBUFFER, 1 );
    // prepare the window
    SDL_Window *window = SDL_CreateWindow(argv[0], 0, 0,
            800, 600,
            SDL_WINDOW_OPENGL|SDL_WINDOW_RESIZABLE);
    SDL_GLContext context = SDL_GL_CreateContext(window);
    // enable textures and bind a name (say 50)
    glEnable(GL_TEXTURE_2D);
    glBindTexture(GL_TEXTURE_2D, 50);

    glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER,
                     GL_LINEAR_MIPMAP_NEAREST );
    glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);

    glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT );
    glTexParameterf( GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT );
    // load image with SDL
    SDL_Surface *s = IMG_Load("texture.png");
    // the following doesn't work (white space)
    //glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, s->w, s->h, 0, GL_RGB, GL_UNSIGNED_BYTE, s->pixels);
    gluBuild2DMipmaps(GL_TEXTURE_2D, GL_RGB, s->w, s->h, GL_RGB, GL_UNSIGNED_BYTE, s->pixels);

    glViewport(0, 0, 800, 600);
    glClearColor(1,1,1,1);
    glMatrixMode(GL_PROJECTION);
    glLoadIdentity();
    gluPerspective(70, 0.75, 0.2, 1000);

    glMatrixMode(GL_MODELVIEW);
    glLoadIdentity();
    glClear( GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT );
    gluLookAt(0, 10, 0, 0, 0, 0, 1, 0, 0);

    glActiveTexture(50);
    // display texture as 2 triangles.
    glBegin(GL_TRIANGLES);
    glTexCoord2d(0,0); glVertex3d(-5, 0, -5);
    glTexCoord2d(0,1); glVertex3d(-5, 0, 5);
    glTexCoord2d(1,0); glVertex3d(5, 0, -5);

    glTexCoord2d(0,1); glVertex3d(-5, 0, 5);
    glTexCoord2d(1,0); glVertex3d(5, 0, -5);
    glTexCoord2d(1,1); glVertex3d(5, 0, 5);

    glEnd();
    glFinish();
    SDL_GL_SwapWindow(window);
    // wait for quit procedure
    SDL_Quit();
    return 0;

}
$\endgroup$
  • $\begingroup$ Is there any reason why you use the old style openGL $\endgroup$ – joojaa Jun 10 '16 at 14:06
  • $\begingroup$ It is a computer graphics project in OpenGL and SDL. $\endgroup$ – phagio Jun 11 '16 at 14:58
  • $\begingroup$ that's not a reason its a circular definition. $\endgroup$ – joojaa Jun 11 '16 at 15:07
  • 1
    $\begingroup$ Yes but why are you using obsolete and deprecated openGL calls? $\endgroup$ – joojaa Jun 12 '16 at 21:57
  • 1
    $\begingroup$ Yes that's what deprecated means, any new code should not use this method if possible (here its possible). Read its not very performant why-do-vertex-buffer-objects-improve-performance. Nobody should be teaching you this stuff anymore. $\endgroup$ – joojaa Jun 14 '16 at 8:03
7
$\begingroup$

This type of artifact is a tell-tale sign that you've messed up your texture image format at the byte level. It's hard to tell what exactly is wrong, but it's something along the lines of bad pitch or a component layout mismatch.

Have a read of this wiki page and try again. glTexImage2D should work, keep trying until it does.

$\endgroup$
  • $\begingroup$ Thank you! I might as well try to reimplement some basic reader - but in the sample code that was given as example the calls didn't mess up things like this. I'm going to look at it again! $\endgroup$ – phagio Jun 11 '16 at 15:00
  • $\begingroup$ I see you're using the SDL surface's pixel buffer directly. You could get the debug version of the SDL library and the source, and inspect what's happening inside SDL. The core of the problem is that OpenGL expects the pixels to be laid out in memory differently than what is actually in the buffer. $\endgroup$ – IneQuation Jun 11 '16 at 16:29
  • $\begingroup$ I "surprisingly" solved by letting the code load a jpg rather than a png. I guess SDL likes MPEG codecs more than PNG. $\endgroup$ – phagio Jun 17 '16 at 11:55
  • 1
    $\begingroup$ PNG supports alpha, JPEG doesn't. Have you tried uploading your PNG texture as GL_RGBA, not GL_RGB? Because you haven't solved your problem, you just sidestepped it. $\endgroup$ – IneQuation Jun 20 '16 at 7:26

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.