简介: 在翻看 Unity6 的升级log时,看到了UNITY6 提供了一个叫做 GPU Resident Drawer 的功能,它解决了我心心念念的 SRBatch 和 GPUInstancing 的合批问题
unity版本: 6000.0b15
管线: URP
SrpBatch的痛
当前做项目还在用 unity2022.3,作为优化的主要项目就是批次的优化,untiy最近的几个版本都在大力推荐 SrpBatch 功能,这个SrpBatch 功能的合批原则就是,只要着色器是同一个且使用了同一套状态,那么不管模型是否一样,材质球是否是同一个,都可以实现合批,这里的着色器同一状态就是指关键字的开关状态是否一样。
其原理很好理解。我们先回顾一下 drawcall 的概念,CPU 向 GPU 发起一次绘制指令称之为一个 DC。这一次绘制呢,就是要把资源发过去,然后告诉 GPU 可以干活了。
资源都有哪些呢,纹理,模型,渲染逻辑和一些材质参数。可以看到 其实渲染逻辑就是着色器要用的渲染代码,这也解释了上面提到的着色器使用同一套状态,因为一套关键字组合就是一段完整的 gpu 渲染代码。
官方指出,其实资源的传送消耗更高,那么 SrpBatch 就诞生了,随着SrpBatch诞生的一个概念就是 SetPassCall,原本是一套 DC ,发送一次资源,而 SrpBatch 干的活就是一次发送大量能接受的渲染资源到GPU ,在接下来的几次绘制中通过地址偏移直接在使用调用 GPU 绘制,而这一次资源的发送就称之为 SetPassCall,当然实现这个前提就是都是使用的同一套渲染逻辑,然后就可以调用多次 DC 。
所以当我们在工程中开启了 SrpBatch 的时候就会发现,虽然SetPassCall 降低了,但是 Batches 却大量增加了。
因为 SRBatch 不和 GPUInstancing 兼容。而且开启SRBatch 后,引擎优先选择使用 SRBatch 。上对比图。
九个物体,两种材质
-
未开启srpbatch
两次dc
-
开启srpbatch
一个 setpasscall 9个drawcall
GPU Resident Drawer
开启 GPU Resident Drawer 后,相当于兼容了 SrpBatch 和 GpuInstancing
![](https://img.haomeiwen.com/i19189157/e91ad390c3fa956d.png)
在GPU 端直接合批
- GPU Resident Drawer 下的 Instancing 没有占用 cpu 的合批计算逻辑,是在 GPU 本地完成的,所以我们在 State 窗口使用 GPU Resident Drawer 虽然减少了batches ,但是并没有增加 Saved by batching。证明 srpbatch 里的 gpuinstancing 并没有经过 cpu 处理,直接使用的GPU,高级~~
![](https://img.haomeiwen.com/i19189157/cfedac6ad24f0ace.png)
![](https://img.haomeiwen.com/i19189157/7d148d7ce052c7b5.png)
按面积剔除
GPU Resident Drawer 还支持根据物体在屏幕中的面积大小进行剔除 。但是会增加一些计算用的 DC
![](https://img.haomeiwen.com/i19189157/2a752bf61edd2afc.png)
![](https://img.haomeiwen.com/i19189157/2cdd3dff1a3ceba2.png)
开启方式
- 在 UniversalRenderPipelineAsset 配置文件中打开 GPU Resident Drawer
-
UniversalRenderPipelineAsset 配置文件中必须开启 SRP Batch
UniversalRenderPipelineAsset 配置文件中的设置
-
ProjectSetting 中必须设置 BatchRendererGroupVariants 为 keep All
设置 BatchRendererGroupVariants 为 keep All
网友评论