前言:拼UI相信每个Unity程序都做过的事,也是普遍认为最简单、最入门、最没有技术的工作。不出意外的情况下,都会做出策划需要的效果,但是功能实现了,真的就是正确的吗?或者说真的就是合理的吗?那就不一定了。
Unity的优化不简单的归咎于改一行代码,更改一个参数或者勾选一个选项就会发生质的变化,如果真的是这样,无非两种,官方出了新的功能,或者在开发中有很不合理的地方。
优化的本质其实就是本着能省就省,量身定做,只有保持匠心精神,成系统的优化,才能在性能上有优异的表现。从资源(图片,模型等)进到工程到的那一刻起,就应该保证他是符合规范或者可控,只有在层层的有规范的检查下,才能最大限度保证出包的品质和减少无谓的加班~~~
只有把地基打好,才能稳定层层叠加,下面是笔者整理关于拼UI相关的注意事项,希望能够帮到大家
其他优化点会陆续添加
有说的不正确或者不准确的地方欢迎留言指正
主要参考如下:
![](https://img.haomeiwen.com/i7643202/838c36e63a86756b.png)
Unity版本 2018.4.0f1
示例工程下载地址
准备工作,先打开Sprite Packer中的Mode
![](https://img.haomeiwen.com/i7643202/8ea61bb5a51410c3.png)
![](https://img.haomeiwen.com/i7643202/1ca35e70a2bd9590.png)
如果要 Sprite Atlas合批设置成 Always Enabled
![](https://img.haomeiwen.com/i7643202/46c46d8fcd9fa8c1.png)
1. 设置图集的图片可以合批
![](https://img.haomeiwen.com/i7643202/225b334f44c62d7b.png)
![](https://img.haomeiwen.com/i7643202/627b8ae1ac42776b.png)
![](https://img.haomeiwen.com/i7643202/91194781b74a8807.png)
2. 避免不同图集或材质的倾轧,Scene视图调节为Writeframe模式可以更容易查看
![](https://img.haomeiwen.com/i7643202/cafc83abe1239e47.png)
![](https://img.haomeiwen.com/i7643202/196607fa606bb859.png)
3. 倾轧时,在Hierarchy视图中排序错误,导致合批的步骤增加
![](https://img.haomeiwen.com/i7643202/9902d043a3dd13df.png)
![](https://img.haomeiwen.com/i7643202/f50db18fdf579053.png)
![](https://img.haomeiwen.com/i7643202/956c248fd853f1f9.png)
![](https://img.haomeiwen.com/i7643202/92cf4ee575751996.png)
4. Mask会增加一个Draw,并且Mask里面的图片不会和外面的图片合批
![](https://img.haomeiwen.com/i7643202/5ced03a2dba3e31b.png)
![](https://img.haomeiwen.com/i7643202/9e316fe81dbb7f7f.png)
5. RichText会造成三角面增加
![](https://img.haomeiwen.com/i7643202/aaf899af041c7d90.png)
![](https://img.haomeiwen.com/i7643202/7a4d7a9f2d3e081d.png)
6. 空的Image造成一个Drawcall并且会打断合批
![](https://img.haomeiwen.com/i7643202/e310dda268626d78.png)
![](https://img.haomeiwen.com/i7643202/a83cc5eb6dea7bd3.png)
7. 颜色渐变和可以用material控制,本质是更改Tint属性,这样既能满足颜色渐变,又能避免网格频繁重建造
![](https://img.haomeiwen.com/i7643202/77481cffed53ce72.png)
![](https://img.haomeiwen.com/i7643202/23161151cc0ab69f.png)
![](https://img.haomeiwen.com/i7643202/50bf12fe334e41cd.png)
![](https://img.haomeiwen.com/i7643202/03b831c15a6632aa.png)
8. 接受射线脚本:Empty4Raycast
![](https://img.haomeiwen.com/i7643202/eb9355339e01ae52.gif)
9. 减少OverDraw脚本:PolygonImage
![](https://img.haomeiwen.com/i7643202/e924ccd7cc60f49c.png)
10. 关闭不需要的Raycast Target选项(Image、Text、RawImage),降低每帧检测射线的性能消耗。检测勾选Raycast Target脚本 :DebugUILine
![](https://img.haomeiwen.com/i7643202/49d875172be9f78c.png)
11. 用多个Canvas将屏幕划分出不同的区域,降低网格重建带来的性能损耗
12. 避免或者降低赋值的操作,降低网格重建频率 例如在Update中执行textComponent.text = "菜鸟海澜"
,如果数值没有变化可以不用赋值,有变化一秒赋值一次
13. 避免使用Blocking Objects来遮挡射线,因为这是一个相当消耗性能的操作
![](https://img.haomeiwen.com/i7643202/68ca62e70c296cbb.png)
14. Screen Space 和 World Space 中的Camera必须要指定,负责会每帧7-10次调用Object.FindObjectWithTag!!!
![](https://img.haomeiwen.com/i7643202/15c23c9c1cbb19e0.png)
![](https://img.haomeiwen.com/i7643202/1b70b85bfc49451b.png)
![](https://img.haomeiwen.com/i7643202/10e46d0f4e513efe.png)
15. Layout这种东西少用,或者用了尽可能减少子节点的变动,(让结构简单点也行)因为会从变动节点递归向上调用GetComponents,而且要最大可能减少嵌套Layout。(不过没有开发时间还是用吧~~~)
![](https://img.haomeiwen.com/i7643202/c592064a6ad025ca.png)
![](https://img.haomeiwen.com/i7643202/e14898b95beca870.png)
![](https://img.haomeiwen.com/i7643202/01b5269eae74670d.png)
16. Canvas下面的UI元素移动到屏幕外很远处,会分情况出现Drawcall数量变动的情况
- Screen Space -Camera模式下移除全部UI会引起Drawcall的变化
- Screen Space - Overlay模式下移除全部UI不会引起Drawcall的变化
- 但是这两种模式只移除部分UI(图片部分)并不会引起Drawcall的变化
-
而且在UI移动后会影响原来的Depth排序,造成合批失败产生更多的Drawcall
17. 频繁需要SetActive的物体可以使用Canva Group组件,可以有效降低重建消耗
![](https://img.haomeiwen.com/i7643202/c72884ecb414d06b.png)
18. 禁用Canvas组件本身可以避免重建消耗来达到隐藏的效果(前提节点没有改变),但是对应脚本上的OnEnable、OnDisable会触发,所以笔者一直用Canva Group组件
19. outline和shadow组件就不要用了,Text Mesh Pro性能更好,功能强大,还免费!!!
![](https://img.haomeiwen.com/i7643202/4b3c18956a567953.png)
20. Frame Debug真是一个好工具,可以有效查看渲染顺序和不能合批的原因
![](https://img.haomeiwen.com/i7643202/940e5a0c1916076e.png)
21. 配合Profiler中新添加的UI性能监控真是锦上添花
![](https://img.haomeiwen.com/i7643202/0489b0f058911614.png)
22. Scroll Rect 组件对应的Content填加 Canvas 组件 ,因为对应的Mask 子元素依然参与全局的Depth排序,避免因拖动打乱原有的Depth排序,造成合批失败
![](https://img.haomeiwen.com/i7643202/e9ad1f55d26bcdb7.png)
![](https://img.haomeiwen.com/i7643202/4cd6277dcc320d3a.png)
23. 用户协议等巨型篇幅的文字显示,会造成Canvas.sendWillRenderCanvases 开销过大。因为内容过大,导致vertexhelper中的list的capacity过大,基本的clear操作都会非常耗时,所以用反射调用每个List的TrimExcess函数,如果反射不熟悉的同学请看Unity C#基础之 反射反射,程序员的快乐
下面为UGUI部分源码
![](https://img.haomeiwen.com/i7643202/fd7736c0b2940721.png)
![](https://img.haomeiwen.com/i7643202/a750338705ab0cd1.png)
网友评论