Unity 2017 Game Optimization 读书笔记 The Benefits of Batching

batching(合批) 和大量的描述一个3D物体的数据有关系,比如meshes,verices,edges,UV coordinates 以及其他不同类型的数据。在Unity中谈论batching,指的是用于合批mesh数据的两个东西:Dynamic Batching(动态合批) 和 Static Batching(静态合批)。渲染管线特别喜欢处理合在一起提交的mesh数据而不是单独的一个个的mesh数据。

Draw Calls

在讨论Dynamic Batching(动态合批) 和 Static Batching(静态合批)之前,先理解下Dynamic Batching(动态合批) 和 Static Batching(静态合批)要解决渲染管线的问题:降低用于绘制当前视图所有物体的Draw calls。

Draw call是从CPU发送到GPU的一个请求,用于物体的绘制。在Draw call请求之前,需要完成一系列的准备工作。

首先,mesh和textrue数据必须从CPU 的内存(RAM)推送到GPU内存(VRAM),对于已经存在于场景里的,这通常发生在场景初始化的时候。对于预先没有在场景内的,只能在它们被instantiate的时候进行该操作。其次,cpu必须为gpu准备渲染所需要的设置和数据。cpu和gpu之间的通信是通过不同平台的图形API来完成的,有可能是DirectX,OpenGL,Vulkan等等。

API通过驱动程序调用,大量繁杂的渲染管线渲染物体所需的设置信息通常被叫做Render State。在Render State改变之前,GPU都将会一直使用这个Render State来渲染物体。对Render State做改变是一个开销非常大的过程,比如我们设置Render State使用一张蓝色texture去渲染mesh,这会将整个mesh渲染成蓝色,我们可以再渲染9个完全不同的mesh,它们都会被渲染成蓝色,因为我们没有改变使用的texture。但是如果我们想渲染10个mesh哟个10张不同的贴图,就会十分耗时,因为需要渲染每个mesh时都去准备新的贴图信息发送draw call。越少更改Render State,图形api处理我们的请求就会越快。

能触发Render State同步的操作包括但不限于:添加实时的texture到GPU,修改Shader,修改灯光信息,修改阴影和透明度等等有关渲染的设置。

CPU和GPU之前通过Command Buffer保持通信,这个队列存储了CPU创建好的用于渲染的操作指令,GPU在每次完成渲染指令后再从这个队列中获取。

一个新的Draw Call并不意味着必须有一个新的Render State。合批能够提供渲染性能的原因是如果俩个物体使用同样的RenderState信息来渲染,GPU就可以立刻渲染下一个物体,这消除了Render State的同步时间,合批同样可以减少渲染的指令数量,减少CPU和GPU的负荷。

Materials and Shaders

Unity中通过Materials来把Render State暴露给我们。Materials是一个Shader的容器,shader本身并不感知实际的Render State,shader所需的diffuse textures,normal maps等实际就是隐式的Render State变量。

每一个shader都需要一个Material,一个Material也必须有一个Shader。因此如果我们想减少Render State的变化,我们可以通过减少场景中Materials的数量。CPU每帧会消耗更少的时间来生成和传输渲染指令,GPU也不需要频繁停下来重新同步Render State的变化。

做个实验,四个cube,四个sphere,各自不同的material,关掉shadow,关掉dynamic batching 和 static batching:

结果为9个batches(还有一个是背景,比如天空盒)

像之前介绍的那样,我们可以减少material数量来提高效率,如果都用同样的material会是什么效果:依然还是9个,这是因为我们没开启Dynamic Batching,渲染管线并不能够意识到需要重复使用Render State。

The Frame Debugger

Unity中调试渲染非常有用的工具,可以查看每一帧的渲染过程,对于跟踪场景中DrawCall来源,优化游戏非常有用。这一小节就不详细介绍了

 Dynamic Batching

三个特性:

1. 运行中实时动态合批

2. 根据主摄像机视野中可见的物体,每一帧合批的内容都可以不同

3. 运动的物体也可以进行合批

上一小节的例子,开启动态合批后结果为:6个batches,这是因为4个Sphere因为不满足动态合批条件而没有进行合批。

动态合批的条件具体参考Unity的文档,这玩意随着Unity版本的变化不断在变化。

https://docs.unity3d.com/Manual/DrawCallBatching.html

