0

我正在尝试使用多边形偏移填充执行隐藏线移除。如果我直接渲染到窗口缓冲区但在通过 FBO 时无法绘制线条,则代码可以完美运行,如下所示

替代文字

我用来绘制对象的代码

void drawCubes (GLboolean removeHiddenLines)
{
  glLineWidth(2.0);
  glPushMatrix();
    camera.ApplyCameraTransform();
    for(int i = 0; i < 50; i ++){
    glPushMatrix();
      cube[i].updatePerspective();
      glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
      glColor3f(1.0,1.0,1.0);
      cube[i].draw();
      glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);

      if(removeHiddenLines){
          glEnable(GL_POLYGON_OFFSET_FILL);
          glPolygonOffset(1.0, 1.0);
          glColor3f(1.0, 0.0, 0.0);  //fill polygons for hidden line removal
          cube[i].draw();
          glDisable(GL_POLYGON_OFFSET_FILL);
      }
    glPopMatrix();
  }
  glPopMatrix();
}

对于此示例,第一遍涉及渲染到窗口缓冲区和 FBO。

void firstPass()
{
  glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0);
  glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

  glViewport(0, 0, fboWidth, fboHeight);

  glEnable(GL_DEPTH_TEST);
  glDisable(GL_TEXTURE_2D);
  drawParticleView(GL_TRUE);
  glDisable(GL_DEPTH_TEST);

  glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, framebufferID[1]);
  glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

  glViewport(0, 0, fboWidth, fboHeight);

  glEnable(GL_DEPTH_TEST);
  glDisable(GL_TEXTURE_2D);
  drawParticleView(GL_TRUE);
  glDisable(GL_DEPTH_TEST);
}

第二遍将 FBO 渲染回窗口缓冲区。

void secondPass()
{
  glEnable(GL_TEXTURE_2D);

  glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0);
  glBindTexture(GL_TEXTURE_2D, renderTextureID[0]);

  glViewport(fboWidth, 0, fboWidth, fboHeight);
  glMatrixMode(GL_PROJECTION);
  glLoadIdentity();
  glMatrixMode(GL_MODELVIEW);
  glLoadIdentity();

  glBegin(GL_QUADS);
    glTexCoord2i(0, 0);
    glVertex2f(-1.0f, -1.0f);
    glTexCoord2i(1, 0);
    glVertex2f(1.0f, -1.0f);
    glTexCoord2i(1, 1);
    glVertex2f(1.0f, 1.0f);
    glTexCoord2i(0, 1);
    glVertex2f(-1.0f, 1.0f);
  glEnd();

  glDisable(GL_TEXTURE_2D);
}

设置 FBO

void setupRC()
{
  setupTextures();
  glGenFramebuffersEXT(2, framebufferID);

  glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, framebufferID[0]);
  glGenRenderbuffersEXT(1, &renderbufferID);
  glBindRenderbufferEXT(GL_RENDERBUFFER_EXT, renderbufferID);
  glRenderbufferStorageEXT(GL_RENDERBUFFER_EXT, GL_DEPTH_COMPONENT32, fboWidth, fboHeight);
  glFramebufferRenderbufferEXT(GL_FRAMEBUFFER_EXT, GL_DEPTH_ATTACHMENT_EXT, GL_RENDERBUFFER_EXT, renderbufferID);
  glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT, GL_TEXTURE_2D, renderTextureID[0], 0);
  GLenum fboStatus = glCheckFramebufferStatusEXT(GL_FRAMEBUFFER_EXT);
  if(fboStatus != GL_FRAMEBUFFER_COMPLETE_EXT){
    fprintf(stderr, "FBO #1 Error!");
  }
  glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, framebufferID[1]);
  glFramebufferTexture2DEXT(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT, GL_TEXTURE_2D, renderTextureID[1], 0);
  fboStatus = glCheckFramebufferStatusEXT(GL_FRAMEBUFFER_EXT);
  if(fboStatus != GL_FRAMEBUFFER_COMPLETE_EXT){
     fprintf(stderr, "FBO #2 Error!");
  }
  glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, 0);
}

设置纹理

void setupTextures(void)
{
  glGenTextures(2, renderTextureID);

  for (GLint i = 0; i < 2; i++){
    glBindTexture(GL_TEXTURE_2D, renderTextureID[i]);
    glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
    glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
    glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
    glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
    // this may change with window size changes
    glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA8, fboWidth, fboHeight, 0, GL_RGBA, GL_UNSIGNED_BYTE, 0);
  }
  glBindTexture(GL_TEXTURE_2D, 0);
}

我不明白为什么这两种观点不一样?我错过了什么(显然我是)?
谢谢

4

2 回答 2

1

问题是我在没有深度附件的情况下渲染到 FBO。将第二个 FBO 设置为与第一个相同,得到了正确的结果。

于 2010-04-18T13:44:17.313 回答
0

你的代码对我来说似乎没问题。奇怪的是,您仍然绘制了红色立方体,但没有绘制线条……您的 OpenGL 实现是什么,驱动程序版本是什么?

您是否可以在不启用GL_POLYGON_OFFSET_FILL和/或glLineWidth查看是否看到线条的情况下进行测试(尽管隐藏部分可见)?

于 2010-04-02T00:49:35.497 回答