Difference between revisions of "Framebuffer Object Extension Examples"

From OpenGL Wiki
Jump to: navigation, search
m
Line 1: Line 1:
 +
RTT = render_to_texture<br>
 +
<br>
 +
 
=== Quick example, render_to_texture (2D) ===
 
=== Quick example, render_to_texture (2D) ===
  
Line 63: Line 66:
 
   //Bind 0, which means render to back buffer
 
   //Bind 0, which means render to back buffer
 
   glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0);
 
   glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0);
 +
 +
=== Quick example, render_to_texture (2D), mipmaps ===
 +
  //RGBA8 2D texture, 24 bit depth texture, 256x256
 +
  glGenTextures(1, &color_tex);
 +
  glBindTexture(GL_TEXTURE_2D, color_tex);
 +
  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
 +
  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
 +
  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR);
 +
  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
 +
  //NULL means reserve texture memory, but texels are undefined
 +
  //**** Tell OpenGL to reserve level 0
 +
  glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8, 256, 256, 0, GL_BGRA, GL_UNSIGNED_BYTE, NULL);
 +
  //You must reserve memory for other mipmaps levels as well either by making a series of calls to
 +
  //glTexImage2D or use glGenerateMipmapEXT(GL_TEXTURE_2D).
 +
  //Here, we'll use :
 +
  glGenerateMipmapEXT(GL_TEXTURE_2D)
 +
  //-------------------------
 +
  glGenFramebuffersEXT(1, &fb);
 +
  glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, fb);
 +
  //Attach 2D texture to this FBO
 +
  glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT, GL_TEXTURE_2D, color_tex, 0);
 +
  //-------------------------
 +
  glGenRenderbuffersEXT(1, &depth_rb);
 +
  glRenderbufferStorageEXT(GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT24, 256, 256);
 +
  //-------------------------
 +
  //Attach depth buffer to FBO
 +
  glFramebufferRenderbufferEXT(GL_FRAMEBUFFER_EXT, GL_DEPTH_ATTACHMENT_EXT, GL_RENDERBUFFER_EXT, depth_rb);
 +
  //-------------------------
 +
  //Does the GPU support current FBO configuration?
 +
  GLenum status;
 +
  status = glCheckFramebufferStatusEXT(GL_FRAMEBUFFER_EXT);
 +
  switch(status)
 +
  {
 +
      case GL_FRAMEBUFFER_COMPLETE_EXT:
 +
      cout<<"good";
 +
  default:
 +
      HANDLE_THE_ERROR;
 +
  }
 +
  //-------------------------
 +
  //and now you can render to GL_TEXTURE_2D
 +
  glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, fb);
 +
  glClearColor(0.0, 0.0, 0.0, 0.0);
 +
  glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
 +
  //-------------------------
 +
  glViewport(0, 0, 256, 256);
 +
  glMatrixMode(GL_PROJECTION);
 +
  glLoadIdentity();
 +
  glOrtho(0.0, 256.0, 0.0, 256.0, -1.0, 1.0);
 +
  glMatrixMode(GL_MODELVIEW);
 +
  glLoadIdentity();
 +
  //-------------------------
 +
  glDisable(GL_TEXTURE_2D);
 +
  glDisable(GL_BLEND);
 +
  glEnable(GL_DEPTH_TEST);
 +
  //-------------------------
 +
  glColor3f(1.0, 1.0, 0.0);
 +
  glBegin(GL_TRIANGLES);
 +
  glVertex2f(0.0, 0.0);
 +
  glVertex2f(256.0, 0.0);
 +
  glVertex2f(256.0 , 256.0);
 +
  glEnd();
 +
  //-------------------------
 +
  GLubyte pixels[4*4*4];
 +
  glReadPixels(0, 0, 4, 4, GL_BGRA, GL_UNSIGNED_BYTE, pixels);
 +
  //pixels 0, 1, 2 should be white
 +
  //pixel 4 should be black
 +
  //----------------
 +
  //Bind 0, which means render to back buffer
 +
  glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0);
 +
  //----------------
 +
  //**** Now that we rendered to level 0 of the texture, we must generate the mipmaps.
 +
  //This should be quick since it is done on the GPU.
 +
  glBindTexture(GL_TEXTURE_2D, color_tex);
 +
  glGenerateMipmapEXT(GL_TEXTURE_2D)
  
 
=== Quick example, render_to_texture (Cubemap) ===
 
