• ゲーム
  • Industry
  • リソース
  • コミュニティ
  • 学習
  • サポート
開発
Unityエンジン
任意のプラットフォーム向けに2Dおよび3Dゲームを構築
ダウンロードプランと価格
収益化
アプリ内課金(IAP)
ストア全体でIAPを発見し、管理する
Mediation
収益を最大化し、マネタイズを最適化する
Ad Quality
アプリのユーザーエクスペリエンスを保護する
Tapjoy
長期的なユーザーの忠誠心を構築する
すべてのマネタイズ製品
詳しく見る
詳しく見る
発見され、モバイルユーザーを獲得する
UnityベクターAI
プレイヤーを適切なゲームに接続する
Auraのオンデバイス広告
ピークエンゲージメント時にデバイス上のユーザーにリーチする
すべての成長製品
活用事例
3Dコラボレーション
リアルタイムで3Dプロジェクトを構築およびレビューする
没入型トレーニング
没入型環境でのトレーニング
顧客体験
インタラクティブな3D体験を作成する
すべての業界ソリューション
業界
製造業
運用の卓越性を達成する
小売
店内体験をオンライン体験に変換する
自動車
革新と車内体験を高める
全業界
技術ライブラリ
ドキュメント
公式ユーザーマニュアルとAPIリファレンス
開発者ツール
リリースバージョンと問題追跡
ロードマップ
今後の機能をレビューする
用語集
技術用語のライブラリ
インサイト
ケーススタディ
実際の成功事例
ベストプラクティスガイド
専門家のヒントとコツ
すべてのリソース
新機能
ブログ
更新情報、情報、技術的ヒント
お知らせ
ニュース、ストーリー、プレスセンター
コミュニティハブ
ディスカッション
議論、問題解決、つながる
イベント
グローバルおよびローカルイベント
コミュニティストーリー
Made with Unity
Unityクリエイターの紹介
ライブストリーム
開発者、クリエイター、インサイダーに参加する
Unity Awards
世界中のUnityクリエイターを祝う
すべてのレベルに対応
Unity Learn
無料でUnityスキルをマスターする
プロフェッショナルトレーニング
Unityトレーナーでチームをレベルアップ
Unity初心者向け
スタートガイド
学習を開始しましょう
Unityエッセンシャルパスウェイ
Unity は初めてですか?旅を始めましょう
ハウツーガイド
実用的なヒントとベストプラクティス
教育
学生向け
キャリアをスタートさせる
教育者向け
教育を大幅に強化
教育機関向けライセンス
Unityの力をあなたの機関に持ち込む
認定教材
Unityのマスタリーを証明する
サポートオプション
ヘルプを得る
Unityで成功するためのサポート
Success Plan
専門的なサポートで目標を早く達成する
FAQ
よくある質問への回答
お問い合わせ
私たちのチームに連絡する
プランと価格
言語設定
  • English
  • Deutsch
  • 日本語
  • Français
  • Português
  • 中文
  • Español
  • Русский
  • 한국어
ソーシャル
通貨
購入
  • プロダクト
  • Unity Ads
  • サブスクリプション
  • Unity Asset Store
  • リセラー
教育
  • 学生
  • 教育関係者
  • 教育機関
  • 認定資格試験
  • 学ぶ
  • スキル開発プログラム
ダウンロード
  • Unity Hub
  • ダウンロードアーカイブ
  • ベータプログラム
Unity Labs
  • ラボ
  • 研究論文
リソース
  • Learn プラットフォーム
  • コミュニティ
  • ドキュメント
  • Unity QA
  • FAQ
  • サービスのステータス
  • ケーススタディ
  • Made with Unity
Unity
  • 当社について
  • ニュースレター
  • ブログ
  • イベント
  • キャリア
  • ヘルプ
  • プレス
  • パートナー
  • 投資家
  • アフィリエイト
  • セキュリティ
  • ソーシャルインパクト
  • インクルージョンとダイバーシティ
  • お問い合わせ
