Unity-URP延迟渲染SSR
SSR(Screen-Space Reflection,屏幕空间反射)沿表面的反射方向寻找屏幕深度中的交点,再读取该位置的场景颜色。它利用了当前帧已有信息,也因此无法看到屏幕之外或深度层之后的内容。
本文以 2023 年 3 月 26 日笔记为主,合并后续 Hi-Z 实现思路。重点区分视角空间射线、屏幕步进、深度判定与最终合成,不把“模糊一下”当成完整的粗糙反射。

1. 输入与空间约定
基础输入通常包括深度、法线、场景颜色,以及粗糙度或反射 Mask。深度重建为观察位置后,法线也要转换到同一空间。
若 V 指向相机,入射方向为 -V,则反射方向可写成 reflect(-V,N)。向量定义与法线朝向必须一致,不能把世界法线和观察位置直接混用。
场景颜色一般应取自适当阶段,避免把本次反射结果递归采回自己。透明、后处理、曝光与历史颜色也会影响结果语义。
2. 沿射线做深度判定
1 | |
射线样本与深度图需要在同一深度定义下比较。设备深度是非线性的,直接用固定阈值相减通常不能表示固定世界厚度。
单层深度无法知道物体真实厚度,Thickness 是一种容错近似。阈值过大产生穿墙,太小又漏掉薄表面。二分细化只在已有合理交点区间时有意义,不能修复完全漏过的几何。
3. 为什么采用屏幕空间 DDA
观察空间等距步进,投到屏幕后并不等距,可能近处跳过像素、远处又重复采样。DDA 类方法沿屏幕主轴组织步进,让样本覆盖更均匀。

但线性插值屏幕坐标时,观察深度不能随便做普通线性插。需使用与透视投影一致的插值关系,正确处理起点、终点、裁剪和深度区间。

4. Hi-Z 是深度层级,不是梯度
深度金字塔的粗层代表更大屏幕区域,可帮助判断整段区域是否可能相交。能安全跳过时走大步,可能命中时下降到更细层级。
原笔记“从最小 Mip 开始逐渐增大就缩小范围”的说法混淆了索引与尺寸。通常第 0 级最细,索引增加图像变小、区域变粗;具体遍历可以动态升降层级,不是只朝一个方向走。
归约取 min、max 还是区间,取决于设备深度方向、算法需要的界限与保守性。Reversed-Z 下尤其不能直接照搬正向深度比较。
5. 粗糙度与降噪
简单按粗糙度模糊锐利结果,可以改善外观,但不等于按微表面 BRDF 正确积分。更完整的方法涉及方向采样、权重、像素足迹与重建,并要处理深度边缘。
随机抖动可以把带状误差转成噪声。Halton 序列、Dither 与其他采样模式有不同定义,不能把“Halftone”当作所有时域抖动的统称。
时域累积需要运动重投影、历史有效性、深度/法线拒绝与亮度约束。仅保留一张 HistoryTex 直接平均,会在遮挡变化和运动反射中拖影。
6. 命中失败要有明确回退
屏幕边缘、背向表面、离屏对象与被遮住的颜色会导致失败。应结合反射探针或其他方案,并用可信度平滑过渡,避免反射在边界突然截断。

优化可以从反射 Mask、降分辨率、步数预算与分层遍历入手。比较时应保留命中率与稳定性,不能只报告省了多少采样却忽略反射缺失。
总结
SSR 是在有限屏幕数据上做射线查询。正确空间、透视插值与深度界限决定命中是否可信,回退与时域处理决定最终是否稳定;Hi-Z 提供加速机会,不替代这些前提。