unity-记录
关于 unity 项目相关优化经验的墨迹
前篇
插件
- Unity Asset Store上优质好用的47款插件——Unity开发者必备工具(适合收藏) - https://zhuanlan.zhihu.com/p/62471100
- Unity插件素材精选 - https://zhuanlan.zhihu.com/c_1101849362937880576
其他
版本更新计划
- Unity全新的版本发布计划(2018) - https://blog.csdn.net/dengshunhao/article/details/80578285
- 长期支持版 - https://unity.cn/releases/lts
- Long Term Support - https://unity3d.com/unity/qa/lts-releases
Unity TECH版本每年将有三次主要更新,它们会带来最新的功能与特性。
Unity LTS版本将从TECH版本每年最后一个版本开始,持续支持二年的时间。
全新版本的发布方式
首个Unity LTS版本将是Unity 2017.4,也就是Unity 2017.3最新更新版本。版本号的改变标志着新的LTS周期的开始。所以xxxx.1、xxxx.2和xxxx.3都是TECH版本,而xxxx.4则是LTS版。
版本新功能
- Unity 2019
- Unity 2019 中的新功能 - https://docs.unity3d.com/cn/2019.4/Manual/WhatsNew2019.html
Unity 2020
Unity 2020 LTS 中的新功能 - https://docs.unity3d.com/cn/2020.3/Manual/WhatsNew2020LTS.html
Unity 2019 LTS 与 2020 LTS 比较 - https://networm.me/2021/04/04/unity-2019lts-vs-2020lts/
达哥深入解读,Unity 2020.1 不容错过的新功能 - https://zhuanlan.zhihu.com/p/168377106
- Unity 2021
- a
内置包
内置包允许用户通过 Package Manager 启用或禁用 Unity 功能。启用或禁用某个包会减小运行时构建大小。例如,大多数项目不使用旧版粒子系统。
删除此功能的内置包时,Unity 不会在您构建最终应用程序时包含相关的代码和资源。通常,这些内置包中仅包含包清单,并与 Unity 捆绑在一起(而不是在包注册表中提供)。
Editor 日志路径
- win
- 查找闪退日志,在目录 C:\Users\yangxuan\AppData\Local\Unity\Editor 下 Editor.log 文件中可以查看 Debug.Log 日志
- 或者 C:\Users\wilker\AppData\Local\Temp\Unity\Editor\Crashes 目录下
- mac
~/Library/Logs/Unity/Editor.log
打包环境配置
android
直接解压 nas 上的 android sdk, ndk, java , 然后配置进去即可.
另外 java 需要添加环境变量中 ( JAVA_HOME )
编译宏
常用的几个宏
UNITY_STANDALONE : 计算机平台运行包体, 如: Mac OS X, Windows or Linux.
- 细分: UNITY_STANDALONE_OSX, UNITY_STANDALONE_WIN, UNITY_STANDALONE_LINUX
UNITY_EDITOR : 计算机平台编辑器模式
- 细分: UNITY_EDITOR_OSX, UNITY_EDITOR_WIN, UNITY_EDITOR_LINUX
UNITY_IOS : ios 平台 (UNITY_IPHONE 已废弃)
UNITY_ANDROID : android 平台
AssetBundle 打包踩坑
打包闪退
可能是包含了导入 fbx 文件时, 导入了 里面的贴图, 及生产了一个材质球 导致的. 干掉这两个目录就ok了
同一个 ab 下, 有两个 文件名 相同的资源.
如果 ab 有生成 manifest 文件, 查看一下里面的资源是否有跨目录同名
闪退日志里会有资源冲突的信息, 关键字
Conflict happened between Asset
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132Building AssetBundle failed because hash collision was detected in the deterministic id generation.
Conflict happened between Asset "Assets/Res/UI/Atlas/gg_review_1928/bg_flicker_05.png" and "Assets/Res/UI/Atlas/gg_review_1928/cards/bg_flicker_05.png".
UnityEditor.BuildPipeline:BuildAssetBundlesWithInfoInternal(String, AssetBundleBuild[], BuildAssetBundleOptions, BuildTargetGroup, BuildTarget)
UnityEditor.BuildPipeline:BuildAssetBundles(String, AssetBundleBuild[], BuildAssetBundleOptions, BuildTargetGroup, BuildTarget) (at C:\buildslave\unity\build\Editor\Mono\BuildPipeline.bindings.cs:471)
UnityEditor.BuildPipeline:BuildAssetBundles(String, AssetBundleBuild[], BuildAssetBundleOptions, BuildTarget) (at C:\buildslave\unity\build\Editor\Mono\BuildPipeline.bindings.cs:457)
PackAssetBundle:BuildArtAB(BuildTarget, String) (at Assets\Code\Editor\EditorShare\Package\PackAssetBundle.cs:272)
---
#### 文件打包成 ab
unity 的 ab 打包文件, 文件名必须以 unit支持的格式 结尾, 才可以打成 ab 中的*TextAssets* .
unity 支持的格式为: `.txt, .html, .htm, .xml, .bytes, .json, .csv, .yaml, .fnt`
比如: aaa.lua, 要修改为 *aaa.bytes* 或 *aaa.lua.bytes* 才能打成 ab.
参考:
- https://www.cnblogs.com/123ing/p/3812188.html
- https://blog.csdn.net/sibaison/article/details/71249363
---
#### 系统找不到指定的文件

