コガネブログ

平日更新を目標に Unity や C#、Visual Studio、ReSharper などのゲーム開発アレコレを書いていきます

【Unity】Addressables でリモートカタログをキャッシュに保存する時にメインスレッドが止まらないようにする方法

検証環境

  • Addressables 1.16.19

概要

  • Addressables で管理しているグループが多いと、
    リモートカタログをキャッシュに保存する処理に時間がかかるようになり、
    メインスレッドが止まってしまう
  • 重たい処理は ContentCatalogProvider.OnCatalogLoaded 関数で
    File.WriteAllText を使用して .json を書き込んでいる箇所なので
    この部分を Tesk.Run で別スレッドに処理を逃してあげることで
    メインスレッドが止まることは防げる

ContentCatalogProvider.cs

272 行目以降

private async void OnCatalogLoaded(ContentCatalogData ccd)
{
    Addressables.LogFormat("Addressables - Content catalog load result = {0}.", ccd);
    if (ccd != null)
    {
        ccd.location = m_ProviderInterface.Location;
        ccd.localHash = m_LocalHashValue;
        if (!string.IsNullOrEmpty(m_RemoteHashValue) && !string.IsNullOrEmpty(m_LocalDataPath))
        {
            var dir = Path.GetDirectoryName(m_LocalDataPath);
            if (!string.IsNullOrEmpty(dir) && !Directory.Exists(dir))
                Directory.CreateDirectory(dir);
            var localCachePath = m_LocalDataPath;
            Addressables.LogFormat("Addressables - Saving cached content catalog to {0}.", localCachePath);
            await Task.Run( () => File.WriteAllText(localCachePath, JsonUtility.ToJson(ccd)) );
            File.WriteAllText(localCachePath.Replace(".json", ".hash"), m_RemoteHashValue);
            ccd.localHash = m_RemoteHashValue;
        }
    }
    m_ProviderInterface.Complete(ccd, ccd != null, ccd == null ? new Exception($"Unable to load ContentCatalogData  from location {m_ProviderInterface.Location}.") : null);
}