技术分享连载(九十一)

技术分享连载(九十一)

我们将从日常技术交流中精选若干个开发相关的问题,建议阅读时间15分钟,认真读完必有收获。如果您有任何独到的见解或者发现也欢迎联系我们,一起探讨。

UWA QQ群:465082844
UWA 问答社区:answer.uwa4d.com


内存

Q1:我的项目刚升级到Unity 5.6版本,然后在测试的时候出现了很严重的卡顿,我用Profiler真机检测的时候,发现CPU的Others选项耗时很高,但是看了下也没什么粒子消耗,然后Animator的消耗也不高,这是为什么呢?
请输入图片描述

Unity引擎中有10+的模块,而Profiler面板中也就明确显示出6个,Rendering、Scripts、Physics等等,其余模块的耗时都在被统计在Others中,所以Others高其实也是正常的。

在题主的Profiler截图中可以看到,当前帧的CPU耗时为166ms,但面板上的BehaviorUpdate和LateBehaviorUpdate分别为36ms和37ms,这说明还有大量的CPU耗时在面板下方,题主需要往下拉,看看下面都有哪些耗时存在,理论上,这些耗时加起来是需要等于166ms的。

该问题来自UWA问答社区,如您对该问题仍有疑问,可以转至社区进行进一步交流。
https://answer.uwa4d.com/question/5a2f74959d49d2a42cfa3a37


动画

Q2:我项目中的骨骼“Weapon R”的轨迹很奇怪,想请教下UWA。
我是这么操作的,第一步:设置@skin.fbx

请输入图片描述
依次执行Reset -》Enforce T-Pose

第二步:设置动画文件
请输入图片描述
请输入图片描述

第三步:Play。观察骨骼"Weapon R”,从Idle -》 Run会有诡异的曲线。

再重复上述设置,设置@skin.fbx时仅Reset,不执行Enforce T-Pose,我观察到Weapon R就是正常的,我在本帖里提供了例子。

我们从附件的工程来看,因为Weapon R骨骼的存在,如果Enforce T-Pose,会使手部的旋转失真,并且从Idle->Run时会导致humanoid的插值混乱,从而得到错误的手部动画,并因此影响Weapon R。可以使用configuration中Pose->BindPose,这样可以保证可以身体各部位能够正确映射,并且插值时不会出现问题,这边这样测试时没有出现诡异轨迹。另外修改完config后不要忘了动画fbx中update一下。
请输入图片描述

该问题来自UWA问答社区,如您对该问题仍有疑问,可以转至社区进行进一步交流。
https://answer.uwa4d.com/question/5a260564d99fdb2b3c62886e


UI

Q3:我们项目现在用的版本是Unity 4.7,NGUI。我们有几个小的字体图集,本来是部分功能模块特有的,现在很多功能界面交叉引用了。大概是几个256×256和512×256的图集,我想把它们合并成一张1024×1024的大的公用图集。使用会方便一些,但是公用图集已经有2张1024的,加上这个就是3张大的,我想问下NGUI在使用过多1024图集的时候,是不是上传到GPU的时候也会有影响,如果是UGUI也会有这样的问题吗?注:公用图集常驻内存,独立打包。

“上传到GPU”一般只是发生在加载后的,所以如果这几张小图集确实是经常同时被用到的话,合在一个1024图里是合理的做法,对DrawCall的合并也会有明显的好处。 针对小图合并大图造成的影响这个问题,UGUI和NGUI是差不多的,只是UGUI需要通过Sprite Packer查看下是不是确实只合成一张了。

该问题来自UWA问答社区,如您对该问题仍有疑问,可以转至社区进行进一步交流。
https://answer.uwa4d.com/question/5a30ec9080dbcb53066289ea


内存

Q4:Unity 5.4.6f3版本中UGUI的窗口资源无法卸载,如果该窗口没有使用字体,仅仅使用了图集的话是可以被回收的,但是只要UI使用了字体,就会导致无法回收。在Unity 5.6.4f1版本中无此问题。 已在问答社区提交了例子。

这个问题在真机上是不会出现的,已经通过题主的附件进行了验证。
而Editor下会出现的原因,可参考类似的这个问题 。另外补一句,查资源的内存情况,不建议在Editor下进行,一方面是有可能Editor下的逻辑代码和Runtime下会有差别,另一方面在Editor里被编辑过的资源也会被加载进内存,并有可能被缓存住。

该问题来自UWA问答社区,如您对该问题仍有疑问,可以转至社区进行进一步交流。
https://answer.uwa4d.com/question/5a278aee9e3affe04a6aa8cd


加载

Q5:Shader.WarmupAllShaders(); 这个是预编译了所有的Shader么? 我还需要把那些常用的Shader放到一个Prefab上面,然后在游戏启动的时候加载么?

Shader.WarmupAllShaders有两个问题,一个是它只warmup当前时刻的所有Shader,如果后续有新的Shader加载进来,还是会重新解析的,但如果warmup时刻已经能保证绝大部分Shader都已经在内存中,那么使用这个API就足够了;第二是这个API的耗时非常高,因为它会warmup所有的keywords组合,无论你是否在项目中使用到,所以在Unity 5.0以后可以尝试通过shadervariantcollection.warmup来取代。

该问题来自UWA问答社区,如您对该问题仍有疑问,可以转至社区进行进一步交流。
https://answer.uwa4d.com/question/5a3257b8710664857e39b40b


今天的分享就到这里。当然,生有涯而知无涯。在漫漫的开发周期中,您看到的这些问题也许都只是冰山一角,我们早已在UWA问答网站(answer.uwa4d.com)上准备了更多的技术话题等你一起来探索和分享。欢迎热爱进步的你加入,也许你的方法恰能解别人的燃眉之急;而他山之“石”,也能攻你之“玉”。
官网:www.uwa4d.com
官方技术博客:blog.uwa4d.com
官方问答社区:answer.uwa4d.com
官方技术QQ群:465082844(仅限技术交流)