您的位置:首页 > 移动开发 > Unity3D

unity profiler and optimize and compress android Package

2015-07-17 16:00 573 查看


Webplayer

For webplayer profiling, follow these steps:

1. Check
theDevelopment Build checkbox inUnity’s Build Settings
dialog and also open the Profiler window before startingthe build.

2. When
the game is running in the webplayer, make sure thatRelease Channel
is set toDevelopment. Alt+right-click on the web
player toopen the release channel selection menu.

3. SelectOSXWebPlayer(YOURCOMPUTERNAME)
orWindowsWebPlayer(YOURCOMPUTERNAME) as appropriate
from the Profiler Window’s Active Profiler drop-down
menu.

iOS

Remote profiling can be enabled on iOS devices by following these steps:

1. Connect
your iOS device to your WiFi network (local/adhoc WiFi network isused by profiler to send profiling data from device to the Unity Editor).

2. Check
“Autoconnect Profiler” checkbox in Unity’s build settings dialog.

3. Attach
your device to your Mac via cable, check the “Development Build”checkbox in Unity’s build settings dialog, and hit “Build & Run” in Unity Editor.

4. When
app launches on device open profiler window in Unity Editor(Window->Profiler).

If you are using a firewall, you need to make sure that ports 54998 to55511 are open in the firewall’s outbound rules - these are the ports used byUnity
for remote profiling.

Note: Sometimes
Unity Editor might notautoconnect to the device. In such cases profiler connection might be initiatedfrom Profiler WindowActive
Profiler drop down menu byselect appropriate device.

Android

Remote profiling can be enabled on Android devices through two differentpaths : WiFi orADB.

For WiFi profiling, follow these steps:

1. Make
sure to disable Mobile Data on your Android device.

2. Connect
your Android device to your WiFi network.

3. Attach
your device to your Mac/PC via cable, check the “Development Build”and “Autoconnect Profiler” checkboxes in Unity’s build settings dialog, and hit“Build & Run” in Unity Editor.

4. When
the app launches on the device, open the profiler window in UnityEditor (Window->Profiler)

5. If
the Unity Editor fails to autoconnect to the device, select theappropriate device from the Profiler WindowActive Profiler
drop down menu. Note: The Android device
and host computer (running the Unity Editor) must bothbe on the same subnet
for the device detection to work.

For ADB profiling, follow these steps:

Attach your device to your Mac/PC viacable and make sure ADB recognizes the device (i.e. it shows inadb devices
list).

Check the “Development Build” checkboxin Unity’s build settings dialog, and hit “Build & Run”.

When the app launches on the device,open the profiler window in Unity Editor (Window->Profiler)

Select theAndroidProfiler(ADB@127.0.0.1:54999)
from the Profiler WindowActive Profiler drop down
menu.Note: The Unity editor will automaticallycreate an adb tunnel for your application when you press “Build & Run”.
Ifyou want to profile another application or you restart the adb server you haveto setup this tunnel manually. To do this, open a Terminal window / CMD promptand enter:

adb forward tcp:54999localabstract:Unity-{insert bundle identifier here}

Note: The
entry in the drop down menu is onlyvisible when the selected target is Android.

If you are using a firewall, you need tomake sure that ports 54998 to
55511 are open in the firewall’s outbound rules -these are the ports used by Unity for remote profiling.

using UnityEngine;

public class MyScript :MonoBehaviour {

voidUpdate() {

Profiler.BeginSample("MySample");

Debug.Log("Loggingsomehing");

Profiler.EndSample();

}

}

。。AndroidSDK\Androidandroid-sdk\tools\monitor.bat

以下 转自 xiyongjian1001的:
1、cpu stage
A. WaitForTargetFPS:

Vsync(垂直同步)功能所,即显示当前帧的CPU等待时间

B. Overhead:

Profiler总体时间-所有单项的记录时间总和。用于记录尚不明确的时间消耗,以帮助进一步完善Profiler的统计。

C. Physics.Simulate:

当前帧物理模拟的CPU占用时间。

D. Camera.Render:

相机渲染准备工作的CPU占用量

E. RenderTexture.SetActive:

设置RenderTexture操作.

底层实现:1.比对当前帧与前一帧的ColorSurface和DepthSurface.

2.如果这两个Buffer一致则不生成新的RT,否则则生成新的RT,并设置与之相对应的Viewport和空间转换矩阵.

F. Monobehaviour.OnMouse_ :

用于检测鼠标的输入消息接收和反馈,主要包括:SendMouseEvents和DoSendMouseEvents。(只要Edtor开起来,这个就会存在)

