Unity AssetBundle加载依赖包

//=====================================================
// - 文件名:AssetBundleManager
// - 作   者:刘佳
// - 时   间:
/*
 * 
 */
//======================================================
using System;
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.Networking;


public class AssetBundleManager
{
    
    


    //加载路径 多个客户端需要代码设置
    public static string path = Application.streamingAssetsPath + "/assetbundle";

    private AssetBundleManager()
    {
    
    
        bundleDict = new Dictionary<string, AssetBundle>();
    }

    private static AssetBundleManager instance;
   static AssetBundle abMain;
   static AssetBundleManifest abMainfest;
    public static AssetBundleManager Instance
    {
    
    
        get
        {
    
    
            if (instance == null)instance = new AssetBundleManager();

            return instance;
        }
    }
    //初始化主包  以便后面加载依赖
    public void InitMainAB(string assetBundleName)
    {
    
    
        //1.加载主包
        abMain = AssetBundle.LoadFromFile(path + "/" + assetBundleName);
        //  2.加载主包中的固定文件
        //      (固定写法,死死记住即可)
        abMainfest = abMain.LoadAsset<AssetBundleManifest>("AssetBundleManifest");
    }
   //加载ab资源
    public T LoadAsset<T>(string key, string assetName) where T : UnityEngine.Object
    {
    
    

#if UNITY_EDITOR
        if (UnityEditor.EditorPrefs.GetBool("Editor"))
        {
    
    
            string[] paths = UnityEditor.AssetDatabase.GetAssetPathsFromAssetBundleAndAssetName(key, assetName);
            if (paths.Length == 0)
            {
    
    
                Debug.LogError("没有资源:" + key + ":" + assetName);
                return null;
            }
            string path = paths[0];
            T go = UnityEditor.AssetDatabase.LoadAssetAtPath<T>(path);
            return go;
        }
#endif

        if (!bundleDict.ContainsKey(key))
        {
    
    
            LoadBundle(key);
        }
        return bundleDict[key].LoadAsset<T>(assetName);
    }
    public T[] LoadAssetWithSubAssets<T>(string key, string assetName) where T : UnityEngine.Object
    {
    
    

#if UNITY_EDITOR
        if (UnityEditor.EditorPrefs.GetBool("Editor"))
        {
    
    
            string[] paths = UnityEditor.AssetDatabase.GetAssetPathsFromAssetBundleAndAssetName(key, assetName);
            if (paths.Length == 0)
            {
    
    
                Debug.LogError("没有资源:" + key + ":" + assetName);
                return null;
            }
            string path = paths[0];
            object[] dd = UnityEditor.AssetDatabase.LoadAllAssetsAtPath(path);
            T[] a = new T[dd.Length];
            for (int i = 0; i < dd.Length; i++)
            {
    
    
                a[i] = dd[i] as T;
            }
            return a;
        }
#endif

        if (!bundleDict.ContainsKey(key))
        {
    
    
            LoadBundle(key);
        }
        return bundleDict[key].LoadAssetWithSubAssets<T>(assetName);
    }

    Dictionary<string, AssetBundle> bundleDict = new Dictionary<string, AssetBundle>();
    //传入 需要加载ab的名字
    public void LoadBundle(string resName)
    {
    
    
#if UNITY_EDITOR
        if (UnityEditor.EditorPrefs.GetBool("Editor"))
        {
    
    
            Debug.Log("编辑模式模拟加载AB:" + resName);
            return;
        }
        Debug.Log($"开始加载资源:<color=red>{
      
      resName}</color>");
#endif

         //加载ab资源
        AssetBundle bundle = AssetBundle.LoadFromFile(path + "/" + resName);
        //加载ab所有关联的依赖
        string[] strs = abMainfest.GetAllDependencies(resName);
      
        for (int i = 0; i < strs.Length; i++)
        {
    
    
            Debug.Log($"{
      
      resName}的依赖包有{
      
      strs[i]}");
            if (!bundleDict.ContainsKey(strs[i]))//判断依赖包是否已经被加载过
            {
    
    
               AssetBundle ab = AssetBundle.LoadFromFile(path + "/" + strs[i]);//记载依赖包
                bundleDict.Add(strs[i],ab);//吧依赖包添加到字典
            };
        }
        bundleDict.Add(resName, bundle);//吧所加载的ab 也添加到字典
    }
    //异步加载
    public void LoadAsynceBundle(string resName, Action<float> progressAction, Action CallBack = null)
    {
    
    
#if UNITY_EDITOR
        if (UnityEditor.EditorPrefs.GetBool("Editor"))
        {
    
    
            Debug.Log($"编辑模式模拟异步加载AB:<color=red>{
      
      resName}</color>");
            progressAction?.Invoke(1);
            CallBack?.Invoke();
            return;
        }
#endif
        HotFixAssets.CoroutineHandle.Instance.StartCoroutine(IELoadBundle(resName, progressAction, CallBack));
    }
    IEnumerator IELoadBundle(string resName, Action<float> progressAction, Action CallBack)
    {
    
    
        AssetBundleCreateRequest request = AssetBundle.LoadFromFileAsync(path + "/" + resName);
        while (!request.isDone)
        {
    
    
            progressAction?.Invoke(request.progress);
            yield return null;
        }
        progressAction?.Invoke(1);
        bundleDict.Add(resName, request.assetBundle);
        CallBack?.Invoke();
    }
    public void UnLoadBundle(string resName)
    {
    
    
#if UNITY_EDITOR
        if (UnityEditor.EditorPrefs.GetBool("Editor"))
        {
    
    
            Debug.Log($"编辑模式模拟卸载:<color=green>{
      
      resName}</color>");
            return;
        }
#endif
        if (bundleDict.ContainsKey(resName))
        {
    
    
#if UNITY_EDITOR
            Debug.Log($"卸载资源:<color=green>{
      
      resName}</color>");
#endif
            bundleDict[resName].Unload(false);
            bundleDict.Remove(resName);
        }
        else
        {
    
    
            Debug.LogError($"AssetBundel:{
      
      resName}还没有加载");
        }
    }
    public bool CheckBundle(string resName)
    {
    
    
        return bundleDict.ContainsKey(resName);
    }
}

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class NewBehaviourScript : MonoBehaviour
{
    
    
    // Start is called before the first frame update
    void Start()
    {
    
    
        //初始化主AB包
        AssetBundleManager.Instance.InitMainAB("AssetbundleTest");

        GameObject go = GameObject.Instantiate(AssetBundleManager.Instance.LoadAsset<GameObject>("assets/prefabs/sphere", "Sphere"));
        GameObject go1 = GameObject.Instantiate(AssetBundleManager.Instance.LoadAsset<GameObject>("assets/prefabs/cube", "Cube"));
    }

    // Update is called once per frame
    void Update()
    {
    
    
        
    }
}

在这里插入图片描述
在这里插入图片描述
在这里插入图片描述

使用的AB包工具 AssetBundle-Browser
https://blog.csdn.net/WenHuiJun_/article/details/113178688

//借鉴链接
https://blog.csdn.net/SEA_0825/article/details/127253708

猜你喜欢

转载自blog.csdn.net/o_ojjj/article/details/128564864