UnityUnityメモ

UnityでAIを実装!ビヘイビアツリーと状態マシンで賢いNPCを作る方法

Unity

1. はじめに

ゲームの世界では、プレイヤーだけでなく、敵キャラ(NPC)や仲間キャラがどのように動くかがゲームの面白さを左右します。例えば、敵がプレイヤーを発見すると追いかけてきたり、プレイヤーが攻撃すると逃げたりするなど、NPCの動きを「知的」にすることがAI(人工知能)の役割です。

Unityには、こうしたNPCの行動を制御するためにさまざまな方法がありますが、その中でも特に人気なのが**「状態マシン(State Machine)」と「ビヘイビアツリー(Behavior Tree)」**です。

これらの手法を使うと、以下のようなゲームAIを作ることができます。

RPGの敵AI → プレイヤーを見つけると攻撃し、HPが減ると逃げる
ステルスゲームの警備兵 → 一定ルートを巡回し、異常を感知すると警戒モードになる
マルチプレイヤーゲームのBOT → プレイヤーの動きを学習し、最適な行動をとる

本記事では、UnityでAIを実装する方法として、状態マシンとビヘイビアツリーの基本概念から、実際の実装方法までを解説します。
これを読めば、「NPCがランダムに動く」だけではなく、プレイヤーの行動に応じて適切に判断するAIを作れるようになります!

それでは、まずは「状態マシン」について詳しく見ていきましょう。




2. 状態マシン(State Machine)とは?

ゲーム開発では、キャラクターやNPC(Non-Player Character)が特定の状況に応じて適切に行動することが求められます。例えば、敵キャラクターが「プレイヤーを発見 → 追いかける → 攻撃する → 逃げる」といった一連の動きを自然にこなす必要があります。
このような動作を管理するために役立つのが 「状態マシン(State Machine)」 です。


状態マシンの基本概念

状態マシン(Finite State Machine: FSM)は、オブジェクトがいくつかの 「状態(State)」 を持ち、それらを 「遷移(Transition)」 によって切り替える仕組みです。
例えば、敵キャラクターのAIを考えてみましょう。

状態(State)
巡回中マップを歩き回る
警戒中プレイヤーが近くにいると気づく
追跡中プレイヤーに向かって移動する
攻撃中近距離で攻撃を繰り出す
逃走中HPが減ったら逃げる

このように、敵キャラは状況に応じて状態を変化させながら行動します。


ゲームAIでの一般的な使い方

状態マシンは、ゲームAIの管理に広く使われています。例えば:

  • 敵AI(プレイヤーを発見して追いかける、攻撃する、逃げる)
  • プレイヤーのアニメーション管理(歩く、走る、ジャンプ、攻撃)
  • ゲーム内のUI状態管理(メニューを開く、設定画面に移動する)

状態が明確に分かれているため、管理しやすく、バグが発生しにくいのが特徴です。


Unityでの実装方法

では、Unityでシンプルな状態マシンを実装してみましょう!

1. 状態を定義する

まずは、状態を管理する 「EnemyState」 という列挙型(enum)を作成します。

public enum EnemyState
{
Patrol, // 巡回中
Alert, // 警戒中
Chase, // 追跡中
Attack, // 攻撃中
Flee // 逃走中
}

この列挙型を使って、敵キャラの現在の状態を管理します。


2. 状態遷移を管理する

次に、敵キャラの状態を管理するスクリプトを作成します。

手順:

  1. プロジェクトウィンドウを右クリック
  2. 「Create」→「C# Script」を選択
  3. スクリプト名を「EnemyAI」に設定

そして、以下のコードを入力してください。

using UnityEngine;

