Unityでゲーム開発を始めると、必ず出てくるのが「ライフサイクルメソッド」の話。Awake()
や Start()
、Update()
や OnEnable()
など、スクリプトの中で使われる“おまじない”のようなメソッドたちです。
なんとなく書いて動いてしまうけど、それぞれが「いつ呼ばれるのか」「何をするべきか」を理解しておくと、コードの見通しやデバッグ効率がぐっと上がります。
今回は、Unityスクリプトのライフサイクルについて、順を追って丁寧に解説していきます。
■こちらのエントリーも合わせてどうぞ!
スクリプトのライフサイクルとは?
「ライフサイクル」とは、ゲームオブジェクトが生成されてから破棄されるまでの間に、Unityが自動で呼び出す一連のメソッドの流れのことです。
たとえば、シーン開始時に初期化される Awake()
や Start()
、
毎フレーム呼び出される Update()
、
ゲームオブジェクトが非表示になったときに呼ばれる OnDisable()
などがその代表です。
それぞれのメソッドが「いつ」「どんな順番で」呼ばれるのかを知っておくことで、意図した動作を書けるようになります。
シーン開始時の処理の流れ
実はAwakeより前がある
Unityのシーンが読み込まれたとき、最初に呼び出されるのは Awake()
…
と思いきや、そのさらに前に呼ばれる特別なメソッドがあります。
それが、[RuntimeInitializeOnLoadMethod]
属性をつけた静的メソッドです。
[RuntimeInitializeOnLoadMethod(RuntimeInitializeLoadType.BeforeSceneLoad)]
static void OnBeforeSceneLoad()
{
Debug.Log("Awakeより絶対先に呼ばれるマン");
}
このようにして定義されたメソッドは、シーンロード直後のどのオブジェクトよりも先に実行されるため、
・ゲーム起動直後に一度だけグローバルな初期化をしたい
・マネージャー系のシングルトンを確実に用意しておきたい
という場面で活用されます。
そのあと、以下の順番で通常のライフサイクルが流れていきます。
通常のライフサイクル
- Awake
スクリプトがアクティブな状態で読み込まれた直後に呼ばれる初期化メソッド。
自分自身の内部状態を初期化するのに最適です。 - OnEnable
オブジェクトが有効化された瞬間に呼ばれます。
ボタンなどのUIで再表示時にリスナーを再登録するなど、有効状態に応じた処理をここに書きます。 - Start
Awake()
やOnEnable()
のあと、最初のフレームの手前で一度だけ呼ばれるメソッド。
他オブジェクトとの連携や外部リソースの利用など、他の準備が終わっている前提の処理に向いています。 - Update
ここからが毎フレーム実行される処理です。
キャラクターの移動、入力の取得、カウントダウンの処理などが典型例です。 - LastUpdate
Update()
の後に呼ばれる処理。
カメラ制御や、他オブジェクトの動きに追従したい場合はここを使うとズレが出にくくなります。
一時的な状態変化に反応する:OnDisableとOnEnable
オブジェクトが非アクティブになると、OnDisable()
が呼ばれます。
逆に再アクティブ化されたときには OnEnable()
が再度呼び出される仕組みです。
これにより、一時停止中のUI処理の停止や、必要なタイミングでのイベント再登録など、状態の切り替えに応じた処理が可能になります。
ゲーム終了時:OnDestroy
シーンがアンロードされたり、GameObjectがDestroyされるとき、OnDestroy()
が呼び出されます。
イベントの解除、シングルトンの破棄、データの書き出しなど、後処理や後始末の最終ポイントとして利用されます。
ResetはInspector専用の初期化
Reset()
は少し特殊で、スクリプトをInspectorにドラッグ&ドロップしたときに一度だけ呼ばれる開発補助用のメソッドです。
プレイ中には呼ばれないため、初期値の自動設定などで使われます。
結論:流れを知ればUnityはもっと思い通りになる
Unityのライフサイクルを把握しておくだけで、
「なぜかnullになる」「思ったより早く呼ばれている」「処理がかぶっている」といったよくあるミスが減らせます。
最後にまとめておくと、シーン開始直後の呼び出し順は以下のようになります:
RuntimeInitializeOnLoadMethod
→Awake
→OnEnable
→Start
→Update
→LateUpdate
そして、状態変化で OnDisable
や OnEnable
、オブジェクト破棄時に OnDestroy
が実行されていきます。
Unityの挙動がなんとなくではなく「意図通り」に動くようになるには、このライフサイクルの理解が必須です。
今後もっと複雑な処理や状態遷移を作っていくためにも、ぜひこの基本を押さえておきましょう。