OpenGL/GLSL 4.1中的全向照明

OpenGL/GLSL 4.1中的全向照明,opengl,glsl,Opengl,Glsl,我的平行光可以正常使用阴影,但在点光源方面我有点不知所措。我的想法是使用立方体贴图渲染灯光周围所有六个面的深度。到目前为止,一切都很好。我已经通过将立方体的每个面渲染为二维图像来验证了这一步骤,并且它似乎是正确的 现在我正试图让阴影出现在这个世界上。为此,我使用GLSL的samplerCubeShadow数据类型。有了它,我做到了: vec3 lightToFrag = light.position - fragPos float lenLightToFrag = length(lightToF

我的平行光可以正常使用阴影,但在点光源方面我有点不知所措。我的想法是使用立方体贴图渲染灯光周围所有六个面的深度。到目前为止,一切都很好。我已经通过将立方体的每个面渲染为二维图像来验证了这一步骤,并且它似乎是正确的

现在我正试图让阴影出现在这个世界上。为此,我使用GLSL的samplerCubeShadow数据类型。有了它,我做到了:

vec3 lightToFrag = light.position - fragPos
float lenLightToFrag = length(lightToFrag)
vec3 normLightToFrag = normalize(lightToFrag)
float shadow = texture(depthTexture, vec4(normLightToFrag, lightToFrag))

我尝试了许多配置,这总是以黑色渲染我的场景。有什么想法吗?我的fragPos只是模型矩阵乘以顶点位置。我应该将灯光的模型视图矩阵应用到它吗?或者,类似地,我应该将世界的模型视图矩阵应用于灯光吗?非常感谢您的反馈

假设您正在cubemap中存储深度值

AFAIK立方体贴图是世界空间中的AABB,因此您需要在世界空间中进行计算。在您的情况下,
light.position
fragPos
必须在世界空间中,或者如果您在其他地方的视图空间中使用这些名称,例如每片段灯光计算,则提供替代变量/成员

在传递到
纹理之前,还需要将lightToFrag转换为深度值。
此答案显示了如何将lightToFrag转换为深度值:

这里是我的实现(我删除了#ifdef SHAD_CUBE,因为其他人使用相同的名称):

如果只有ModelViewProjection(MVP),则可能需要统一的模型矩阵

以下是如何计算客户端的uNearFar:

  float n, f, nfsub, nf[2];

  n = sm->near;
  f = sm->far;

  nfsub = f - n;
  nf[0] = (f + n) / nfsub * 0.5f + 0.5f;
  nf[1] =-(f * n) / nfsub;

  glUniform2f(gkUniformLoc(prog, "uFarNear"), nf[0], nf[1]);
这只是一个优化,但你不必使用它,而是遵循我前面提到的链接

您可能需要偏差值,相关答案使用偏差,但我不确定如何将其正确应用于立方体贴图。我不确定d-+0.0001是否正确


如果您想在cubemap中存储世界距离,那么本教程似乎是上帝的选择:

这里是您的答案:如果您在cubemap中存储深度值,您需要将lightToFrag转换为深度值以比较延迟响应,但仅此而已!在C++代码中,您为我节省了大量的调试。我应该事先把它读完。无论如何,谢谢你的参考资料和一切!
  float n, f, nfsub, nf[2];

  n = sm->near;
  f = sm->far;

  nfsub = f - n;
  nf[0] = (f + n) / nfsub * 0.5f + 0.5f;
  nf[1] =-(f * n) / nfsub;

  glUniform2f(gkUniformLoc(prog, "uFarNear"), nf[0], nf[1]);