由Unity提供的AssetBundle,最早出现于2017版本。允许您通过Unity的WebRequest类下载资源,并在运行时实例化它们。
二、使用Assetsbundle 2.1 准备资源工作-
新建Unity工程项目
-
工程命名:Assetsbundle(其他均可)
-
导入项目
-
将必要的模型以预制件形式存储于资源文件夹内
-
选中对应预制件资源(可多选) Inspector窗口会出现关于预制件资源的可视窗口。在窗口的正下方即为Assetsbundle
-
设置资源包名称(释义:预制件被打包到XXX.unity3d文件中)
- 在Scripts目录下新建Editor目录(编辑器脚本)
- 新建Packager.cs脚本(打包器) 参考API文档:AssetsBundles 文档
using UnityEditor; using System.IO; public class Packager { [MenuItem("AssetBundle/Build AssetBundle")] static void BuildAssetbundles() { //输出目录 string outPath = Application.streamingAssetsPath; //检查输出目录是否存在 if(Directory.Exists(outPath)) Directory.Delete(outPath, true) //删除 //新建目录 Directory.CreateDiretory(outPath); //打包 BuildPipeline.BuildAssetBundles(outPath, BuildAssetBundleOptions.None, BuildTarget.StandaloneWindows64); } }三、认识AssetBundler Browser
由Unity提供的便于操作AssetBundler的窗口插件。呈现出当前项目工程中打包的资源,与其之间的依赖关系。
3.1 如何下载Windows -> Package Manager -> 搜索"AssetBundler Browser"下载。
3.2 如何打开WIndows -> AssetBundler Browser
3.3 依赖关系 Configure
打包过程中,Unity为我们自动生成的。
目录:在StreamingAssets路径下。
将共用的材质或其他资源打包在一起。
Unity提供打包的过程的准备,如控制打包路径,目标平台等。
Clear Folder:检查有无存在这个文件,有则删除
Copy to streamingAssets:复制到StreamAssets文件(如果我们希望是这个路径)
Advanced Setting 高级选项
- Compression压缩
查看打包文件内的资源。
四、加载更新资源 4.1 准备工作- 在Scripts目录下新建ABTest.cs脚本
- 创建新GameObject对象,命名"ABTest"
- 挂载ABTest.cs脚本于对象上
引用命名空间:UnityEngine、UnityEngine.SceneManagement
//添加场景 private void LoadScene(AssetBundle ab) { //添加场景名 SceneManager.LoadScene("TanksExample"); } //添加坦克 private void AddTank(AssetBundle ab) { //添加包所有资源 GameObject[] objs = ab.LoadAllAssets<GameObject>(); foreach(GameObject go in objs) { Debug.Log(go.name); Instantiate(go); } //只添加坦克 GameObject tank = ab.LoadAsset<GameObject>("Tanke.Prefab"); }
如上所示,为添加场景与预制件的方法。
4.2.2 从本地文件加载引用命名空间:UnityEngine、UnityEngine.Events
//从本地文件加载 private IEnumerator LoadFormFile(string assetsName, UnityAction<AssetBundle> OnLoaded) { string path = Application.streamingAssetsPath + "/" + assetsName; AssetBundle ab = AssetsBundle.LoadFromFile(path); yield return ab; //等待加载完毕 //判断 if(ab == null) Debug.LogError("AssetsBundle:" + path + "为空") else OnLoaded(ab); }
在Start()中使用
- StartCoroutine(LoadFromFile("Tank.unity3d", AddTank));
- StartCoroutine(LoadFromFile("tanks-scene-bundle", LoadScene));
引用命名空间:UnityEngine、UnityEngine.Events
//从本地文件异步加载 private IEnumerator LoadFormFileAsync(string assetsName, UnityAction<AssetBundle> OnLoaded) { string path = Application.streamingAssetsPath + "/" + assetsName; AssetBundleCreateRequest request = AssetBundle.LoadFromFileAsync(path); yield return request; //等待加载完毕 AssetBundle ab = request.assetBundle; //判断 if(ab == null) Debug.LogError("AssetsBundle:" + path + "为空") else OnLoaded(ab); }
在Start()中使用
- StartCoroutine(LoadFromFileAsync("Tank.unity3d", AddTank));
- StartCoroutine(LoadFromFileAsync("StreamingAssets", LoadManifest));
//AssetBundleMainfest //加载Manifest文件 private void LoadManifest(AssetBundle ab) { //命名在StreamingAssets.manifest中获取 AssetBundleManifest manifest = ab.LoadAsset<AssetBundleManifest>("AssetBundleManifest"); //获取依赖包 string[] dependencies = manifest.GetAllDependencies("tank-scene-bundle"); foreach(string s in dependencies) { Debug.Log(s); } }
注:有依赖包优先加载依赖包。防止出错。
4.2.5 从内存中加载//从内存中加载 private IEnumerator LoadFormFileAsync(string assetsName, UnityAction<AssetBundle> OnLoaded) { string path = Application.streamingAssetsPath + "/" + assetsName; WWW www = new WWW(Path); yield return www; //等待下载完成 byte[] data = www.bytes; AssetBundle ab = AssetBundle.LoadFromMemory(data); //加载 //判断 if(ab == null) Debug.LogError("AssetsBundle:" + path + "为空") else OnLoaded(ab); }
优点:两个过程之间多一中间环节,可用于解密、加密保护资源。