# Unity でのゲーム開発で ECS の思想を取り入れた話
Operation R の情報ページは こちら
# はじめに
Unity で個人開発したゲーム One Librarian の開発では、コードを書き進めていくにつれて、クラスの依存関係が複雑になってしまいました。 その反省から、デザインパターンなどを勉強して、Operation R を開発をする際に設計をしてみました。
# オブジェクト指向はゲームに向かない?
筆者はゲーム作りを通して、オブジェクト指向を学んでいたのですが、継承を使った設計ではどうも上手くいかないことがありました。
そこで下記の記事を見つけました。
オブジェクト指向でゲームを作るのをやめよう (opens new window)
この記事では、ゲームプログラミングにおいて、継承の代わりにコンポジションを扱うことの有用性について話しています。 その際に ECS について少しだけ触れられており、もっと深掘りすることにしました。
筆者はコンポジションのことをよく知らなかったのですが、広義の意味の委譲として考えられるようです。
【Unity】ゲームにおける委譲と継承、その違いと使い分け【タワーディフェンス】 (opens new window)
# ECSとは
ECS とは Entity component system の略で、エンティティ、コンポーネント、システムの 3 つからなるアーキテクチャパターン(設計の考え方のようなもの)です。 データ指向型の設計で用いられることが多いようです。
Entity Component Systemについてまとめてみる (opens new window)
詳しくは上記の記事をご参考ください。
# 📜 設計をする
# レイヤーを分ける
エンティティ層、コンポーネント層、システム層のほかにアプリケーション層、データ層の 5 層のレイヤーに分けました。
依存方向は上から下に一方向になっています。
アプリケーション層とエンティティ層に MonoBehaviour を継承させます。
# システム間通信
エンティティ・コンポーネント・システム - Wikipedia (opens new window)
Wikipedia にはシステム間でのデータの送信方法として Observer パターンが紹介されていますが、今回は出版-購読型モデル (opens new window)を採用しました。これを採用することにより、出版側と講読側の関係が疎になり、相手の状態に左右されずに正常に動作し続けることが可能になります。
using System;
public class GameEvent
{
public Action<int> Attack;
public Action<int> Damage;
}
public class GameRule
{
GameEvent _gameEvent;
public void SetEvent()
{
_gameEvent.Attack += Damage;
void Damage()
{
_gameEvent.Damage?.Invoke();
}
}
GameRule の中身を書きかえるだけで、簡単にシステム間のやりとりを組み替えることができます。
# システム、エンティティ間通信
システム間通信ではデータの送信方法として出版-講読型モデルを採用しましたが、こちらでは Observer パターンを採用します。
# 🖋️ PlantUMLを用いてクラス図を書く
Visual Studio Code で UML を描こう! (opens new window)
上記の記事を参考にして、クラス図を作成します。
β 版時点でのクラス図はこんな感じです。 PlantUML で綺麗にクラス図を書くのは、なかなか難しいですね...