unity animator 动画 结束后保持位移_Unity资源性能黑榜

在今年的UWA DAY 2020的《轻量级流水线结合方案助力打造高品质游戏》一讲中,我们罗列了在【UWA本地资源检测】上检测未通过的触发规则。无论是大家在开发时的疏忽,还是相关知识点的缺失,这些问题的积累最终都会反映到项目的性能表现上。为此,我们将这些规则曝光出来,并且以一个个知识点的形式逐一解读,从而让大家更深刻地明白,它们是如何对项目的整体性能情况产生影响的。 7cdc566693034ac5bd32389100effe4a.png 本文力图以浅显易懂的表达,让职场萌新或优化萌新深入理解。

今天我们先逐一讲解下这个Top 10 中的前三条规则:“尺寸过大的纹理”,“面片过大的网格”以及“纯色纹理”。

1、尺寸过大的纹理

97%的项目中招

本条规则会扫描指定区域内的所有纹理资源,即所有图片格式的资源。

a7048615dbfc714beba25d3ed48b2564.png

在开发中遇到和纹理尺寸相关的的问题一般有如下几种: 1、一张大型纹理中,很有可能实际使用、复用的,只是这张大型纹理中的一小部分。如图,在这种情况下,如果只需要用到下方纹理中的角色部分,那其余部分于项目而言,就造成了没有必要的内存占用上的浪费。

44c0921ba9722235be6e943d89be17a2.png

2、纹理使用上,没有考虑到实际的显示效果。一张1024*1024纹理的展示效果,可能相较于512*512纹理的展示效果,并没有多大感官上的提升。为了些许的展示效果提升,却要耗费将近4倍的内存空间,那么这种情况是需要大家根据实际需求去仔细商榷的。

4a5b38a677c82db26f8fdf09bef278b3.png

如上图所示,可能只是视觉效果上的些许细微不同,但是在内存占用上,两者却有着4倍的差距。

3、纹理尺寸大小,不单单影响到内存上的占用,对于加载的耗时也有影响。我们曾在之前的文章中对相同格式、不同分辨率的纹理在同一机型下的加载效率进行过比较,戳此了解详情。 00f91f57f41bdc4b7333fc10f1db68a3.png 结论:纹理资源的分辨率对加载性能影响较大,分辨率越高,其加载越为耗时。设备性能越差,其耗时差别越为明显。 对于项目来说,单个纹理尺寸大小带来的影响,可能显得微不足道;但当这些一点一滴的内存与加载耗时累积起来,最终都会作用到整体项目的性能表现。   需要说明的是,这个规则检测是灵活多变的,对于一些较为重度的项目,确实有画质精度的要求,那么大家可以自定义阈值,或者通过自定义规则的方式改善判定规则,从而更贴近项目的实际需求,戳此了解详情。

2、面片数过大的网格

95%的项目中招

这里涉及到两个概念:面片数,网格。

在Unity中,物体是由若干个网格面组成;而每一个网格面,则由若干个三角形面片组成;三角形面片,则是由最基本的“顶点—连线—成面”组成。

面片数的多寡,很大程度上决定了整体展示效果的优劣。面片数少的网格,可能仅能做到“只可意会”;而面片数多的网格,则往往能够做到“所见即所得”。

fdcfc518bd4638a7f0ac99ef669a8eac.png

     左侧为《古墓丽影1》实际游戏中的劳拉形象

右侧为《古墓丽影:暗影》官方宣传片里的形象

这是《古墓丽影》早期的劳拉形象和新三部曲中的形象对比。人物形象的变迁从另一个角度上来讲,其实很好地反映了面片数的数量对展示效果的影响。

但实际的项目开发中,我们可以发现,三角形面片的数量其实是把“双刃剑”:大量的三角形面片能够达成非常好的展示效果;可是一旦三角形面片的数量过大,则势必会对项目的内存占用和加载耗时,以及渲染方面的性能开销上造成不容忽视的压力。

面片数多寡的影响因素有很多:

1、设计水平造成的冗余面片数过多,会不断地挤占内存的有限空间和造成加载耗时的上升。       

0d0d75f9ec99d0de46c1be2a2c16a1ed.png

同一个游戏的不同阶段,或者同一个类型的不同游戏,在设计同种用途的网格时,使用面片数的差异有时达到一个数量级。

2、没有考虑到物体在项目内的实际应用情况。比如作为远方背景的物体,依然以近景设计的要求,在网格中应用了大量的三角形面片,从而造成了面片数的增加,对内存和加载形成了额外的压力。

实际的项目开发中,有时为了追求更好的展现效果而采用了大量面片去设计网格,但由此带来的内存、加载和渲染性能上的消耗,如果远超展示效果上的提升,那就很有可能是得不偿失了。

3、使用了纯色纹理

92%的项目中招

78f88586dd783ee418f462607cb736fd.png       

面对项目中关于单一纯色的需求,我们可以在Shader中直接进行设置,从而达到我们想要的效果。在实际操作中,也就不需要那张纯色纹理的存在,本属于这部分纹理的内存占用和计算耗时就可以直接省下来。 例如为物体添加纯红色,直接就可以在Shader中进行如下设置以达到相应的效果:

