You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Unity SRP自定义渲染通道中DrawRenderers排序异常问题求助

自定义渲染通道DrawRenderers排序异常问题

我在自定义渲染通道中使用DrawRenderers函数时遇到排序错误,以下是该通道的Execute函数代码:

public override void Execute(ScriptableRenderContext context, ref RenderingData renderingData)
{
    CommandBuffer cmd = CommandBufferPool.Get("VisibilityPass");
    SortingSettings ss = new SortingSettings(renderingData.cameraData.camera) {
        criteria = SortingCriteria.BackToFront
    };
    DrawingSettings drawSettings = new DrawingSettings(new ShaderTagId("UniversalForward"), ss) {
        overrideShader = visibilityShader
    };
    FilteringSettings filteringSettings = FilteringSettings.defaultValue;
    cmd.ClearRenderTarget(true, true, new Color(0, 0, 1, 1));
    context.ExecuteCommandBuffer(cmd);
    
    context.DrawRenderers(renderingData.cullResults, ref drawSettings, ref filteringSettings);
    context.Submit();
    CommandBufferPool.Release(cmd);
}

预期效果是将场景渲染到RenderTexture中,用指定Shader覆盖所有物体(场景物体纯黑,立方体纯红),RenderTexture显示在屏幕左上角。多数情况功能正常,但当相机与立方体处于平面中心两侧时,排序出现错误。怀疑是SortingSettings的问题,但不确定具体原因,求排查错误。

正常效果:
正常效果

异常效果:
异常效果


问题原因分析

你当前使用的SortingCriteria.BackToFront是基于物体包围盒中心的深度值进行排序,而非像素级的深度测试。当相机和立方体分别在平面两侧时,平面的包围盒中心可能比立方体更靠近相机,导致平面被优先绘制,覆盖了本应在前方的立方体。同时代码未启用深度测试与深度写入,完全依赖排序结果,没有硬件深度缓冲的兜底判断,进一步放大了排序误差。

修复方案

1. 启用深度测试与深度写入

在CommandBuffer中添加深度相关设置,让硬件深度缓冲处理遮挡关系:

cmd.ClearRenderTarget(true, true, new Color(0, 0, 1, 1));
// 启用深度测试和深度写入
cmd.SetDepthState(DepthState.Default);

2. 调整SortingCriteria排序规则

使用更适合不透明物体的通用排序规则,结合距离与渲染队列,减少排序误差:

SortingSettings ss = new SortingSettings(renderingData.cameraData.camera) {
    criteria = SortingCriteria.CommonOpaque
};

3. 精确指定过滤范围

确保FilteringSettings只处理目标渲染队列的物体,避免不必要的干扰:

FilteringSettings filteringSettings = new FilteringSettings(RenderQueueRange.opaque);

修复后完整代码示例

public override void Execute(ScriptableRenderContext context, ref RenderingData renderingData)
{
    CommandBuffer cmd = CommandBufferPool.Get("VisibilityPass");
    SortingSettings ss = new SortingSettings(renderingData.cameraData.camera) {
        criteria = SortingCriteria.CommonOpaque
    };
    DrawingSettings drawSettings = new DrawingSettings(new ShaderTagId("UniversalForward"), ss) {
        overrideShader = visibilityShader
    };
    FilteringSettings filteringSettings = new FilteringSettings(RenderQueueRange.opaque);
    
    cmd.ClearRenderTarget(true, true, new Color(0, 0, 1, 1));
    cmd.SetDepthState(DepthState.Default);
    context.ExecuteCommandBuffer(cmd);
    
    context.DrawRenderers(renderingData.cullResults, ref drawSettings, ref filteringSettings);
    context.Submit();
    CommandBufferPool.Release(cmd);
}

内容的提问来源于stack exchange,提问作者Gabriel Bacon

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.29 23:52:46