Hello! I don't usually ask for help, but I'm at wit's end trying to solve this puzzle. The problem is that I am trying to test a hand-written PNG loader by rendering the image data onscreen, but no matter what I try I can't get it to show up more than a solid white quad(white is the image's background color, though. Without a texture the quad shows up black). I've checked around the internet and tried a bunch of solutions but none of them have worked so far. However, just for a sanity check, I'll go through it all one more time:
1. Make sure that your image isn't loaded before openGL is initialized:
//WNDPROC case WM_CREATE
switch (uMsg){
case WM_CREATE:
hdc = GetDC(hwnd);
PIXELFORMATDESCRIPTOR pfd;
int pixelFormat;
memset(&pfd,0,sizeof(PIXELFORMATDESCRIPTOR));
pfd.nSize = sizeof(PIXELFORMATDESCRIPTOR);
pfd.nVersion = 1;
pfd.dwFlags = PFD_DRAW_TO_WINDOW | PFD_SUPPORT_OPENGL | PFD_DOUBLEBUFFER;
pfd.iPixelType = PFD_TYPE_RGBA;
pfd.cColorBits = 32;
pfd.cDepthBits = 16;
pfd.iLayerType = PFD_MAIN_PLANE;
pixelFormat = ChoosePixelFormat(hdc,&pfd);
SetPixelFormat(hdc,pixelFormat,&pfd);
hrc = wglCreateContext(hdc);
wglMakeCurrent(hdc,hrc);
glewInit(); //Opengl Init somewhere right here
wglMakeCurrent(hdc,hrc);
Window::s_hWnd = hwnd;
g.Initialize(); //Image Load Here
return 0;
2. Make sure that you have mipmaps disabled/ filtering at linear or nearest:
//Image. Load(), not called with constructor
//Load Image...
glEnable( GL_TEXTURE_2D );
glActiveTexture(GL_TEXTURE0);
glGenTextures(1,&TexID); //create TexBuffer
glBindTexture(GL_TEXTURE_2D,TexID); //Finalize and make it current
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_BASE_LEVEL, 0);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAX_LEVEL, 0);
glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MAG_FILTER,GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D,GL_TEXTURE_MIN_FILTER,GL_NEAREST);
glTexImage2D(GL_TEXTURE_2D,0,GL_RGBA8,Width,Height,0,GL_RGBA,GL_UNSIGNED_BYTE,getImageData());
//getImageData() returns &ImageData[0];
glDisable( GL_TEXTURE_2D ); //I heard this solved one person's problem, no change either way.
}
3.Make sure your shaders are set up properly
#version 130 //fragment shader
uniform sampler2D texture0;
uniform vec3 Material; //future uniform
uniform vec3 Color; //future uniform
in vec2 texCoord; //matches with vertex shader
out vec4 outColor;
void main(void) {
outColor = texture(texture0, texCoord.st);
}
The attribute for tex coords is bound at slot 2, and at runtime the uniform slot for "texture0" is 2 according to the debugger
4. Make sure your draw calls send tex coordinates
(Like I said before I tried this with immediate mode and it still didn't work)
//rendering loop
glEnable( GL_TEXTURE_2D );
glActiveTexture(GL_TEXTURE0);
//for loop{
glBindTexture(GL_TEXTURE_2D,Store.Models.Block[i].Data->TexID);
glUniform1i(Cam.Lens.TEXTURE_0,0);
//matrix transforms..
glBindBuffer(GL_ARRAY_BUFFER,Store.Models.Block[i].VBO);
//stored as one big buffer, 3 vertex floats, 3 normal floats,and 2 texcoord floats per vertex
glVertexAttribPointer(0,3,GL_FLOAT,GL_FALSE,8*sizeof(float),0); //Veticies
glVertexAttribPointer(1,3,GL_FLOAT,GL_FALSE,8*sizeof(float),(GLvoid*)(3*sizeof(float))); //Normals
glVertexAttribPointer(2,2,GL_FLOAT,GL_FALSE,8*sizeof(float),(GLvoid*)(6*sizeof(float))); //TexCoords
glDrawElements(GL_TRIANGLE_STRIP,Store.Models.Block[i].Data->ILength,
GL_UNSIGNED_SHORT,&Store.Models.Block[i].Data->Index[0]);
}
glDisable( GL_TEXTURE_2D );
}//end
5. What are you trying to draw?
//Data for the model
float VertsNormUV[32] = {1,0,0, 0,0,1 ,0,0,
1,1,0, 0,0,1 ,0,1,
0,1,0, 0,0,1 ,1,1,
0,0,0, 0,0,1 ,1,0,};
short indecies[6] = {1,2,3,1,0,3};
6 Where are you storing it?
The model data, model instances, and images are all stored in a container class owned by a global Graphics class (g), which initializes it's data at the end of the WndProc Create message(in #1).
On top of that, after I load the image data into the texture object, I can get the same data back out with glGetTexImage().So the texture is loading properly, and the vertecies are rendering correctly, but it still isn't textured right. The image is a small 16x16 sprite, which should work because it's a power of two.
Anyways, I'm struggling to figure this one out, so any help would be appreciated!