Copyright © 2025 Unity Technologies
  • 法規事項
  • プライバシーポリシー
  • クッキーについて
  • 私の個人情報を販売または共有しないでください

「Unity」の名称、Unity のロゴ、およびその他の Unity の商標は、米国およびその他の国における Unity Technologies またはその関係会社の商標または登録商標です(詳しくはこちら)。その他の名称またはブランドは該当する所有者の商標です。

Hero background image

ScriptableObjectをデリゲート・オブジェクトとして使用する

このページでは、ScriptableObjectをロジックコンテナとして使用する方法を説明します。こうすることで、デリゲート・オブジェクト、つまり必要なときに呼び出せるアクションの小さなバンドルとして扱うことができる。

本書は、電子書籍に付属するデモでUnity開発者を支援するために作成された6つのミニガイドシリーズの第4弾です、 UnityでScriptableObjectsを使用してモジュラーゲームアーキテクチャを作成する.

このデモは、古典的なボールとパドルを使ったアーケード・ゲームのメカニズムにインスパイアされたもので、ScriptableObjectが、テスト可能でスケーラブル、かつデザイナーフレンドリーなコンポーネントの作成にどのように役立つかを示しています。

電子書籍、デモプロジェクト、そしてこれらのミニガイドを合わせると、UnityプロジェクトでScriptableObjectクラスを使用してプログラミングデザインパターンを使用するためのベストプラクティスが提供されます。これらのヒントは、コードを単純化し、メモリ使用量を減らし、コードの再利用性を促進するのに役立つ。

このシリーズには以下の記事が含まれる:

  • Unity ScriptableObjectsデモを始める
  • ScriptableObjectでゲームデータとロジックを分離する
  • UnityプロジェクトでScriptableObjectベースの列挙型を使用する
  • ゲームコードのイベントチャンネルとしてScriptableObjectを使用する
  • ScriptableObjectベースのランタイムセットの使い方
  • 開始前の重要な注意
  • 戦略パターン
  • プラグ可能な動作
  • 例:AudioDelegate
  • パターン・デモ
  • 例:目的システムにおける戦略パターン
  • その他のScriptableObjectリソース

開始前の重要な注意

ScriptableObjectのデモ・プロジェクトやこの一連のミニ・ガイドに飛び込む前に、デザイン・パターンの核心は単なるアイデアに過ぎないということを覚えておいてほしい。すべての状況に当てはまるわけではない。これらのテクニックは、UnityとScriptableObjectの新しい使い方を学ぶのに役立ちます。

それぞれのパターンには長所と短所がある。特定のプロジェクトに有益なものだけを選ぶ。デザイナーはUnity Editorを多用していますか?ScriptableObjectベースのパターンは、開発者とのコラボレーションを助ける良い選択かもしれない。

結局のところ、最良のコード・アーキテクチャとは、あなたのプロジェクトとチームに合ったものなのだ。

ScriptableObject
スクリプタブルオブジェクトには、モノビヘイビア内の "戦略 "が含まれている。

戦略パターン

ストラテジー・パターンを使えば、インターフェイスやベースとなるScriptableObjectクラスを定義し、実行時にそれらのデリゲート・オブジェクトを交換可能にすることができる。

その応用例のひとつが、特定のタスクを実行するためのアルゴリズムをScriptableObjectにカプセル化し、そのScriptableObjectを他の何かのコンテキストで使うというものだ。

例えば、EnemyUnitクラスのAIや経路探索システムを書く場合、経路探索テクニック(A*やダイクストラなど)を持つScriptableObjectを作成するかもしれない。

EnemyUnit自体にはパスファインディングのロジックは含まれていない。その代わりに、別の "戦略 "ScriptableObjectへの参照を保持する。この設計の利点は、オブジェクトを交換するだけで別のアルゴリズムに切り替えられることだ。これは、実行時に異なるビヘイビアを選択する一つの方法である。

MonoBehaviourはタスクを実行する必要がある場合、自身のメソッドではなく、ScriptableObjectの外部メソッドを呼び出します。例えば、ScriptableObjectにはMoveUnitや SetTargetのパブリックメソッドがあり、敵ユニットを駆動したり、目的地を指定したりすることができる。

ダウンロード PaddleBallSO

プラグ可能な動作

抽象的な基底クラスやインターフェイスを使えば、このパターンを改良することができる。そうすることで、そのストラテジーを実装したScriptableObjectを別のものと入れ替えることができる。このホットスワップ可能なScriptableObjectは、それを参照するMonoBehaviourに「プラグイン」します。

ゲームの状況によってEnemyUnitの動作を変更する必要がある場合は、外側のコンテキスト(MonoBehaviour)でその状況をチェックできます。そして、別のScriptableObjectをレスポンスとして差し込むことができる。

実装の詳細をScriptableObjectに分離することで、チーム内の責任分担もスムーズになります。ある開発者はScriptableObject内のアルゴリズムに集中し、別の開発者はMonoBehaviourコンテキストに取り組む。

このプラグイン可能な動作を作るには、次のことを確認する:

  • ストラテジーの基本クラスまたはインターフェイスを定義する:このクラスまたはインターフェースは、ストラテジーを実行するために必要なメソッドとプロパティを含んでいなければならない。
  • ScriptableObject クラスを作成します:それぞれが異なる戦略の実行を提供することができる。例えば、単純なAIアルゴリズムを実装するクラスと、より複雑なアルゴリズムを実装するクラスを作ることができる。
  • ストラテジーを実装する ScriptableObject を作成する:不足しているロジックを入力し、必要な値をインスペクタに入力します。
  • 文脈の中で戦略を使う:MonoBehaviourで、ScriptableObjectに実装されているメソッドやプロパティを呼び出します。これらのメソッドを簡単に呼び出すには、依存関係をパラメータとして渡す。

このようにコードを整理することで、同じ戦略の異なる実装を簡単に切り替えることができる。このプラグイン可能な動作は、デバッグやメンテナンスが容易になる。

例:AudioDelegate

アルゴリズムや戦略は複雑である必要はない。例えば、PaddleBallSOプロジェクトでは、SimpleAudioDelegateでかなり基本的なオーディオ再生システムをデモしている。

抽象クラスAudioDelegateSOは、AudioSourceパラメータを受け付ける単一のPlayメソッドを定義している。具体的な実装はこれを上書きする。

SimpleAudioDelegateSOサブクラスは AudioClips の配列を定義します。ランダムにクリップを選び、オーバーライドされたPlayメソッドの実装を使って再生する。これは、ピッチとボリュームのバリエーションをカスタム範囲内で追加するものです。

わずか数行のコードですが、以下のコード・スニペットでさまざまなオーディオ・エフェクトを作ることができます。

この具体的な例は、オーディオを多用するのには適していないが、ストラテジー・パターンにおけるScriptableObjectの基本的な使い方のデモとして、ここで紹介する。

デザイナーはコードに触れることなく、サウンドエフェクトを表現する様々なScriptableObjectを作成できます。この場合も、ベースとなるScriptableObjectが完成すれば、開発者からのサポートは最小限で済む。

PaddleBallSOでは、レベルの壁にボールが当たった時に再生される新しいサウンドを誰でも設定できるようになりました。デザイナーは、完全にエディター内で仕事をするため、クリエイティブな独立性と柔軟性を得ることができる。このアプローチでは、開発者がすべての設計決定を支援する必要がなくなるため、プログラミング・リソースが解放される。

ダウンロード PaddleBallSO
デレゲート・オブジェクト
AUDIODELEGATESのデモ・シーンでは、スクリプト可能なオブジェクトがどのようにロジックを保持できるかを示している。

パターン・デモ

Patterns demoでオーディオの例も見ることができます。各サウンドは、インスタンス間で若干の違いがありますが、わずかに異なるSimpleAudioDelegateSOアセットから派生します。

この例では、各コーナーにAudioSourceが含まれている。カスタムAudioModifier MonoBehaviourは、ScriptableObjectベースのデリゲートを使ってサウンドを再生します。

ピッチの違いは、各ScriptableObjectアセットの設定(BeepHighPitched_SO、BeepLowPitched_SOなど)に起因するものです。

ScriptableObjectを使ってアクションロジックを制御すれば、デザインチームがアイデアを試しやすくなります。これにより、デザイナーは開発者からより独立して仕事をすることができる。

オブジェクティブ・マネージャー
OBJECTIVEMANAGERのMONOBEHAVIOURは、スクリプト可能なオブジェクトを使用して勝利条件をテストします。

例:目的システムにおける戦略パターン

PaddleBallSOプロジェクトもまた、目的システムに戦略パターンを使用している。これは実行時に変化させる必要はないが、各オブジェクトをScriptableObjectにカプセル化することで、勝ち負けの条件を柔軟にテストできるようになる。

抽象的な基本クラスであるObjectiveSOは、目的の名前や完了したかどうかなどの値を保持します。

ScoreObjectiveSOのような具体的なサブクラスは、各目的を達成するための実際のロジックを実装する。ObjectiveSOのCompleteObjectiveメソッドをオーバーライドして、勝利条件のロジックを追加するのだ。

プレイヤーは特定のスコアを達成したり、一定数の敵を倒したりする必要があるのか?特定の場所に到着する必要があるのか、特定の品物を受け取る必要があるのか。これらは、ScriptableObjectベースの目標となりうる一般的な勝利条件である。

ObjectiveManagerは、ScriptableObjectの大きなコンテキストとして機能する。ObjectiveSOのリストを保持し、各ScriptableObjectが完了したかどうかを判断する。すべてのオブジェクティブSOが完了の状態を示したら、試合終了。

例えば、ScoreObjectiveSOは得点目標を実装する一つの方法を示している:

  • カスタムPlayerScore構造体は、プレーヤーID、インターフェイスのUI要素、および実際のスコア値に一致します。
  • ScoreManagerコンポーネントが更新されるたびに、目的は勝利条件をチェックします。
  • プレイヤーのスコアがm_TargetScore以上であれば、勝利したPlayerScoreオブジェクトをイベントとして送信する。

ObjectiveManagerは、与えられた目標がすべて完了していることだけを気にする。各目標の細部そのものに気づいていないのだ。

繰り返しになるが、ここでの目標はモジュール化である。これにより、既存のものに影響を与えることなく、各ObjectiveSOをカスタマイズすることができます。

PaddleBallSOゲームの目的はただ一つ。どちらかのプレーヤーが勝利スコアのゴールに到達した場合、ゲームプレイは終了する。

しかし、これを拡張したり、目標を組み合わせてより複雑な目標システムを作ることもできる。新しいゲームモード(例えば、時間切れになる前に最低得点を獲得する)を構築できるか実験してみよう。

ロジックは ScriptableObject 内にカプセル化されているため、任意の ObjectiveSO を別のものと入れ替えることができます。新しい勝利条件を作るには、ObjectiveManagerのリストを再設定するだけでよい。ある意味、目標は周囲の文脈に "プラグイン可能 "なのだ。

ObjectiveSOの便利な点は、GameObject間でメッセージを送るためのイベントである。次に、このイベント・ドリブン・アーキテクチャーを実装するためにScriptableObjectsを使用する方法を探ります。

ダウンロード PaddleBallSO
スクリプト可能なアウトロ

その他のScriptableObjectリソース

ScriptableObjectsを使ったデザインパターンについて、電子書籍で詳しく読む UnityでScriptableObjectsを使用してモジュラーゲームアーキテクチャを作成する.また、一般的なUnity開発のデザインパターンについては、以下をご覧ください。 ゲームプログラミングパターンでコードをレベルアップ.

このコンテンツにご満足いただけましたか?

はい!

満足しました

いいえ。

いまいちでした