BLOGブログ

2023.07.18UEFN

[UEFN] ボスバトルシューティング『MIMIZU』開発ブログ – Verseを利用したザコ敵の作り方

こんにちは、ヒストリアUEFNチームです。

今回はボスバトルシューティング『MIMIZU』で登場する幼虫(ザコ敵)のAIの作り方について紹介していきます。

「仕掛け構成」「Verseを使用した幼虫のAI挙動や移動の実装」「幼虫を生み出すスポーンの仕組み」の3つの内容に触れています。

【ヒストリアUEFNタイトル第二弾】
超巨大生物に立ち向かえ!ボスバトルシューティング『MIMIZU』

https://historia.co.jp/archives/34206/

マップコード:2955-7164-3106

 


 

幼虫AIの仕掛け構成について

『MIMIZU』の影の立役者である自爆幼虫。今回はその中でもアタッチや仕掛けをどのように構成しているかについてお話します。

現在、UEFNではスケルタルメッシュをクリエイティブデバイスから直接参照してVerseで動かすことはできません。
しかし、クリエイティブプロップは動かすことができるので、オリジナルのクリエイティブプロップを作成し、それにアタッチすることで間接的にスケルタルメッシュを動かすことができます。

このため、基本的に位置情報が重要になるオブジェクトは全てこのクリエイティブプロップ(正確にはBuiding Prop)にアタッチしています。

 

幼虫の攻撃・ダメージ判定には「爆破の仕掛け」を使用しています。「爆破の仕掛け」はこの両方に対応できる非常に汎用性の高い仕掛けです。
この仕掛けはVerse側から爆発をコントロールすることができるため、爆発ダメージやノックバックを利用すれば純粋な攻撃判定として利用できます。
また、一定のダメージを受けると自動で爆発するようにも設定できます。爆発したタイミングはVerse側から取得できるため、爆発ダメージとノックバックを無効にしておけば、今度はダメージ判定としても利用できます。

また、各スケルタルメッシュのアニメーションを制御するためにシーケンサーを使用しています。
アニメーション再生を行うシーケンサーを「ムービーシーケンスの仕掛け」で参照し、その「ムービーシーケンスの仕掛け」をVerseで独自に定義したクリエイティブデバイスで参照することで、Verseを使用したアニメーションやその他の制御が可能です。

このプロジェクトでは、幼虫移動時のアニメーションをスケルタルメッシュのデフォルトアニメーションとして設定した上で、攻撃爆発時、死亡時、登場時などのアニメーションや爆発時の衝撃ブラーをこの方法で実装しています。

サウンドは「スピーカーの仕掛け」を介して、アニメーションと同様にVerseから制御しています。
こちらはシーケンサーと違い音が鳴る位置も重要になるため、クリエイティブプロップにアタッチして鳴らしています。

パーティクルエフェクトは「ビジュアルエフェクトスポナーの仕掛け」がありますが、こちらはどちらかというと静的なエフェクトに適しています。
そのため、ナイアガラエフェクトを直接クリエイティブプロップにアタッチし、アニメーションと同じくシーケンサーによって再生しています。

結果としてこのプロジェクトでは幼虫1匹あたりの全体構成は以下のようになりました。

幼虫1匹あたりのオブジェクト間の構成

クリエイティブプロップにアタッチされた各オブジェクトのアウトライナー上の表示

AI用クリエイティブデバイスからの各参照

 

Verseを使用した幼虫のAI挙動や移動の実装について

ここからはVerseによってどのようなロジックを用いてプレイヤーを追いかける幼虫のAI挙動を実装しているかを解説していきます。

まずは幼虫AIの実際の動きをご覧ください。

 

 

移動はアタッチ元となるクリエイティブプロップをMoveTo()関数によって動かすことで実現しています。
登場時のシーケンサーが終了した後、全てのプレイヤーを検索し、生き残っていて2D座標上で最も近くにいるプレイヤーをターゲットとして選びます。
そして、MoveTo()でターゲット方向へ向かせた後に、再びMoveTo()を用いて自分の正面方向へと進ませます。

これを繰り返すことで幼虫はターゲットの方向へと進むという仕組みになっています。
ただ、繰り返すだけでは移動の動作が上手くいかない場合があったので、間に0.2秒間だけ何もしない時間を設けています。

幼虫はこれとは別のスレッドで定期的に爆発の判定を行っています。
この判定のタイミングでプレイヤーが一定以上近くにいた場合は移動を止めて爆発アニメーションのシーケンサーを再生し、一定時間待った後に攻撃用の「爆破の仕掛け」を爆発させます。

また、生きている間は常にダメージ判定用の「爆破の仕掛け」が爆発したかどうかも監視しています。
これが爆発したということは幼虫の体力が尽きたということであり、爆発アニメーションの途中であっても死亡アニメーションへと移行します。

移動の仕組みを見てみると分かる通り、幼虫はとても単純にターゲットの方向をサーチし向かっているだけで、地面や障害物を感知することができません。
例えば段差があっても、そこで落下することはできません。そのため、今回は幼虫の出現する戦闘時のフィールドは全て平らにし、障害物もほとんど置かないようにしています。

この弱点を補完するアイデアも考えていますが、今回は実装の手間などの関係から見送っています。

幼虫AIのロジック構成については以上です。

 

幼虫を生み出すスポーンの仕組み

最後に、幼虫のスポーンとそれを可能にするオブジェクトプーリングの仕組みについて解説します。

プロジェクト制作時点ではVerseはオリジナルのクリエイティブプロップのスポーンはサポートしていませんでした。
また、現在でも単純なプロップのスポーンはサポートしているものの、今回のように仕掛け同士が複雑に構成されたオブジェクトをVerseでスポーンさせ、制御するのは非常に難しいと思います。

そこで幼虫はデザインパターンにおける「オブジェクトプールパターン」を使うことにしました。
これは生成、消滅を繰り返すオブジェクトをあらかじめプールに作成・保存しておき、生成する場合はプールから取り出し、消滅させる場合はプールに戻すことで生成・消滅したように見せるというシステムです。

ゲームプログラミングでは主に最適化の方法として用いられるこのパターンですが、今回のようにオブジェクトのスポーンそのものに制限がかかっている場合も有効です。

 

オブジェクトプールのデバイスの参照構成としては、個々の幼虫を管理しているクリエイティブデバイス(AI用デバイス)を参照するプール用のクリエイティブデバイス(プール用デバイス)を作り、それを更に管理用のクリエイティブデバイス(AI管理用デバイス)で参照してそれぞれの幼虫の集団を管理しています。

レベル上に配置されるクリエイティブデバイスの数が増え、見分けにくく感じるかもしれません。
しかし、このように配列などのまとまったデータを持ったクリエイティブデバイスと、それを参照して実際に処理を行うクリエイティブデバイスは分けることで、管理用デバイスを置くたびにAI用デバイスをいちいち参照する必要がなくなり、管理がよりやりやすくなると思います。