目录
🟥 AssetBundle用途
🟧 创建AssetBundle资源
1️⃣ AssetBundle可打包的资源
2️⃣ AssetBundle的UI
3️⃣ 打包
🟨 解读
1️⃣ 代码解读:BuildAssetBundleOptions、BuildTarget
2️⃣ 打包出的内容解读
3️⃣ Manifest文件解读
🟩 Manifest接口
🟥 AssetBundle用途
为减少网页游戏的下载时间,通常将游戏进行拆分,玩家边玩边下载,手机端游戏同样适用。
在Unity中可以为任何资源创建AssetBundle,AssetBundle包含模型、贴图甚至脚本(有限制),我们可以将这些资源从游戏的主要版本中分离出来,减少最后游戏包的大小,再通过网络下载这些资源,加载到游戏里。
具体使用流程:
1、利用脚本创建AssetBundle文件
2、上传到服务器
3、下载到本地
4、加载
🟧 创建AssetBundle资源
1️⃣ AssetBundle可打包的资源
a、任意Unity引擎可识别的资源。例如模型、纹理、音频、动画片段甚至场景等
b、将Unity不能识别的二进制文件后缀名改为,bytes,Unity即可识别为TextAsset文件,进而可打包到AssetBundle
2️⃣ AssetBundle的UI
a、右下角第一个选项表示该资源所标记的AssetBundle名称(即该资源打包到这个名称的AssetBundle中)。
第二个选项用于设置AssetBundle Variant,用在不同版本资源的使用和动态替换AssetBundle。
注意:AssetBundle标记的名称要小写,可以有后缀,如a.unity3d
b、当有很多AssetBundle标记的对象,想要看包含含有某个字符串的AssetBundle(可能有多个)中的资源时,可:
方法1:单击AssetBundle名称选项(第一个选项),选择“Filter Selected Name”
方法2:project视窗搜索:“b:AssetBundle名称”
3️⃣ 打包
1)、将创建脚本,将下段代码复制进去
注意:
1、这个打包功能还会顺带着切换平台。即你原先处于android平台,打win包,不会打包成功,你会被先切到win平台。
2、该脚本必须放在Assets / Editor文件夹下。否则打包时会报缺少引用。
3、要打包的资源预先不能在StreamingAssets下,否则打包不成功!
4、先给资源设置标记,否则打包不成功!
5、PC端可以给视频打AB包,并加载出来。但在安卓端,不能加载AB包中的视频,Unity官方说不打算支持该功能
链接
// ========================================================
// 描述:给资源打AB包
// 作者:Skode
// 创建时间:2019-10-10 09:54:56
// 版 本:1.0
// ========================================================
using UnityEngine;
using UnityEditor;
public class Skode_AssetBuilder : MonoBehaviour
{
//这是在Unity上方菜单栏创建Custom Editor选项,并创建Buile AssetBundles打包按钮
[MenuItem("Custom Editor/Build AssetBundle")]
//这是在Unity Asset右键创建打包按钮
[MenuItem("Assets/Build AssetBundle")]
static void CerateAssetBundlesMain()
{
//输出路径为Assets下的StreamingAssets文件夹(确定存在该路径),该路径可改
//BuildAssetBundleOptions.None表示默认的压缩格式LZMA,优点:压缩的非常小。缺点:解压时可能卡顿
//BuildAssetBundleOptions.UncompressedAssetBundle:不压缩
//BuildAssetBundleOptions.ChunkBasedCompression:这种方案。推荐使用
//第三个参数是平台
BuildPipeline.BuildAssetBundles("Assets/Bundles/Win",
BuildAssetBundleOptions.ChunkBasedCompression, BuildTarget.StandaloneWindows);
}
[MenuItem("Custom Editor/Get AssetBundle names")]
[MenuItem("Assets/Get AssetBundle names")]
static void GetAssetBundleNames() //获取所有AssetBundle名称
{
string[] names = AssetDatabase.GetAllAssetBundleNames();
foreach (var name in names)
{
Debug.Log("AssetBundle:" + name); //显示全部AssetBundle名称
}
}
}
2)、按脚本所示,创建Assets/Bundles/Win文件夹。
注:因脚本路径不同,同样的文件打包出来的部分文件名也不同。
比如脚本设置的路径是Assets/Bundles/Win,打包出来的是下方第一个红框文件
路径设置的为Assets/StreamingAssets,打包出来的是第二个红框文件
3)、在Asset中右键需要打包的文件,选择Build AssetBundle,即可在StreamingAssets文件夹看到打包的文件
🟨 解读
1️⃣ 代码解读:BuildAssetBundleOptions、BuildTarget
1、BuildAssetBundleOptions:
.None | 构件Assbundle没有任何特殊选项 |
.DisableWriterTypeTree | 在AssetBundle中不包含类型信息。主要注意的是:如果要将AssetBundle发布到Web平台上,则不能使用该选项 |
.DeterministicAssetBundle | 使每一个Object具有唯一不变的hash ID,可用于增量发布AssetBundle |
UncompressedAssetBundle | 不进行数据压缩,如果使用该选项,因为没有压缩/解压缩过程,AssetBundle的发布和加载会更快,但AssetBundle也会更大,导致下载速度变慢 |
ForceRebuildAssetBundle | 强制重新Build所有AssetBundle |
IngoreTypeTreeChanges | 忽略TypeTree的变化,不能与DisableTypeTree同时使用 |
AppendHashToAssetBundleName | 附加到Hash到AssetBundle名称中 |
2、BuildTarget选项
目标的构建平台,AssetBundle在不同平台间是不完全兼容的,在多个独立平台构建(包括WebPlayer)的AssetBundle可以在这些平台上加载,但并不能在iOS和Android上加载,这需要单独制定他们的BuildTarget。此外,Android和iOS之间也不能相互兼容。
2️⃣ 打包出的内容解读
1、打包的AssetBundle文件
2、Manifest文件
对资源进行打包后,在输出的路径文件下会有一个总的Manifest文件,文件名和文件所在文件夹名称相同——(一个);
然后每一个打包的资源分别会有一个自己的Manifest文件——(若干个)。
3️⃣ Manifest文件解读
Manifest包含:
在Editor模式下,Unity为每个AssetBundle都会生成一个Manifest文件,在Manifest文件中包含:
1、CRC
2、所包含的Assets
3、所依赖的AssetBundles
4、Hash
5、ClassTypes
Name:表示AssetBundle的名称
Dependencies:表示该AssetBundle所依赖的AssetBundle,如果内容为空,则说明AssetBundle没有依赖AssetBundle。
🟩 Manifest接口
AssetBundle Manifest提供以下访问接口:
GetAllAssetBundles() | 获取所有AssetBundle的名字 |
GetAllAssetBundlesWithVariant() | 获取所有指定Variant的AssetBundle的名字 |
GetAllDependencies(string) | 获取给定AssetBundle所依赖的AssetBundles的名字 |
GetAssetBundleHash(string) | 获取给定AssetBundle的Hash |
GetDirectDependencies(string) | 获取给定AssetBundle直接依赖的AssetBundles |
AssetBundle Manifest接口示例代码如下:
IEnumerator<WWW> Skode_ABTest()
{
WWW wwwManifest = new WWW("Manifest文件的路径");
yield return wwwManifest;
AssetBundle mainfestBundle = wwwManifest.assetBundle;
//Loads asset with name of type T from the bundle.
//public Object LoadAsset(string name);
AssetBundleManifest manifest = (AssetBundleManifest)mainfestBundle.LoadAsset("AssetBundleManifest");
//卸载包中的所有资产
mainfestBundle.Unload(false);
string[] allAssetBundles = manifest.GetAllAssetBundles();
string[] depedentAssetBundles = manifest.GetAllDependencies("assetbundle的名称");
}