动态合批需要满足的条件:

  • 使用相同的材质引用
  • 只有ParticleSystem和MeshRender可以合批,SkinnedMeshRender等其他Component无法合批.Currently, only Mesh Renderers, Trail Renderers, Line Renderers, Particle Systems and Sprite Renderers are batched. This means that skinned Meshes, Cloth, and other types of rendering components are not batched.
  • 每个mesh最多300个顶点索引。
  • 最多900个顶点属性 。
  • mesh的Scale要么都统一,要么都别统一(这句没看懂,令人费解)
  • 材质的shader不能使用多passes
  • mesh不能接收实时阴影
  • 合批后mesh总共的索引数不能超过各自平台的上限,一般是32k-64k个。

Vertex attributes

顶点属性是每个顶点的一系列信息,比如位置,法线,UV等。如果每个顶点3个属性,则如果想合批,可以最多支持的顶点数是900/3 = 300。如果每个顶点5个属性,则最多可以持的顶点数是900/5 = 180。要注意的是即使顶点属性少于3个,合批最多也只能支持300个顶点(另外一条规则)

Mesh scaling

奇数个负数Scale不能合批,比如(1,-1,1),偶数个可以(1,-1,-1)

Dynamic Batching summary

  • 适用于场景中含有大量简单的物体,比如大片有石头和树木的森林等。
  • 如果只是单纯的texture不同,可以考虑使用图集的方式,这样就可以合批。
  • 如果场景中有很多个比较简单的物体,但是只有少数可以合批的话,还不如不开启合批,因为遍历场景判断合批的操作可能更费。
  • 动态合批的条件非常苛刻,经常会出现打破了合批规则而自己不知道,所以要多注意,要经常不定期的去调试check来保持Draw call的合理值,当然,常常的状况是我们直到Draw Call真的成为性能瓶颈影响表现时,并不需要去考虑Draw call。
  • 最后一条建议,多尝试,看看哪些不能合批哪些能合批来保证Draw call

Static Batching

Unity 提供了第二种合批方式,那就是Static Batching。Static Batching的条件:

  • 物体必须被标记为Static
  • 需要额外的内存
  • 合批后mesh总共的索引数不能超过各自平台的上限,一般是32k-64k个。
  • mesh可以不同,但是必须使用相同的材质引用

The Static flag

要小心如果只是把物体标记为Batching Static,运行时可能会产生奇怪的现象:mesh由于Static Batching没有移动,但是Rigidbody什么的可能会动。

Memory requirements

额外的内存开销是Static Batching的一个缺点,Static Batching copy 需要合批的mesh的数据到一个单独的大mesh buffer中,并将其传入渲染管线中通过一个Draw Call进行渲染,完全忽略掉原始的mesh。如果需要合批的mesh都是不同的,那是否使用静态合批内存的开销是一样的。然而如果渲染的是相同的object,则内存开销会翻倍,平常渲染一个,10个或者100万个同样object的clone花费的内存开销是一样的,因为他们引用的是相同的mesh 数据,对于每个Object唯一不同的只是transform。然而Static Batching 需要copy mesh 数据到大的buffer中,这种引用关系就没有了,每个物体都会将原始的mesh数据copy到buffer中。因此使用Static Batching 渲染1000个tree的内存开销是不使用Static Batching的1000倍,所以在使用Static Batching时要慎重,要判断使用的是否合适。

Material references

有时候,Static Batching会需要处理多个Materials,在这种情况下,每个Material会被分组到各自的Static Bathc中,也就是说Static Batching可以用和Materials数量相等的Draw Call渲染所有的静态meshes。

Static Batching caveat & Edit Mode debugging of Static Batching & Instantiating static meshes at runtime

  • Static Batching 不能在编辑器中立刻查看效果,只能运行起来后看效果,调试起来非常麻烦
  • 运行时将物体动态标记成Static并不会被合批,但是可以通过 StaticBatchUtility.Combine() 强制合批,但是要非常谨慎使用,这个函数开销极大

Static Batching summary

Static Batching 是一个十分有用但是又十分危险的工具,如果使用的好会给渲染带来提升,如果使用的不好,内存的开销以及各种其它弊端都会很蛋疼。

Summary

Dynamic Batching 和 Static Batching summary都是有用但是又有风险的工具,要真正搞明白它们才能正确的使用它们。第六章会更多更深入的介绍Dynamic Graphics。

 

GPU Instancing