G. HandleUtility.SetViewInfo:

仅用于Editor中,作用是将GUI和Editor中的显示看起来与发布版本的显示一致。

H. GUI.Repaint:

GUI的重绘(说明在有使用原生的OnGUI)

I. Event.Internal_MakeMasterEventCurrent:

负责GUI的消息传送

J. Cleanup Unused Cached Data:

清空无用的缓存数据,主要包括RenderBuffer的垃圾回收和TextRendering的垃圾回收。

1.RenderTexture.GarbageCollectTemporary:存在于RenderBuffer的垃圾回收中,清除临时的FreeTexture.

2.TextRendering.Cleanup:TextMesh的垃圾回收操作

K. Application.Integrate Assets in Background:

遍历预加载的线程队列并完成加载,同时,完成纹理的加载、Substance的Update等.

L. Application.LoadLevelAsync Integrate:

加载场景的CPU占用,通常如果此项时间长的话70%的可能是Texture过长导致.

M. UnloadScene:

卸载场景中的GameObjects、Component和GameManager,一般用在切换场景时.

N. CollectGameObjectObjects:

执行上面M项的同时,会将场景中的GameObject和Component聚集到一个Array中.然后执行下面的Destroy.

O. Destroy:

删除GameObject和Component的CPU占用.

P. AssetBundle.LoadAsync Integrate:

多线程加载AwakeQueue中的内容,即多线程执行资源的AwakeFromLoad函数.

Q. Loading.AwakeFromLoad:

在资源被加载后调用,对每种资源进行与其对应用处理.
2. GPU Usage

A. Device.Present:

device.PresentFrame的耗时显示,该选项出现在发布版本中.

B. Graphics.PresentAndSync:

GPU上的显示和垂直同步耗时.该选项出现在发布版本中.

C. Mesh.DrawVBO:

GPU中关于Mesh的Vertex Buffer Object的渲染耗时.

D. Shader.Parse:

资源加入后引擎对Shader的解析过程.

E. Shader.CreateGPUProgram:

根据当前设备支持的图形库来建立GPU工程.
3. Memory Profiler
A. Used Total:

当前帧的Unity内存、Mono内存、GfxDriver内存、Profiler内存的总和.

B. Reserved Total:

系统在当前帧的申请内存.

C. Total System Memory Usage:

当前帧的虚拟内存使用量.(通常是我们当前使用内存的1.5~3倍)

D. GameObjects in Scene:

当前帧场景中的GameObject数量.

E. Total Objects in Scene:

当前帧场景中的Object数量(除GameObject外,还有Component等).

F. Total Object Count:

Object数据 + Asset数量.
4.
Detail Memory Profiler

A. Assets:

Texture2d:记录当前帧内存中所使用的纹理资源情况,包括各种GameObject的纹理、天空盒纹理以及场景中所用的Lightmap资源.

B. Scene Memory:

记录当前场景中各个方面的内存占用情况,包括GameObject、所用资源、各种组件以及GameManager等(天般情况通过AssetBundle加载的不会显示在这里).

A. Other:

ManagedHeap.UseSize:代码在运行时造成的堆内存分配,表示上次GC到目前为止所分配的堆内存量.

SerializedFile(3):

WebStream:这个是由WWW来进行加载的内存占用.

System.ExecutableAndDlls:不同平台和不同硬件得到的值会不一样。
5.
优化重点

A. CPU-GC Allow:

关注原则:1.检测任何一次性内存分配大于2KB的选项 2.检测每帧都具有20B以上内存分配的选项.

B. Time ms:

记录游戏运行时每帧CPU占用(特别注意占用5ms以上的).

C. Memory Profiler-Other:

1.ManagedHeap.UsedSize: 移动游戏建议不要超过20MB.

2.SerializedFile: 通过异步加载(LoadFromCache、WWW等)的时候留下的序列化文件,可监视是否被卸载.

3.WebStream: 通过异步WWW下载的资源文件在内存中的解压版本,比SerializedFile大几倍或几十倍,重点监视.****

D. Memory Profiler-Assets:

1.Texture2D: 重点检查是否有重复资源和超大Memory是否需要压缩等.

2.AnimationClip: 重点检查是否有重复资源.

3.Mesh: 重点检查是否有重复资源.
6.
项目中可能遇到的问题
A.
Device.Present:

1.GPU的presentdevice确实非常耗时,一般出现在使用了非常复杂的shader.

2.GPU运行的非常快,而由于Vsync的原因,使得它需要等待较长的时间.

3.同样是Vsync的原因,但其他线程非常耗时,所以导致该等待时间很长,比如:过量AssetBundle加载时容易出现该问题.