2d64986d9e30bdcc314145983a5ce5d3.png

4、包含空纹理采样的材质 91%的项目中招  fc4e71a27a91b650d7220465d9b3e4fe.png 我们在编写Shader时,会声明一些贴图进行计算。但在使用该Shader创建Material实例时,可能并不需要这些纹理,或者因为疏忽忘记对材质添加纹理,那么Unity会为材质赋予一个默认的“纹理”。这个情况虽然不会对计算结果和显示效果造成影响,但是Unity依然会对它进行相关的计算,从而产生性能上的消耗。   所以我们提供这条规则的检测,方便开发团队定位这些不需要用到纹理的材质,删除或注释掉相关的纹理声明,从而避免Unity进行不必要的计算,减轻GPU的压力;同时也能对那些原本预定添加纹理的材质进行判断,进一步优化材质的结构。 5、未开启OptimizeGameObjects的Animator组件 87%的项目中招         27ff8dd53cfdbc34b015487451bcb5f2.png

关于动画系统,我们知道Animation组件对应于Unity老版本的动画系统,而Animator为新版动画系统Mecanim所对应的组件。

        3fec7a9f2c88c98249b754900ec10103.png        

使用Mecanim动画系统,我们可以在对应资源的Import Settings中开启"Optimize Game Objects"选项。

     a74aadd430ba5d3075d970725401f353.png         在不勾选的状态下,Unity在处理动画片段时,不会移除Transform的层级信息,导致在骨骼动画播放时产生不必要的CPU计算开销。      058eb6daeb2777d7264864089c3f1eac.png         而在勾选之后,Unity会进行相关的优化。简单地说,那些只包含Transform组件的骨 骼节点不会被Unity进行导入(但是可以通过在Extra Transform Paths中勾选对应骨骼名称来保留想要的骨骼节点)。相关的骨骼信息会被映射到avatar中, 动画系统 不用每帧再去更新这些骨骼节点(GameObject)的Transform , 而是 直接通过拿 取avatar骨骼信息来实现更新蒙皮,表现动画,从而节省了CPU计算,降低动画开销。   这里需要说明的是:UI用的Animator组件是不支持OptimizeGameObjects的优化项的,不需要进行处理。所以本条检测规则中会过滤掉这部分Animator不再检测。

6、包含Scale曲线的动画片段

86%的项目中招

       4d77bbab2995ddd571c84e07331c2891.png        

我们知道,Scale缩放动画是负责用来控制物体的缩小与放大的。那么Scale曲线的作用,就是记录一段动画中物体每一帧的缩放情况。

       a771a96e4b0cb4d36ec3c219c1347bf4.png        

