Loading Texture

Started by
9 comments, last by Gorax 18 years, 9 months ago
Hi there, I'm a newbie to Opengl programming and am currently trying to work with texture mapping. Now i'm trying to build a function to load a texture from a bitmap as the below code shows. However the texture is not loading at all my box is drawn but without any texture. Can somebody please take a look and point out what i'm doing wrong, as i've been working on this piece of code for 2 day. #include <windows.h> ##include <stdio.h> #include <stdlib.h> #include <math.h> #include <gl\gl.h> #include <gl\glu.h> #include <gl\glaux.h> GLuint texture; int LoadGLBitmap(const char*, LONG*, LONG*, GLubyte*); int LoadTexture(const char*, GLuint*); int InitGL(GLvoid) { glEnable(GL_TEXTURE_2D); LoadTexture("C:\\wood02.bmp", &texture); DrawBox() return TRUE; } int LoadGLBitmap(const char* FileName, LONG *Width, LONG *Height, GLubyte* pData) { ////// Defines #define BITMAP_ID 0x4D42 // the universal bitmap ID FILE *filePtr; BITMAPINFOHEADER InfoHeader; BITMAPFILEHEADER FileHeader; int imageIdx = 0; // image index counter unsigned chartempRGB; // swap variable // open filename in "read binary" mode filePtr = fopen(FileName, "rb"); if (filePtr == NULL) return NULL; // read the bitmap file header fread(&FileHeader, sizeof(BITMAPFILEHEADER), 1, filePtr); // verify that this is a bitmap by checking for the universal bitmap id if (FileHeader.bfType != BITMAP_ID) { fclose(filePtr); return NULL; } // read the bitmap information header fread(&InfoHeader, sizeof(BITMAPINFOHEADER), 1, filePtr); // move file pointer to beginning of bitmap data fseek(filePtr, FileHeader.bfOffBits, SEEK_SET); // allocate enough memory for the bitmap image data pData = (unsigned char*)malloc(InfoHeader.biSizeImage); // verify memory allocation if (!pData) { free(pData); fclose(filePtr); return NULL; } // read in the bitmap image data fread(pData, 1, InfoHeader.biSizeImage, filePtr); // make sure bitmap image data was read if (pData == NULL) { fclose(filePtr); return NULL; } // swap the R and B values to get RGB since the bitmap color format is in BGR for (imageIdx = 0; imageIdx < InfoHeader.biSizeImage; imageIdx+=3) { tempRGB = pData[imageIdx]; pData[imageIdx] = pData[imageIdx + 2]; pData[imageIdx + 2] = tempRGB; } // close the file and return the bitmap image data fclose(filePtr); *Width = InfoHeader.biWidth; *Height = InfoHeader.biHeight; return TRUE; }// End of LoadGLBitmap Function int LoadTexture(const char* Filename, GLuint* Texture) { LONG Width; LONG Height; GLubyte *pmsData=0; if(!LoadGLBitmap(Filename, &Width, &Height, pmsData)) { MessageBox(NULL,"Unable to Load Texture!","SHUTDOWN ERROR",MB_OK | MB_ICONINFORMATION); return 0; } glGenTextures(1, Texture); glBindTexture(GL_TEXTURE_2D, *Texture); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST); // generate the texture image glTexImage2D(GL_TEXTURE_2D, 0, GL_RGB, Width, Height, 0, GL_RGB, GL_UNSIGNED_BYTE, pmsData); free(pmsData); return 1; }// End of LoadTexture Function glEnable(GL_TEXTURE_2D); LoadTexture("C:\\wood02.bmp", &texture);
Advertisement
Hi, I do not know if this will solve your problem: but I do see something
you should correct:

The third parameter (components) you pass to glTexImage2D() can only be 1, 2, 3 or 4(not GL_RGB).

typically you can get this value by dividing the bits per pixel (bpp) value by
the number of bits per component->

and, typically for a 24 bit bmp you would have 24/8 = 3:
That is 3 components.

so put 3 in there and see how you go.
I'm afraid to say steven katic that you are infact wrong.
The third parameter of glTexImage() is infact the internal format flag, which has many different values which can be placed there, GL_RGB and GL_RGBA being the most common.
Now, you might have ment the 7th paramter, which indeed indictes the format of the incoming data, however this is a GLenum type and thus it is perfectly valid to use GL_RGB, GL_RGBA or any other valid enum value in that place.

This is why out of data tutorials should be burned from the internet as we know it [grin]

anyways, gp343, is your texture size a power-of-two in both dimentions? (ie 16x16, 32x16, 256x256 etc?)

also, the glaux library is out dated and as close to pure evil as you can get, you'll be wanting to find something else to load textures with (infact, gimmie 10mins and I'll add some links to the FAQ [grin])
Thankyou _The_Phantom_ for the correction.
Sorry I did reference old documentation for that information. Naughty me.

Speaking of using something else to load textures:

From a practical point of view I do not have any problems using

gluBuild2DMipmaps() function. What do you think phantom?
Nowt wrong with using it, however I favour just turning on automatic mipmap generation before uploading the base texture image and let the hardware sort it out (GL_SGIS_generate_mipmap being the extension in question) or using the FBO GenerateMipmap() function.

These should both give you the same result as using the glu function, possibly a little faster, if you need todo any complex mipmap generation you'd be better off doing it yaself anyways.
All i'm trying to achieved with the previous posted code is to apply a texture to a simple QUAD. That is all. I wanted to code to be as Loosely Couple as possible. Most of the previous codes i've seen uses Global BITMAPINFOHEADER, BITMAPFILEHEADER structures, which does not follow the Loosely Couple-Highly Cohesive principles.

Regards

James (GP343)
....does that mean that the advice here has not helped you yet?
I'm sorry, but not yet, i'm still trying to load the texture onto a Quad.
I'm dereferencing all of my pointers correctly, i just can't see why this isn;t working.
so your texture is definately a power of two in both its directions?
Yes, my texture is a power of two in both direction. I solved the problem anyway by re-arranging the code a bit.

All i did was to Re-defined the signature of the "LoadGLBitmap" function from:
int LoadGLBitmap(const char*, LONG*, LONG*, GLubyte*);

To:
GLubyte* LoadGLBitmap(const char* FileName, LONG *Width, LONG *Height)

Now the codes work as follow:

GLuint textureObject;
LoadTexture("C:\\wood02.bmp", &textureObject);

Anyway, thanks to everybody for all the help rendered.

James.

This topic is closed to new replies.

Advertisement