OpenGL API로 분산 그림자 맵 기술을 구현하려고합니다. 나는 튜토리얼 (Fabien Sanglard의 Soft Shadows with VSM)을 사용하여 매 단계마다 따라했지만, 그림자 맵은 이상하게 보였다. 내가 알아 차 렸던 주요한 점은 내가 빛 (원근감) 투영 행렬의 클리핑 평면 근처에서 바뀌면 이상하게 보입니다. 가 (이 결과는 좋은으로 간주)OpenGL 분산 그림자 매핑 반전 falloff
을 http://postimg.org/image/rupf6wqcx/ 클리핑 근처 1.0F에 보이는 그리고 여기 http://postimg.org/image/fox04z14z/
공지 빛의 위치는 동일하게 유지 0.1F 값에 얼마나 예를 들어
여기 있어요.
나는 결과가없는 3 일 동안 잘못 된 것을 찾으려고 노력해 왔습니다. 그걸 도와 주실 수 있습니까?
다음은 그림자 조각 셰이더 코드입니다.
in vec4 v_position;
out vec4 color;
void main()
{
float depth = v_position.z/v_position.w;
depth = depth * 0.5 + 0.5;
float dx = dFdx(depth);
float dy = dFdy(depth);
float moment1 = depth;
float moment2 = depth * depth - 0.25 * (dx * dx + dy * dy);
color = vec4(moment1, moment2, 0.0, 1.0);
}
그리고
in vec4 ShadowPosition;
out vec4 outColor;
uniform sampler2D shadowMap;
vec4 sc;
float chebyshevUpperBound(float distance)
{
float p = 0.0;
// We retrive the two moments previously stored (depth and depth*depth)
vec2 moments = texture2D(shadowMap, sc.xy).rg;
// Surface is fully lit. as the current fragment is before the light occluder
if (distance <= moments.x)
p = 1.0;
// The fragment is either in shadow or penumbra. We now use chebyshev's upperBound to check
// How likely this pixel is to be lit (p_max)
float variance = moments.y - (moments.x * moments.x);
variance = max(variance, 0.00001);
float d = distance - moments.x;
float p_max = variance/(variance + d*d);
return max(p, p_max);
}
void main()
{
/* Shadow Mapping */
vec3 pixColor = vec3(1.0, 1.0, 1.0);
sc = ShadowPosition/ShadowPosition.w;
sc = sc * 0.5 + 0.5;
float visibility = chebyshevUpperBound(sc.z);
outColor = vec4(visibility * pixColor, 1.0);
}
버텍스 쉐이더, 조명이나 MVP를 사용하여 뷰의 카메라 점에서 정점을 계산하기 때문에 아주 간단 행렬되어 렌더링 실제 패스 프래그먼트 쉐이더에서 그림자 매핑 부분을 내가 필요가 있다고 생각하지 말아 그들을 게시하십시오.
이 코드는 초기화하고 렌더링 할 수 있습니다 :
glEnable(GL_DEPTH_TEST);
glDepthFunc(GL_LESS);
glEnable(GL_CULL_FACE);
glCullFace(GL_BACK);
glGenFramebuffers(1, &FramebufferName);
glGenTextures(1, &light_s.shadowBO);
glBindTexture(GL_TEXTURE_2D, light_s.shadowBO);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA32F, 1024, 1024, 0, GL_RGBA, GL_FLOAT, 0);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_BORDER);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_BORDER);
glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_BORDER_COLOR, borderColor);
glGenTextures(1, &light_s.shadowBOZ);
glBindTexture(GL_TEXTURE_2D, light_s.shadowBOZ);
glTexImage2D(GL_TEXTURE_2D, 0, GL_DEPTH_COMPONENT32, 1024, 1024, 0, GL_DEPTH_COMPONENT, GL_FLOAT, 0);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_BORDER);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_BORDER);
glTexParameterfv(GL_TEXTURE_2D, GL_TEXTURE_BORDER_COLOR, borderColor);
glBindFramebuffer(GL_FRAMEBUFFER, FramebufferName);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_COLOR_ATTACHMENT0, GL_TEXTURE_2D, light_s.shadowBO, 0);
glFramebufferTexture2D(GL_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, light_s.shadowBOZ, 0);
while (running)
{
if (PeekMessage(&msg, NULL, 0, 0, PM_REMOVE))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
else
{
/* Shadow pass */
glBindFramebuffer(GL_FRAMEBUFFER, FramebufferName);
glViewport(0, 0, 1024, 1024);
glDrawBuffer(GL_BACK);
glClearColor(1.0f, 1.0f, 1.0f, 1.0f);
glClear(GL_DEPTH_BUFFER_BIT | GL_COLOR_BUFFER_BIT);
glUseProgram(theShadowProgram);
glEnableVertexAttribArray(svxposition);
glUniformMatrix4fv(spmatrix, 1, GL_FALSE, light_s.mProjection);
glUniformMatrix4fv(svmatrix, 1, GL_FALSE, light_s.mView);
glUniformMatrix4fv(smmatrix, 1, GL_FALSE, bunny_s.mModel);
glBindBuffer(GL_ARRAY_BUFFER, bunny_s.vertexBufferObject);
glVertexAttribPointer(svxposition, 3, GL_FLOAT, GL_FALSE, 0, NULL);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, bunny_s.elementBufferObject);
glDrawElements(GL_TRIANGLES, bunny_s.elementBufferSize, GL_UNSIGNED_INT, NULL);
glBindBuffer(GL_ARRAY_BUFFER, vbplaneVert);
glVertexAttribPointer(svxposition, 3, GL_FLOAT, GL_FALSE, 0, NULL);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, vbplaneElem);
glDrawElements(GL_TRIANGLES, 6, GL_UNSIGNED_INT, NULL);
glDisableVertexAttribArray(svxposition);
/* Rendering pass */
glBindFramebuffer(GL_FRAMEBUFFER, 0);
glViewport(0, 0, 1024, 768);
glDrawBuffer(GL_BACK);
glClearColor(0.0f, 0.0f, 0.0f, 1.0f);
glClear(GL_DEPTH_BUFFER_BIT | GL_COLOR_BUFFER_BIT);
glUseProgram(theProgram);
glActiveTexture(GL_TEXTURE0);
glBindTexture(GL_TEXTURE_2D, light_s.shadowBO);
glEnableVertexAttribArray(vxposition);
glEnableVertexAttribArray(normals);
glUniformMatrix4fv(dpmatrix, 1, GL_FALSE, light_s.mProjection);
glUniformMatrix4fv(dvmatrix, 1, GL_FALSE, light_s.mView);
glUniformMatrix4fv(dbmatrix, 1, GL_FALSE, mDepthBias);
glUniformMatrix4fv(pmatrix, 1, GL_FALSE, camera_s.mProjection);
glUniformMatrix4fv(vmatrix, 1, GL_FALSE, camera_s.mView);
glUniformMatrix4fv(mmatrix, 1, GL_FALSE, bunny_s.mModel);
glUniform3f(campos, camera_s.x, camera_s.y, camera_s.z);
glUniform3f(lightpos, light_s.x, light_s.y, light_s.z);
glUniform1i(frsampler, 0);
glBindBuffer(GL_ARRAY_BUFFER, bunny_s.vertexBufferObject);
glVertexAttribPointer(vxposition, 3, GL_FLOAT, GL_FALSE, 0, NULL);
glBindBuffer(GL_ARRAY_BUFFER, bunny_s.normalBufferObject);
glVertexAttribPointer(normals, 3, GL_FLOAT, GL_FALSE, 0, NULL);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, bunny_s.elementBufferObject);
glDrawElements(GL_TRIANGLES, bunny_s.elementBufferSize, GL_UNSIGNED_INT, NULL);
glBindBuffer(GL_ARRAY_BUFFER, vbplaneVert);
glVertexAttribPointer(vxposition, 3, GL_FLOAT, GL_FALSE, 0, NULL);
glBindBuffer(GL_ARRAY_BUFFER, vbplaneNorm);
glVertexAttribPointer(normals, 3, GL_FLOAT, GL_FALSE, 0, NULL);
glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, vbplaneElem);
glDrawElements(GL_TRIANGLES, 6, GL_UNSIGNED_INT, NULL);
glDisableVertexAttribArray(vxposition);
glDisableVertexAttribArray(normals);
}
}
이 최적화되어 있지 않습니다,하지만 지금 할 것입니다. 당신이 color.zw
(BA
) 이후 GL_RG32F
대신 GL_RGBA32F
을 사용하는 경우
코드 없이는 진단하기가 어려울 것입니다. 일부 게시 할 수 있습니까? –
@ChrisMantle 일부 코드 샘플을 사용하여 제 질문을 편집했습니다. 도움이되기를 바랍니다. –