opengl - 具有延迟渲染的阴影贴图

标签 opengl shadow-mapping deferred-rendering

我正在尝试实现阴影贴图技术,但在使其发挥作用时遇到一些问题。

我在灯光位置有一个相机,这是我得到的阴影贴图。所有顶点均已乘以每个 modelViewProjectionMatrix

Camera light's view

我还有一个带有顶点世界位置的纹理。它是一个 GL_RGBA32F 纹理,因为所有点都已乘以每个 ModelMatrix 以获得世界空间中的点。

enter image description here

和着色器:

layout(binding=5) uniform sampler2D shadowMap;
layout(binding=6) uniform sampler2D positionMap;

in vec2 texcoord;
uniform mat uViewProjectionMatrix;

out vec4 color;

void main() {

   vec4 pos = texture(positionMap, texcoord);

   vec4 ShadowCoord = uViewProjectionMatrix * pos;
   ShadowCoord.xy = ShadowCoord.xy * vec2(0.5,0.5) + vec2(0.5,0.5);

   float a = texture(shadowMap, ShadowCoord.xy).z;
   color = vec4(a, a, a, 1.0);
}

输出(相机几乎处于光线的相同位置):

enter image description here

我只是想看看每个顶点的投影是否与相机的位置垂直,但看起来并非如此。 所有这一切的目的是比较:

if ( texture(shadowMap, ShadowCoord.xy).z <  ( ShadowCoord.z-bias ) )

但它也不起作用。

如果有任何帮助,我将不胜感激。 谢谢。

最佳答案

您错过了透视鸿沟,并且您似乎完全忽略了深度范围。

这里的总体思路是将 ShadowCoord.xyz 放入范围 [0,1](用于纹理查找和深度比较) 。您的代码运行的假设是 uViewProjectionMatrix * pos (剪辑空间坐标)在 [-1,1] 范围内,但事实是除非除以 w(NDC 坐标),否则无法真正保证。

我会考虑这样的事情:

void main() {
  vec4 pos = texture(positionMap, texcoord);

  vec4 ShadowCoord = uViewProjectionMatrix * pos;
  ShadowCoord /= ShadowCoord.w;

  ShadowCoord.xyz = ShadowCoord.xyz * vec3 (0.5f, 0.5f, 0.5f) + vec2 (0.5f, 0.5f, 0.5f);

  float a = texture(shadowMap, ShadowCoord.xy).z;
  color = vec4(a, a, a, 1.0);
}

此后,ShadowCoord.xy 将是要在阴影贴图中查找的纹理坐标,ShadowCoord.z 将是当前片段距离光源的深度看法。您可以使用 ShadowCoord.z 与采样深度进行比较。

事实上,您甚至可以考虑使用 sampler2DShadow 来更有效地完成此操作。有关示例,请参阅 this related question and answer

关于opengl - 具有延迟渲染的阴影贴图,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27461958/

相关文章:

python - PyOpenGL + PyGame 上的奇怪 "X"

c++ - CreateWindowEx WS_POPUP 为什么要打边框?

c++ - 阴影贴图产生不正确的结果

c++ - 深度缓冲区未填充阴影贴图渲染 channel 中的数据

opengl - 来自对数深度缓冲区的世界空间位置

opengl - 延迟渲染和移动点光源

opengl - 使用多个 openGL VBO 绘制多个模型

c - OpenGL 中矩阵堆栈的意义何在?

python - 如何制作阴影贴图?

opengl - 从深度重建的世界位置是错误的