4.Shader.CreateGPUProgram:Shader在runtime阶段(非预加载)会出现卡顿(华为K3V2芯片).

B. StackTraceUtility.PostprocessStacktrace()和StackTraceUtility.ExtractStackTrace():

1.一般是由Debug.Log或类似API造成.

2.游戏发布后需将Debug API进行屏蔽.
C.
Overhead:

1.一般情况为Vsync所致.

2.通常出现在Android设备上.

D. GC.Collect:

原因: 1.代码分配内存过量(恶性的) 2.一定时间间隔由系统调用(良性的).

占用时间:1.与现有Garbage size相关 2.与剩余内存使用颗粒相关(比如场景物件过多,利用率低的情况下,GC释放后需要做内存重排)

E. GarbageCollectAssetsProfile:

1.引擎在执行UnloadUnusedAssets操作(该操作是比较耗时的,建议在切场景的时候进行).

2.尽可能地避免使用Unity内建GUI,避免GUI.Repaint过渡GC Allow.

3.if(other.tag == GearParent.MogoPlayerTag)改为other.CompareTag(GearParent.MogoPlayerTag).因为other.tag为产生180B的GC Allow.

F. 少用foreach,因为每次foreach为产生一个enumerator(约16B的内存分配),尽量改为for.

G. Lambda表达式,使用不当会产生内存泄漏.

H. 尽量少用LINQ:

1.部分功能无法在某些平台使用.

2.会分配大量GC Allow.

I. 控制StartCoroutine的次数:

1.开启一个Coroutine(协程),至少分配37B的内存.

2.Coroutine类的实例 -- 21B.

3.Enumerator -- 16B.

J. 使用StringBuilder替代字符串直接连接.

K. 缓存组件:

1.每次GetComponent均会分配一定的GC Allow.

2.每次Object.name都会分配39B的堆内存.

把Android包大小降下来:

1、 删除无效的、废弃的资源

理由是显然的,无效的、废弃的资源就应该移除项目工程之外。确认是否废弃资源可以通过以下几个方面考量:

Texture:(1)在prefab中搜索texture.png.meta文件的guid,确认是否被引用;(2)在C#代码中搜索文件名,确认是否被动态指定。

图集Atlas:(1)在prefab中搜索atlas.prefab.meta文件的guid,确认是否被引用。

图集Atlas的单个图片:(1)在prefab中搜索图片文件名,确认是否被直接引用;(2)在C#代码中搜索图片完整或局部文件名,确认是否被动态指定。

2、 取消图集Atlas的正方形限制

工程项目中提供了图集制作工具(HDAtlasMaker),默认是生成正方形图集Atlas。然而此举很浪费,因为若限制图集为正方形,很多时候图集大部分区域是空白。事实上应取消正方形限制。

例子(无损):宽*高:2048*2048(16M) => 1024*2048(8M)

适用场合:去掉正方形限制后可缩减一个尺寸的Atlas。

4、 调整Texture初始默认导入设置

Texture的默认导入设置包含Mip Maps。然而Mip Maps是为了物体在视野远近不同而生成不同分辨率的纹理。而UI贴图不需要考虑远近,无需生成小纹理。所以应将Texture导入设置改用Advanced,并取消Generate Mip Maps。

无损:1.3M => 1.0M

适用场合:默认导入设置为Texture的全部UI图片资源。

5、 调整Texture导入设置(Advanced:无Alpha透明通道)

(1) 无损:RGBA 32 Bits(2.3MB) => RGB 24
Bits(1.7MB)

适用场合:无Alpha透明通道的单个图片,如登陆背景、通用背景。

(2) 有损:RGB 24 Bits(1.7MB) => RGB ETC
4Bits(256KB)

此项压缩有损画质,然而压缩效果却很明显。注意ETC需设置资源宽高为2幂次方。实际尺寸非2幂次方时,将以伸缩处理。

适用场合:无Alpha透明通道,且画质要求较低的单个图片,如:结算背景、领奖背景、通用背景、Loading图、3D模型贴图等。

(3) 有损:RGB ETC 4Bits & Max 1024(256KB)
=> RGB ETC 4Bits & Max 512(64KB)

在(2)的基础上,此处设置宽高最大512,当实际尺寸超过512时将拉伸到实际尺寸,会进一步模糊画质。此处512也可根据实际情况选用256、128、64、32等。

适用场合:同(2),无Alpha透明通道,且画质要求更低的单个图片。

6、 调整Texture导入设置(Advanced:有Alpha透明通道)

