技术分享连载(七十九)

技术分享连载(七十九)

本期聚集话题:如何利用相机的拾取功能获取多个物体、Mono堆内存莫名下降、Unity与Android视图融合、Unity 4.x和5.x的音频格式差异...


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

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


制作

Q1:如果场景中有大量物体,请问如何利用相机拾取获取不同范围内的物体?

题主可以采用Physics.SphereCastAll函数来获取,类似下面这个场景:
请输入图片描述
在SphereCastAll这个API的参数中,第二radius可以控制获取半径,我们分别设置5和10的效果是这样的:
radius=5:
请输入图片描述

radius=10:
请输入图片描述

该问题来自UWA问答社区,感谢Andrew提供了回答,如您对该问题仍有疑问,可以转至社区进行进一步交流。
https://answer.uwa4d.com/question/59b60249167ed31465945c2d


内存管理

Q2:将一个Unity 4.7.2的项目升级到Unity 5.5.3。打成安卓包,发现APK文件比之前大了200MB。然后分别对4.7.2打出来的APK包和5.5.3打出来的包分别进行解包,发现音频文件个数一样,但所占大小多了200MB左右,平均每个文件都大了几百KB。Unity 4.7.2的解包为Mp3格式,Unity 5.5.3的解包为Wav格式。

于是我在Unity 4.7.2和Unity 5.5.3下,分别新建一个空工程,将单独一个音频文件(ogg格式)放入Resources文件下,即两个Unity版本的空工程里只有一个Resources文件夹,文件夹里只有一个相同的Ogg格式音频文件,打成安卓包。使用解包工具解包,发现Unity 4.7.2的音频文件转成了mp3格式,大小几十kb;Unity 5.5.3的音频文件转成Wav格式,大小200多KB。

请问这种问题怎么解决?针对音频,Unity 4.x和Unity 5.x在打包过程中,作了那些修改?

引用Unity 5.0的release note:https://unity3d.com/unity/whats-new/unity-5.0

“Rewritten Audio asset pipeline and AudioClip backend.”"Much improved audio formats in terms of memory and CPU usage.** The Format property no longer refers to a specific platform-specific file format, but to a encoding method** (Uncompressed, Compressed, ADPCM)."

可以看到,在Unity 5.x中,不同平台的音频不再与特定的文件格式关联,而是与文件编码关联。文件格式不等同于音频编码,虽然同是Wav格式的文件,但其有不同的编码方法(PCM,ADPCM,Vorbis,Wav也可以用mp3编码),编码方法会影响到Apk的大小。
请输入图片描述
选定编码方式后降低quality和sample rate也会降低apk大小。

该问题来自UWA 社区,感谢Saber提供了回答,如您对该问题仍有疑问,可以转至社区进行进一步交流。
https://answer.uwa4d.com/question/59b76e7ac66541837c1fd911


制作

Q3:如下图,蓝色部分为Unity视图,绿色为Android图片,我现在需要把Unity蓝色区域透视或者去除,iOS上已经透视成功,但Android一直失败,Unity版本为5.5.2,大家有什么建议呢?
请输入图片描述

我在安卓平台上实现了下,基本思路是:
1)使用TextureView代替SurfaceView;
2)TextureView需要setOpaque(false)来透明;
3)Camera的Clear Flags需要使用Solid Color,Background 为 #00000000 必须是黑色,不然和安卓视图颜色混合有问题;
4)由于Unity在安卓上额外做了一步操作,会把Alpha强制改成1后输出,这里需要改libunity.so的二进制文件来临时绕过,后面Unity2017.2可选了,详见https://forum.unity3d.com/threads/big-performance-issue-with-unity5-on-android.338847

Demo工程放在Github上:https://github.com/littlesome/UnityTransparent

该问题来自UWA问答社区,感谢 littlesome提供了回答,如您对该问题仍有疑问,可以转至社区进行进一步交流。
https://answer.uwa4d.com/question/59a92dcaaa04563e0d0d7bd8


制作

Q4:scrollPosition = GUILayout.BeginScrollView(scrollPosition, false, true); 这个函数创建之后一直尝试更改对应的滑动条宽度均告失败,请问如何更改呢?
请输入图片描述

我写了个简单的例子:

GUIStyle gs = GUI.skin.verticalScrollbar;
GUIStyle gs1 = GUI.skin.verticalScrollbarThumb;
        
gs.fixedWidth = 30;
gs1.fixedWidth = 30;
......
pos = GUILayout.BeginScrollView(pos);
......
GUILayout.EndScrollView();
......
gs.fixedWidth = 0;
gs1.fixedWidth = 0;

请输入图片描述

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


内存管理

Q5:我在Editor下测试, 前一帧Mono还是67.2MB,下一帧突然自己掉到了51.5MB。然而并没有gc.collect()调用,这Mono是为什么减少?因为有不明原因的减少,所以担心也有不明原因的增多。
请输入图片描述
请输入图片描述

如果题主是在Editor测的,这个Mono的回落就正常了。Editor本身(渲染窗口,处理交互事件等)就会造成内存分配,同时也会触发GC。

但默认情况下,Editor本身的开销在Profiler里是看不到的,除非题主点击一下“Profile Editor”。 点击之后,就可以看到Editor本身函数的耗时和GC的触发了。例如下图:
请输入图片描述

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


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