public class EnemyAI : MonoBehaviour
{
public EnemyState currentState; // 現在の状態
public Transform player; // プレイヤーのTransform
public float detectionRange = 5f; // プレイヤーを見つける範囲

void Start()
{
currentState = EnemyState.Patrol; // 初期状態を巡回に設定
}

void Update()
{
switch (currentState)
{
case EnemyState.Patrol:
Patrol();
break;
case EnemyState.Alert:
Alert();
break;
case EnemyState.Chase:
Chase();
break;
case EnemyState.Attack:
Attack();
break;
case EnemyState.Flee:
Flee();
break;
}
}

void Patrol()
{
Debug.Log("巡回中...");
if (Vector3.Distance(transform.position, player.position) < detectionRange)
{
currentState = EnemyState.Alert;
}
}

void Alert()
{
Debug.Log("警戒中...");
currentState = EnemyState.Chase; // すぐに追跡状態へ移行
}

void Chase()
{
Debug.Log("追跡中...");
transform.position = Vector3.MoveTowards(transform.position, player.position, Time.deltaTime * 2);
if (Vector3.Distance(transform.position, player.position) < 1f)
{
currentState = EnemyState.Attack;
}
}

void Attack()
{
Debug.Log("攻撃中!");
// ここで攻撃の処理を書く
}

void Flee()
{
Debug.Log("逃走中...");
// 逃げる処理を追加
}
}

3. スクリプトを敵キャラにアタッチ

スクリプトを作成したら、敵キャラクターのオブジェクトにドラッグ&ドロップ してアタッチしてください。

また、Inspector(インスペクター)で「Player」フィールドにプレイヤーオブジェクトを設定 しておきましょう。


状態マシンを活用するメリット

シンプルで管理しやすい → 状態が明確なので、処理を分けやすい。

バグを減らせる → 予期しない動作を防ぐため、デバッグがしやすい。

拡張が容易 → 新しい状態を追加するだけで、簡単に機能を増やせる。


まとめ

  • 状態マシンは、キャラクターの行動管理に最適!
  • 「状態」「遷移」 を決めることで、シンプルかつ明確なAIが作れる。
  • UnityでC#スクリプトを使って簡単に実装可能!

次のステップでは、ビヘイビアツリーを活用してより複雑なAIを作る方法 を解説します! 🎮✨




3. ビヘイビアツリー(Behavior Tree)とは?

ビヘイビアツリー(Behavior Tree)は、NPCの行動を制御するための手法の一つで、ゲームAIで広く使われています。特に、複雑なAIのロジックを整理しやすく、直感的に管理できるのが特徴です。では、ビヘイビアツリーがどのように機能するのかを見ていきましょう!


ビヘイビアツリーの基本概念

ビヘイビアツリーは「木構造」のデータ構造を使い、親ノード(ルート)から順番に子ノードへと処理が流れる仕組みになっています。これにより、NPCの行動を階層的に管理することができます。

ビヘイビアツリーの主な要素

  1. ルートノード(Root)
    • ツリーの一番上に位置し、全体のエントリーポイントになるノード。
  2. コンポジットノード(Composite)
    • 選択ノード(Selector): 子ノードを順番にチェックし、成功するノードが見つかったら処理を終了する
    • シーケンスノード(Sequence): すべての子ノードを順番に実行し、途中で失敗したら処理を終了する
  3. デコレーターノード(Decorator)
    • 子ノードの動作を変更する(例:「何回も繰り返す」など)
  4. リーフノード(Leaf)
    • アクションノード: 実際にNPCの行動を実行する(例:「敵を攻撃する」「プレイヤーを追いかける」など)
    • 条件ノード(Condition): AIの判断を行う(例:「プレイヤーが見えているか?」など)

状態マシンとの違い

状態マシン(State Machine)とビヘイビアツリーは、どちらもNPCの行動制御に使われますが、考え方が異なります。

比較項目状態マシン(State Machine)ビヘイビアツリー(Behavior Tree)
構造「状態」と「遷移」の組み合わせ階層構造(ツリー)
記述方法明示的な状態遷移を定義ルールベースの選択
メリットシンプルで軽量複雑なAIの管理がしやすい
デメリット状態が増えると管理が難しくなるツリーが大きくなりすぎると処理が重くなる