(1) 有损:RGBA 32 Bits(1.1MB) => RGBA 16
Bits(0.5MB)

适用场合:有Alpha透明通道,且画质要求较低的单个图片。

(2) 有损:RGBA 16 Bits & Max 1024(0.5MB)
=> RGBA 16 Bits & Max 512(360KB)

适用场合:同(2),有Alpha透明通道,且画质要求更低的单个图片。画质在(2)的基础上进一步模糊。

7、 Texture从Atlas分离出来

例子(几乎无损):宽高:512*512(1M) => 256*512(0.5M)+
RGBA 16Bits(50KB)

适用场合:分离出尺寸最大的单个图片后,剩下小图片生成的图集Atlas能缩小一个尺寸。

8、 去掉边缘发光

例子(几乎无损):宽高:640*326(0.8M) => 234*126(115KB)

适用场合:边缘发光去掉后对画质不影响或影响甚微的单个图片。

9、 去掉边缘装饰

例子(几乎无损):宽高:585*141(322KB) => 510*79(157KB)

适用场合:边缘装饰去掉后对画质不影响或影响甚微的单个图片。

10、 整合图集Atlas

例子(几乎无损):两个256*512(0.5M*2) => 一个256*512(0.5M)+若干独立小图

适用场合:图集小图片有交集,所属模块类似,且都有剩余空间,放一起刚刚好。

11、 重新裁切透明边框尺寸(Atlas)

例子(几乎无损):512*512(0.5M) => 512*256(256KB)

适用场合: NGUI Font。由于UI Font不能直接Trim,需处理原始资源,切掉透明边框。

12、 重新裁切透明边框尺寸(Texture)

例子(无损):640*499(0.6M) => 640*450(0.5M)

适用场景:有透明边框的Texture。由于Texture不能直接Trim,需处理原始资源,切掉透明边框。

13、 缩小资源原始尺寸(Atlas)

例子(有损):宽*高:1024*2048(8M) => 1024*1024(4M)

适用场景:图集Atlas空白太多,且图集元素能接受小范围的画质模糊。

将小图片缩小80%,重新制作图集,实际应用UISprite时再通过代码恢复125%回到原始尺寸。

14、 缩小资源原始尺寸(Texture)

例子(有损):宽*高:577*1024(1.7M)vs 480*852(1.2M)vs 288*512(432KB)

适用场景:登陆界面背景原始尺寸640*1136。

若直接导入原尺寸,则资源较大(2.1M)。

若按Max 1024导入也不小(1.7M)。

若按Max 512导入则只需432KB,然而此图为重要门面背景,画质不能忍。又因为导入设置不支持512~1024的中间尺寸,唯有手动缩小原始尺寸到合适尺寸和画质,比如此处中间版本【原图66.6% = 480*852(1.2M)】。

15、 调整策划需求

例子(无损):640*630(1.2M) => 32*32(3KB)

适用场景:特定需求,特定应用场景。

项目中的具体需求是,特定时间区间内显示运营Loading图,其他时间显示默认Loading图。这里可以让运营策划调整该特定时间区间,使之包含整个测试期间,那么默认Loading图就无需显示,其导入尺寸可缩小到最小。此处不直接删除默认Loading图是为了避免逻辑出错,且方便日后恢复。

16、 统一背景资源

例子:背景大图。

背景大图等资源应尽量复用。以下曾经出现过的几个背景图差异微小,经商讨后,最终统一用第三个,删除另外两个。

17、 缩减关键图集Atlas尺寸

例子:Common图集Atlas把ABCS品质独立出来,剩下打包更小尺寸的Atlas。关键图集出现概率很高,此处缩减操作是为内存考虑。

18、 分析构建日志

例子:分析C:\Users\[你的用户名]\AppData\Local\Unity\Editor\Editor.log当中的构建日志部分,查看打包资源列表,发现:

(1)NGUI样例图集被打包进去了。
搜索发现并无被直接引用,而是间接引用。为防止出错不直接删除,而是将Max Size调整到很小。

(2)发现了重复图集。

(3)宠物图集占用5.3MB,而不是4.0MB,经检查发现导入设置有误,生成了Mip
Maps。类似的大图集有好几个,逐一检查处理。

(4)新手引导和头像集合这两个图集很大,进一步将重点优化。

19复用部分背景图

由于视觉效果需求,美术给了相似的两个背景图(1和3),应用在不同场景。为了省资源,项目中实际是通过1+2来拼接出3。

20接入专用shader,实现灰度图标

策划有需求:当一个道具已使用,或一个角色已获得时,显示彩色Icon资源,反之显示灰度的Icon资源。
图标实际是同一份资源(彩色),通过专用shader实现灰度图,能达到节省灰度图标资源。

