Skip to content

Commit

Permalink
Optimize from where RT rays start
Browse files Browse the repository at this point in the history
  • Loading branch information
godlikepanos committed Nov 29, 2024
1 parent f0c48ee commit 9a4a323
Show file tree
Hide file tree
Showing 4 changed files with 32 additions and 23 deletions.
4 changes: 4 additions & 0 deletions AnKi/Shaders/Common.hlsl
Original file line number Diff line number Diff line change
Expand Up @@ -212,6 +212,10 @@ T ndcToUv(T ndc)
scalarType func##3(scalarType x, scalarType y, scalarType z) \
{ \
return func(x, func(y, z)); \
} \
scalarType func##2(vectorType##2 v) \
{ \
return func(v.x, v.y); \
}

#define DEFINE_COMPARISON2(func) \
Expand Down
2 changes: 1 addition & 1 deletion AnKi/Shaders/Include/MiscRendererTypes.h
Original file line number Diff line number Diff line change
Expand Up @@ -148,7 +148,7 @@ struct PixelFailedSsr
{
U32 m_pixel;
U32 m_reflectionDirAndRoughness;
F32 m_pdf;
U32 m_pdf_f16_rayDirT_f16;
};

// Vol fog
Expand Down
31 changes: 17 additions & 14 deletions AnKi/Shaders/Reflections.ankiprog
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,8 @@ constexpr F32 kGaussianSigma = 0.55;
constexpr Bool kStochasticReflections = true;
constexpr Bool kTryShadowmapFirst = true;
constexpr Bool kDisableDenoising = false;
constexpr F32 kTMinBias = -1.0;
constexpr Bool kExtraSsrRejection = true;

