I am currently porting the atmosphere algorithm used by the UE4 engine to my engine.
As the original algorithm from Bruneton is in Kilometers i had to adapt it to my engine which uses meters. Everything is working and its correctly scaled now but i am having some z precision issues on the horizon when drawing the fog. This, i believe, i due to the following math:
float DepthBufferValue = texture(ViewDepthTexture, depthValueUV).r; vec3 depthClipSpace = vec3(pixPos / vec2(gResolution) * vec2(2.0f) - vec2(1.0f), DepthBufferValue); vec4 DepthBufferWorldPos = gInvViewProjMat * vec4(depthClipSpace, 1.0); DepthBufferWorldPos /= DepthBufferWorldPos.w; // perspective division DepthBufferWorldPos.xyz *= 0.001;
Here, i am basically reading the depth texture, getting the real world position value and scaling it to be in KMs. Due to this scaling (and the inverse multiplication) i am getting some shimmering in the horizon (where the z distance is the greatest)
Since the depth equation is equal to:
d = a * (1/z) + b
(with a = near, b = far clip and z the distance from camera) is there any mathematical way to scale the DepthBufferValue to a value where the world position would be in kilometers?
In a more practical way, imagining that we have a World Position of (0, 1000, 0) and that gives us a DepthBufferValue of 0.998, can we scale that 0.998 value to the value that we would obtain if we had used the World Position (0, 1, 0) ? (Assuming of course the same near and far clips)
Edit: This is the DepthBufferWorldPos outputed to the screen: