※編集履歴
- 2018/11/21 「Componentが複数の場合の実行順」について誤認していたため書き直しました
- 2018/11/21 サンプルコードを置いておきます
- 2018/11/22 「複数のComponentのイベント関数の実行順」について別の記事に書き直しました
目次
検証環境
Unity:2017.4.5f1
主な関数の順番
- Awake : one time
- OnEnable : each time object is enabled
- Start : one time
- Update : iteration
- OnDisable : each time object is disabled
- OnDestroy : one time
GameObjectとComponentがactive/non-activeの時に呼ばれる関数
Awake/OnDestroyは、GameObjectに紐づき、他はComponentに紐づくっぽい。
AwakeはGameObjectが有効になった時に最初に1度だけ呼ばれる。Componentに紐づくその他の関数は、GameObjectの初期化であるAwakeをトリガーに呼ばれるようになる。
activeかどうかは自身のGameObject(activeSelf)に加え、親の影響(activeInHierarchy )も受ける。
bool isActiveFirst; void Awake() { Debug.Log("Awake"); } void OnEnable() { isActiveFirst = true; Debug.Log("OnEnable"); } void Start() { Debug.Log("Start"); } void Update() { if (isActiveFirst) { isActiveFirst = false; Debug.Log("Update"); } } void OnDisable() { Debug.Log("OnDisable"); } void OnDestroy() { Debug.Log("OnDestroy"); }
Initial state
- GameObject : non-active / Component : non-active
- not called
- GameObject : non-active / Component : active
- not called
- GameObject : active / Component : non-active
- Awake
- GameObject : active / Component : active
- Awake
- OnEnable
- Start
- Update
Activate
- GameObject : non-active / Component : non-active
- not called
- GameObject : active / Component : non-active
- Awake
- GameObject : active / Component : active
- OnEnable
- Start
- Update
Disable/Enable
- GameObject : active / Component : active
- Awake
- OnEnable
- Start
- Update
- GameObject : active / Component : non-active | GameObject : non-active / Component : active
- OnDisable
- GameObject : active / Component : active
- OnEnable
- Update
Destroy
- GameObject : active / Component : active
- Awake
- OnEnable
- Start
- Update
- GameObject : destroy
- OnDisable
- OnDestroy
StartのCoroutine(コルーチン)を使った場合に呼ばれる順番
Coroutineの再開はUpdateが呼ばれた後に実行される。
IEnumerator Start() { Debug.Log("Start1"); yield return null; Debug.Log("Start2"); } int counter = 0; void Update() { if (counter < 3) { counter++; Debug.Log("Update" + counter); } }
- Start1
- Update1
- Update2
- Start2
- Update3
StartのCoroutine(コルーチン)完了後にUpdateを開始する
CoroutineはGameObjectが有効な時に実行され、Coroutineが開始された後GameObjectが無効になるとCoroutineも無効になる。CoroutineはUpdateと異なり、1度開始されるとComponentの有効/無効とは関係なく動作する。
IEnumerator Start() { var i = 1; Debug.Log("Start" + i); enabled = false; foreach (var x in Enumerable.Range(0, 3)) { i++; Debug.Log("Start" + i); yield return null; } enabled = true; i++; Debug.Log("Start" + i); } int counter = 0; void Update() { if (counter < 3) { counter++; Debug.Log("Update" + counter); } }
- Start1
- Start2
- Start3
- Start4
- Start5
- Update1
- Update2
- Update3
イベント関数以外の関数
独自に実装したメソッドの呼び出しは、GameObject/Component の有効/無効とは関係なく実行できる。これはAwakeが呼ばれていないGameObjectやComponentでもメソッドの呼び出しは可能であることも意味する。
public Script4Sub script; bool done; void Update() { if (!done) { done = true; Debug.Log("Update"); script.WriteLog(); Debug.Log("- GameObject : non-active / Component : active"); script.gameObject.SetActive(false); script.WriteLog(); Debug.Log("- GameObject : non-active / Component : non-active"); script.enabled = false; script.WriteLog(); } }
public void WriteLog() { Debug.Log("GameObject is active ? :" + gameObject.activeSelf); Debug.Log("Component is active ? :" + enabled); }
- GameObject : active / Component : active
- GameObject is active ? : True
- Component is active ? : True
- GameObject : non-active / Component : active
- GameObject is active ? : False
- Component is active ? : True
- GameObject : non-active / Component : non-active
- GameObject is active ? : False
- Component is active ? : False