UE5 Chooserについてのメモ

# 概要
UnrealEngine5 のプラグイン Chooser についてのメモ。
Chooserは UE5.5 から `Production Ready` になったようです。


## 更新履歴
| 日付 | 内容 |
|:-----|:----|
|2025/01/06| 初版 |


## 参考
以下の記事を参考にいたしました、ありがとうございます。
[その動き、機械が見つけます!? モーション・マッチングで、 やるぜ働き方改革！【CEDEC2024】 ](https://www.docswell.com/s/EpicGamesJapan/56VGGW-CEDEC2024_MotionMatching#p86)
[Thouhgts on Chooser plugin in UE5](https://bigm227.medium.com/thouhgts-on-chooser-plugin-in-ue5-8665b921c0df)
[UE公式：動的アセットの選択](https://dev.epicgames.com/documentation/ja-jp/unreal-engine/dynamic-asset-selection-in-unreal-engine)
[【UE5】猫でも分かるChooser（動的アセットの選択）ことはじめ Part1](https://pafuhana1213.hatenablog.com/entry/2024/12/13/224559)
[【UE5】猫でも分かるChooser（動的アセットの選択）ことはじめ Part2 - Proxy Asset , Table編 -](https://pafuhana1213.hatenablog.com/entry/2024/12/27/201243)
[【UE5】C++でChooser Table・Proxy Tableを使う方法について](https://pafuhana1213.hatenablog.com/entry/2024/12/31/161529)
[[UE5]アニメーションアセットをProxyTableで管理してみた備忘録](https://zenn.dev/kokuban/articles/f5ea4c4819d03c)


## 環境
Windows10
Visual Studio 2022
UnrealEngine 5.5.1

## 関連ソース
"Engine\Plugins\Chooser\Source\Chooser\Public\ChooserFunctionLibrary.h"
"Engine\Plugins\Chooser\Source\ChooserEditor\Public\ChooserInitializer.h"


# Chooserについて
入力パラメータに基づいてアセットや出力パラメータを設定できるデータテーブルです。
プラグイン形式になっているので使用するにはプラグインの追加設定が必要です。

![PluginChooser.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/303806/d794e744-02b0-8d82-6bb4-517602fc31ea.png)

アセットブラウザ右クリックから[アニメーション]->[チューザーテーブル]を選んで使用できます。
（もしくは [その他]->[チューザーテーブル] でも可）
![ContextMenu.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/303806/a4d8ef17-89d0-8423-777c-db96cce338ea.png)

Chooserテーブルはアニメーションに分類されていますが、アニメーション以外でも使えるようです。チューザーテーブル作成時に `Generic Chooser`を選択すると任意のアセットを指定できるのでサウンドなどにも利用が可能です。

<img width="450" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/303806/5bda0baf-cc0f-f00e-eefc-0555404a844e.png">


# Chooserを使ってみる
## チューザーテーブルを作成
チューザーテーブルを作成したら詳細の[Parameters]にてバインドする先の設定をします。
下記では、`GA_Test2BP`というブループリントクラスを設定しています。（対象がStructなら[Struct Parameter]にする必要があります）

バインド対象にしたブループリント `GA_Test2BP` には `BoolVariable` というブール型変数がありこれをチューザーテーブルで選択する条件にします。
チューザーテーブルにて[Add Column]で[Bool]を追加すると、`BoolVariable` が選択できるようになります。
また、[Add Row]で選択すべきアセットを追加し、条件を設定します。どれにも該当しないケースを設定する場合は[Add Row]から[Add Fallback Result]で追加します。


▼ CHT_Test
![CHT_Test.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/303806/18c5e174-4cc2-c295-59fc-bd9ba4d9c29b.png)

バインドされた側のBPは `BoolVariable`の変数を必要に応じて変更します。チューザーテーブル評価時にこの値が使われます。

▼ GA_Test2BP
![GA_Test2BP.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/303806/4192575f-1dd4-3bb6-a667-0e67cbad69dc.png)


## チューザーテーブルを評価して使用する
BPにて、[Evaluate Chooser]ノードを使用し、テーブルを指定します。このノードの返り値がチューザーテーブルで設定したアセットから条件にあったものが選択されます。

<img width="300" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/303806/a2436787-dd9c-6bbc-37d4-e4f439af2213.png">

評価ノード後、そのまま使用できます。

![EvaluateChooser.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/303806/ea2d9406-3203-4be7-1c58-0fef49625ff0.png)


## チューザーテーブルからのパラメータ出力
[Add Column]に出力型を設定することでパラメータの出力ができます。
その際は出力先の変数を持つクラス(orストラクト)のバインド先指定と入出力方向の設定が必要です。
以下のようにすると、[GA_Test2BP]がもつ`BoolVariable`というbool型変数に対しバインドしチューザーテーブル評価後に値が書き換わります。
（同じ変数を入出力に使って反転させるようにしています）
![ChooserOutputParam.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/303806/73438966-ac9f-4788-3426-c9d9d9c6c81d.png)


## 扱えるデータ型について
[Add Column]で追加できるのは以下のようになっています。
`Bool`、`Enum`、`Float`、`ゲームプレイタグ`、`オブジェクト`とあり、状態に応じてアニメーションを変える時などはFloatやEnumを使うケースが多いのではないでしょうか。

<img width="200" src="https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/303806/99488293-aa1d-b0fe-cfc2-6857a5060519.png">



# C++で扱う
:::note
UE5.5 にてC++コードをコンパイルすると以下のようなエラーに遭遇しましたのでメモ書き。

「パッケージ System.Data.DataSetExtensions、バージョン 4.5.0 が見つかりませんでした。NuGet の復元により、削除された可能性があります。それ以外の場合、NuGet の復元が最大パス長の制限のために一部分しか完了していない可能性があります。」

▼対処
(1) \UE_5.5\Engine\Source\Programs\AutomationTool\Mutable\Run Mutable Commandlet\obj
の読み取り専用設定を解除する
(2)VisualStudio でソリューションを右クリックし、[Nuget パッケージの復元] を行う
:::


### モジュールの追加
Build.cs に "Chooser" を追加します。

```cs:Build.cs
public class Sample00 : ModuleRules
{
	public Sample00(ReadOnlyTargetRules Target) : base(Target)
	{
		PublicDependencyModuleNames.AddRange(new string[] {
			"Core",
			"CoreUObject",
			"Engine",
..省略..
        	"Chooser"      	// ←追加
			});
	}
}

```

### C++コードでチューザーテーブルを評価する
`UChooserFunctionLibrary`にチューザーテーブルを評価するメソッドがあります。バインドされたオブジェクト、チューザーテーブル、結果のオブジェクトクラスを渡すことで使うことができます。
以下サンプルコード。

```C++:サンプルコード
// ヘッダファイルで定義
//UPROPERTY(EditAnywhere, BlueprintReadOnly)
//TObjectPtr<UChooserTable>	CHT_Test;

#include "Chooser.h"
#include "ChooserFunctionLibrary.h"

UGameplayAbility* _GA_Test2BP; /* テーブルで設定したバインドオブジェクト */

// チューザーテーブルを評価して結果を受け取る
UObject* _Obj = UChooserFunctionLibrary::EvaluateChooser(_GA_Test2BP, CHT_Test, UAnimMontage::StaticClass());
if (_Obj) {
	UE_LOG(LogTemp, Log, TEXT("結果：%s"), *_Obj->GetFName().ToString());
}

```

返り値が配列型の `EvaluateChooserMulti` というのもあるようです。

```C++:ChooserFunctionLibrary.h
    UFUNCTION(BlueprintPure, meta = (BlueprintThreadSafe, BlueprintInternalUseOnly = "true", DeterminesOutputType = "ObjectClass"))
    static TArray<UObject*> EvaluateChooserMulti(const UObject* ContextObject, const UChooserTable* ChooserTable, TSubclassOf<UObject> ObjectClass);

```



# まとめ
データドリブンな設計にするためには Chooser はかなり有用な機能のように思えました。
このプラグインには他に ProxyTable という機能もありますがまだ実験段階のようです。みた感じより複雑なケースを扱えるチューザーテーブル？といったところでしょうか。