=== Quick example, render_to_texture (Cubemap) ===
Line 104: Line 181:
 
   //-------------------------
 
   //-------------------------
 
   //and now you can render to GL_TEXTURE_CUBE_MAP_POSITIVE_X
 
   //and now you can render to GL_TEXTURE_CUBE_MAP_POSITIVE_X
 +
  //In order to render to the other faces, do this :
 +
  glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT, GL_TEXTURE_CUBE_MAP_POSITIVE_Y, color_tex, 0);
 +
  //... now render
 +
  glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT, GL_TEXTURE_CUBE_MAP_POSITIVE_Z, color_tex, 0);
 +
  //... now render
 +
  //... and so on

Revision as of 04:55, 31 August 2008

RTT = render_to_texture

Quick example, render_to_texture (2D)

  //RGBA8 2D texture, 24 bit depth texture, 256x256
  glGenTextures(1, &color_tex);
  glBindTexture(GL_TEXTURE_2D, color_tex);
  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
  //NULL means reserve texture memory, but texels are undefined
  glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8, 256, 256, 0, GL_BGRA, GL_UNSIGNED_BYTE, NULL);
  //-------------------------
  glGenFramebuffersEXT(1, &fb);
  glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, fb);
  //Attach 2D texture to this FBO
  glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT, GL_TEXTURE_2D, color_tex, 0);
  //-------------------------
  glGenRenderbuffersEXT(1, &depth_rb);
  glRenderbufferStorageEXT(GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT24, 256, 256);
  //-------------------------
  //Attach depth buffer to FBO
  glFramebufferRenderbufferEXT(GL_FRAMEBUFFER_EXT, GL_DEPTH_ATTACHMENT_EXT, GL_RENDERBUFFER_EXT, depth_rb);
  //-------------------------
  //Does the GPU support current FBO configuration?
  GLenum status;
  status = glCheckFramebufferStatusEXT(GL_FRAMEBUFFER_EXT);
  switch(status)
  {
     case GL_FRAMEBUFFER_COMPLETE_EXT:
     cout<<"good";
  default:
     HANDLE_THE_ERROR;
  }
  //-------------------------
  //and now you can render to GL_TEXTURE_2D
  glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, fb);
  glClearColor(0.0, 0.0, 0.0, 0.0);
  glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
  //-------------------------
  glViewport(0, 0, 256, 256);
  glMatrixMode(GL_PROJECTION);
  glLoadIdentity();
  glOrtho(0.0, 256.0, 0.0, 256.0, -1.0, 1.0); 
  glMatrixMode(GL_MODELVIEW);
  glLoadIdentity();
  //-------------------------
  glDisable(GL_TEXTURE_2D);
  glDisable(GL_BLEND);
  glEnable(GL_DEPTH_TEST);
  //-------------------------
  glColor3f(1.0, 1.0, 0.0);
  glBegin(GL_TRIANGLES);
  glVertex2f(0.0, 0.0);
  glVertex2f(256.0, 0.0);
  glVertex2f(256.0 , 256.0);
  glEnd();
  //-------------------------
  GLubyte pixels[4*4*4];
  glReadPixels(0, 0, 4, 4, GL_BGRA, GL_UNSIGNED_BYTE, pixels);
  //pixels 0, 1, 2 should be white
  //pixel 4 should be black
  //----------------
  //Bind 0, which means render to back buffer
  glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0);

