混合渲染管线 (Hybrid Rendering):光栅化几何结合光追局部反射

在当前的主流硬件环境下,全量路径追踪(Full Path Tracing)在 4K 60 帧或移动端实时游戏中依然是不切实际的算力黑洞。即便在桌面端旗舰显卡上,单像素发射数百根光线的全光追管线也高度依赖昂贵的时间序列超分辨率降噪器(如 DLSS 3.5 光线重建)。
因此,现代商业 3A 引擎(如 Unreal Engine Lumen、寒霜引擎以及自研管线)普遍采用混合渲染架构(Hybrid Rendering Pipeline):
- 主几何与主视线(Primary Rays):继续由传统的高吞吐光栅化管线(Rasterization)负责,完美继承 Early-Z 剔除、硬件 MSAA/TAA 以及成熟的材质着色器分支;
- 次级光线交互(Secondary Rays:局部镜面反射与接触阴影):精准指派硬件光追(Hardware Ray Tracing)只在光滑金属、水面、玻璃等高感知度材质表面发射局部光线(1 Ray per Pixel),并配合屏幕空间反射(SSR)作为保底回退。
这套混合方案将光追算力消耗严格控制在总帧时间的 15%~25% 以内,以极高的性价比实现了物理真实的视觉飞跃。
混合渲染管线的调度流程与数据流转
[ 场景静态/动态网格几何体 ]
│
┌──────────────────┴──────────────────┐
▼ ▼
[ 传统光栅化 G-Buffer Pass ] [ 硬件 BVH 加速结构刷新 ]
(Depth / Normal / Roughness / BaseColor) (TLAS / BLAS 更新)
│ │
└──────────────────┬──────────────────┘
│
▼
[ 光栅化直接光照计算 (Direct Lighting) ]
│
▼
┌─────────────────────────────────────────┐
│ 光线追踪局部反射 Pass (RT Reflection) │
│ 1. 依据 Roughness 掩码筛选反射像素 │
│ 2. 优先屏幕空间追踪 (Screen-Space Ray) │
│ 3. 失败/越界时光追求交 (BVH Traversal) │
└──────────────────────┬──────────────────┘
│
▼
[ 时空双边滤波降噪 (Spatio-Temporal Denoiser) ]
│
▼
[ 色调映射与后期合成 (ToneMapping & Compositing) ]
光追局部反射 HLSL 计算着色器实现
在 Direct3D 12 (DXR) 或 Vulkan KHR 光追中,我们可以在 Ray Generation Shader 中读取光栅化阶段生成的 G-Buffer,精确判断当前像素是否值得发射光线:
// RayTracingReflection.hlsl
#define HLSL
#include "RayTracingCommon.hlsli"
// 输入光栅化 G-Buffer 纹理绑定
Texture2D<float> g_DepthTexture : register(t0);
Texture2D<float4> g_NormalTexture : register(t1);
Texture2D<float4> g_MaterialTexture : register(t2); // R: Metallic, G: Roughness
RaytracingAccelerationStructure g_SceneTLAS : register(t3);
// 输出带降噪前置的反射辐射度纹理
RWTexture2D<float4> g_OutputReflection : register(u0);
struct RayPayload
{
float3 Radiance;
float HitDistance;
};
[shader("raygeneration")]
void ReflectionRaygenShader()
{
uint2 pixelPos = DispatchRaysIndex().xy;
uint2 screenSize = DispatchRaysDimensions().xy;
float depth = g_DepthTexture[pixelPos];
if (depth >= 1.0f) // 背景天空盒不发射反射光线
{
g_OutputReflection[pixelPos] = float4(0, 0, 0, -1.0f);
return;
}
float4 matParams = g_MaterialTexture[pixelPos];
float metallic = matParams.r;
float roughness = matParams.g;
// 粗糙度大于 0.45 的漫反射表面直接走光栅化探针 (IBL),跳过光追计算
if (roughness > 0.45f)
{
g_OutputReflection[pixelPos] = float4(0, 0, 0, 0.0f);
return;
}
// 重建世界空间坐标与法线
float3 worldPos = ReconstructWorldPosition(pixelPos, depth, screenSize);
float3 worldNormal = normalize(g_NormalTexture[pixelPos].xyz * 2.0f - 1.0f);
float3 viewDir = normalize(worldPos - g_CameraWorldPos);
// 计算完美镜面反射向量
float3 reflectDir = reflect(viewDir, worldNormal);
// 沿法线做微小偏移,规避自相交(Self-Intersection Acne)
float3 rayOrigin = worldPos + worldNormal * 0.002f;
RayDesc ray;
ray.Origin = rayOrigin;
ray.Direction = reflectDir;
ray.TMin = 0.001f;
ray.TMax = 100.0f; // 限制最大追踪距离为 100 米
RayPayload payload;
payload.Radiance = float3(0, 0, 0);
payload.HitDistance = -1.0f;
// 发射单条求交光线(RAY_FLAG_CULL_BACK_FACING_TRIANGLES 提升求交速度)
TraceRay(
g_SceneTLAS,
RAY_FLAG_CULL_BACK_FACING_TRIANGLES,
0xFF, // Instance Mask
0, // Hit Group Index
1, // Multiplier
0, // Miss Shader Index
ray,
payload
);
// 写入反射颜色与击中深度(供后续时域滤波降噪器使用)
g_OutputReflection[pixelPos] = float4(payload.Radiance, payload.HitDistance);
}
[shader("miss")]
void ReflectionMissShader(inout RayPayload payload)
{
// 未击中任何几何体,采样远景环境天空贴图 (HDRI)
float3 dir = WorldRayDirection();
payload.Radiance = SampleEnvironmentMap(dir);
payload.HitDistance = 1000.0f;
}
混合渲染管线的性能与带宽平衡策略
- 半分辨率追踪 + 联合双边重建(Half-Res Dispatch & Bilateral Reconstruction):
- 绝不要以原生 4K 分辨率发射光追反射。在 $1920 \times 1080$ 的半分辨率缓冲区发射光线,随后利用法线与深度权重指导的双边滤波(Bilateral Upsampling)插值回全分辨率,性能提升接近 300%,画面细节几乎无损。
- 混合 SSR 梯次兜底(Hybrid Screen-Space Fallback):
- 在 Shader 中优先执行 8~16 步轻量屏幕空间光线投射(Hi-Z SSR)。如果屏幕空间已经包含该反射物体的颜色,直接采样屏幕缓存;只有当 SSR 投射出屏幕边界或被前景遮挡时,才回退发射硬件光追光线。
- 简化光追命中材质 Shader(Simplified Hit Shader):
- 在光追的 Closest Hit Shader 中,绝不能复用光栅化阶段包含复杂视差贴图、次表面散射与复杂多光源计算的沉重 Pixel Shader。命中着色器应大幅简化为纯 Albedo 采样 + 简易方向光求和,大幅降低寄存器压力(VGPR Pressure)。
混合架构不是对纯光追的妥协,而是在摩尔定律减速的物理客观规律下,工程师运用数学与系统工程榨取极致画面的最优解。
转载自 CSDN-专业IT技术社区
原文链接:https://blog.csdn.net/rain_sxr/article/details/165614172



