문제

에 따르면 arb_geometry_shader4 지오메트리 셰이더와 프레임 버퍼 객체에 첨부 된 큐브 맵이있는 큐브 맵의 6면에 장면을 렌더링 할 수 있습니다. 이 방법을 사용하여 그림자 맵을 만들고 싶습니다. 그러나 내가 해결할 수없는 갈등이있는 것 같습니다.

  1. GL_DEPTH_COMPONTIN을 GL_DEPTH_ATTACHMENT_EXT의 내부 유형으로 텍스처 만 첨부 할 수 있습니다.
  2. 깊이 텍스처는 1D 또는 2D 일 수 있습니다.
  3. 큐브 맵을 첨부하려면 다른 모든 첨부 된 텍스처도 큐브 맵이어야합니다.

큐브 맵으로 렌더링하고 싶을 때 깊이 테스트를 사용할 수없는 것 같습니다. 아니면 정확히 내가 여기서 누락 된 것은 무엇입니까?

편집하다: 새로운 NVIDIA 드라이버 (180.48)가 깊이 큐브 맵을 지원하는 것처럼 보입니다.

도움이 되었습니까?

해결책

좋아, 다른 몇 가지 질문에 대답하려면 :

물론 각면마다 하나씩 6 개의 FBO를 사용할 수 있습니다. 또는 하나의 FBO를 사용하고 각면을 연결하기 전에 각면을 부착하십시오. 두 경우 모두 큐브 맵면은 다른 2D 텍스처처럼 취급되며 일반 2D 텍스처 또는 렌더 버퍼와 함께 사용할 수 있습니다. 그리고 가능한 모든 방법에 큰 차이가 없을 것입니다 (하드웨어가 지원하는 경우).

그러나 한 걸음에 모든 것을 그릴 수 있으며 이것이 어떻게 이루어 졌는지 궁금해서 연구를했습니다.

단일 첨부 파일 지점에 첨부 된 큐브 맵의 모든면이있는 FBO를 만들려면이 코드를 사용했습니다 (d로 작성).

// depth cube map
glGenTextures(1, &tDepthCubeMap);
glBindTexture(GL_TEXTURE_CUBE_MAP, tDepthCubeMap);
glTexParameterf(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexParameterf(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameterf(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
glTexParameterf(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
glTexParameterf(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_EDGE);
for (uint face = 0; face < 6; face++) {
    glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + face, 0, GL_DEPTH_COMPONENT24,
        width, height, 0, GL_DEPTH_COMPONENT, GL_FLOAT, null);
}

// color cube map
glGenTextures(1, &tColorCubeMap);
glBindTexture(GL_TEXTURE_CUBE_MAP, tColorCubeMap);
glTexParameterf(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
glTexParameterf(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
glTexParameterf(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
glTexParameterf(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
glTexParameterf(GL_TEXTURE_CUBE_MAP, GL_TEXTURE_WRAP_R, GL_CLAMP_TO_EDGE);
for (uint face = 0; face < 6; face++) {
    glTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X + face, 0, GL_RGBA,
        width, height, 0, GL_RGBA, GL_FLOAT, null);
}

// framebuffer object
glGenFramebuffersEXT(1, &fbo);
glBindFramebufferEXT(GL_FRAMEBUFFER_EXT, fbo);
glFramebufferTextureARB(GL_FRAMEBUFFER_EXT, GL_DEPTH_ATTACHMENT_EXT, tDepthCubeMap, 0);
glFramebufferTextureARB(GL_FRAMEBUFFER_EXT, GL_COLOR_ATTACHMENT0_EXT, tColorCubeMap, 0);

glDrawBuffer(GL_COLOR_ATTACHMENT0_EXT);

if (!isValidFBO()) {
    glDeleteFramebuffersEXT(1, &fbo);
    fbo = 0;
}
  • 깊이지도 만 갖고 싶다면 변경해야합니다. gldrawbuffer (gl_color_attachment0_ext); 에게 gldrawbuffer (Gl_none); 검증하기 전에 (그리고 그로 그리기 전에)
  • 최소 및 매그 필터는 유효한 것으로 설정해야합니다 (기본값은 GL_NEAREST_MIPMAP_LINEAR입니다)
  • 모든 텍스처의 너비와 높이는 동일해야합니다.

큐브 맵의 얼굴에 렌더링하려면 지오메트리 셰이더가 필요합니다. 다음 셰이더는 일부 회전을 놓치지 만 그것이 무엇을하는지 명확하게해야합니다. GL_Layer는 원시를 올바른면으로 지시하는 데 사용됩니다 (0 = +x, 1 = -x, ...).

#version 120
#extension GL_EXT_geometry_shader4 : enable

void main(void) {
    int i, layer;
    for (layer = 0; layer < 6; layer++) {
        gl_Layer = layer;
        for (i = 0; i < 3; i++) {
            gl_Position = gl_PositionIn[i];
            EmitVertex();
        }
        EndPrimitive();
    }
}
라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top