Hi,
I was trying to setup a frame buffer and when I'm rendering the texture on a quad it's only rendering the blue component.
The problem is that if I'm not rendering to the FBO all the colors are correct. And rendering to the FBO and then the FBO to the screen only shows the blue component.
I spent a couple of hours trying to figure out the bug. After comparing my code with other frame buffer code I found on the internet and not seeing any "major" differences (well... not things that could make this to render only the blue component) I decided to come here and ask for help :).
This is the code I use to setup the FBO:
// Create frame buffer with the texture and depth buffer
::glGenFramebuffersEXT(1, &m_hFBO);
::glGenRenderbuffersEXT(1, &m_hDepthBuffer);
::glGenTextures(1, &m_hTexture);
// Bind the FBO
::glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, m_hFBO);
// Setup the FBO (texture)
::glBindTexture(GL_TEXTURE_2D, m_hTexture);
::glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, m_nWidth, m_nHeight, 0, GL_RGBA, GL_UNSIGNED_BYTE, NULL);
::glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
::glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
::glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT, GL_TEXTURE_2D, m_hTexture, 0);
::glGenerateMipmapEXT(GL_TEXTURE_2D);
// Setup the FBO (depth)
::glBindRenderbufferEXT(GL_RENDERBUFFER_EXT, m_hDepthBuffer);
::glRenderbufferStorageEXT(GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT24, m_nWidth, m_nHeight);
::glFramebufferRenderbufferEXT(GL_FRAMEBUFFER_EXT, GL_DEPTH_ATTACHMENT_EXT, GL_RENDERBUFFER_EXT, m_hDepthBuffer);
// Check status
GLenum err = ::glCheckFramebufferStatusEXT(GL_FRAMEBUFFER_EXT);
if (err != GL_FRAMEBUFFER_COMPLETE_EXT)
{
// Error
assert(false);
}
::glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0);
::glBindTexture(GL_TEXTURE_2D, 0);
::glBindRenderbufferEXT(GL_RENDERBUFFER_EXT, 0);
This is the code I use to set the FBO:
// Unbind any texture
::glBindTexture(GL_TEXTURE_2D, 0);
// Bind the frame buffer
::glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, pTarget->m_hFBO);
// Push the viewport
::glPushAttrib(GL_VIEWPORT_BIT);
::glViewport(0, 0, pTarget->GetWidth(), pTarget->GetHeight());
This is the code I use to set the target to null:
// Pop the view port attribute and set the target to null
::glPopAttrib();
::glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0);
This is the code used to render the FBO on a quad:
float nWidth = (float)m_pWindow->GetWidth();
float nHeight = (float)m_pWindow->GetHeight();
// Push the projection matrix and set the new projection
::glMatrixMode(GL_PROJECTION);
::glPushMatrix();
::glLoadIdentity();
::glOrtho(0, nWidth, 0, nHeight, 0.1f, 1.0f);
// Push the transform matrix and translate
::glMatrixMode(GL_MODELVIEW);
::glPushMatrix();
::glLoadIdentity();
::glTranslatef(0.0f, 0.0f, -0.5f);
// Render the target buffer to the back buffer.
::glEnable(GL_TEXTURE_2D);
::glBindTexture(GL_TEXTURE_2D, pTarget->m_hTexture);
::glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
// Draw the textured quad
::glBegin(GL_QUADS);
::glTexCoord2f(1.0f, 1.0f); glVertex3f(nWidth, nHeight, 0.0f);
::glTexCoord2f(0.0f, 1.0f); glVertex3f(0.0f, nHeight, 0.0f);
::glTexCoord2f(0.0f, 0.0f); glVertex3f(0.0f, 0.0f, 0.0f);
::glTexCoord2f(1.0f, 0.0f); glVertex3f(nWidth, 0.0f, 0.0f);
::glEnd();
// Pop the transform matrix from the stack
::glPopMatrix();
// Pop the projection matrix from the stack
::glMatrixMode(GL_PROJECTION);
::glPopMatrix();
// Set the mode to the model-view matrix
::glMatrixMode(GL_MODELVIEW);
// Swap the buffers
::SwapBuffers(m_hDC);
This is what I'm rendering on the FBO and only:
::glTranslatef(0.0f, 0.0f, -5.0f);
::glBegin(GL_TRIANGLES);
::glColor3f(1.0f, 0.0f, 0.0f);
::glVertex3f(0.0f, 1.0f, 0.0f);
::glColor3f(0.0f, 1.0f, 0.0f);
::glVertex3f(1.0f, 0.0f, 0.0f);
::glColor3f(0.0f, 0.0f, 1.0f);
::glVertex3f(-1.0f, 0.0f, 0.0f);
::glEnd();
It looks exactly like if the two first glColor3f were setting the color to black and the third one to blue.
JFF