ボットによる置換
はじめに
以下のような状況では、AIにプレイヤーキャラクターを操作させることが有用な場合があります。
- 進行中のマッチで、ゲームから切断されたプレイヤーを代替する。これによって、プレイヤーがゲームに再接続するまでボットがサポートすることでマッチを公平にしたり、萎え落ちしたプレイヤーの埋め合わせが可能です。
- ゲームセッションを開始するのに十分なプレイヤー数がいない場合に、疑似プレイヤーでルームを埋める。これは、ゲームのリリースサイクル初期段階において、プレイヤーベースがまだ小さい場合は特に重要です。
セットアップ
Quantumでは、AIロジックは各クライアント端末でローカルに実行されます。つまり、「ボットの入力をシミュレートするマスタークライアント」の概念はありません。
AIを実行してゲーム要素を制御するのは大抵シンプルですが、その実装はゲーム固有のものになります。もちろん、AI実装の複雑さは、非常にシンプルなものから非常に複雑なものまで様々です。
最も簡単な方法は、どのエンティティがAI制御されているのかを、任意のタイミングでマークすることです。これは様々な方法で実現できます。
- 「フラグコンポーネント」(例:
component AI {}
)を、必要に応じてエンティティに追加/削除する。システムはAI
コンポーネントを持つすべてのエンティティを反復処理して、操作ロジックを実行できます。 - AI制御をオン/オフするブール値(例:
component MyCharacter { bool ControlledByAI; }
)を使用する。 - Bot SDKのエージェントコンポーネント(HFSM, BTなど)や、様々な追加データを持つ独自実装を含む、AIに特化したコンポーネントを追加する。
AIをいつ実行するべきなのか?は、前述の通りユースケースに依存します。次のセクションでは、この詳しい説明を行います。
ゲームマッチ中に実際のプレイヤーを置き換える
PlayerConnectedSystem
を有効にして、ISignalOnPlayerConnected
/ISignalOnPlayerDisconnected
シグナルに反応することで、これを実現できます。システムと関連するシグナルについての説明は、ドキュメントのプレイヤーをご覧ください。
プレイヤーが切断したら、そのプレイヤーが制御していたエンティティを探し、前述のようにAIをセットアップします。
プレイヤーが再接続したら、そのプレイヤーが制御していたエンティティが存在するかを確認し、AI設定を削除してAIからプレイヤーに制御を戻します。
PlayerInputFlags
は、PlayerConnectedSystem
システムを動作させるために使用されていますが、独立して使用することも可能です。詳細はプレイヤーの入力フラグをご覧ください。
ボットでルームを埋める
このケースでは実際のプレイヤーは関与しません。言い換えれば、実際の人間には制御されないエンティティを作成します。
プレイヤーが関与しないため、接続ロジックも必要ありません。以下サンプルのアルゴリズム/スニペットで示されるように、独自ゲームロジックからエンティティでルームを埋めることができます。
- Quantumシステムでゲーム開始後に待機時間を設けて、プレイヤーの接続とプレイヤーデータの送信が行えるようにします。
- プレイヤー接続時に
OnPlayerDataSet
コールバックを使用して、ゲームに正常に接続/参加したプレイヤー数をゲームステート(例:frame.Global
変数)に保存します。 - 待機時間経過後に以下のように、フレームAPIの想定プレイヤー数から参加プレイヤー数を減算します。
int fillAmount = frame.PlayerCount - frame.Global->ConnectedPlayersCount;
- この結果を使用して
for
ループを実行して、ボットエンティティを作成します。
C#
for(int i = 0; i < fillAmount; i++)
{
// ここで新しいエンティティを作成する
// 前述のように、ボットとしてセットアップする
}
上記スニペットは非常にシンプルなので、ゲームデザインの要件にあわせて調整する必要があります。例えばボットエンティティに、疑似的なプレイヤー情報やチームデータなどの特別な情報を割り当てると便利かもしれません。
作成するボットの選択
ゲームの種類によっては、既知データに基づいて新しいボットを作成すると良いでしょう。例えば、まだ選択されていないキャラクターを選択するボットや、強さが異なるボットなどです。
TIPS: RuntimeConfig
アセットは、エンティティプロトタイプの参照(AssetRefEntityPrototype
)を持つことができるため、そこに選択できる様々なキャラクターを参照させることができます。あるいは、1種類のキャラクターから異なるAI制御(例:強さに基づくステートマシン)のアセットを参照する方法もあります。
プレイヤーとボットのアーキテクチャ
キャラクターはQuantumシステムによって制御されます。通常これらのシステムは、プレイヤーの入力を読み取り、キャラクターのゲームステート(例:移動・回転・攻撃のトリガー)を変更する方法を知っています。
同じキャラクターをAIロジックで制御する方法はいくつかあります。以下は、うまく機能するコードアーキテクチャの例です。
- プレイヤーは元々入力を持ち、
Input
型の構造体のポインタを返すframe.GetPlayerInput(playerIndex)
をポーリングします。 - ボットも独自コンポーネント(
component Bot { Input Input }
)に同じ構造体を持ち、AIロジックを使用して構造体にデータを入力することができます。 - 入力データはキャラクターシステムを実行する前に設定してください。するとシステムでは、誰が入力したかに関係なく入力を取得する方法を知るだけで、エンティティがプレイヤーかボットかを判定するための特殊なチェックを追加する必要が無くなります。
- つまりAIシステムとは、エンティティのステートに直接影響を与えるのではなく、意思決定ロジックに基づいた疑似的な入力を生成することを意味します。
このようなアーキテクチャを使用する利点は、「入力」「プレイヤーとボット」「キャラクター」を明確に分離することで、疎結合なシステムを実現できる点です。
重要:これは単なる提案です。このアーキテクチャはまったく必須ではなく、他の様々な方法でも同じ結果を達成することはできます。
この方法はTwin Stick Shooter Sampleで使用されていて、以下の図のようになります。

注意:「Twin Stick Shooter Sample」は高度なサンプルのため、確認する前にQuantumの基礎を理解しておく必要があります。
Bot SDKによるAI
プロジェクトにAIを導入する場合は、QuantumのBot SDKを検討してみると良いでしょう。Bot SDKは、ステートマシン・ビヘイビアツリー・その他の一般的に使用されるソリューションなど、AIエージェントを作成するためのエディターツールのQuantumコードがセットになっています。
Bot SDKの詳細は、こちらをご覧ください。
Back to top