Unity Addressables 管理游戏资源
一、前言
之前开发游戏过程中,有用到Zenject + UniTask + UniRx + Localization + GoogleSheet + Addressables的方式来开发游戏,本篇简单说一下Addressables的简单说明。
最近几年,Unity推出了一个强大的资源管理系统:Addressables。Addressables 允许开发者更加高效灵活地加载、卸载和管理游戏资源,无论这些资源是本地的还是远端的。
二、如何使用 Addressables
1.安装Addressables包
打开Unity的Package Manager,搜索Addressables,然后点击“Install”安装该包。
2.创建Addressable资源
右键点击你想要管理的资源,选择“Addressable Asset” > “Make Addressable”。
3.构建Addressables
打开Addressables窗口 (Window -> Asset Management -> Addressables -> Groups),在这里你可以配置和构建你的Addressables。
此处可对资源做一些远端路径配置
同事可以自定义标签,对资源进行颗粒度的管理。
三、资源加载与卸载
1.加载资源
void Start()
{
Addressables.LoadAssetAsync<GameObject>("AssetLabelOrAddress").Completed += OnLoadDone;
}
private void OnLoadDone(UnityEngine.ResourceManagement.AsyncOperations.AsyncOperationHandle<GameObject> obj)
{
if (obj.Status == UnityEngine.ResourceManagement.AsyncOperations.AsyncOperationStatus.Succeeded)
{
GameObject loadedObject = obj.Result;
// Do something with the loaded object
}
}
2.卸载资源
Addressables.ReleaseInstance(loadedObjectInstance);
四、多个资源加载
Addressables 可以方便地加载多个资源:
void Start()
{
// 多个资源的键列表
List<string> assetKeys = new List<string> { "Asset1", "Asset2", "Asset3" };
foreach (string key in assetKeys)
{
// 异步加载每个资源
Addressables.LoadAssetAsync<GameObject>(key).Completed += OnLoadDone;
}
}
private void OnLoadDone(AsyncOperationHandle<GameObject> obj)
{
// 检查资源是否成功加载
if (obj.Status == AsyncOperationStatus.Succeeded)
{
GameObject loadedObject = obj.Result;
// 处理加载的对象
}
}
五、资源管理
可以使用Addressables提供的Profile和Group来管理和监控资源:
1.Profile Configuration:
Profiles 用于管理不同环境中的资源路径。
2.Group Management:
通过分组,可以集中的管理和调度资源。
六、在热更新中的应用
Addressables 提供了一种方便的方式来实现资源的热更新:
Addressables.InitializeAsync().Completed += (initHandle) =>
{
Addressables.CheckForCatalogUpdates().Completed += (updateHandle) =>
{
// 检查是否有可用的更新
if (updateHandle.Result.Count > 0)
{
// 更新Catalog
Addressables.UpdateCatalogs(updateHandle.Result).Completed += (catalogsHandle) =>
{
// 在这里加载更新后的资源
};
}
};
};
七、远端资源加载与资源管理
1.加载远端资源并获取进度
public class RemoteResourceLoader : MonoBehaviour
{
private AsyncOperationHandle<GameObject> _handle;
void Start()
{
// 异步加载远端资源
_handle = Addressables.LoadAssetAsync<GameObject>("RemoteAssetAddress");
_handle.Completed += OnLoadDone;
StartCoroutine(CheckLoadingProgress(_handle));
}
private void OnLoadDone(AsyncOperationHandle<GameObject> obj)
{
// 检查资源是否成功加载
if (obj.Status == AsyncOperationStatus.Succeeded)
{
GameObject loadedObject = obj.Result;
// 处理加载的对象
}
}
private IEnumerator CheckLoadingProgress(AsyncOperationHandle handle)
{
// 检查加载进度
while (!handle.IsDone)
{
Debug.Log($"Loading progress: {handle.PercentComplete * 100}%");
yield return null;
}
}
}
2.管理远端资源,避免重复下载
Addressables 内部有缓存机制,可以避免重复下载相同的资源。如果你明确想要删除缓存,可以使用以下代码:
// 清除所有缓存
Caching.ClearCache();
// 清除特定资源
string cachePath = Application.persistentDataPath + "/Addressables";
DirectoryInfo directory = new DirectoryInfo(cachePath);
foreach (FileInfo file in directory.GetFiles())
{
file.Delete();
}
3.资源下载控制和预下载
Addressables 支持预下载资源以提高加载速度:
void Start()
{
// 预下载资源
List<string> assetKeys = new List<string> { "Asset1", "Asset2", "Asset3" };
Addressables.DownloadDependenciesAsync(assetKeys).Completed += (handle) =>
{
if (handle.Status == AsyncOperationStatus.Succeeded)
{
Debug.Log("Assets downloaded successfully.");
}
};
}
八、使用
下面是一个完整的例子,展示了如何使用Addressables进行资源的加载、卸载及进度管理:
public class AddressablesExample : MonoBehaviour
{
private AsyncOperationHandle<GameObject> handle;
void Start()
{
// 开始异步下载和加载资源
StartCoroutine(DownloadAndLoadAsset("RemoteAssetAddress"));
}
private IEnumerator DownloadAndLoadAsset(string assetAddress)
{
// 下载资源及其依赖
AsyncOperationHandle downloadHandle = Addressables.DownloadDependenciesAsync(assetAddress);
while (!downloadHandle.IsDone)
{
Debug.Log($"Download progress: {downloadHandle.PercentComplete * 100}%");
yield return null;
}
// 加载资源
handle = Addressables.LoadAssetAsync<GameObject>(assetAddress);
handle.Completed += OnLoadDone;
StartCoroutine(CheckLoadingProgress(handle));
}
private void OnLoadDone(AsyncOperationHandle<GameObject> obj)
{
// 检查资源是否成功加载
if (obj.Status == AsyncOperationStatus.Succeeded)
{
GameObject loadedObject = obj.Result;
// 实例化加载的对象
Instantiate(loadedObject);
}
}
private IEnumerator CheckLoadingProgress(AsyncOperationHandle handle)
{
// 检查加载进度
while (!handle.IsDone)
{
Debug.Log($"Loading progress: {handle.PercentComplete * 100}%");
yield return null;
}
}
private void OnDestroy()
{
// 释放资源,避免内存泄露
if (handle.IsValid())
{
Addressables.Release(handle);
}
}
}
九、总结
Unity Addressables 插件极大地简化了资源管理的复杂度,提供了全面的解决方案,不仅支持本地资源管理,还可以方便地集成远程资源和热更新,是Unity开发者的不二选择。新人创作不易,谢谢大家。