ADX+UE5で、ゲーム中に存在するキャラクターに応じて環境音を変化させる

# はじめに
ADXアンバサダーとして記事を書いておりますSigと申します。
この記事ではアンリアルエンジン5とサウンドミドルウェア「ADX for UE」を連携させ、「**ゲーム中に登場しているキャラクターに応じて環境音を動的に変化させる**」実装を行ってみます。

## 今回の実装例
たとえばゲーム内の街のマップや拠点において、NPCの数が多いほど街の喧騒音を大きくさせ、また鍛冶屋や商人がいる場合のみ専用の環境音を再生します。
「鍛冶屋がいれば金槌の音が聞こえ、商人がいれば商品をアピールしている声が聞こえる」といったように、よりいきいきとした環境音表現ができる効果が期待できます。ゲーム内世界の雰囲気を演出するのに一役買うでしょう。
また、マルチプレイのゲームにおいても、近くにいるプレイヤーの数に応じて喧騒を大きくする、といった活用法も考えられます。

注意点として、あくまで環境音としての実装のため、厳密に3D空間上に音を配置したい場合は該当部分のみアプローチを変える方法があるかもしれません。

例：街と群衆の喧騒のみこの記事の方法で実装させ、鍛冶屋や商人から発する音はアクターに紐づける形で配置する、等


# 前提

UE5.4+「ADX LE UE SDK(2.03.00)」を使用します（他バージョンにおいても、基本的に実装方法は同じです）。
基本的にブループリントのみでの実装を想定しています。
ADXはインディー向けの「LE版」であれば、無料で使用できます。
https://game.criware.jp/products/adx-le/

なお、ADX2からADXへ名称が変更になりましたが、ツール構成は変更ありません（2がないから古いほう、というわけではありません）。

ADX for UEの導入や基本的な使い方は以下の記事にあります。必要に応じて参照してください。
**ADX for UEの導入で、一歩上のサウンド表現を（導入編）**

https://qiita.com/SigRem/items/4250925f6d66a4fd287a

**ADX for UEの導入で、一歩上のサウンド表現を（実践編）**

https://qiita.com/SigRem/items/c089b71c42e898980a46


# 実装

## AtomCraftで環境音を構成する

### マテリアルの用意
まずは環境音の素材となるマテリアルを用意します。
今回用意したのは以下の4種です。
- 基本の環境音となる「BGS_Town」
- 鍛冶屋がいる場合に再生される「BGS_Town_Blacksmith」
- 商人がいる場合に再生される「BGS_Town_Merchant」
- キャラクター数に応じて音量が変化する、喧騒の環境音「BGS_Town_Crowd」

![A01.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/6abfab9b-6057-0301-c126-0a853520eae8.png)

すべての効果音について、インスペクターにてループするよう設定しておきましょう。
![A02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/20b5e3eb-4852-e153-1c75-2946817eccfb.png)




### キューの作成
街の環境音となるキューを作成します。統合された環境音としたいので、今回作成するキューはこの一つだけです。
ワークユニットツリーのキューシートを右クリックし、「新規オブジェクト」→「キュー『ポリフォニック』の作成」を選びます。
![A03.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/7f5ea1cf-4162-0a30-2653-9a32a6bbf67c.png)

作成したキューに、すべての環境音をトラック別に挿入します。
![A04.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/3541e899-f428-027f-22ef-c72d81586b94.png)



### Aisacコントロールの作成

トラック「Track_BGS_Town_Blacksmith」を右クリックし、「新規オブジェクト」→「AISACの作成」を選択してAisacコントロールを作ります。
![A05.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/df9eefe7-fa74-fb10-feeb-512fcd005717.png)

分かりやすいよう名前をつけますが、UE側では中段にある「AisacControl_00」の名前を使用します。
グラフタイプは「ボリューム」です。
![A06.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/25d3f14c-56f5-f6a7-3388-64f1dd8cd13a.png)

AISACリストから「ボリューム」を選択し、グラフを編集します。
![A07.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/30c9ea52-2ec6-e0e9-e5be-f9c4ff59a0f2.png)

右肩上がりの単純なグラフにします。
右枠を「インスペクター」から「ポイントリスト」にタブを切り替え、数値を入力してもOKです。
![A08.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/29bd14eb-73fc-8415-a9b5-5d42ce75fc1a.png)

編集できたらスライダーを動かし音量の変化をチェックしてみましょう。
![A09.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/6a24231b-de7f-a760-8f67-fd93374553e1.png)

チェックの際は、一時的に他トラックをミュートしてあげると分かりやすいかもしれません。
![A10.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/a127b079-7029-85ed-d70c-41222f91b9b8.png)

同じように、商人用の環境音、喧騒用の環境音に対してもAisacコントロールを作成します。**それぞれIDが異なるよう選択**してください。
![A11.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/75e96234-1a20-84ab-c45a-fb220790e2c0.png)

すべてのトラックに対し、それぞれのAisacコントロールのグラフを同じように編集します。
画像では重なっているため一本のグラフに見えますが、実際は3本の線があります。
![A12.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/d7684c4f-19e7-f5a3-cc6a-6ad62c55ed8b.png)

スライダーを動かし、各トラックのAisacコントロールが正常に動いているかテストします。




### キューシートのビルド
ここまでできたら、キューシートをビルドしてUEに持っていきます。
![A13.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/285ec0d7-29cf-ee80-15b4-89cfd740b3bc.png)
![A14.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/91b249af-797e-504b-8549-c22d7ad120c3.png)




## UEで環境音を変化させる

### キューシートのインポート
UE側のコンテンツブラウザ（コンテンツドロワー）に、ビルドしたacfファイル、acbファイルをドラッグ＆ドロップしてインポートします。
ダイアログでは「Yes」を選択します。これにより、acfファイルがプロジェクトに設定されます。
![B01.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/20f1565d-8c42-566b-8a6a-2e5a607c639d.png)
キューシートとAtomConfigのふたつのアセットがインポートされていることを確認します。
![B02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/bdd50c07-b10d-cb83-0808-85eb6e1d857e.png)
キューシートを開き、正常に再生されるか確認しておきましょう。
![B03.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/a68d16f2-f08f-9ea4-a3a1-a3aca6b18518.png)



### サウンドの配置
レベル上にキューを配置します。
![B04.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/ba7b7f94-bba5-faef-f5cc-138c40ca4523.png)

Detailsパネルにて、Aisacコントロールの初期値が設定できます。ゲーム開始状態では素の環境音だけにしたいので、初期値をすべて「0」にしておきましょう。
「Control Modulations」の要素を追加します。
![B05.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/7cf24057-25bf-aabc-9baf-bbbdc88b4c73.png)

「AisacControl_00」～「AisacControl_02」の値を「0.0」にします。
![B06.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/1551f51a-74ff-8f64-59c6-8c6fe116482c.png)


この状態でゲームを再生すると、プレーンな（NPCがいない状態の）街の環境音だけが聞こえるはずです。
![B07.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/0d15e0e9-c1fd-ef6a-656b-a247f704fb0a.png)



### アクターを検知して鍛冶屋、商人の音を追加する

ブループリントを使用し、検知したアクターに応じて環境音を追加する処理を書いていきます。
検知対象となるアクターを作成します。もし既に目的のアクターを作ってある場合は省いて大丈夫です。
![C01.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/9cf4356a-dbb0-c320-fd5f-acc9e19a7abe.png)

「鍛冶屋」や「商人」は今回、親クラスを「Character」で作ります（それ意外のクラスで作っていても大丈夫です）。
![C02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/57e2ca89-c1dd-308d-f042-594e598d074b.png)

鍛冶屋となるアクターが作成できました。
![C03.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/4bffc4f8-6b80-81e8-e16d-b5c7bcc3aa85.png)

ダブルクリックして開きます。
![C04.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/228cbe98-cef0-c05e-fb12-8cc3ba7437bc.png)

見た目が設定されていませんので、仮でメッシュを指定します。
アニメーションブループリントなども設定しておくと、Idleアニメーションが再生されていい感じかもしれません。
![C05.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/71313368-ea0a-2aa1-ee2d-bdcd07cdbfd2.png)

レベルブループリントを開きます。環境音再生用のアクターを作成しても大丈夫です。
![C06.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/b2a5a649-1592-1b4a-78f7-932edc513ca1.png)

右クリックして、「Add Custom Event」でカスタムイベントを追加します。
![C07.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/8ed19355-4aac-7b94-29e2-e4d627db5d74.png)

今回は「UpdateTownSound」と名付けました。これは街の音を変化させるトリガーになります。
街の状態が変わったり、プレイヤーが街のマップに出入りした際に実行するといいでしょう。
![C08.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/0e4746b2-fb05-4253-a761-cb7848005f45.png)

今回はテスト用として、仮で「1」キーを押してイベントを呼び出すようにしてみます。
![C09.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/490c1943-94d6-fb9d-ae4d-50b9120eb6c0.png)

イベントが開始されたら、**Get All Actors Of Class**ノードでレベル上のアクターを取得します。
まずは「Actor Class」に鍛冶屋となるアクタークラスを指定します。

このノードには「Out Actors」というアウトプットピンがあります。Array（配列）として検知したすべてのアクターのリストが取得できますので、**Length**ノードでリストの長さを測ればアクター数が判明する、というわけです。
![C10.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/be0176f0-f066-840d-90d3-82e4d9f18623.png)

