Unity URP Blit Render Feature在Single Pass Instanced VR模式下渲染异常求助
这个问题是URP自定义Render Pass适配Single Pass Instanced VR的典型问题,核心由三个适配错误导致,修复方案如下:
1. 移除多余的上下文提交调用
你在RaymarchRenderPass.Execute方法末尾手动调用了context.Submit(),SRP管线会自动在所有渲染Pass执行完成后统一提交命令,手动提前提交会打断单通道实例化模式下双眼的批量渲染流程,导致单眼渲染结果丢失,直接删除这行代码即可。
2. 替换原生Blit为SRP适配的全屏绘制接口
Unity旧版CommandBuffer.Blit接口原生不支持Single Pass Instanced模式下的2D数组渲染目标,无法正确传递立体眼索引和实例ID,导致材质只渲染到单个纹理层甚至完全不生效。推荐使用URP内置的Blitter工具类替代原有Blit逻辑,该工具原生适配单通道实例化VR的渲染流程,修改后的代码参考:
// 替换原有两行Blit代码 Blitter.Blit(cmd, cameraColourTexture, _destination, Raymarch.Material, 0); Blitter.Blit(cmd, _destination, cameraColourTexture);
如果项目URP版本较低没有Blitter类,也可以用CoreUtils.DrawFullScreen方法替代。
3. 补全Shader的编译宏和眼索引判断
你当前的Shader缺少实例化和立体渲染的编译宏定义,导致UNITY_VERTEX_INPUT_INSTANCE_ID等VR相关宏完全不生效;同时你使用的SLICE_ARRAY_INDEX并未定义,无法正确获取当前渲染的眼索引,按如下修改即可:
- 在Shader的Pass块中新增编译指令:
#pragma multi_compile_instancing #pragma multi_compile _ _STEREO_INSTANCING_ENABLED
- 将片元着色器中的判断条件替换为Unity内置的
unity_StereoEyeIndex:
if (unity_StereoEyeIndex == 0) { return half4(1,0,0,1); } else { return half4(0,0,1,1); }
4. 确认临时RT配置正确
你当前直接拷贝cameraTextureDescriptor创建临时RT的逻辑是正确的,不要修改descriptor的dimension和volumeDepth参数,确保临时RT和相机渲染目标的格式、维度完全对齐,适配2D数组的立体渲染目标格式。
内容的提问来源于stack exchange,提问作者William Whitehouse

