【问题标题】:LWGL // reconstruct position in fragment shaderLWGL // 在片段着色器中重建位置
【发布时间】:2015-01-22 17:53:29
【问题描述】:

我有正确的逆投影矩阵。但似乎没有什么是对的! 重建的位置是否完全变形,z 值是否太小?有人建议吗?

vec3 calculatePosition(vec2 coord, float depth)
{ 
vec4 clipSpaceLocation;
clipSpaceLocation.x = coord.x * 2.0 - 1.0;
clipSpaceLocation.y = coord.y * 2.0 - 1.0;
clipSpaceLocation.z = depth * 2.0 - 1.0;
clipSpaceLocation.w = 1.0;
vec4 homogenousPosition = uProjectionInverse * clipSpaceLocation;

return homogenousPosition.xyz / homogenousPosition.w;
}

z 值约为 -0,001;为什么会这样?

坐标和深度是:

vec2 coord = vec2(gl_FragCoord.x / width, gl_FragCoord.y / height);
float currentDepth = texture(depthBuffer, coord).r;

我必须为大学实施 SSAO,并且我使用 Eclipse 和 Java 以及 lwjgl-plugin。 请我需要帮助。我不到一星期。

编辑: 我现在已经尝试过了……但仍然没有被 lenearized:

float camera_space_z_from_depth(sampler2D depthbuffer, vec2 uv) {
    float depth = texture(depthbuffer, uv).x;
    return (2 * uNearPlane) / (uFarPlane + uNearPlane - depth * (uFarPlane -       uNearPlane));
}

vec3 calculatePosition(vec2 coord, float depth)
{   
    vec4 clipSpaceLocation;
    clipSpaceLocation.x = coord.x * 2.0 - 1.0;
    clipSpaceLocation.y = coord.y * 2.0 - 1.0;
    clipSpaceLocation.z = depth * 2.0 - 1.0;
    clipSpaceLocation.w = 1.0;
   vec4 homogenousPosition = uProjectionInverse * clipSpaceLocation;

   return homogenousPosition.xyz / homogenousPosition.w;
}
vec3 getPosition(vec2 coord){
    float currentDepth = camera_space_z_from_depth(depthBuffer,coord);  
    vec3 position = calculatePosition(coord, currentDepth);
    return position;
}

【问题讨论】:

  • 到目前为止,原始代码(不是编辑)看起来还不错。假设您的深度渲染通道仅使用正常的 z 坐标,则编辑中的线性化并没有真正意义。在我看来,uProjectionInverse 或 - 这是我的第一个猜测 - 深度纹理(或深度渲染本身)存在问题。您的投影0.001near 值是否有任何机会?如果是这样,看起来您尝试取消投影的深度值在所有点上都只是 0。

标签: opengl shader lwjgl depth zbuffer


【解决方案1】:

我想你需要线性化你的深度值,就像这里说的:

https://www.opengl.org/wiki/Compute_eye_space_from_window_space

试试这个。

float camera_space_z_from_depth(sampler2D depthbuffer, vec2 uv) {
    const float depth = texture(depthbuffer, uv).x;
    return ( camera_near / (camera_far - depth * (camera_far - camera_near)) ) * camera_far;
}

编辑:

试试看。变量含义应该是不言自明的(不需要线性化):)

vec3 GetPosition(vec2 fragmentCoordinates, float depth)
{
    vec3 normalizedDeviceCoordinatesPosition;
    normalizedDeviceCoordinatesPosition.xy = (2.0 * fragmentCoordinates) / uScreenSize - 1;
    normalizedDeviceCoordinatesPosition.z = 2.0 * depth - 1.0;

    vec4 clipSpacePosition;
    clipSpacePosition.w = uProjection[3][2] / (normalizedDeviceCoordinatesPosition.z - (uProjection[2][2] / uProjection[2][3]));
    clipSpacePosition.xyz = normalizedDeviceCoordinatesPosition * clipSpacePosition.w;

    vec4 eyePosition = uInverseProjection * clipSpacePosition;

    return eyePosition.xyz / eyePosition.w;
}

注意:到目前为止,我假设您的深度纹理是 GL_DEPTH_COMPONENT,并作为 GL_DEPTH_ATTACHMENT 附加到帧缓冲区。

即:

glBindTexture(GL_TEXTURE_2D, mDepthTextureId);
glTexImage2D(GL_TEXTURE_2D, 0, GL_DEPTH_COMPONENT, mrScreenWidth, mrScreenHeight, 0, GL_DEPTH_COMPONENT, GL_UNSIGNED_BYTE, 0);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_COMPARE_MODE, GL_NONE);
glFramebufferTexture2D(GL_DRAW_FRAMEBUFFER, GL_DEPTH_ATTACHMENT, GL_TEXTURE_2D, mDepthTextureId, 0);

【讨论】:

  • 请注意,您可以对代码 sn-p 中使用的 camera_near 和 camera_far 变量进行硬编码!
  • 只是为了确保,uScreenSize 将是一个 vec2,相当于您在代码 sn-p 中使用 vec2(width, height) ;)
  • 请注意,我的部分代码和你的一样......真正的区别在于 clipSpacePosition.w 中的计算
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2021-04-21
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-05-24
  • 2018-02-04
相关资源
最近更新 更多