// Functions
Vec3 getDiffuseIndirect(StructuredBuffer<GpuSceneGlobalIlluminationProbe> giProbes, Vec3 worldPos, Vec3 worldNormal,
Expand Down Expand Up @@ -85,7 +87,6 @@ void decodeColorDepthAndSampleCount(Vec4 rgba, out Vec3 color, out F32 depth, ou
// SSR =
// ===========================================================================
#if NOT_ZERO(ANKI_TECHNIQUE_Ssr)
# define EXTRA_REJECTION 1
constexpr F32 kLowAttenuation = 0.01;

SamplerState g_trilinearClampSampler : register(s0);
Expand All @@ -112,7 +113,7 @@ ANKI_FAST_CONSTANTS(ReflectionConstants, g_consts)
groupshared Vec4 g_viewHitPointAndAttenuation[NUM_THREADS_SQRT][NUM_THREADS_SQRT];
groupshared Vec4 g_viewPosAndDepth[NUM_THREADS_SQRT][NUM_THREADS_SQRT];

void doSsr(UVec2 realCoord, UVec2 logicalCoord, Vec2 uv, Vec3 viewReflDir, Vec3 viewPos, F32 depth, F32 randFactor, out F32 attenuation,
void doSsr(UVec2 realCoord, UVec2 logicalCoord, Vec2 uv, Vec3 viewPos, F32 depth, F32 randFactor, inout Vec3 viewReflDir, out F32 attenuation,
out Vec3 outColor, out Vec3 viewHitPoint)
{
attenuation = 0.0;
Expand All @@ -129,19 +130,19 @@ void doSsr(UVec2 realCoord, UVec2 logicalCoord, Vec2 uv, Vec3 viewReflDir, Vec3
const U32 initialStepIncrement = U32(lerp(minStepf, stepIncrementf, randFactor));
raymarchGroundTruth(viewPos, viewReflDir, uv, depth, g_globalRendererConstants.m_matrices.m_projMat00_11_22_23, g_consts.m_ssrMaxIterations,
g_downscaledDepthTex, g_trilinearClampSampler, F32(lod), stepIncrement, initialStepIncrement, hitPoint, attenuation);
}

if(attenuation < kLowAttenuation)
{
return;
}
if(attenuation < kLowAttenuation)
{
viewHitPoint = cheapPerspectiveUnprojection(g_globalRendererConstants.m_matrices.m_unprojectionParameters, uvToNdc(hitPoint.xy), hitPoint.z);
return;
}

// Compute the hit point in viewspace
const F32 depth1 = g_downscaledDepthTex.SampleLevel(g_trilinearClampSampler, hitPoint.xy, 0.0).r;
viewHitPoint = cheapPerspectiveUnprojection(g_globalRendererConstants.m_matrices.m_unprojectionParameters, uvToNdc(hitPoint.xy), depth1);

# if EXTRA_REJECTION
// Reject backfacing
if(kExtraSsrRejection)
{
const Vec3 gbufferNormal = unpackNormalFromGBuffer(g_gbufferRt2.SampleLevel(g_trilinearClampSampler, hitPoint.xy, 0.0));
const Vec3 hitNormal = mul(g_globalRendererConstants.m_matrices.m_view, Vec4(gbufferNormal, 0.0));
Expand All @@ -155,6 +156,7 @@ void doSsr(UVec2 realCoord, UVec2 logicalCoord, Vec2 uv, Vec3 viewReflDir, Vec3
}

// Reject far from hit point
if(kExtraSsrRejection)
{
const Vec3 reflRayHitPointVSpace =
cheapPerspectiveUnprojection(g_globalRendererConstants.m_matrices.m_unprojectionParameters, uvToNdc(hitPoint.xy), hitPoint.z);
Expand All @@ -167,7 +169,6 @@ void doSsr(UVec2 realCoord, UVec2 logicalCoord, Vec2 uv, Vec3 viewReflDir, Vec3
return;
}
}
# endif

// Read the reflection
{
Expand Down Expand Up @@ -272,7 +273,7 @@ void bestCandidateToHallucinate(IVec2 svGroupThreadId, IVec2 offset, F32 depth,
viewReflDir = reflect(-viewDir, viewNormal);
}

doSsr(realCoord, logicalCoord, uv, viewReflDir, viewPos, depth, randFactors.x, ssrAttenuation, outColor, viewHitPoint);
doSsr(realCoord, logicalCoord, uv, viewPos, depth, randFactors.x, viewReflDir, ssrAttenuation, outColor, viewHitPoint);
}

// Stash to groupshared
Expand Down Expand Up @@ -356,7 +357,8 @@ void bestCandidateToHallucinate(IVec2 svGroupThreadId, IVec2 offset, F32 depth,
PixelFailedSsr failedPixel;
failedPixel.m_pixel = (realCoord.x << 16u) | realCoord.y;
failedPixel.m_reflectionDirAndRoughness = packSnorm4x8(Vec4(reflDirWorld, roughness));
failedPixel.m_pdf = pdf;
failedPixel.m_pdf_f16_rayDirT_f16 = f32tof16(pdf) << 16u;
failedPixel.m_pdf_f16_rayDirT_f16 |= f32tof16(length(viewPos - viewHitPoint));

SBUFF(g_pixelsFailedSsr, writeOffset) = failedPixel;

Expand Down Expand Up @@ -402,7 +404,7 @@ RWTexture2D<Vec4> g_hitPosAndDepthTex : register(u1);
const Vec4 packed = unpackSnorm4x8<F32>(pixelFailedSsr.m_reflectionDirAndRoughness);
const Vec3 reflDir = packed.xyz;
const F32 roughness = packed.w;
const F32 pdf = pixelFailedSsr.m_pdf;
const F32 pdf = f16tof32(pixelFailedSsr.m_pdf_f16_rayDirT_f16 >> 16u);

const F32 depth = g_depthTex[logicalCoord].x;
const Vec2 ndc = uvToNdc((Vec2(logicalCoord) + 0.5) / Vec2(viewportSize));
Expand Down Expand Up @@ -463,7 +465,8 @@ ANKI_FAST_CONSTANTS(Consts, g_consts)
const Vec4 packed = unpackSnorm4x8<F32>(pixelFailedSsr.m_reflectionDirAndRoughness);
const Vec3 reflDir = packed.xyz;
const F32 roughness = packed.w;
const F32 pdf = pixelFailedSsr.m_pdf;
const F32 pdf = f16tof32(pixelFailedSsr.m_pdf_f16_rayDirT_f16 >> 16u);
const F32 tmin = f16tof32(pixelFailedSsr.m_pdf_f16_rayDirT_f16 & 0xFFFFu);

const F32 depth = g_depthTex[logicalCoord].x;
const Vec2 ndc = uvToNdc((Vec2(logicalCoord) + 0.5) / Vec2(halfViewportSize.x * 2u, halfViewportSize.y));
Expand Down Expand Up @@ -491,7 +494,7 @@ ANKI_FAST_CONSTANTS(Consts, g_consts)
const U32 cullMask = 0xFFu;
RayDesc ray;
ray.Origin = worldPos;
ray.TMin = 0.05;
ray.TMin = max(tmin + kTMinBias, 0.05);
ray.Direction = reflDir;
ray.TMax = g_consts.m_maxRayT;
TraceRay(g_tlas, flags, cullMask, sbtRecordOffset, sbtRecordStride, missIndex, ray, payload);
Expand Down
18 changes: 10 additions & 8 deletions AnKi/Shaders/SsRaymarching.hlsl
Original file line number Diff line number Diff line change
Expand Up @@ -159,6 +159,7 @@ void raymarchGroundTruth(Vec3 rayOrigin, // Ray origin in view space
out RF32 attenuation)
{
attenuation = 0.0;
hitPoint = Vec3(uv, depthRef);

// Check for view facing reflections [sakibsaikia]
const Vec3 viewDir = normalize(rayOrigin);
Expand Down Expand Up @@ -196,22 +197,23 @@ void raymarchGroundTruth(Vec3 rayOrigin, // Ray origin in view space
I32 crntStep = I32(initialStepIncrement);

// Search
Vec3 origin;
[loop] while(maxIterations-- != 0u)
{
origin = start + dir * (F32(crntStep) * stepSize);
const Vec3 newHit = start + dir * (F32(crntStep) * stepSize);

// Check if it's out of the view
if(origin.x <= 0.0 || origin.y <= 0.0 || origin.x >= 1.0 || origin.y >= 1.0)
if(any(newHit <= 0.0) || any(newHit >= 1.0))
{
hitPoint = start;
break;
}

const F32 depth = depthTex.SampleLevel(depthSampler, origin.xy, depthLod).r;
const Bool hit = origin.z - depth >= 0.0;
const F32 depth = depthTex.SampleLevel(depthSampler, newHit.xy, depthLod).r;
const Bool hit = newHit.z >= depth;
if(!hit)
{
crntStep += stepIncrement;
hitPoint = newHit;
}
else if(stepIncrement > 1)
{
Expand All @@ -228,12 +230,12 @@ void raymarchGroundTruth(Vec3 rayOrigin, // Ray origin in view space
const RF32 blackMargin = 0.05 / 4.0;
const RF32 whiteMargin = 0.1 / 2.0;
const RVec2 marginAttenuation2d =
smoothstep(blackMargin, whiteMargin, origin.xy) * (1.0 - smoothstep(1.0 - whiteMargin, 1.0 - blackMargin, origin.xy));
smoothstep(blackMargin, whiteMargin, newHit.xy) * (1.0 - smoothstep(1.0 - whiteMargin, 1.0 - blackMargin, newHit.xy));
const RF32 marginAttenuation = marginAttenuation2d.x * marginAttenuation2d.y;
attenuation = marginAttenuation * cameraContribution;

// ...and hit point
hitPoint = origin;
hitPoint = newHit;

break;
}
}
Expand Down

0 comments on commit 9a4a323

Please sign in to comment.