PDA

View Full Version : REnder to FBO larger than window



OldMan
02-11-2009, 05:35 AM
Hello.

I am working in a project where the rendered images are to be retrieved to CPU side. I render the image into a FBO with a render buffer created with 1024x1024 resolution. Then using PBO I copy them to be processed.

Works, with exception of one thing. If the window is smaller than the FBO render buffer, then the image rendered is also smaller.

Example if my window is 512x512 and my FBO render buffer is 1024x1024 , only 1/4 of the final image has something drawn.

Any ideas what I could be doing wrong? Or Is there some limitation of the render buffers need to be smaller than the application window?

Thanks in advance.

Jackis
02-11-2009, 05:40 AM
It could happen, if you forget to set new glViewport() and glScissor() when you activate your FBO, so it rests from the window viewport.

OldMan
02-11-2009, 06:05 AM
Hi again. That made sense, and I tried it. But made no difference. I forgot to say that is not only the draw commands that seem to be restricted to the window size, but the clear buffer commands as well. In fact 3/4 of the image are simply trash and interference.

But I assume, due to your answer, that then I should be able to make a FBO with a render frame larger than the window.

ZbuffeR
02-11-2009, 07:01 AM
FBO is meant to be independent from the window size.
Most probably it is something you do not set up correctly on your side.
What is your hardware ?

OldMan
02-11-2009, 07:31 AM
A QUADRO NVS 290 in a linux box.

Its the first time I work with FBO without attaching a texture to it as target. All the material for learning that I found has examples with render to texture (but that is not what I need), so very likely I am doing something wrong. If anyone can point for an example where FBO are used to render to offscreen and then copy the data to CPU side, so I could doublechack all my steps, I would appreciate a lot.

OldMan
02-11-2009, 07:42 AM
Well I found out that in fact the rendering is NOT being performed to the FBO (just added a SDL:SwapBuffers to check) (don't know why since I do bind it.) Since the rendering is going to the normal window that explains why of the strange size issues :)

OldMan
02-11-2009, 10:46 AM
Hi sorry to bother again. I went back to basics and made it work.. in a PYTHON prototype.

Then I decided to do a C++ prototype to check all again. The code follows of a prototype without PBO. This exact code in python works and the image read from FBO and saved is a red triangle and nothing appears on window. But in CCp is like the FBO never binds and nothing is rendered to the FBO, in fact all goes to the back buffer.

The code is very short to just summarize the issue. If any one can point me what is so wrong that the FBO is never used I would appreciate a lot.

#include "GLee.h"
#include <GL/glut.h>
#include <fstream>
#include <iostream>

float color[3];

GLuint framebuffer,colorbuffer,depthbuffer;
void renderScene(void);

void init()
{
//create a FBO
glGenFramebuffers(1, &framebuffer);
glBindFramebuffer(GL_FRAMEBUFFER_EXT, framebuffer);

// Setup depthbuffer and colorbuffer
glGenRenderbuffers(1,&depthbuffer);
glGenRenderbuffersEXT(1,&colorbuffer);
glBindRenderbufferEXT (GL_RENDERBUFFER_EXT,depthbuffer);
glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT, 1024, 1024);
glFramebufferRenderbufferEXT(GL_FRAMEBUFFER_EXT, GL_DEPTH_ATTACHMENT,GL_RENDERBUFFER_EXT, depthbuffer);
glBindRenderbufferEXT (GL_RENDERBUFFER_EXT,colorbuffer);
glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_RGBA, 1024, 1024);
glFramebufferRenderbufferEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT,
GL_RENDERBUFFER_EXT, colorbuffer);


GLuint status = glCheckFramebufferStatusEXT (GL_FRAMEBUFFER_EXT);
if( status != GL_FRAMEBUFFER_COMPLETE)
{
std::cout<< "Error in framebuffer activation:"<<status<<std::endl;
}

glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, framebuffer);
glDrawBuffer(GL_COLOR_ATTACHMENT0_EXT);
glViewport (0, 0, 1024, 1024);

//make render red
color[0]=1.0f;
color[1]=0.0f;
color[2]=0.0f;
//render
renderScene();
//read data from the buffer
glReadBuffer(GL_COLOR_ATTACHMENT0_EXT);
char * data = new char[1024*1024*4];
glReadPixels (0, 0, 1024, 1024, GL_RGBA, GL_UNSIGNED_BYTE,data);
//write to file
std::ofstream file("/tmp/foca.raw");
file.write(data,1024*1024*4);
delete[] data;

//make it render green
color[0]=0.0f;
color[1]=1.0f;
color[2]=0.0f;


}

void renderScene(void)
{
glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT);
glColor3fv(color);
glBegin(GL_TRIANGLES);
glVertex3f(-0.5,-0.5,0.0);
glVertex3f(0.5,0.0,0.0);
glVertex3f(0.0,0.5,0.0);
glEnd();
glutSwapBuffers();

}

int main(int argc, char **argv)
{
glutInit(&argc, argv);
glutInitDisplayMode(GLUT_DEPTH | GLUT_DOUBLE | GLUT_RGB);
glutInitWindowPosition(100,100);
glutInitWindowSize(256,256);
glutCreateWindow("I HATE FBOs!!");
GLeeInit();
init();
glutDisplayFunc(renderScene);
glutMainLoop();
}

Brolingstanz
02-11-2009, 01:35 PM
have you tried using one of the sized internal formats (depth and color)?

OldMan
02-12-2009, 02:52 AM
You mean:
glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT,GL_DEPTH_COMPONENT16, 1024, 1024);
glFramebufferRenderbufferEXT(GL_FRAMEBUFFER_EXT, GL_DEPTH_ATTACHMENT,GL_RENDERBUFFER_EXT, depthbuffer);
glBindRenderbufferEXT (GL_RENDERBUFFER_EXT,colorbuffer);
glRenderbufferStorageEXT (GL_RENDERBUFFER_EXT, GL_RGBA4, 1024, 1024);
?

Makes no difference :(

Impressive how hard is to find an example where the render target is not a texture but a simple FBO to copy to CPU with the PBOs.

Brolingstanz
02-12-2009, 04:45 PM
Don't see anything else. Bind 0 framebuffer at end of init so you'll get output to window.

Nicolas Lelong
02-14-2009, 03:26 AM
Just a quick thought, untested like hell, but wouldn't it be related to the fact that you systematically call 'glutSwapBuffers', even after drawing to your FBO. I'd tend to think that you don't need this call, and that it perhaps destroys the FBO content, perhaps...