試しに**Print String**ノードを使い、アクター数を文字として出力してみましょう。
![C11.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/02f95a8c-eb38-8c09-cd99-1ce15e18a941.png)

レベル上に鍛冶屋アクターを何体か配置し、ゲームを再生します。

レベル上に配置しているアクター数により、画面に出力される数字が変わるはずです。
![C12.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/4fcb1a8a-f159-2783-c747-aaa685aa2adb.png)
鍛冶屋を3体配置し、ゲーム再生中に「1」キーを押すと画面左上に「3」と表示されました。正常に取得できているようです。


正常に動いていることが分かったら、キューに対してAisacコントロールをかけていきます。
レベル上でキューを選択しておき、レベルブループリントに戻ります。
![C13.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/f18446da-db53-8488-c9d8-08260bcc63dd.png)

右クリックし、キューのリファレンスノードを配置します。
![C14.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/afbb545b-1e8d-e33e-3fb3-96614954af61.png)

リファレンスノードから、AIsacコントロールを行うためのノード**Set Aisac by Name**を作成します。
![C15.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/bd2309ce-90d4-d027-e5f7-1ab33bf0f57f.png)

対象のAisacControlを、鍛冶屋の環境音のボリュームを担当しているものに設定します。
![C16.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/067cefa0-c635-ef8e-f46b-95ca6c46660f.png)


**Select**ノードを使い、「レベルに鍛冶屋が一人以上いればAisacコントロールの値を1に、いなければ0に」します。
![C17.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/bfc4aefb-9488-e857-2268-60073f9b2cc6.png)
これで鍛冶屋の検知をし、いれば専用の環境音を鳴らす処理ができました。

同じように商人用のアクターも用意し、処理を組んでみましょう。
Characterクラスを継承したアクター「BP_Char_Town_Merchant」を作成しました。
分かりやすいように、鍛冶屋とは色を変えています。
![C18.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/b3d4a02f-0782-9848-79c6-4bc0316577b9.png)

レベルブループリントに戻ります。
**Sequence**ノードでグラフを整理しましょう。
![C19.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/a8b8f858-e23f-2cd6-c178-d0a2a5374ed5.png)

鍛冶屋用のノードをコピペし、**検知するクラスとAisacコントロール名**を変更すれば完成です。
![C20.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/966c8733-7b2f-0f1f-48ce-f462f15efbf6.png)
コピペした後、変更すべきは画像内でマークした2箇所です。
![C21.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/7bd63298-7696-c5e4-2057-3babb2aa86d8.png)

この状態でコンパイルすると、参照クラスを変えたためにエラーが出ることがあります。
![C22.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/1493e134-1ffa-9c59-6b1d-7f13a3a962a2.png)

その場合は**Length**ノードを作り直し、コンパイルすることでエラーが解消されます。
双方との再接続を忘れないように注意してください。
![C23.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/b9986b80-0c48-1024-d15b-ffc8bf7532c2.png)
![C24.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/bb34e979-a283-f439-7b09-886d6cefac95.png)




### キャラクター数に応じて喧騒の音量を変化させる

キャラクター数を自動で数え、その数に応じて喧騒の音を大きくしてみましょう。
**Sequence**ノードの「Add pin」ボタンを押し、ピンを追加します。
![D01.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/8dc11746-b5f0-2efb-f2b4-f56d7d76b93a.png)

鍛冶屋「BP_Char_Blacksmith」と商人「BP_Char_Merchant」は「Character」クラスを継承している子アクターですので、「Character」クラスの数を取得すると子クラスとして一緒にカウントされます。
**Get All Actors Of Class**ノードを使用し、レベル上に存在する「Character」クラスのアクター数を数えてみましょう。
![D02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/d3db00c8-e9d8-197c-d94c-91e32967c445.png)

**Map Range Clamped**ノードで、取得したアクター数をAisacコントロールの値としてスケーリングして渡します。
キャラクターが一人もいなければ喧騒のボリュームは0ですが、数が増えるにつれボリュームアップさせます。
キャラクターが10人以上で喧騒のボリュームが最大になります。
![D03.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/fe2a9238-ef66-4f69-c551-4ab2c88f54a1.png)

キャラクターを増やして「1」キーを押すとキャラクター数がカウントされ、喧騒の音量が変化するようになりました。
![D04.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/154452/f5eeb573-8dbd-2fc6-63e1-5f05aaa1fedd.png)



さらにキャラクター数や施設などが増えた場合に、さらに賑やかな環境音を追加するなどの処理を追加すれば、より発展している街や拠点といった雰囲気も出せそうです。
プロジェクトの形態に応じて取り入れて、よりゲームの状態が反映された環境音を再生してみるのも面白いかもしれません。