很多情况下,导入的动画资源当中仅涉及物体的空间位置变换,即Scale曲线值恒为1。所以对动画片段的展示效果没有产生任何影响,但整个曲线数据却是事实存在的,从而导致了内存上不必要的的浪费。   为了避免这种不必要的内存消耗,我们通过本条规则规则将这些包含Scale曲线的动画片段筛选出来,便于开发团队进行排查。 上周,我们罗列了在【性能黑榜】上的Top6规则无论是大家在开发时的疏忽,还是相关知识点的缺失,这些问题的积累最终都会反映到项目的性能表现上。为此,我们将这些规则曝光出来,并且以一个个知识点的形式逐一解读。 今天,我们来继续剖析榜单上的其他问题,包括 “精度过高的动画片段”、“包含无用纹理采样的材质”、“粒子数上限超过30的粒子系统”和“引用纹理尺寸大于256的粒子系统” 。 我们将力图以浅显易懂的表达,让职场萌新或优化萌新深入理解。 *性能黑榜是指在【UWA本地资源检测】中前十名检测未通过的触发规则,近80%的项目已躺枪,值得大家高度重视。
7、精度过高的动画片段 86%的项目中招     9741369303efddce54284c6e99875c3b.png 我们知道,Unity的动画片段中包含着各个动画曲线在每一帧上的关键信息。在很多动画资源当中,关键信息往往是以精度很高的浮点数来进行记录的。         18cf3a54d6bba870fc046eeeb5e1a58a.png        如果动画文件的浮点精度很高,动画片段的表现效果一般来讲也会更好更细致,但是会在内存上带来额外的开销。而适当进行精度压缩,虽然表现效果上会有所降低,但考虑到动画片段的数量和帧数,由此带来的内存节省将会十分可观。   我们建议将精度缩减到3~4位,基于UWA长久以来的实际项目经验,动画片段的精度为3~4位时,能在对表现效果影响较小的情况下,有效降低内存上的开销。   所以UWA通过本条规则,筛选出那些动画精度过高的动画片段,在开发团队经过效果和内存上的平衡考量后,再针对性地进行精度压缩或者保留。大家可以参考UWA问答中的 如何降低动画文件的浮点数精度》一文。(https://answer.uwa4d.com/question/593955b6c42dc04f4d8f7341)
8、包含无用纹理采样的材质 79%的项目中招        14c051ce493ed9186b3cfb0ab6029b87.png 在开发过程中,研发团队会依据实际需要的表现效果而对材质球进行Shader的选择与更换。由于Unity自身的机制设定,当切换材质球使用的Shader时,材质球会自动保存上一个Shader的纹理采样信息。  一旦忽略了这方面的处理,就可能会在最终出包的时候,把那些实际不需要的纹理也带进包中,从而造成内存上的浪费。 通过本条检测规则,开发团队就可以把那些包含无用纹理采样的材质全部找出,然后在材质中删除相关的纹理采样信息,减小包体大小,节省空间。
9、粒子数上限超过30的粒子系统 79%的项目中招         b603631d1b0e24ede2546fdd0b2e293e.png        粒子系统在Unity项目中的运用非常普遍,可用来生成各种诸如下雨、飘雪和火焰等动态效果。下图是一个刚在Unity当中“出生”的粒子系统: bb04ef6f2b5e561307abd0f779632b39.png 而规则中指出的粒子数上限,指的就是该组件同时能拥有的最大粒子数。         ea5957554d0bd7cc6fe67494a9b89ffe.png 在粒子系统中,合理的粒子数会使得诸如火焰或者落叶等特效的表现效果恰到好处。而过多的粒子数不仅会造成内存上的大量占用,实际运行时也会给CPU和GPU的计算带来更大压力。   基于UWA工程师的经验总结和对业内大数据的统计分析,我们发现在一般情况下,粒子系统的粒子数上限不超过30,即可满足大部分情况下所需的粒子表现效果。   开发团队可以通过本条规则,依据实际的展示表现,为粒子系统设置合理的粒子数上限,在保留特效水平的前提下优化内存和运算开销。
10、引用纹理尺寸大于256的粒子系统 78%的项目中招      0733f2de61b0b1f5570a97c2fc2518a9.png    在粒子系统中,我们会需要引用纹理来为粒子“穿上衣服”,以此配合需要达成的各种特效展示效果。 针对单个粒子而言,纹理尺寸的增大,对于整体的粒子表现效果的提升可能并不会那么明显。UWA通过对行业大数据的分析发现:针对大部分粒子系统的使用,纹理尺寸达到256x256即可满足大部分的表现需求。   通过本条规则,大家可以过滤出那些引用纹理尺寸“偏大”的粒子系统,为那些展示效果变动不明显的粒子系统进行“瘦身”。既可以减轻内存和计算的压力,也能够空出宝贵的性能空间去用于那些更重要的粒子系统。

今天,我们来继续剖析【UWA本地资源检测】中和网格设置相关的规则:Normal属性的网格”“开启Read/Write选项的网格”“蒙皮网格骨骼数过大”。我们将力图以浅显易懂的表达,让职场萌新或优化萌新深入理解。


11.1、包含Normal属性的网格

f12b3a364b0d5989d1f2b0ed3748a1fc.png本条规则针对的是网格的Normal属性。在实际运用中,如果网格涉及到了光照、阴影等的应用与计算,那么就需要在网格中导入Normal属性,以达到更好的例如高光、漫反射等表现效果。

和前文讲述的网格Tangent属性类似,Normal属性导入后会对空间和加载性能造成影响。所以在不需要的情况下,我们最好去除网格资源冗余的Normal属性。


11.2、开启Read/Write选项的网格   

caa6107ddf7e8db414285fb8eca11ca9.png

6cce07ca674a336a08395da5f0a5eaf2.png

如同Tips里面指出的,Read/Write 选项启用后,将会允许CPU对网格的顶点、三角形等属性进行读写,这就需要在内存中产生网格数据的副本,便于对网格进行实时的编辑和修改,用来达成例如某些网格的动态效果的展示。下图所展示的Demo就在Runtime使用脚本对Mesh属性进行了动态地修改:

640?wx_fmt=gif

开启Read/Write后,一个网格数据就会有接近2倍的内存消耗。不需要进行动态编辑和修改的网格一旦开启了Read/Write选项,就会产生不必要的内存开销。

本条规则会筛选出所有开启了Read/Write选项的网格,以供开发团队进行相应的选项关闭和优化。需要提醒的是,对于需要调用函数StaticBatchingUtility.Combine进行合批的Mesh,以及部分Unity版本中粒子系统里使用到的Mesh,它们的Read/Write选项依然需要保持开启。

UWA曾对网格资源进行过相关的深度解析和对比测试,大家可以参考一下相关的文章:《Unity加载模块深度解析(网格篇)》


11.3、蒙皮网格骨骼数过大

23d505fe83eab68e7fa15a1f62285778.png

对于带有SkinnedMeshRenderer的模型,UWA本地资源检测会扫描其绑定的骨骼。

如果模型的骨骼数量较大,那么在运行时会有较高的性能开销,从而对整体的项目性能造成影响。对于该规则目前UWA给的推荐阈值为50,我们建议研发团队对模型的骨骼数进行限制,将该类美术资源的性能开销控制在一个合理的范围内。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值