**出现原因**:
1. 使用Unity 打包bundle时出现弹框报错,一开始以为是沙盒的问题,后面排查发现是bundle中出现同名文件(条件是:文件名一样,放在不同目录下,打包到同一个Bundle)。
**解决方法**:根据原因规避。
2. prefab 引用的 prefab 丢失, 也会造成这个错误.
参考: https://blog.csdn.net/Xymazpq/article/details/90032563
---
### 踩坑记录
- 报错 ` The requested operation caused a stack overflow`
> 可能有递归调用 死循环
- 修改材质球不生效??
> 没有 ctrl + s 保存. 修改材质球后需要 保存 才能写入 .mat 文件中
- Unity 安装 Support-for-Editor 时出现 failed to local unity.exe
> 在Unity中补充安装Support-for-Editor时会出现failed to local unity.exe错误,为找不到本地的unity启动程序,安装对路径的要求十分严格,要安装选择在对应版本的Editor目录的上一级目录进行安装。
>
> 参考: https://blog.csdn.net/lz0044/article/details/79574055
- 切场景报错: `Some objects were not cleaned up when closing the scene`
> 是因为在切场景的时候 实例化go.
- ios 打包后, 程序运行闪退, xcode报错: `unity [xxx] was compiled with optimization - stepping may behave oddly variables may not be available`
> - 如果是 *Run in Xcode as设置为Debug* , 这需要在 ios 平台下 *Other Settings* 中的 *Strip Engine Code* 取消勾选, 默认是勾选上的
> - 如果是 *Run in Xcode as设置为Release , 未出现问题
>
> 参考: https://www.jianshu.com/p/26fd847f980e
---
### UnityEditor.AsyncHTTPClient:Done(State, Int32)
- Edit -> Preferences -> Show Asset Store Search hit 取消勾选
---
### projectsettings asset 是二进制问题
- 改为明文的text, *Edit -> Project Settings -> Editor* , *Asset Serialization* 的 *Mode* 改为 *Force Text*
---
### 打包使用图集
- *Edit -> Project Settings -> Editor* , *Sprite Packer* 的 *Mode* 改为 *Always Enabled*
2017之后的有新的一个选线, 不过貌似没什么乱用, 参考: [Unity2017的新版图集 & 自带图集实现TP的Polygon布局](https://zhuanlan.zhihu.com/p/32591450), 选 *always enabled(legacy sprite packer)*

实测选项 *always enabled* 打出的包会比 *always enabled(legacy sprite packer)* 大, 所以还是使用以前的好 ( *always enabled(legacy sprite packer)* )
查看图集 *window -> 2d -> sprite packer*

---
### 打包首场景
- 启动游戏的第一个场景,必须在 *Resources* 中,且必是第一个

### UI 局部坐标 转 全局坐标
```csharp
Vector3 wp = Camera.main.WorldToScreenPoint(transform.position);
RectTransform rect = GetComponent<RectTransform>();
Vector2 tempWorldPos;
RectTransformUtility.ScreenPointToLocalPointInRectangle(rect, wp, Camera.main, out tempWorldPos);
Debug.LogFormat("--- tempWorldPos, x:{0}, y:{1}", tempWorldPos.x, tempWorldPos);
RenderTexture 不渲染部分场景物体
- 默认的 Color Format 是 ARGB32, 改成 ARGB Half 就没问题了. 有待探究.
断言 Assert
如果需要断言中断执行,需要 Assert.raiseExceptions = true;
参考链接: https://blog.csdn.net/u010019717/article/details/50375226
vscode没有代码提示解决
可能的原因
- 刚check来的工程, 没有生产 解决方文件 ( xxx.sln, xxx.csproj) , 所以随便打双击项目内的 cs 文件让 vs (注意不是vscode) 打开, 生产这些解决方案. 然后再把 外部编辑器 切回 vscode.
- 没有对应的 .dotnet 版本, vscode 的 OmniSharp 插件 报错:
The reference assemblies for framework ".NETFramework,Version=v4.7.1" were not found
. 下载对应版本的 .NETFramework 安装即可
解决完就能找到符号了
asset bundle 资源查看器
- 官方支持的资源引用查看器 及 ab 查看器 (看不到里面的资源) - https://github.com/Unity-Technologies/AssetBundles-Browser
- 可以查看到 ab资源的查看器 - https://www.jianshu.com/p/d396d3ca1ebd
ios 平台的 team id 设置
构建xcode工程自动配置好签名, 需要设置 ios 平台设置的 Ohter Settings 中的 Signing Team ID
这个字段的配置来自于 ios 证书上的信息. 在 mac 中打开 Keychains, 在 login -> Certificates 中找到打包ios的证书, 右键 GetInfo , Organizational Unit 字段就是需要的 Team ID, 复制粘贴到unity中.
然后构建 xcode 工程就能看到自动签名了
清除控制台日志
1 | public static void ClearConsole() { |
float与double精度
参考: https://www.cnblogs.com/BradMiller/archive/2010/11/25/1887945.html
float和double的精度是由尾数的位数来决定的。浮点数在内存中是按科学计数法来存储的,其整数部分始终是一个隐含着的“1”,由于它是不变的,故不能对精度造成影响。
float:2^23 = 8388608,一共七位,这意味着最多能有7位有效数字,但绝对能保证的为6位,也即float的精度为67位有效数字;16位。
double:2^52 = 4503599627370496,一共16位,同理,double的精度为15
unity 与 3dmax 顶点不一致
- 为什么Unity中的顶点数比Max中的多? - https://zhuanlan.zhihu.com/p/35418837
主要是在 max 中建模时, 可以将相交面设置为相同的平滑组, 这样相交点的法线就是相交面的 均值.
如果设置为不同的平滑组, 则相交面的 相交点的地方可以就有几个顶点, 各自有用所在面的法相, 看起来就会有 硬边
顶点越多, 就越耗gpu计算性能, 毕竟每个顶点都要经过 顶点着色器
什么是平滑组? 参考 3dsmax记录 的笔记 - 平滑组
平滑组相同. 6个顶点. 无硬边
平滑组不同. 8个顶点. 有硬边.
一个Quad四边形mesh的 顶点 排布
所以调uv值是也应该按这个顺序调整 (纹理坐标是笛卡尔坐标系第一象限)
1 | newUvs[index * 4 + 0] = offset; // lb |
组件脚本勾选框
只要脚本中有 Start()
方法, 就可以显示除勾选框
枚举 转成 字符串数组
1 | public enum BlendMode |
C# Dictionary 实现原理
- 浅析C# Dictionary实现原理 - http://www.sohu.com/a/292197925_120050810
和 c++11 中的 hashmap 差不多. 都是先通过 哈希函数 算出一个 哈希值, 对 bucket 数量求余 得到一个 索引值, 直接索引 bucket数组. 在哈希冲突的情况下, 在再通过 一个判定条件判断是否相等, 在桶存储的一个头指针往单链表逐个遍历判定是否相等.
Dictionary 的存储结构是 数组+单链表. 所以时间复杂度是 O(1), 最坏的情况是 O(n)
定点数 和 浮点数
- 定点数和浮点数 - https://www.jianshu.com/p/43830cdcca30
timeline
- 参考
- TimeLine系列教程——编排剧情! - https://zhuanlan.zhihu.com/p/29188275
修改动画参数
如果修改为循环参数,需要用 clipAnimations 判断是否 > 0,然后在重新复制新的 clipAnimations
1 | public static bool CharActionLoop(ModelImporter importer, string path) { |
应用设置
代码修改后的 apply, AssetDatabase.ImportAsset
1 | public static void CharActionLoop(string path) { |
OnCollision,OnTrigger失效原因
OnCollision:
双方必须要有Collider
其中一方必须要有刚体
有刚体的一方不能勾选Is Trigger
PS:此情况下会有刚体的物体碰撞效果,而且无法在没有刚体物理碰撞效果下触发该函数
OnTrigger:
双方必须要有Collider
其中一方勾选Is Trigger
其中一方必须要有刚体
PS:在带刚体的物体下的Colloder中勾选Is Trigger后刚体的物理碰撞效果会失效
参考: https://blog.csdn.net/qq_34818497/article/details/78184790
碰撞后刚体自动旋转, 位置偏移
要防止 刚体 碰撞后物体发生 自动旋转 或 位置偏移, 就要约束 旋转 和 位置, 这里打上勾
碰撞后不断触发 trigger的问题
被碰撞物体B, 包含 碰撞 组件, 里面的 * OnTriggerEnter,OnTriggerExit* 不断被触发.
主动碰撞物体A, 包含 碰撞,刚体 组件
实测得出有两种解决方式
靠谱. 将 主动碰撞物体A 中的 Sphere Collider 勾上 Is Trigger
不靠谱, 耗性能. 将 主动碰撞物体A 中的 Rigidbody 的 Collision Detection 设为 Continuous. 官方文档中有指出这个是为了快速移动的物体使用的. 防止在一帧之内直接穿越碰撞框. 比较消耗性能.
参考: https://docs.unity3d.com/ScriptReference/Rigidbody-collisionDetectionMode.html
These two options have a big impact on physics performance
创建资源到场景(引用)
效果和拖进去的一致
1 | string path = "Assets/res/Prefabs/building/b_leifengta/b_leifengta.prefab"; |
判断物体是否在视锥体内
1 | bool IsCanCulling(Transform tran) |
GUP Instance
- U3D优化批处理-GPU Instancing了解一下 - https://zhuanlan.zhihu.com/p/34499251
- Unity中基于Gpu Instance进行大量物体渲染的实现与分析(一) - https://blog.csdn.net/leonwei/article/details/73274808
聚焦与场景对象
1 | Selection.activeGameObject = rootGo; |
将自定义类对象显示在Unity的Inspector面板上
1 | [// 加上这个属性即可 ] |
参考: https://blog.csdn.net/LIQIANGEASTSUN/article/details/42101989
选中 go 线框显示
修改 线框 颜色: edit -> preferences -> colors -> wire frame selected
面部表情
- 使用3dmax Morpher制作Unity表情动画 - https://blog.csdn.net/hello_crayon/article/details/80430453
修改贴图打包最大值
这样可以不用重新用ps导图, 就能打出比较小的 assetbundle
1 | if (importer.maxTextureSize != 256) { |
去除顶点色
灰度图 与 rbg图 的大小
pc项目上看貌似 灰度图小很多 ( rgb图的 1/3).
实际上 (多平台) 打出的 ab包 都差不多, 所以不太在意 黑白图 是否用 灰度图 还是 rgb图. 直接 rgb 就行了.
且对应所占的内存也是一样
Frame Debugger 使用
- Unity 5.X 编辑器新功能简介-Frame Debugger - http://gad.qq.com/article/detail/18476
iOS平台下RGBA PVRTC4打包图集失真非常严重
Unity 5.5.1版本下,Sprite Packer在iOS平台下RGBA PVRTC4打包图集失真非常严重(对单个的Sprite设置PVRTC4是正常的),参照了4.6.7版本是正常的,我想知道为什么呢?
unity的bug, 在 Windows 下尝试用 4.7 的 pvrtextool.exe 替换了 5.x 的,暂时解决了这个问题,建议也尝试一下。
图形渲染及优化—Unity合批技术实践
资源查看器 AssetStudio
- AssetStudio is a tool for exploring, extracting and exporting assets and assetbundles.
- github仓库地址 - https://github.com/Perfare/AssetStudio
变换局部坐标到世界坐标
1 | Vector3 globalPos = transform.TransformPoint(boxCld.center); |
animation 中替换材质球
unity支持在 animation 中替换材质球, k上关键帧后直接赋予新材质就即可.
unity2018 shader graph
参考
编辑器点击 play 的回调
可以用于 点击 play 时清除控制台 log
1 | [ ] |
视频录制使用插件
AVPro Movie Capture : 视频录制
录制视频时, 选择 离线渲染 方式 才能无卡顿, 实时渲染 可能会卡顿
开启抗锯齿
使用压缩, 不然很大
下载插件位置
- windows : C:\Users\AppData\Roaming\Unity\Asset Store
- Mac OS X : ~/Library/Unity/Asset Store
安装unity支持包
例如安装 xxx-Support-for-Editor-2018.2.exe, 报错:
failed to local unity.exe
安装是所选目录必须是对unity对应版本的根目录, 如 C:\my_install\unity2018.2.8f1 , 否则安装失败
第三方插件 相关
tolua 相关
关于 byte[]
让 csharp 中的 byte[]
压入 lua 中成为 lua string
(lua pb 反序列化使用) 而不是数组 userdata
, 可以有两种姿势
自己封装的数据结构中有
byte[]
属性, 然后加上一个LuaByteBufferAttribute
. 官方的LuaByteBuffer
中有说明1
2
3
4
5
6
7
8
9
10
11// csharp
public class CNetRes {
[ ]
public byte[] buff = null;
// LuaByteBuffer buff = null; 不能讲 LuaByteBuffer 作为数据结构的成员, 否则会报 空指针调用 的错误
}
// lua
local netRes = getNetRes()
local res = PB.PayloadData()
res:ParseFromString(netRes.buff)在回调 lua 方法时,
new LuaByteBuffer(bytes)
传给lua1
2
3
4
5
6
7
8// csharp
mOnMsgFn.Call(new LuaByteBuffer(bytes));
// lua
local function OnDecode(luaBuffer)
local res = PB.PayloadData()
res:ParseFromString(luaBuffer)
end
besthttp 相关
回包时粘包
如: 上行 a, b 两个包, 下行时 a,b 包的返回值粘在一起, 在一个响应里回来, 那么, 另一个响应里就会出现, data 长度为 0 的情况.
踩坑
android 平台打包报错
1
Found plugins with same names and architectures, Assets/Plugins/x86/tolua.dll (ARMv7) and Assets/Plugins/x86_64/tolua.dll (ARMv7). Assign different architectures or delete the duplicate.
修改这两个 tolua.dll 的设置, 两个都 排除掉 android 平台, 然后 Apply 即可
ios 平台打包报错, 和上面一样的错. 勾选上 IOS, 然后 Apply 即可
摄像机
场景中一定要有一个 透视摄像机 并且 clear flags 是 skybox 或者是 solid color. 不然会出现类似 残影 效果.
踩坑
做ar项目时, 在 ar 场景中为了时 ar相机 和 普通相机同时渲染, 叠加上去. 将 普通相机(dont destroy)设置 clear flags 为 depth only. 切回 普通场景时, 只有一个普通相机, 所以出现了餐饮.
解决办法: 一个 全局普通相机a(dont destroy), clear flags 为 solid color , ar 模式下, ar 场景使用 ar相机 和 普通相机b (clear flags 为 solid color), 此时 相加a active 为 false.
资源加载 Resources.Load
关于这个api的调用, 资源是存放在 Resources 目录之下的, 但是 Resources 可以在任何文件夹下, 比如
1 | if (combineMaterial == null) combineMaterial = new Material(Resources.Load<Shader>("SSR/Combine")); |
这时候命名就比较重要了, 不然不同 Resources 目录下的资源容易冲突, 加载时错误
此规则同样适用于 Editor 目录下, 这样打包时如果只是编辑器工具相关的话就不会打包进去.
资源内存管理
- Unity 3D中的内存管理 - https://blog.csdn.net/zhaoguanghui2012/article/details/71940778
特效 与 ui 绘制顺序问题
要修改 特效 绘制在 ui之上,只要确保 特效的 renderer.sortingOrder 大于 ui 所在 的canvas 的 Sorting Layer
参考辅助脚本 UIdepth.cs
1 | ParticleSystem[] particles = GetComponentsInChildren<ParticleSystem>(); |
RawImage 在没有 RenderTexture 的时候,会出现黑块(Android)
先隐藏 rawimage ,rt加载完在让它显示出来,rt附上去
使用遮罩shader,没有效果
如果需要使用 透明度做遮罩 的 shader,被处理图 不能打图集,因为 uv 映射的是 被处理图 所在的图集
unity 自动打出的图集拉伸边沿
切单图没有预留几个 透明像素点导致的,需要预留一两个像素点
ios uv流动长时间后卡顿
使用了错误的uv流动方式,并且错误的去修改 偏移值
错误的做法
1 | void Update () { |
真确做法
start 中缓存好 material ,而不是 update 中去 get material
切场景后灯光丢
场景的 灯光 不要放在 prefab 中打灯,这样灯光信息是放在 prefab 上,只要 break prefab 就会造成灯光丢失,场景里面的东西就不要弄预制了吧
android,UIInput拉起输入法字都是白色的问题
出现这种情况,一般是因为修改了AndroidManifast.xml的主题
如果是unity5.5及以上的版本,则需要在application标签加上unity的默认主题设置
android:theme=”@style/UnityThemeSelector”
如果是unity5.5以下的版本,可以将unity工程导出成android工程看下AndroidManifast的默认主题配置
android,烘焙的光照图丢失
修改设置 Edit -> Project Settings ->Graphics ,将 Shader stripping 下的 Lightmap Modes 由 默认的 Automatic 修改为 Manual,然后 去掉 Realtime Non-Directional 和 Realtime Directional 的 勾选
拖进脚本的prefab,运行时不能加载
asset bundle 打包时 不会 关联脚本上的 prefab,只会关联 prefab 之间的引用, 这个很容一踩坑
比如 虚拟列表 中, item 的关联可以采取弄一个 item prefab 到 虚拟列表 prefab 中 隐藏, 然后脚本中去给这个 item prefab,千万不要只是 cs 脚本中弄一个 public GameObject go
去关联 item prefab, 这样 ab 打包不会把 item prefab 打包进去.
Android播放音效延迟优化
- Android播放音效延迟优化 - https://blog.csdn.net/yhhwatl/article/details/82933227
Android 合并后的 AndroidManifest.xml
打包后, 在路径: %PROJECT%\Temp\gradleOut\build\intermediates\merged_manifests\release\AndroidManifest.xml
可以找到
分辨率问题,pc、ios 相同,但与Android不同
- 设置 canvas 中 的 Canvas Scalar
- UI Scale Mode 为 Scale With Screen Size
- Reference Resolution 为 720x1280 (竖屏)
- Screen Match Mode 为 Match Width Or Height
- Match 为 1(竖屏为1,横屏为0)
- 参考链接:http://blog.csdn.net/huutu/article/details/43770273
UI 分辨率
当前 (2020.1) 市场上大部分的手机是 9:16
分辨率比例, 分辨率一般设计为 720x1280
目前跨高比最小的是 iPhone X, 分辨率比例为 1125x2436
, 设计的图片最大高度 x = 1560
- 16:9 分辨率
- 1280 x 720
- 1920 x 1080 (full hd)
- 2560 x 1440 (2k)
- 3840 x 2160 (4k)
安全区域 SafeArea
Ios : try disabling strip engine code 报错
在Player Setting – Other Setting,去掉勾选 Strip Engine
Enable Bitcode 报错
打 debug (build setting)包默认 enable bitcode 是 on的,关掉即可
相关链接:https://forum.unity.com/threads/set-enable-bitcode-default-value-when-building-for-ios.353236/
如果我们的工程需要支持bitcode,则必要要求所有的引入的第三方库都支持bitcode
http://www.cocoachina.com/ios/20150818/13078.html
粒子特效 不受深度影响需求
项目中有个需求就是 特效粒子 不需要手 深度测试 的影响, 要总是通过深度测试
默认的 透明shader 是受 深度测试 影响, 虽然不写入深度.
解决方案很简单, 深度测试 总是通过就行了
1 | ZTest Always Cull Off ZWrite Off |
编辑器日志
位于 C:\Users\%USER%\AppData\Local\Unity\Editor\Editor.log
也可以右键 console 打开
编辑器打开时都是不可编辑, 应该是该进程拿着文件的句柄, 必须关掉编辑器才可以 编辑 这个而文件.
去掉 Android 初次启动 授权弹窗
去掉安装 apk 后启动弹的授权 照片, 媒体内容和文件 提示. 在使用到的时候动态申请.
player settings -> other settings -> wirte permission, 选择 internal 就不会有授权提示, 选择 external 则会有授权提示.
至于为什么, 还没完全搞明白.
从 write permission 看出好像是在 AndroidManifest.xml 中加了 android.permission.WRITE_EXTERNAL_STORAGE
写外部存储 的权限. 但是在 选择 internal 的情况下, 在 AndroidManifest.xml 中加这个 写外部存储 的权限, 不会有授权提示. 从 apk 反编译出来的 AndroidManifest.xml 中也是有这个权限. so, 搞不懂
网上了解到的说这个授权提示是 android.permission.READ_EXTERNAL_STORAGE 读外部存储 的权限引起的. 实际测试中在 AndroidManifest.xml 去掉了这个权限, 选择了 external, 依旧会有授权提示. 从 apk 反编译出来的 AndroidManifest.xml 也是没有这个权限.
- Android 6.0 的权限管理 - https://www.jianshu.com/p/b0d823a4c8dd
综上实测结论: 要干掉这个授权, write permission 就必须选择 internal, 至于 AndroidManifest.xml 中可以随意添加.
优化包体大小
Android
- 开启 Android 混淆.
- 开启 代码剥离. https://docs.unity3d.com/Manual/ManagedCodeStripping.html
csharp
同步锁
- c# - 如果锁定对象内部发生异常,是否保持锁定状态? - https://code5.cn/so/c%23/83997
使用锁
1 | lock(mLockTcp) { |
锁定将被释放, lock本质上是:
1 | Monitor.Enter(lockObj); |
所以不用担心 lock 块内异常.
mac 平台 vscode 报错 .NETFramework not found
vscode 控制台报错: .NETFramework not found, 解决办法:
参考:
- https://stackoverflow.com/questions/52296678/using-net-4-x-in-unity-on-a-mac
- https://stackoverflow.com/questions/56118898/vscode-unity-omnisharp-netframework-not-found/56197605
下载 mono 最新版的 mono. 传送门: https://www.mono-project.com/download/stable/
配置 vscode 的 omnisharp 使用全局的 mono
mac 环境下 多开 unity
新建一个可执行 sh, 内容如下
1
open -n /Applications/Unity2018.4.15f1/Unity.app
- 然后双击即可多开了.
ugui 对齐方式
三角形就是对齐标记.
上下都对齐底部, 左边对齐左边, 右边对齐右边.
- 1 的间距是 固定的, 不会随着屏幕左右拉伸和变化, 白色图片的 宽度 会随着宽度的变化而变化, 也就是图片的 宽 是 拉伸的
- 2 的间距是 变化的, 随着屏幕的上下拉伸而变化, 白色图片的 高度 不会随着宽度的变化而变化, 也就是图片的 高 是 固定的
预制件编辑模式
双击 prefab 可以进入 预制件编辑 模式, 使用 unity 默认的 canvas, 可以修改成自定义的 canvas, 这样编辑所见即运行时所得.
创建一个 ui 制作的场景 make_ui , 和运行时的一致
将 make_ui 拖入 edit -> project settings -> editor -> prefab editing environments -> ui environment 中
done. 测试一下, 先双击 预制件 进入 编辑 模式, 调整分辨率, 如果编辑模式下的 ui 没有刷新, 再双击 预制件 即可.
- 预制件会 挂在 自定义场景里的第一个 canvas 下.
iOS 横竖屏问题
在 ios player settings 中, default orientation
要设置为 auto rotation
- 如果
default orientation
选择 非auto rotation
的选项, 会出现奇怪的旋转问题.
跳帧语法糖
在看 EnhancedScroller 无限列表时看到的语法糖, 在一个协程方法里实现跳帧逻辑
这样的好处是可以让一些 临时变量内聚到方法里; 如果是使用 Update 函数的话, 则需要将临时变量放到成员变量里
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283IEnumerator TweenPosition(TweenType tweenType) {
while (_tweenTimeLeft < time && _tweenStop == TweenStop.none) {
case TweenType.linear: newPosition = linear(start, end, (_tweenTimeLeft / time)); break;
...
yield return null;
}
...
}
---
### ui 图集 - sprite atlas
- Sprite packer 和 Sprite Atlas 使用总结 - https://blog.csdn.net/weixin_36961960/article/details/86707085
- Sprite Atlas使用介绍 - https://blog.csdn.net/wealupa/article/details/108216912
---
### unity hub 激活问题
添加免费证书时报错: `There was a problem activating a new personal license. Make sure you are logged in, and have internet connection. 错误`
解决办法, 退出 unity hub, 用管理员身份启动, 然后添加就没问题了
参考: https://forum.unity.com/threads/there-was-a-problem-activating-a-new-personal-license-make-sure-you-are-logged-in-and-have-intern.1167806/
---
### unity 国际版下载
国际版可以破解, 国内版加壳了破解不了
1. 科学上网 (全局, 一般我用 日本 梯子).
2. 打开 unity 下载网页: https://unity3d.com/get-unity/download/archive , LTS: https://unity3d.com/unity/qa/lts-releases
查看网页上 unity hub 的 html 代码, 国际版版本
- 2020
- Unity 2020.3.26 - unityhub://2020.3.26f1/7298b473bc1a
- Unity 2020.3.2 - unityhub://2020.3.2f1/8fd9074bf66c
- 2019
- Unity 2019.4.34 - unityhub://2019.4.34f1/6a9faed444f2
- Unity 2019.4.22 - unityhub://2019.4.22f1/9fdda2fe27ad
---
### 编辑器失去焦点后停止渲染
默认时不再后台运行, 修改方法

---
### prefab 的脚本参数修改不能保存到本地
- 执行一下这个代码即可: `EditorUtility.SetDirty(xxx);`
---
### Android 环境配置
- Android environment setup - https://docs.unity3d.com/Manual/android-sdksetup.html
---
#### Android 构建
- Gradle for Android https://docs.unity3d.com/cn/2019.4/Manual/android-gradle-overview.html
---
#### 更详细的构建日志
方便查看哪里错误
- https://blog.csdn.net/u012416928/article/details/47356887
- 在 gradle 中加入编译参数
```json
allprojects {
// 加入编译参数
gradle.projectsEvaluated {
tasks.withType(JavaCompile) {
options.compilerArgs << "-Xlint:unchecked" << "-Xlint:deprecation"
}
}
}
---
### 升级到 2019.4
1. JDK 8 (OpenJDK version 1.8)
2. NDK LTS r19
3. gradle 升级, 创建个原生工程, 导出 Android Studio 工程查看即可
---
### 价格
- 选择适合您的方案 - https://store.unity.com/cn/compare-plans
---
### 解决 预览包问题
升级引擎后, 在编辑器顶部出现 `PREVIEW PACKAGES IN USE` 的字眼.
原因是因为旧引擎中使用了某个包是 预览版 的, 在新引擎中已经转为 正式版, 解决办法: *window -> package manager -> advanced*, 点击 *reset packages to defaults*

- https://answers.unity.com/questions/1632351/what-is-preview-packages-in-use.html
---
### UI Toolkit
- [Unity]浅尝UI Toolkit Runtime - https://zhuanlan.zhihu.com/p/313321005
- 槽点满满的UIElements/UIToolkit - https://zhuanlan.zhihu.com/p/416575768
- Unity新的UI系统已经改成传统模式了 - https://www.toutiao.com/w/1733808796898371
总结: 还是 UGUI 最好用
---
### unity 文件管理器屏蔽文件夹
命名文件夹时加上 `~` 结尾即可, 如:

---
### csharp 编译器版本
- https://docs.unity3d.com/2019.4/Documentation/Manual/CSharpCompiler.html
| **Scripting Runtime Version** | **C# compiler** | **C# language version** |
| :---------------------------- | :----------------------------------------- | :----------------------------------------------------------- |
| .NET 4.6 equivalent | [Roslyn](https://github.com/dotnet/roslyn) | [C# 7.3](https://docs.microsoft.com/en-us/dotnet/csharp/whats-new/csharp-7-3) |
---
### 坐标系
坐标系区分

- 拇指指向 x 轴正方形, 食指指向 y 轴正方形, 中指指向 z 轴正方形
unity 是 左手坐标系, 3ds max 是 右手坐标系

---
### 为什么 Android 默认不开硬件加速
- https://forum.unity.com/threads/android-hardwareaccelerated-is-forced-false-in-all-activities.532786/
官方解释是 unity 所有的 activity 都不开硬件加速. 如果 packages and webviews 最好是在一个新的 activity 中打开, 并自由开启硬件加速
---
### 代码修改贴图格式报错
错误: `Selected texture format 'Unsupported' for platform 'iPhone' is not valid with the current texture type 'Default'.`
TextureImporterFormat格式指定有问题,ASTC整合了带A的格式。所以代码里都统一成 *ASTC_6x6*了。在新的2020版本里已经没有ASTC_RGBA与ASTC_RGB的区分,都统一到一个接口里了ASTC_*x*,应该是版本过度的问题,unity2019有很多的过渡问题。在2020上面就好很多了
参考:https://answer.uwa4d.com/question/61f11918d8413e18eb9613cd
---
### Android 构建工具报错
错误: `Installed Build Tools revision 33.0.0 is corrupted`
原因是构建工具使用的最高版本 33.0.0 里面, 没有去修改 d8 为 dx 文件
(不修改这个将会报错: `android Installed Build Tools revision 32.0.0 is corrupted`)
1. 将 `%ANDROID_SDK%\build-tools\32.0.0` 目录下的 d8.bat 改成 dx.bat
2. 将 `%ANDROID_SDK%\build-tools\32.0.0\lib` 目录下的 d8.jar 改成 dx.jar
---
### 批量打包失败
- 报错日志
```json
***Player size statistics***
Level 0 'Assets/Res/Scenes/scene_main.unity' uses 33.3 KB compressed / 128.8 KB uncompressed.
Total compressed size 33.4 KB. Total uncompressed size 128.8 KB.
Opening scene 'Assets/Res/Scenes/scene_room.unity'
Load scene 'Assets/Res/Scenes/scene_room.unity' time: 0.009500 ms
Unloading 29 Unused Serialized files (Serialized files now loaded: 0)
System memory in use before: 232.6 MB.
System memory in use after: 232.6 MB.
Unloading 47 unused Assets to reduce memory usage. Loaded Objects now: 3835.
Total: 10.203400 ms (FindLiveObjects: 0.528900 ms CreateObjectMapping: 0.049000 ms MarkObjects: 9.348000 ms DeleteObjects: 0.276300 ms)
[00:00:00] Enlighten: Precompute started.
[00:00:00] Enlighten: Finished 1 Layout Systems job (0.00s execute, 0.00s integrate, 0.00s wallclock)
[00:00:00] Enlighten: Finished 1 Tetrahedralize Probes job (0.00s execute, 0.00s integrate, 0.01s wallclock)
[00:00:00] Enlighten: Precompute took 0.015188 seconds.
Enlighten scene contents: 0 geometries. 0 instances. 0 systems. 0 probe groups. 0 cube maps. Scene is up-to-date.
[00:00:00] Enlighten: Bake started.
[PathTracer] Updated environment lighting, hash 2ffa242b7d049f5ac4b5bc7aa18135c6.
[PathTracer] Common reset.
[PathTracer] Lightmap reset.
[PathTracer][LP] Light probes reset.
[PathTracer] building lightmap data asset.
[PathTracer] m_Clear = false;
[PathTracer] building lightmap data asset.
[00:00:00] Enlighten: Finished 1 Bake Ambient Probe job (0.00s execute, 0.00s integrate, 0.02s wallclock)
[00:00:00] Enlighten: Finished 1 Reflection System job (0.00s execute, 0.00s integrate, 0.01s wallclock)
[00:00:00] Enlighten: Finished 1 Bake Runtime job (0.74s execute, 0.00s integrate, 0.76s wallclock)
[00:00:00] Enlighten: Bake took 0.755905 seconds.
[PathTracer] building lightmap data asset.
[PathTracer] Fetching lightmaps for lightmap data asset started.
[PathTracer] Fetching lightmaps for lightmap data asset finished.
> Collecting Enlighten data
Error while rolling data back after failed file move operation from 'E:/a_its/rummy_itc-v5/Temp/UnityTempFile-773f970dc55d51e4e82ca71f63cbc770' to 'C:/Users/its-packer02/AppData/LocalLow/Unity/Caches/GiCache/1c/1caa9e6aaa50a08e21bcf8e4fdc12c2f.LightingData.asset'. Backup is located at 'C:/Users/its-packer02/AppData/LocalLow/Unity/Caches/GiCache/1c/1caa9e6aaa50a08e21bcf8e4fdc12c2f.LightingData.asset.bak'
Fatal Error! Error while rolling data back after failed file move operation from 'E:/a_its/rummy_itc-v5/Temp/UnityTempFile-773f970dc55d51e4e82ca71f63cbc770' to 'C:/Users/its-packer02/AppData/LocalLow/Unity/Caches/GiCache/1c/1caa9e6aaa50a08e21bcf8e4fdc12c2f.LightingData.asset'. Backup is located at 'C:/Users/its-packer02/AppData/LocalLow/Unity/Caches/GiCache/1c/1caa9e6aaa50a08e21bcf8e4fdc12c2f.LightingData.asset.bak'
UnityEditor.BuildPipeline:BuildAssetBundles(String, AssetBundleBuild[], BuildAssetBundleOptions, BuildTarget)
Exiting without the bug reporter. Application will terminate with return code 1可能是因为开了灯光, 导致 batch 模式下打包报错
锯齿问题
- Unity抗锯齿设置 - https://blog.csdn.net/f_957995490/article/details/106445628
- Unity 抗锯齿方案梳理 - https://www.jianshu.com/p/ba97cf44c71e
- 深入浅出Temporal Antialising - https://zhuanlan.zhihu.com/p/142922246
官方的后处理插件PostProcessing抗锯齿用法:
- 在Package Manager中找到Post Processing并安装
- 给相机添加 Post-process Layer
TAA
TAA据说(未考证)是目前业内游戏大厂使用最多,最广泛的抗锯齿。使用运动矢量组合两帧,以确定在何处对前一帧进行采样。在每一帧对屏幕区域内的像素进行一个抖动操作,这样当连续的多个帧的数据混合起来以后,就相当于对每个像素进行了多次采样,他将采样点从单帧分布到多个帧上,使得每一帧并不需要多次采样增加计算量,但TAA往往会盲目地跟随移动物体的运动矢量,从而造成屏幕上的细节模糊不清。
据说(未考证)大厂基本会自己根据自己的项目写TAA的效果。如果物体运动过快会导致画面糊、残影,性能方面好像各有说辞,3个DrawCalls,这里如果是小团队,建议这几个方案都试试根据项目需求录取吧。Post Processing除了抗锯齿之外还提供了很多其他的后处理效果,小伙伴们可以自行百度试试(这应该是TA的事情)。
TAA是一种更先进的抗锯齿技术,它可以将过去的几帧存储在历史缓冲区中,用于更有效的平滑边缘。这种技术可以很有效的在运动中平滑边缘,但是需要开启运动模糊,并且比FXAA更消耗性能。因此建议使用在主机和PC平台使用
注意事项 | 不支持GLES2平台 |
---|---|
要求支持 | Shader Model3 Motion Vectors Depth texture |
动画制作
animator 中的动画触发条件设置时, 默认是会平滑上一个动作和目的动作, 这个会导致不能完整播放目的动作, 需要将这个过渡去掉
粒子大小缩放
问题描述
在Unity中调整粒子系统的Scale,怎么改都不起作用,希望达到调整父Particle System的Scale,整个粒子系统做出相应尺寸调整的变化。解决方法
粒子系统中有一个属性叫Scaling Mode,Scaling Mode:缩放模式,Hierarchy(同时受自己与父节点的缩放影响),Local(自受自己影响),Shape(天塌下来也不缩放)。
particle system默认设置为Local,并且不允许通过transform修改Scale。
参考: https://blog.csdn.net/qq_41452267/article/details/111571416
平台判断
编译宏 https://docs.unity3d.com/Manual/PlatformDependentCompilation.html, 如: UNITY_ANDROID 是判断 build settings 切到那个平台的
运行时, 如:
Application.platform == RuntimePlatform.Android
是判断包体运行时的平台