此处加一点书中这章没写的内容,GPU Instancing也会有效降低DrawCall,它的原理详见

https://learnopengl-cn.github.io/04%20Advanced%20OpenGL/10%20Instancing/

GPU Instancing 非常高效,它的要求也更高,不仅要求Material引用一样,mesh也必须一样,因为mesh一样所以才不会存在Batching合并大mesh带来的内存开销。

Unity Batching优先级:静态合批 > GPU Instancing  > 动态合批

 

 

 

 

 

 

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/246204.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Unity 2017 Game Optimization 读书笔记 Dynamic Graphics (3)

Rendering performance enhancements Enable/Disable GPU Skinning 开启GPU Skinning可以减轻CPU或GPU中Front End部分中某一个的负担,但是会加重另一个的负担。Skinning是mesh中的顶点根据动画中骨骼的当前位置进行计算,从而让角色摆出正确的姿势。 …

Unity手游开发札记——布料系统原理浅析和在Unity手游中的应用

原文:https://zhuanlan.zhihu.com/p/28644618 0. 前言 项目技术测试结束之后,各种美术效果提升的需求逐渐成为后续开发的重点,角色效果部分的提升目标之一便是在角色选择/展示界面为玩家提供更高的品质感,于是可以提供动态效果的…

行为树(Behavior Tree)实践(1)– 基本概念

原文:http://www.aisharing.com/archives/90 行为树(Behavior Tree)实践(1)– 基本概念 自从开博以来,每天都会关心一下博客的访问情况,看到一些朋友的订阅或者访问,不胜欣喜&…

Unity 2017 Game Optimization 读书笔记 Dynamic Graphics (5) Shader优化

Shader optimization Fill Rate和 Memory Bandwidth开销最大的地方就是Fragment Shader。开销多大取决于Fragment Shader的复杂程度:多少纹理需要采样,多少数学计算函数需要使用等等。GPU的并行特性意味着在线程中如果任何地方存在瓶颈,都会…

Unity 2017 Game Optimization 读书笔记 Dynamic Graphics (6)

1. Use less texture data 这条优化技巧非常直接,减少texture的数据量,减少分辨率或者降低位数,虽然可能会降低渲染质量。但是通常使用16-bit textures并不会明显的感觉到渲染效果下降。 MipMap技术可以有效减少VRAM和Texture Cache之间来回…

LeetCode 面试题57 - II(剑指offer) 和为s的连续正数序列

今天毕业五年了,一直忙于工作和享受,自从当年找完工作后就一直没有再刷过题,作为搬砖的码农,觉得还是应该养成长期刷题的习惯坚持下去。之前坚持了每天被一会单词,如今雅思一本也快看完了,从今天开始准备在…

反走样技术相关文章

https://zhuanlan.zhihu.com/p/28800047 https://zhuanlan.zhihu.com/p/57503957 https://zhuanlan.zhihu.com/p/33444125 https://zhuanlan.zhihu.com/p/33444429 走样的原因及其分类 说到走样,首先要说的就是采样。这也算是很多图形学专著中提到反走样相关技…

求n的阶乘的算法框图_单片机常用的14个C语言算法

问:怎么每天看到这种文章?答:只需搜索公众号"51单片机学习网"免费关注算法(Algorithm):计算机解题的基本思想方法和步骤。算法的描述:是对要解决一个问题或要完成一项任务所采取的方法和步骤的描述&#xff…

LeetCode 286. 墙与门 多源BFS和DFS

思路1&#xff1a; DFS&#xff0c;对于每个门进行一次DFS搜索&#xff0c;记录每个位置对每个门的距离&#xff0c;当有更小距离的门时更新这个数值 public void WallsAndGates(int[][] rooms) {for (int i 0; i < rooms.GetLength(0); i){for (int j 0; j < rooms[i]…

贝塞尔曲线

文章参考于&#xff1a;https://www.jianshu.com/p/0c9b4b681724 https://gameinstitute.qq.com/community/detail/129188 贝赛尔曲线的前世今生&#xff1a; 贝塞尔曲线&#xff0c;这个命名规则一眼看上去大概是一个叫贝塞尔的数学家发明的。但&#xff0c;贝塞尔曲线依据…

如何控制局域网网速_单臂路由|N1盒子(OpenWRT)单线多拨实现网速叠加