例えば、「敵キャラがプレイヤーを見つけたら攻撃する」というAIを作る場合、**状態マシンでは「待機」→「追跡」→「攻撃」という順番の遷移を作ります。一方、ビヘイビアツリーでは「プレイヤーが見えているか?」→「見えていたら追跡する」→「攻撃する」**と、条件に応じて処理を進める形になります。




Unityでのビヘイビアツリーの実装

Unityでは、**「Behavior Designer」「NodeCanvas」**などのアセットを使えば、ビジュアルエディターで簡単にビヘイビアツリーを作成できます。しかし、基本的なビヘイビアツリーはC#スクリプトで自作することも可能です。

シンプルなビヘイビアツリーの例

using UnityEngine;

public class EnemyAI : MonoBehaviour
{
public Transform player;
public float attackRange = 2.0f;
public float chaseRange = 5.0f;

private void Update()
{
if (CanSeePlayer()) // プレイヤーが見えているか?
{
if (IsInAttackRange()) // 攻撃範囲内か?
{
Attack();
}
else
{
Chase();
}
}
else
{
Patrol();
}
}

private bool CanSeePlayer()
{
return Vector3.Distance(transform.position, player.position) < chaseRange;
}

private bool IsInAttackRange()
{
return Vector3.Distance(transform.position, player.position) < attackRange;
}

private void Attack()
{
Debug.Log("敵が攻撃する!");
}

private void Chase()
{
Debug.Log("敵が追跡する!");
}

private void Patrol()
{
Debug.Log("敵が巡回する!");
}
}

このコードでは、「プレイヤーが見えるかどうか」を判断し、攻撃するか追跡するかを決めるシンプルなAIを作っています。これはビヘイビアツリーの考え方に近く、条件に応じて処理が流れていく形になっています。


まとめ

  • ビヘイビアツリーは、NPCの行動をツリー構造で管理する手法
  • コンポジットノード、デコレーターノード、リーフノードを使ってAIを構築
  • 状態マシンと比べて、柔軟で複雑なAIの作成が可能
  • Unityでは専用アセットやC#スクリプトで実装可能

次のステップとして、ビヘイビアツリーを実際にUnityで作成し、状態マシンと組み合わせる方法を学んでいきましょう!



4. Unityでの実装手順

ここからは、Unityで実際にAIを実装する方法を解説していきます。
今回は 状態マシン(State Machine)とビヘイビアツリー(Behavior Tree) を組み合わせて、シンプルなNPCのAIを作ってみましょう!


ステップ1: 必要なアセットを準備する

まず、UnityでAIを動かすための基本環境を整えます。

① UnityのNavMeshを設定する

