|
|
|
|
|
|
// which allows us to perform HW interpolation which is linear in the view space. |
|
|
|
float ComputeLerpPositionForLogEncoding(float linearDepth, float logEncodedDepth, |
|
|
|
float4 VBufferScaleAndSliceCount, |
|
|
|
float4 VBufferDepthEncodingParams) |
|
|
|
float4 VBufferDepthDecodingParams) |
|
|
|
{ |
|
|
|
float z = linearDepth; |
|
|
|
float d = logEncodedDepth; |
|
|
|
|
|
|
float s1 = ceil(d * numSlices - 0.5); |
|
|
|
float d0 = saturate(s0 * rcpNumSlices + (0.5 * rcpNumSlices)); |
|
|
|
float d1 = saturate(s1 * rcpNumSlices + (0.5 * rcpNumSlices)); |
|
|
|
float z0 = DecodeLogarithmicDepth(d0, VBufferDepthEncodingParams); |
|
|
|
float z1 = DecodeLogarithmicDepth(d1, VBufferDepthEncodingParams); |
|
|
|
float z0 = DecodeLogarithmicDepthGeneralized(d0, VBufferDepthDecodingParams); |
|
|
|
float z1 = DecodeLogarithmicDepthGeneralized(d1, VBufferDepthDecodingParams); |
|
|
|
|
|
|
|
// Compute the linear interpolation weight. |
|
|
|
float t = saturate((z - z0) / (z1 - z0)); |
|
|
|
|
|
|
float4 SampleVBuffer(TEXTURE3D_ARGS(VBufferLighting, trilinearSampler), bool clampToEdge, |
|
|
|
float2 positionNDC, float linearDepth, |
|
|
|
float4 VBufferScaleAndSliceCount, |
|
|
|
float4 VBufferDepthEncodingParams) |
|
|
|
float4 VBufferDepthEncodingParams, |
|
|
|
float4 VBufferDepthDecodingParams) |
|
|
|
{ |
|
|
|
float numSlices = VBufferScaleAndSliceCount.z; |
|
|
|
float rcpNumSlices = VBufferScaleAndSliceCount.w; |
|
|
|
|
|
|
|
|
|
|
// The distance between slices is log-encoded. |
|
|
|
float z = linearDepth; |
|
|
|
float d = EncodeLogarithmicDepth(z, VBufferDepthEncodingParams); |
|
|
|
float d = EncodeLogarithmicDepthGeneralized(z, VBufferDepthEncodingParams); |
|
|
|
|
|
|
|
// Unity doesn't support samplers clamping to border, so we have to do it ourselves. |
|
|
|
// TODO: add the proper sampler support. |
|
|
|
|
|
|
float w = d; |
|
|
|
#else |
|
|
|
// Adjust the texture coordinate for HW trilinear sampling. |
|
|
|
float w = ComputeLerpPositionForLogEncoding(z, d, VBufferScaleAndSliceCount, VBufferDepthEncodingParams); |
|
|
|
float w = ComputeLerpPositionForLogEncoding(z, d, VBufferScaleAndSliceCount, VBufferDepthDecodingParams); |
|
|
|
#endif |
|
|
|
|
|
|
|
return SAMPLE_TEXTURE3D_LOD(VBufferLighting, trilinearSampler, float3(uv, w), 0); |
|
|
|
|
|
|
float2 positionNDC, float linearDepth, |
|
|
|
float4 VBufferResolution, |
|
|
|
float4 VBufferScaleAndSliceCount, |
|
|
|
float4 VBufferDepthEncodingParams) |
|
|
|
float4 VBufferDepthEncodingParams, |
|
|
|
float4 VBufferDepthDecodingParams) |
|
|
|
VBufferScaleAndSliceCount, VBufferDepthEncodingParams); |
|
|
|
VBufferScaleAndSliceCount, |
|
|
|
VBufferDepthEncodingParams, |
|
|
|
VBufferDepthDecodingParams); |
|
|
|
#else |
|
|
|
// Perform biquadratic reconstruction in XY, linear in Z, using 4x trilinear taps. |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
// The distance between slices is log-encoded. |
|
|
|
float z = linearDepth; |
|
|
|
float d = EncodeLogarithmicDepth(z, VBufferDepthEncodingParams); |
|
|
|
float d = EncodeLogarithmicDepthGeneralized(z, VBufferDepthEncodingParams); |
|
|
|
float w = ComputeLerpPositionForLogEncoding(z, d, VBufferScaleAndSliceCount, VBufferDepthEncodingParams); |
|
|
|
float w = ComputeLerpPositionForLogEncoding(z, d, VBufferScaleAndSliceCount, VBufferDepthDecodingParams); |
|
|
|
|
|
|
|
float2 weights[2], offsets[2]; |
|
|
|
BiquadraticFilter(1 - fc, weights, offsets); // Inverse-translate the filter centered around 0.5 |
|
|
|