🎉 Celebrating 25 Years of GameDev.net! 🎉

Not many can claim 25 years on the Internet! Join us in celebrating this milestone. Learn more about our history, and thank you for being a part of our community!

Wrong colors with tutorial 5+6 using SDL

Started by
4 comments, last by lc_overlord 17 years, 5 months ago
Hi there, first this is an impressive collection of tutorials here on NeHe Productions, really appreciated! My question is about OpenGL tutorial 6. I was able to successfully complete the tutorial. I wanted to test using the objects used in tutorial 5 and put them back in tutorial 6. I found out that the two old objects from tutorial 5 lost some of its colors. The pyramid showed black corners instead of red ones, and the cube has lost several of its colored faces, including red and orange, which are now showing black instead. I discovered that simply removing the line "glEnable(GL_TEXTURE_2D);" makes all colors back to normal again. But of course, the new cube from tutorial 6 is pink and no longer has any textures, as expected. It's also worth saying that I'm using the Linux/SDL environment. I have played a bit with the glTexImage2D function and I found out that the Linux/SDL port of tutorial 6 used GL_BGR instead of GL_RGB. When I tried to change to GL_RGB, of course the bitmap had the wrong color, but the red was back and the blue was missing too! And I thought glTexImage2D wasn't supposed to affect colors outside a texture! Anybody could help me with that issue?
Advertisement
I hope I'm not entirely wrong, but I think that when you want to change the color of a textured object or when you enable lightning you should use glMaterial instead of glColor to change the color of the object. As an alternative you could use glColorMaterial, and you'll be able to use glColor as usual.
I want to change correctly the color of non-textured objects when textures are enabled. When I completely remove my textured object, the simple fact of loading my texture messes my glColors.

I also tried using SDL_image and IMG_Load with a PNG file instead of a BMP, but it gives the same result.

I haven't noticed before, but the texture I used (nehe.bmp) lost its green. I tried with a small BMP having every basic color and green becomes black and white becomes the same pink that I got when I disabled textures.

I tried adding a glColor3f(1.0f,1.0f,1.0f) before the textured object... and SURPRISE everything was back to normal! Just as if all of the screen was actually tainted pink before any drawing.

I then tried with different images. The Nehe logo (nehe.bmp) was back to normal, but colors of non-textured objects were wrong. My small test picture drawn in Paint was normal and all other objects too. And finally I tried with http://en.wikipedia.org/wiki/Image:PNG_transparency_demonstration_1.png because it has an alpha channel, and it showed correctly, but all non-textured object are completely black!

Seems like something is not reset correctly between each draw or something...

By the way here is some sample code I'm trying to use:


*******************************

GLuint textures[1];

GLuint SDL_GL_LoadTexture(SDL_Surface *surface/*, GLfloat *texcoord*/)
{
GLuint texture;
int w, h;
SDL_Surface *image;
SDL_Rect area;
Uint32 saved_flags;
Uint8 saved_alpha;

/* Use the surface width and height expanded to powers of 2 */
w = power_of_two(surface->w);
h = power_of_two(surface->h);
//texcoord[0] = 0.0f; /* Min X */
//texcoord[1] = 0.0f; /* Min Y */
//texcoord[2] = (GLfloat)surface->w / w; /* Max X */
//texcoord[3] = (GLfloat)surface->h / h; /* Max Y */

image = SDL_CreateRGBSurface(
SDL_SWSURFACE,
w, h,
32,
#if SDL_BYTEORDER == SDL_LIL_ENDIAN /* OpenGL RGBA masks */
0x000000FF,
0x0000FF00,
0x00FF0000,
0xFF000000
#else
0xFF000000,
0x00FF0000,
0x0000FF00,
0x000000FF
#endif
);
if ( image == NULL ) {
return 0;
}

/* Save the alpha blending attributes */
saved_flags = surface->flags&(SDL_SRCALPHA|SDL_RLEACCELOK);
saved_alpha = surface->format->alpha;
if ( (saved_flags & SDL_SRCALPHA) == SDL_SRCALPHA ) {
SDL_SetAlpha(surface, 0, 0);
}

/* Copy the surface into the GL texture image */
area.x = 0;
area.y = 0;
area.w = surface->w;
area.h = surface->h;
SDL_BlitSurface(surface, &area, image, &area);

/* Restore the alpha blending attributes */
if ( (saved_flags & SDL_SRCALPHA) == SDL_SRCALPHA ) {
SDL_SetAlpha(surface, saved_flags, saved_alpha);
}

/* Create an OpenGL texture for the image */
glGenTextures(1, &texture);
glBindTexture(GL_TEXTURE_2D, texture);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); // *** GL_LINEAR
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); // *** GL_LINEAR
glTexImage2D(GL_TEXTURE_2D,
0,
GL_RGBA,
w, h,
0,
GL_RGBA,
GL_UNSIGNED_BYTE,
image->pixels);
SDL_FreeSurface(image); /* No longer needed */

return texture;
}

bool loadTextures() {
int status = false;
SDL_Surface *temp, *TextureImage[1];
if ((temp = IMG_Load("tva.png"))) {
TextureImage[0] = SDL_DisplayFormatAlpha(temp);
SDL_FreeSurface(temp);
status = true;
textures[0] = SDL_GL_LoadTexture(TextureImage[0]);
}

if (TextureImage[0]) SDL_FreeSurface(TextureImage[0]);

return status;
}
What you could do is to first disable GL_TEXTURE_2D and render the non-textured objects and then enable textures again and render the textured objects. That's what I do. :)
I think that should fix your problem.
It... IT WORKED! :O I wonder if OpenGL is supposed to behave like or if this method is only a workaround... but I don't care now! :P

Thank you very very very much, now I can finally finish the engine for my indie game! Can't tell you what it is now, but if you want I can send you a PM once details will be finalized. ;)
It's supposed to work like this, openGL is state machine which means that the last value or mode set(like texturing, texture coordinates, normals, color and so on) stays that way until you say otherwise.
So if you are rendering a textured object and then an untextured object, you have to disable texturing between the two or else the untextured object will also have a texture on it (although be it a single textel streched across the whole object).

This topic is closed to new replies.

Advertisement