NPCを移動させるために NavMesh を使用します。

  1. シーン内に地面(Planeなど)を配置
    • ヒエラルキーウィンドウで「右クリック」 → 「3D Object」 → 「Plane」を選択
    • Planeのサイズを適宜調整
  2. NavMeshをベイクする
    • 「Window」 → 「AI」 → 「Navigation」を開く
    • 地面オブジェクトを選択 し、「Navigation」ウィンドウの「Bake」タブで「Bake」をクリック
  3. NPC用のキャラクターを作成
    • 「右クリック」 → 「3D Object」 → 「Capsule」を選択
    • 「NavMeshAgent」コンポーネントをアタッチ(インスペクターの「Add Component」から追加

これで、NPCがNavMeshを使って移動できる準備ができました!


ステップ2: シンプルな状態マシンを作る

状態マシンをC#スクリプトで作成し、NPCの動きを制御します。

① 状態マシンスクリプトを作成

  1. プロジェクトウィンドウを右クリック → 「Create」 → 「C# Script」を選択
  2. スクリプト名を StateMachine に変更し、以下のコードを入力
using UnityEngine;

public abstract class State
{
public abstract void Enter();
public abstract void Update();
public abstract void Exit();
}

🔍 ポイント:

  • State クラスはAIの行動を管理するベースクラス
  • Enter() は状態が切り替わった時に呼ばれる
  • Update() は状態ごとの挙動を記述
  • Exit() は状態が終了するときの処理



ステップ3: ビヘイビアツリーを作成する

状態マシンだけでは単調な動きになりがちなので、ビヘイビアツリーを組み合わせてAIの行動を強化 します!

① ビヘイビアツリーのノードを作成

  1. プロジェクトウィンドウを右クリック → 「Create」 → 「C# Script」
  2. スクリプト名を BehaviorTree に変更し、以下のコードを入力
using UnityEngine;

public abstract class Node
{
public abstract bool Execute();
}
  1. 動作するノード(例: Patrol, Chase, Attack)を作成
public class PatrolNode : Node
{
public override bool Execute()
{
Debug.Log("NPC is patrolling...");
return true; // 成功
}
}
  1. 状態マシンと組み合わせる
public class AIController : MonoBehaviour
{
private State currentState;
private Node behaviorTreeRoot;

void Start()
{
behaviorTreeRoot = new PatrolNode();
}

void Update()
{
behaviorTreeRoot.Execute();
}
}

🔍 ポイント:

  • Node クラスを基に、NPCの行動ごとにノードを作成
  • behaviorTreeRoot.Execute() を実行し、行動を決定

ステップ4: デバッグと調整

最後に、デバッグを行いながらNPCの動きを確認します。

① NPCの動きを確認する

  1. Unityエディターで 再生ボタン(▶) を押す
  2. Consoleに「NPC is patrolling…」と表示される か確認
  3. AIの動作を変更する場合は、BehaviorTree のノードを入れ替えて調整

まとめ

この手順で、状態マシンとビヘイビアツリーを活用したシンプルなAI を作成できました!

  • 状態マシンでNPCの基本行動を管理
  • ビヘイビアツリーで行動の選択を強化
  • NavMeshを使ってNPCを移動可能にする

ここから、より複雑なAIを作成するために 攻撃・追跡などのノードを追加 したり、アニメーションを組み合わせる ことで、よりリアルなAIが作れるようになります!次のステップとして、AIの行動をプレイヤーの動きに応じて変化させる方法 を学ぶと、さらに面白いゲームが作れるようになりますよ!




5. 応用編:状態マシンとビヘイビアツリーを組み合わせるメリット

ここまでで、状態マシンとビヘイビアツリーの基本的な使い方を学びました。でも、実際のゲームAIではどちらか一方を使うだけではなく、両方を組み合わせることでより賢いNPCを作ることができます。

このステップでは、状態マシンとビヘイビアツリーのハイブリッドな使い方や、さらに高度なAIの作り方について紹介します。


① 状態マシンとビヘイビアツリーを組み合わせるメリット

「状態マシンは細かい動作に向いているが、大きな意思決定には向かない」
一方、「ビヘイビアツリーは大きな意思決定に向いているが、細かい動作には向かない」 という特徴があります。

例えば、敵のAIを作る場合:

  • 状態マシン を使って「巡回」「戦闘」「逃走」のような大きな行動の遷移を管理
  • ビヘイビアツリー を使って、「どのルートを巡回するか?」「どの攻撃を選択するか?」など、細かい動作の制御を行う

これによって、単純なAIではなく、より賢く自然に動くNPCを作ることができます。


② 状態マシンとビヘイビアツリーを組み合わせてみよう

では、状態マシンをベースにして、ビヘイビアツリーで細かい動作を制御する方法を試してみましょう。

例:敵キャラクターのAI

基本的な行動パターン

  1. 巡回(Patrol)
  2. プレイヤーを発見(Detect)
  3. 戦闘(Attack)
  4. 逃走(Flee)

この4つの行動を 状態マシン(State Machine) で管理し、それぞれの行動の中で具体的な動作を ビヘイビアツリー(Behavior Tree) で制御します。

C#で状態マシンを作る

まず、状態管理の基本 を作ります。

using UnityEngine;

public class EnemyAI : MonoBehaviour
{
public enum State { Patrol, Detect, Attack, Flee }
public State currentState;

private void Update()
{
switch (currentState)
{
case State.Patrol:
Patrol();
break;
case State.Detect:
Detect();
break;
case State.Attack:
Attack();
break;
case State.Flee:
Flee();
break;
}
}

void Patrol()
{
// 巡回行動のロジック
}

void Detect()
{
// プレイヤー発見時のロジック
}

void Attack()
{
// 攻撃行動のロジック
}

void Flee()
{
// 逃走行動のロジック
}
}



ビヘイビアツリーで戦闘の動作を作る

次に、「Attack」状態の中でどのように攻撃するか を決めるためにビヘイビアツリーを実装します。

using UnityEngine;
using BehaviorDesigner.Runtime;
using BehaviorDesigner.Runtime.Tasks;

public class AttackBehavior : Action
{
public float attackRange = 2.0f;
public GameObject target;

public override TaskStatus OnUpdate()
{
if (target == null)
return TaskStatus.Failure;

float distance = Vector3.Distance(transform.position, target.transform.position);

if (distance < attackRange)
{
Debug.Log("敵が攻撃した!");
return TaskStatus.Success;
}
else
{
Debug.Log("敵が攻撃範囲外");
return TaskStatus.Failure;
}
}
}

③ より複雑なAIを作るには?

状態マシンとビヘイビアツリーを組み合わせるだけでなく、さらに複雑なAIを作る方法もあります。

NavMeshを使って移動を最適化
AIのキャラクターが障害物を避けながら移動するには、NavMesh を使うのがオススメです。

ML-Agentsを使って学習するNPCを作る
UnityのML-Agentsを使えば、機械学習を導入して、AIがプレイヤーの行動に適応する仕組みを作れます。

Sensor Toolkitを使って感知能力を強化
敵が視界や聴覚を持つようにし、よりリアルなAIを実装できます。


④ AI向けのおすすめUnityアセット

AIを作るのに役立つアセットを紹介します。

アセット名価格説明
Behavior Designer有料ビヘイビアツリーをGUIで作成できる
NodeCanvas有料状態マシンとビヘイビアツリーを統合できるツール
Emerald AI有料簡単にAIを作成できるオールインワンソリューション

まとめ

  • 状態マシンは大まかな行動の管理に向いている
  • ビヘイビアツリーは詳細な動作の制御に向いている
  • 両方を組み合わせることで、より賢いNPCを作成できる
  • Unityアセットを活用すれば、さらに高度なAIを実装可能

これで、状態マシンとビヘイビアツリーを組み合わせた応用的なAIの作り方を紹介しました!
次のステップとして、NavMeshやML-Agentsを活用してより高度なAIを作るのも面白いですね!🔥




6. まとめ

UnityでAIを実装する方法として、「状態マシン(State Machine)」と「ビヘイビアツリー(Behavior Tree)」の2つの手法を紹介しました。どちらもゲーム開発において重要な役割を果たしますが、それぞれの特徴を理解し、適切に使い分けることがポイントです。

状態マシン(State Machine)のポイント

  • シンプルで直感的なAIの制御が可能
  • 小規模なプロジェクトや単純なAIの行動に最適
  • 状態が増えると管理が複雑になる可能性あり

ビヘイビアツリー(Behavior Tree)のポイント

  • AIの行動をツリー構造で管理しやすい
  • より高度で拡張性のあるAIの設計が可能
  • 大規模なゲームや複雑なNPCの行動を作るのに向いている

「どちらを使うべきか?」
→ 小規模なAIや単純な処理なら「状態マシン」、複雑なAIを作りたいなら「ビヘイビアツリー」がオススメです!
ただし、両者を組み合わせて使うことで、より柔軟で賢いNPCを作ることも可能です。


次のステップ

AIの基本を理解したら、さらに発展させていきましょう!例えば:

  • NavMeshを活用して、NPCの移動を最適化
  • ML-Agentsを導入して、機械学習を使ったAIの強化
  • センサーロジックを追加して、よりリアルな行動パターンを実装

AIの仕組みを学ぶことで、ゲームに深みを加えることができます。
ぜひ、今回学んだことを活かして、より賢いNPCを作ってみてください!


タイトルとURLをコピーしました