Addressableのことはじめ的な記事。

最近はResourcesをやめてAddressableを使う現場が増えてきたと自分の身の回りでも感じられるようになってきました。(遅いかな?^^;)
というわけでこの記事ではAddressableの基本をまとめてます。(全く使ったことない人が見るレベルね)

環境:Unity2021.3.3f1(win10)

Addressable何がいいの?

Addressableの登場前は、
パッケージに組み込む(ローカル)アセットはResources等の内部フォルダに置いていて、
パッケージ外(リモート)に置いてDLして使うアセットはアセットバンドルを使う。
というケースが大半だったと思います。

Resourcesはそんなに迷わずお手軽に使っちゃってました*1が、アセットバンドルは仕組みを実装するのが非常に複雑でした。
そんな時に出てきたのがAddressable!

Addressableを使うと、
・リモートでもローカルでもコードを変える必要がない(設定の切り替えだけで済む)
・リモートアセットもアセットバンドルで実装するよりも非常にわかりやすく実装できる。
という恩恵をすぐに得ることができます:)

PackageManagerからインストール

(環境によるかもしれないけど)現在はデフォルトで入っていないので、PackageManagerからインストールする必要があります!

インストールが終わるとすべてのアセットにAddressableを設定する欄↓ができます。

アドレスを登録

Addressableの入力欄にチェックを入れて、任意のアドレスを入力します。

Selectを押すか Window -> Asset Management -> Addressable -> Groups で出てくる「Addressable Group」ウィンドウで
設定されているアドレスとリソースの一覧が表示されます。
上で入力したアセットがあるか確認してみましょう:)
何もしていなければ 「Default Local Group」に入ります。

非同期ロードする

以下のようにしてアドレスを指定してからリソースを取得できます。(以下は画像を取得する例)

using UnityEngine;
using UnityEngine.AddressableAssets; //←これが必要
using UnityEngine.ResourceManagement.AsyncOperations;
using UnityEngine.UI;

public class TestAddressable : MonoBehaviour
{
    AsyncOperationHandle<Sprite> handle;

    async void Start()
    {
        handle = Addressables.LoadAssetAsync<Sprite>("bg/town_1"); //アドレスを指定してSpriteを取得
        await handle.Task;
        GetComponent<Image>().sprite = handle.Result;
    }

    private void OnDestroy()
    {
        Addressables.Release(handle); //使い終わったら解放してあげる必要あり!
    }
}

注意なのは、Addressableは基本、非同期ロードになることです。
今までResources.LoadAsync を使っていた箇所では、
Addressables.LoadAssetAsyncに単純に置き換えれられると思います。

同期ロードする

上述で基本Addressableは基本、非同期ロードになると言いましたが、同期ロードの仕組みも後から実装されたようです。
AsyncOperationHandle#WaitForCompletion でロードされるまで待機し、戻り値で結果を返してくれます。

using UnityEngine;
using UnityEngine.AddressableAssets; //←これが必要
using UnityEngine.ResourceManagement.AsyncOperations;
using UnityEngine.UI;

public class TestAddressable : MonoBehaviour
{
    AsyncOperationHandle<Sprite> handle;
    void Start()
    {
        handle = Addressables.LoadAssetAsync<Sprite>("bg/town_1"); //アドレスを指定してSpriteを取得
        GetComponent<Image>().sprite = handle.WaitForCompletion(); //同期ロード
    }

    private void OnDestroy()
    {
        Addressables.Release(handle); //使い終わったら解放してあげる必要あり!
    }
}

実機ビルドする時はアセットもビルドする必要があるけど、自動でやってくれるよ

Androidやios、Window版等パッケージでリソースをロードするには、アセットをビルドする必要があります。
※エディタでもPlay Mode Script を Use Existing Build にしている場合はビルドされたアセットを使うのでアセットのビルドをする必要があるよ!

手動で行う時は「Addressable Group」ウィンドウBuild -> New Build -> Default Build Scriptでアセットのビルドをしてから、
パッケージ(ゲーム本体)のビルドを行います。

(このような記事が多いですが↑)
最新のバージョンでは、自動で行う仕組みが既に実装されていて手動で行うケースはあまりなさそうです。
AddressableAssetSettingsというファイルの Build->Build Addressables on Player Build の項目が、
「Build Addressables content on Player Build」になっていればパッケージのビルドの際に、一緒にアセットバンドルもビルドされます。

ちなみに、「Use grobal Settings (stored in preferences)」になっている場合は、

Prefarences にある Addressables の項目で指定した値が使われます。

*1:正直Unity公式から非推奨という情報もかなり前から出ていたが…