记录学习过程


目录

  • AssetBundle 资源打包
  • 一,相关知识点
  • 二,代码
  • 打包方式
  • 加载资源
  • 加载资源方法

录)

AssetBundle 资源打包

Unity版本:2018.3.0f2

一,相关知识点

  1. 定义:AssetBundle是一个压缩包,包含模型,贴图,预制体,声音,场景,脚本,可以在游戏运行的时候被加载
  2. 使用流程:指定资源的AssetBundle属性,生成AssetBundle包,上传,加载AssetBundle里的资源
  3. 分组策略
    A,逻辑实体:a,UI界面,b,角色(模型和动画),c,场景(模型和贴图)
    B,按照类型:a,声音资源,b,模型,c,shader,d,材质
    C,按照使用:a,某个时间内使用的资源,b,关卡使用的资源,c,场景所需的资源
    总结
    ①把经常更新的资源放在一个单独的包
    ②把需要同时加载的资源放在一个包里
    ③把其他包共享的资源放在一个单独的包里面
    ④把一些需要同时加载的小资源放在同一个包
    ⑤如果对于一个同一个资源有两个版本,可以通过后缀区分
  4. 压缩类型BuildAssetBundleOptions,常用
    ①None 使用LZMA压缩,包小,加载较慢,使用前需整体解压,解压后会使用LZ4重新压缩
    ②UncompressAssetBundle 不压缩,包大,加载快
    ③ChunkBasedCompression 使用LZ4压缩,压缩率没有LZMA高,但可以加载指定资源而不用加载解压全部
  5. manifest文件
    属性说明
    Assets:资源文件
    Dependencies 依赖文件
  6. AB的卸载
    减少内存使用,
    AssetBundle.Unload(true) 卸载所有资源
    AssetBundle.Unload(false) 卸载没被用的资源,之后资源没有用也不会再去卸载
    加载另一个场景会自动加载Resources.UnloadUnusedAssets();,或者确定资源没有时调用esources.UnloadUnusedAssets()的
  7. 文件校验
    CRC,MD5,SHA1 校验数据的完整性
    比较:
    安全性:SHA1>MD5>CRC
    效率:CRC>MD5,SHA1

二,代码

打包方式

1.编写脚本
Assets目录下新建Editor文件夹
新建脚本

[MenuItem("Assets/Build AssetBundles")]
   static void BuildAllAssetBundles()
   {
       string dir = "AssetBundles";
       if (!Directory.Exists(dir))
       {
           Directory.CreateDirectory(dir);
       }
       BuildPipeline.BuildAssetBundles(dir, BuildAssetBundleOptions.None,BuildTarget.StandaloneWindows64);
    }

2.AssetBundleBrowser(GitHub上一个插件)
https://github.com/Unity-Technologies/AssetBundles-Browser

加载资源

加载本地资源

//share是cube的必需资源,需要先加载
AssetBundle.LoadFromFile("AssetBundles/share.unity3d");//加载依赖资源,
AssetBundle ab = AssetBundle.LoadFromFile("AssetBundles/cube.unity3d");

GameObject cube= ab.LoadAsset<GameObject>("Cube");
Instantiate(cube);

在不清楚AB包里面有哪些资源时可以加载AB包里面的全部资源

Object[] objs = ab.LoadAllAssets();//获取全部的资源
foreach (Object o in objs)
{
    Instantiate(o);
}

加载依赖资源
加载依赖资源时,只要在使用前加载所有依赖资源即可

加载资源方法

Async异步加载

1.AssetBundle.LoadFromMemoryAsync(从内存加载)
2.AssetBundle.LoadFromFile(从文件加载)
3.WWW.LoadFromCacheOrDownLoad(从服务器或本地加载)
4.UnityWebRequest(取代WWW)

string path = "AssetBundles/cube.unity3d";

第一种方法 LoadFromMemoryAsync

AssetBundleCreateRequest request = AssetBundle.LoadFromMemoryAsync(File.ReadAllBytes(path));//异步加载
        yield return request;//等待加载完成
        AssetBundle ab = request.assetBundle;

        //AssetBundle ab = AssetBundle.LoadFromMemory(File.ReadAllBytes(path));//同步加载

        GameObject go = ab.LoadAsset<GameObject>("Cube");
        Instantiate(go);

第二种方法 LoadFromFileAsync

AssetBundleCreateRequest request = AssetBundle.LoadFromFileAsync(path);
        yield return request;
        AssetBundle ab = request.assetBundle;
        GameObject go = ab.LoadAsset<GameObject>("Cube");
        Instantiate(go);

第三种方法 WWW

while (!Caching.ready)//检测缓存是否准备好
            yield return null;

        //WWW www=  WWW.LoadFromCacheOrDownload(@"file:\\E:\Unity3D Project\AssetBundle\AssetBundles\cube.unity3d", 1);//本地
        WWW www = WWW.LoadFromCacheOrDownload(@"http://localhost/AssetBundles\cube.unity3d", 1); //本地或网络,可开启一个本地服务

        if (!string.IsNullOrEmpty(www.error))//如果有错
        {
            Debug.Log(www.error);
            yield break;
        }

        AssetBundle ab = www.assetBundle;
        GameObject go = ab.LoadAsset<GameObject>("Cube");
        Instantiate(go);

第四种方法 UnityWebRequest

string uri = @"file:\\E:\Unity3D Project\AssetBundle\AssetBundles\cube.unity3d";//本地资源
        //string uri = @"http://localhost:52012/AssetBundles\cube.unity3d";//服务器地址,NetBox2,随机端口号

        UnityWebRequest request = UnityWebRequestAssetBundle.GetAssetBundle(uri);
        yield return request.SendWebRequest();//发送请求

        //AssetBundle ab = DownloadHandlerAssetBundle.GetContent(request);
        AssetBundle ab = (request.downloadHandler as DownloadHandlerAssetBundle).assetBundle;//另一种方式

        GameObject go = ab.LoadAsset<GameObject>("Cube");
        Instantiate(go);

通过manifest加载包的依赖包

AssetBundle manifestAB = AssetBundle.LoadFromFile("AssetBundles/AssetBundles");//AssetBundles文件包含所有包的依赖文件
        AssetBundleManifest manifest = manifestAB.LoadAsset<AssetBundleManifest>("AssetBundleManifest");//AssetBundleManifest,固定的name

        string[] strs = manifest.GetAllDependencies("cube.unity3d");//获取cube.unity3d的依赖包
        foreach (string name in strs)
        {
            print(name);
            AssetBundle.LoadFromFile("AssetBundles/" + name);//加载所依赖的包
        }