URP 渲染实战 / 第 17 章 顶点动画 / 案例 17.2
案例 17.2阴影 Pass 同步顶点偏移入门
目标:直观看到“只在颜色 Pass 里做顶点动画”的后果,理解为什么必须在 ShadowCaster、DepthOnly 中做同样的变形。
原理:主光阴影贴图是在相机渲染之前,由 ShadowCaster Pass 从光源视角单独渲染的。如果 ShadowCaster 不做变形,阴影贴图里记录的就是原始的平面旗子:地面上的影子是一个规规矩矩的矩形,而且旗子自己接收的自阴影也是“平面旗子”投下的,与它实际的起伏完全无关。
Flag Shader 为演示这个错误,给阴影 Pass 准备了一个带开关的变形函数,通过 VA_DEFORM_SHADOW 宏替换公共文件里阴影 Pass 调用的函数(见上一节 deform 片段末尾)。实际项目里不需要这个开关,公共文件默认就让阴影 Pass 调用同一个 Deform。

阴影 Pass 里的变形还有一个容易忽略的细节:ApplyShadowBias 的法线偏移(Normal Bias)使用的是变形后的法线。如果 Deform 只改位置不改法线,在起伏剧烈的地方法线偏移的方向是错的,可能产生阴影痤疮或漏光。本章的框架里 Deform 同时更新 normalOS,阴影 Pass 自然拿到正确的法线。
深入:其他需要同步的地方① DepthOnly / DepthNormals:开启了 Depth Texture、SSAO 或 Depth Priming 时它们会被执行;不同步会导致 SSAO 的暗角留在原位置、软粒子在错误的地方变淡。② MotionVectors:URP 14 有对象运动矢量 Pass(
MotionVectorRenderPass 绘制 LightMode 为 MotionVectors 的 Pass,Shader 没有这个 Pass 时使用内置的回退材质)。回退材质不知道你的顶点动画,所以依赖运动矢量的效果(例如 TAA、运动模糊的对象模式)看到的是静止的物体。需要的话可以仿照 URP 的 ObjectMotionVectors.shader 自己写一个 MotionVectors Pass,在里面用当前帧和上一帧的时间各算一次 Deform。③ Meta Pass:烘焙光照贴图时用,顶点动画物体一般不参与烘焙,可以忽略。本案例出自《URP 渲染实战》第 17 章「顶点动画」。在章节中阅读上下文 →