加载中...
unity性能优化心得
发表于:2024-04-06 | 分类: Learn

为什么需要性能优化?

性能优化的本质 : 慢与快的问题

性能优化流程

发现问题(什么平台,操作系统,情况,一般还是特殊)
定位身体(什么地方造成的?需要工具 Or 方法?)
研究问题(处理方案?性能优化前提条件?)
解决问题

影响性能的cpu,gpu,带宽,内存

优化思路:

空间换时间等

拼ui
取消勾选uiimage的射线检测

资源的设置和检查

AssetChecker工具使用

生成资源检测报告,根据检测报告去进行具体优化

静态资源优化

AudioSource
  1. 立体声道(ForceTOMono)
  2. 加载模式
  3. 平台对应压缩格式

优化后 :
apk大小从560下将到544
audio 包体 76下降了70
cpu占有 从2.5上升到了5%
是因为部分audio 使用stream模式加载

模型

  1. 优化原始导入模型文件
    统一单位
    模型中的 多余文件(摄像机 ,灯光,材质)
    模型中纹理(不建议纹理随模型导出)

  2. Animationtype 设置
    骨骼对应设置
    model 的read/Write

优化后 :仅只有scene 场景内存从400降低到377.4

纹理

  1. 纹理的导入
    纹理类型的设置
    平台对应压缩格式
    加载模式
    纹理贴图大小(2的倍数)
    alpha is Transparency(半透明,增加内存,alpha占1字节)
    read/Write
    纹理过滤 2.纹理图集
    优点:静态合批 减少drawcall
    减少碎纹理,通过压缩图集可以降低纹理内存和冗余
    缺点:
    美术需要合理规划,制作修改成本高 3.mipmap
    逐级降低分辨率保存纹理副本,生成纹理Lod,根据像素在屏幕中占用纹理空间来选择mipmap级别进行采样
    优点:
    提高纹理采样性能gpu不需要远距离对对象进行纹理采样
    纹理渲染质量:远距离下过采样导致的噪点问题
    缺点:
    造成额外的内存开销:mipmap纹理需要生成低分辨率副本
    实际上
  2. 纹理图集利用率偏低,浪费内存
  3. 不合理的半透明纹理
  4. 不打图集的序列帧动画
  5. 大量重复纹理
  6. 内容相似贴图只是颜色信息变化
  7. 大量颜色渐变贴图不压缩,也不采用单像素宽度
    优化后 :
    apk 大小从544.6 变化到402.9
    整体运行内存从1.36G 变化到1.21g
    graphic& graphic Dirver 从0.98g 变化到0.77g
    Texture 个数404 减少到359
    内存从670 减少到 511.9

动画

优化查看原则:

看效果差异(与原始动画是否明显)
曲线数量(总曲线数量与各种曲线数量,常量曲线比重 大更好)
动画文件大小(通常都在1m以内 超过1m需要排查)

注意事项

1.Animationtype 设置
通用比人性节省30% cpu
2.动画压缩格式

unity资源

unity资源导入工作流

ToTd:暂时未理解
1.presets
2.AssetGraph
3.自己写工具

unity资源创建注意

1.减少空节点
2.嵌套预制体

性能优化

渲染优化

TODO: 暂时没有实际做过

  1. rameDebugger与XCode的GPU Frame Capture工具的使用
  2. SSao优化
    TODD: 暂时未理解
  3. AA 渲染
  4. 后处理优化

渲染剔除

看不见的像素,网格,对象

unity 中的剔除:
像素剔除:摄像机平截头体剔除、Back-face Culling、EarlyZ、Pre-Z Pass
网格剔除:Layer Mask、可见距离剔除、Occlusion
灯光剔除:Tile-Based Deferred Rendering、Forward+
场景剔除:Additive Scene

用户扩展剔除:
场景数据结构:Octree、BSP Tree、Portal、Voxelization、SDF等
GPU Culling: Hi-Z Pass、 Temporal Reprojection CullingCluster、Tile-based Visible Buffer等

简化方案

Unity下的简化:
Quality Settings
通过烘焙光照简化实时光照
通过BoundingBox或替代体碰撞代替Mesh碰撞
通过Local Volume代替Global Volume
RayCast代替SphereCast、CapsuleCast等
纹理文字代替系统文字
Mesh LoD
Shader LoD
HLOD
通过Camer Override代替URP管线中的一些通用设置
各种OnDemand更新或分级设置接口

用户扩展简化:
场景简化数据结构
第三方LOD方案
Mesh Impostor
Animation LOD
骨骼LOD
2D寻路代替Navigation Mesh
扩展类似OnDemand接口

batching

哪些内容需要Batching

广义上讲:
资源Batching(Mesh、Texture、Shader参数、材质属性)
Draw call Batching (Static Batching、Dynamic Batching)
GPU Instancing(直接渲染、间接渲染、程序化间接渲染 )
Set Pass call Batching.( SRp Batching)

资源的Batching

Mesh:
Mesh.CombineMesh,合并静态网格对象
Submeshes->Single Mesh,合并材质与贴图,不同材质通过通道图标记
Texture:
AtlasTexture,通过纹理坐标映射多张贴图
TextureArray纹理数组
Shader变量与材质属性
Material Property Block(Build In管线)
Const buffer(SRP管线)

Draw caBatching:

Static Batching

StaticBatchingUtility.Combine

Static Batching限制

额外内存开销
64000个顶点限制
影响Culling剔除

Dynamic Batching限制

合批不超过900个顶点属性,(注意不是900个顶点)
除了渲染阴影对象外,相同材质,不同材质实例也不能合并
具有光照贴图的游戏对象如果有附加渲染器参数时,如果需要动态合批这些对象他们必须指向相同的光照贴图位置。
有多Shader Pass的游戏对象无法做动态合批
受多个光照影响的游戏对象,满足动态合批条件合批后,只会受一个光源的影响
延迟渲染下不支持动态合批
 CPU开销可能会增大,需要测试开启使用

Gpuinstancing:

DrawMeshInstanced
DrawMeshInstancedIndirect
DrawMeshInstancedProcedural

Batching优化顺序

资源Batching >SRP Batching =Static Batching >GPU
Instancing>Dynamic Batching

Batching失败原因

内存优化

托管内存优化

Boxing Allocation装箱操作

String字符串拼接
闭包分配
避免使用Linq库

Unity中提供了NonAloc函数

如Physics.RayCastAl用Physics.RayCastAlINonAlloc代替
Unity.Object.FindobjectsOfType,
UnityEngine.Component.GetComponentsInParent,
UnityEngine.Component.GetComponentsinChild 等
成员变量访问方式
UnityEngine.Mesh.vertices=>UnityEngine.Mesh.GetVertices,
UnityEngine.Mesh.uv=> UnityEngine.Mesh.GetUV
UnityEngine.Renderer.sharedMaterials=> UnityEngine.Renderer.GetSharedMaterials
Unity.Input.touches=> Unity.Input.GeTouches等

引用文献

Unity性能优化

上一篇:
Rider编译器破解
下一篇:
unity性能优化心得
本文目录
本文目录