受于某些现实条件&#xff0c;有些同学苦于家里的网络带宽太小无法尽情冲浪。如何在不额外花钱升级宽带的情况下提升家里网络呢&#xff1f;且看一个盒子加路由器即可实现网络单线多拨&#xff0c;成倍提升网速完成网速叠加。题图是我家里的路由器加N1盒子。前置条件光猫有超级…

linux离线安装redmine_Linux 下一款非常好用的翻译软件

前面有一个半月的时间&#xff0c;我非常详细且非常基础的介绍了 Ubuntu 18.04 desktop 桌面系统的安装和基本使用&#xff0c;在知乎上也开了一个专栏《Linux 漫游之旅》&#xff0c;上面记录了所有的文章&#xff0c;这个专栏的目的呢是手把手教新接触 Linux 操作系统的朋友如…

vivo应用商店电脑版_VIVO应用商店代理商江湖的那些关系

VIVO应用商店代理商江湖的那些关系需要源文件清晰版本加微信wps007其他干货文章如何不花钱或者少花钱把ASO的活给干了&#xff1f;2020最新主流安卓应用市场ASO技巧以及注意事项App推广的高阶玩法&#xff0c;一箭双星&#xff01;今日头条定向优化技巧今日头条广告创意优化指南…

华为阅读下载的文件在哪里找_华为手机还要天天清理内存?1键关闭这2个设置,手机用到2035年...

阅读本文前&#xff0c;请您先点击上面的蓝色字体“科技荟 ”&#xff0c;再点击“关注”&#xff0c;这样您就可以继续免费收到最新文章了。每天都有分享。完全是免费订阅&#xff0c;请放心关注。 华为手机还要天天清理内存&#xff1f;1键关闭这2个设置&#xff0c;手机用到…

pyautogui 打包 运行 窗口_试试动态窗口管理器 dwm 吧

以不到 2000 标准行的代码写就的 dwm&#xff0c;是一个速度极快而功能强大&#xff0c;且可高度定制的窗口管理器。-- Adam Šamalk(作者)如果你崇尚效率和极简主义&#xff0c;并且正在为你的 Linux 桌面寻找新的窗口管理器&#xff0c;那么你应该尝试一下 动态窗口管理器(dy…

ArcMap 导入 wrl_flmic拍摄的素材如何无损导入电脑

点击上方“九尾短视频研习室” 可以订阅哦&#xff01;今天分享使用 iPhone 或者安卓版 filmic 拍摄的素材&#xff0c;如何无损导入到win 或 Mac 电脑中~01iPhone Mac使用 iPhone 和 Mac 的朋友&#xff0c;可以使用“隔空投送”无线传输&#xff0c;但是这个过程中&#xff…

LeetCode 97: 交错字符串

这里我们考虑用 s1和 s2的某个前缀是否能形成 s3 的一个前缀。 这个方法的前提建立于&#xff1a;判断一个 s3的前缀&#xff08;用下标 k表示&#xff09;&#xff0c;能否用 s1和 s2 的前缀&#xff08;下标分别为 i和 j&#xff09;&#xff0c;仅仅依赖于 s1 前 i个字符和…

苹果6发布时间_苹果秋季发布会将在北京时间9月16日举办

点击上方蓝字&#xff0c;关注我们苹果正式公布了苹果秋季发布会9月16日举办&#xff0c;届时国内可在五大平台上观看直播&#xff0c;据悉本次发布会将发布的产品有iPhone、ipad和Apple Watch等系列新品&#xff0c;那么这场发布会可以在哪看呢?下面小编带来了2020年苹果秋季…

安装ccs5.5总出现错误_《西游记》“斗法降三怪”,出现错误而补拍,观众总觉得改过结尾...

文|平小山86版《西游记》播出多年&#xff0c;每一年寒暑假都会在电视台重播&#xff0c;看了无数遍还是让观众乐在其中。后来无论是TVB版、浙版、还是张纪中版翻拍的《西游记》&#xff0c;都始终无法撼动它的经典地位。在86版《西游记》中有一集&#xff0c;就是在车迟国的“…

LeetCode面试题03. 数组中重复的数字

方法一&#xff1a;遍历数组 由于只需要找出数组中任意一个重复的数字&#xff0c;因此遍历数组&#xff0c;遇到重复的数字即返回。为了判断一个数字是否重复遇到&#xff0c;使用集合存储已经遇到的数字&#xff0c;如果遇到的一个数字已经在集合中&#xff0c;则当前的数字是…