Quick example, render_to_texture (2D), mipmaps

  //RGBA8 2D texture, 24 bit depth texture, 256x256
  glGenTextures(1, &color_tex);
  glBindTexture(GL_TEXTURE_2D, color_tex);
  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_REPEAT);
  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_REPEAT);
  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR_MIPMAP_LINEAR);
  glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
  //NULL means reserve texture memory, but texels are undefined
  //**** Tell OpenGL to reserve level 0
  glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8, 256, 256, 0, GL_BGRA, GL_UNSIGNED_BYTE, NULL);
  //You must reserve memory for other mipmaps levels as well either by making a series of calls to
  //glTexImage2D or use glGenerateMipmapEXT(GL_TEXTURE_2D).
  //Here, we'll use :
  glGenerateMipmapEXT(GL_TEXTURE_2D)
  //-------------------------
  glGenFramebuffersEXT(1, &fb);
  glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, fb);
  //Attach 2D texture to this FBO
  glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT, GL_TEXTURE_2D, color_tex, 0);
  //-------------------------
  glGenRenderbuffersEXT(1, &depth_rb);
  glRenderbufferStorageEXT(GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT24, 256, 256);
  //-------------------------
  //Attach depth buffer to FBO
  glFramebufferRenderbufferEXT(GL_FRAMEBUFFER_EXT, GL_DEPTH_ATTACHMENT_EXT, GL_RENDERBUFFER_EXT, depth_rb);
  //-------------------------
  //Does the GPU support current FBO configuration?
  GLenum status;
  status = glCheckFramebufferStatusEXT(GL_FRAMEBUFFER_EXT);
  switch(status)
  {
     case GL_FRAMEBUFFER_COMPLETE_EXT:
     cout<<"good";
  default:
     HANDLE_THE_ERROR;
  }
  //-------------------------
  //and now you can render to GL_TEXTURE_2D
  glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, fb);
  glClearColor(0.0, 0.0, 0.0, 0.0);
  glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
  //-------------------------
  glViewport(0, 0, 256, 256);
  glMatrixMode(GL_PROJECTION);
  glLoadIdentity();
  glOrtho(0.0, 256.0, 0.0, 256.0, -1.0, 1.0); 
  glMatrixMode(GL_MODELVIEW);
  glLoadIdentity();
  //-------------------------
  glDisable(GL_TEXTURE_2D);
  glDisable(GL_BLEND);
  glEnable(GL_DEPTH_TEST);
  //-------------------------
  glColor3f(1.0, 1.0, 0.0);
  glBegin(GL_TRIANGLES);
  glVertex2f(0.0, 0.0);
  glVertex2f(256.0, 0.0);
  glVertex2f(256.0 , 256.0);
  glEnd();
  //-------------------------
  GLubyte pixels[4*4*4];
  glReadPixels(0, 0, 4, 4, GL_BGRA, GL_UNSIGNED_BYTE, pixels);
  //pixels 0, 1, 2 should be white
  //pixel 4 should be black
  //----------------
  //Bind 0, which means render to back buffer
  glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0);
  //----------------
  //**** Now that we rendered to level 0 of the texture, we must generate the mipmaps.
  //This should be quick since it is done on the GPU.
  glBindTexture(GL_TEXTURE_2D, color_tex);
  glGenerateMipmapEXT(GL_TEXTURE_2D)

Quick example, render_to_texture (Cubemap)

//RGBA8 Cubemap texture, 24 bit depth texture, 256x256

 glGenTextures(1, &color_tex);
 glBindTexture(GL_TEXTURE_CUBE_MAP, color_tex);
 glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
 glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
 glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_EDGE);
 glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
 glTexParameteri(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
 //NULL means reserve texture memory, but texels are undefined
 glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X+0, 0, GL_RGBA8, 256, 256, 0, GL_BGRA, GL_UNSIGNED_BYTE, NULL);
 glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X+1, 0, GL_RGBA8, 256, 256, 0, GL_BGRA, GL_UNSIGNED_BYTE, NULL);
 glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X+2, 0, GL_RGBA8, 256, 256, 0, GL_BGRA, GL_UNSIGNED_BYTE, NULL);
 glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X+3, 0, GL_RGBA8, 256, 256, 0, GL_BGRA, GL_UNSIGNED_BYTE, NULL);
 glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X+4, 0, GL_RGBA8, 256, 256, 0, GL_BGRA, GL_UNSIGNED_BYTE, NULL);
 glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X+5, 0, GL_RGBA8, 256, 256, 0, GL_BGRA, GL_UNSIGNED_BYTE, NULL);
 //-------------------------
 glGenFramebuffersEXT(1, &fb);
 glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, fb);
 //Attach one of the faces of the Cubemap texture to this FBO
 glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT, GL_TEXTURE_CUBE_MAP_POSITIVE_X, color_tex, 0);
 //-------------------------
 glGenRenderbuffersEXT(1, &depth_rb);
 glRenderbufferStorageEXT(GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT24, 256, 256);
 //-------------------------
 //Attach depth buffer to FBO
 glFramebufferRenderbufferEXT(GL_FRAMEBUFFER_EXT, GL_DEPTH_ATTACHMENT_EXT, GL_RENDERBUFFER_EXT, depth_rb);
 //-------------------------
 //Does the GPU support current FBO configuration?
 GLenum status;
 status = glCheckFramebufferStatusEXT(GL_FRAMEBUFFER_EXT);
 switch(status)
 {
    case GL_FRAMEBUFFER_COMPLETE_EXT:
    cout<<"good";
 default:
    HANDLE_THE_ERROR;
 }
 //-------------------------
 //and now you can render to GL_TEXTURE_CUBE_MAP_POSITIVE_X
 //In order to render to the other faces, do this :
 glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT, GL_TEXTURE_CUBE_MAP_POSITIVE_Y, color_tex, 0);
 //... now render
 glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT, GL_TEXTURE_CUBE_MAP_POSITIVE_Z, color_tex, 0);
 //... now render
 //... and so on