上一篇讲到,效果类查询可以每像素只发 1/4 条光线,再靠时空滤波重建回全屏。这就带出一个开光追的玩家都见过的现象:静止看水面还好,一转视角,粗糙反射和间接光那里就浮出一层颗粒;快速转身时,物体边缘还会拖出一条半透明的尾巴。这篇回答:这些颗粒是什么,降噪器凭什么把它抹掉,代价又是什么。
噪点的根源:一个像素要的是一个平均值
先纠正一个很自然的误解:像素的颜色不是“某一条光线的颜色”。真实世界里,一个点的亮度来自四面八方射过来的光的总和。渲染器要算的正是这个“所有方向的平均”,而方向有无限多个,算不完。所以路径追踪用 蒙特卡洛采样:随机挑几个方向发光线,用这少数几个样本的平均值代表整体平均。
每帧每像素只发 1 条光线,就是拿 1 个随机样本来猜这个平均值。猜得准不准是随机的,猜出来的偏差就是画面上那层颗粒。
关键在于偏差下降得很慢,大致按 走( 是样本数):从 1 spp 提到 4 spp,误差只减一半;想让误差降到十分之一,需要 100 倍光线。正是这条平方根曲线,让“再多采样一点”从解法变成了不可能——实时预算就那几条光线,缺口只能靠降噪补 1。
同样是 1 spp,为什么有的地方干净、有的地方满屏颗粒
噪声大小取决于要估的那个分布有多“尖”。
面向一大片光源只算直接光时,几乎朝哪边扔都能碰到灯,样本彼此差别不大,平均一下就准,所以亮面和阴影内部往往很干净。
而间接光要弹几次才落到光源上,光源在场景里常常只是一个小而亮的区域。随机扔出去的光线绝大多数碰不到它,偶尔碰到的那一次带回极大的一笔。同一个像素,这一帧拿到 0,下一帧拿到 10——忽明忽暗,看起来就像画面在“沸腾”(boiling)。极端的版本叫 fireflies(火萤):少数样本贡献极大,画面上冒出孤立的亮点 5。
要记住的是:噪点不是“画错了”,而是“估计得不够准”。
降噪器补的是什么:拿邻居和过去当额外样本
降噪器不在“推测画面里应该有什么”,它做的是用空间和时间上的冗余,去换那些没发出来的光线。
空间滤波:一个像素的邻居看的是同一块表面上附近的一点,光照理应差不多。把邻域的值加权平均,等于帮这个像素凑出更多样本。
时间累积:用 运动矢量(motion vector)把当前像素投影回上一帧,找到它当时在屏幕上的位置,再把历史值和新帧按比例混合。新帧的权重常取 0.1–0.2,也就是 80%–90% 的颜色来自历史 2;静止不动时,几十帧累积下来,等效样本数能从每像素 1 条涨到几十条。
SVGF 就是这套做法的范例:输入是每像素一条路径,先用时间累积提高有效采样数,再估计每个像素的亮度方差,用方差决定哪里该多滤、哪里该少动,最后走一遍小波滤波,2017 年的硬件上跑 1080p 约 10 ms 1。
它的全部本钱是“同一块表面在空间上大片相连、在时间上前后相似”。前提成立就能补;前提破了就会补错。
它会补错什么
拖影(ghosting)。 运动矢量描述的是几何的运动,但阴影和反射不跟着接收面走。影子从地面滑过时,地面的运动矢量长度是零,可“正确的历史”本该跟着影子移动;照着运动矢量去取历史,取到的是几帧前同一块地面的颜色,于是影子后面拖出一条浅色尾巴,而且这条尾巴和地面一样静止,用常规的遮挡检测抓不到 2。同一篇工作还给出两个同类失效:反射里的虚像在动而反射面不动;原本被前景挡住的背景露出来时,历史里那块记的是遮挡物的颜色。
糊掉细节(overblur)。 判断该滤多少靠方差:噪声会推高方差,方差大的地方就多滤。但反过来不成立——方差大不一定是噪声,也可能这里真有细节。在 1 spp 的输入下,渲染器分不清“这个像素亮是因为采样噪声,还是因为它本来就亮”,纹理的高频细节就和噪声一起被抹平。SVGF 的论文自己说,空间上算出的方差只是噪声的不完美代理:噪声会增加方差,但有方差不一定有噪声 1。NVIDIA 也提到,手工降噪器混得过多会丢掉高频信息,后面超分时没东西可用 4。
慢半拍(lag)。 历史占比越高越干净,也越“重”。镜头一转、光源一变,画面还拖着几帧前的信息。
对付拖影的标准做法叫 邻域钳制:把从历史取回的颜色限制在当前帧邻域颜色的取值范围里,偏离太远就作废。但它只是把问题换了个形状——钳制越强,鬼影越少,可有效历史丢得越多,噪声和闪烁就回来;钳制越弱,画面稳,鬼影就出来。SIGGRAPH Asia 2024 那篇改进钳制方法的论文给出了实验结论:最不闪的版本鬼影最多,最不鬼影的版本最闪 3。
另外要说明的是,降噪后是 有偏 的:蒙特卡洛本身是对的,只是不准;滤波用偏差换方差,结果更接近真实光照,但不再是无偏估计 1。所以降噪器必须按场景手调,开发者实际上在选择“我愿意接受哪一种错”。
看到症状,判断原因
- 站着不动,颗粒还在轻轻沸腾:采样不够,降噪压不住。间接光和粗糙反射最容易出现。
- 快速移动时,物体边缘或阴影后拖出半透明尾巴:历史复用失败,ghosting。
- 转动视角时阴影或反射慢半拍:时间迟滞。
- 整体发糊、远处纹理发软、反光像被抹过:空间滤波过度。
这四种症状在同一档光追设置里此消彼长。理解了这个权衡,就能解释一件常被当成“优化差”的事:为什么同一个光追档位,在不同游戏、不同场景里的观感差别会那么大——它们只是在同一根滑杆上落在了不同的位置。