21有损压缩Atlas图集

个别资源若能接受调色板数量减少,可选用RGBA 16 bit代替RGBA 32 bit。此举对画质有损。一般来说Atlas都选用32位真彩,然而也有个别例外的,要根据实际情况选用。

22美术字改用程序字

由于UI风格变更,原先一些美术字改用程序字来实现,直接节省贴图资源。

23字体统一整合

由于UI风格变更,原先使用了大黑简体和综艺简体两种中文字体,后来风格更新了,综艺简体被整合为大黑简体。

通过批量替换guid,可以快速整合字体。然而由于字体样式有区别,还需要人工逐一调整坐标、字号、阴影等细节。

一、程序方面

  01、务必删除脚本中为空或不需要的默认方法;

  02、只在一个脚本中使用OnGUI方法;

  03、避免在OnGUI中对变量、方法进行更新、赋值,输出变量建议在Update内;

  04、同一脚本中频繁使用的变量建议声明其为全局变量,脚本之间频繁调用的变量或方法建议声明为全局静态变量或方法;

  05、不要去频繁获取组件,将其声明为全局变量;

  06、数组、集合类元素优先使用Array,其次是List;

  07、脚本在不使用时脚本禁用之,需要时再启用;

  08、可以使用Ray来代替OnMouseXXX类方法;

  09、需要隐藏/显示或实例化来回切换的对象,尽量不要使用SetActiveRecursively或active,而使用将对象远远移出相机范围和移回原位的做法;

  10、尽量少用模运算和除法运算,比如a/5f,一定要写成a*0.2f。

  11、对于不经常调用或更改的变量或方法建议使用Coroutines & Yield;

  12、尽量直接声明脚本变量,而不使用GetComponent来获取脚本;

iPhone

  13、尽量使用整数数字,因为iPhone的浮点数计算能力很差;

  14、不要使用原生的GUI方法;

  15、不要实例化(Instantiate)对象,事先建好对象池,并使用Translate“生成”对象;

 

二、模型方面

  01、合并使用同贴图的材质球,合并使用相同材质球的Mesh;

  02、角色的贴图和材质球只要一个,若必须多个则将模型离分离为多个部分;

  02、骨骼系统不要使用太多;

  03、当使用多角色时,将动画单独分离出来;

  04、使用层距离来控制模型的显示距离;

  05、阴影其实包含两方面阴暗和影子,建议使用实时影子时把阴暗效果烘焙出来,不要使用灯光来调节光线阴暗。

  06、少用像素灯和使用像素灯的Shader;

  08、如果硬阴影可以解决问题就不要用软阴影,并且使用不影响效果的低分辨率阴影;

  08、实时阴影很耗性能,尽量减小产生阴影的距离;

  09、允许的话在大场景中使用线性雾,这样可以使远距离对象或阴影不易察觉,因此可以通过减小相机和阴影距离来提高性能;

  10、使用圆滑组来尽量减少模型的面数;

  11、项目中如果没有灯光或对象在移动那么就不要使用实时灯光;

  12、水面、镜子等实时反射/折射的效果单独放在Water图层中,并且根据其实时反射/折射的范围来调整;

  13、碰撞对效率的影响很小,但碰撞还是建议使用Box、Sphere碰撞体;

  14、建材质球时尽量考虑使用Substance;

  15、尽量将所有的实时反射/折射(如水面、镜子、地板等等)都集合成一个面;

  16、假反射/折射没有必要使用过大分辨率,一般64*64就可以,不建议超过256*256;

  17、需要更改的材质球,建议实例化一个,而不是使用公共的材质球;

  18、将不须射线或碰撞事件的对象置于IgnoreRaycast图层;

  19、将水面或类似效果置于Water图层

  20、将透明通道的对象置于TransparentFX图层;

  21、养成良好的标签(Tags)、层次(Hieratchy)和图层(Layer)的条理化习惯,将不同的对象置于不同的标签或图层,三者有效的结合将很方便的按名称、类别和属性来查找;

  22、通过Stats和Profile查看对效率影响最大的方面或对象,或者使用禁用部分模型的方式查看问题到底在哪儿;

  23、使用遮挡剔除(Occlusion Culling)处理大场景,一种较原生的类LOD技术,并且能够“分割”作为整体的一个模型。

三、其它

  场景中如果没有使用灯光和像素灯,就不要使用法线贴图,因为法线效果只有在有光源(Direct Light/Point Light/Angle Light/Pixel Light)的情况下才有效果。
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: