Unity Call Order in Depth

FreeTale
4 min readSep 20, 2020

--

This post dedicate for how Unity ordered awake object while instancing, scene change, Coroutine, ExecuteInEditMode, ExecuteAlways and hot reload both editmode and play mode.

If you search about game loop or excution order you see find this official post but not has many description about behaviour. only tell me do self initialize in Awake and another initialize in Start today I digging up that behaviour.

Photo by Roman Synkevych on Unsplash

In Runtime

Awake call first when scene loaded whatever scene component enable or disable, OnEnable call right after awake called if component enable. If GameObject not enable (in hierarchy) they will not call. When Instantiate thay call immediately if GameObject enable.

Start call after all object already awake and before Update when Instantiate thay call before next frame Update.

OnDisable call immediately when component disable also call immediately when object flag by Destroy.

OnDestroy call when component actually destroy that mean if use Destroy this callback run at end of frame, if use DestroyImmediate will call at after all OnDisable called.

StartCoroutinerun code immediately untils reach first yield. StopCoroutine require referance to same IEnumerator object. If use string overload to start, need string to stop. If disable GameObject all coroutines are stop. coroutine cannot start if GameObjet is inactive.

Call order spacify when GameObject add to Scene in reverse order not by order in scene. Unity not guarantee that component call order at all.

If set Excution Order in project setting they will call first regardless GameObject that component attach to. for example component A and B has order 0 and 100, all instance of component A will call Awake and OnEnable before any component B call Awake and OnEnable.

RuntimeInitializeOnLoadMethod run in this order SubsystemRegistration AfterAssembliesLoaded BeforeSplashScreen BeforeSceneLoad scene load and awake all object AfterSceneLoad than start

In Editor

ExecuteInEditMode and ExecuteAlways attribute (official referance) different is ExecuteInEditModewill force exit prefab edit mode when change to play mode.

In edit mode Awake, Start, OnEnable, OnDisable, OnDestroy work same as play mode but Update, LateUpdate call only when any change, and call one when application focus. when enter play mode Object will destroy and when exit play mode Object will instance (and call Awake) again. if attribute use in super class, subclass also recive effect too even no attribute specify.

When create prefab GameObject will disable and enable again. When enter prefab edit mode a new instance (in prefab) awake, and another one in scene still alive not disable or destroy.

In hot reload both edit mode and play mode OnDisable will call before unity serialize object then reload assembly and call OnEnable again, no Awake or Start call here, all field show in debug inspector will survive in hot reload (include private field that not show in normal inspector) all static field not survive. I found useful blog post here that explain some hot reload behaviour.

In multiple scene editing Unity call active scene first then call another scene(s) in order from top to bottom. On normal call step (Awake, Start, OnEnable, OnDisable, OnDestroy) call order sort by Scene then ExcutionOrder then Object, but update call step (Update, FixedUpdate, LateUpdate) call order sort by ExcutionOrder then Scene then Object.

RuntimeInitializeOnLoad.AfterSceneLoad call after active scene awake and before another scene awake.

About Testing

I use Unity version 2019.4.8f1 with NaughtyAttributes for some button in editor.

I set target frame rate to 15 for reduce spaming on update loop, also fixed time step to 0.1 for reduce fixed update spam

This class allow me to inspect what object are log this message, to understand calling order

Some empty sub class dedicate for component test include ExecutionOrder, ExecuteInEditMode, ExecuteAlways and Inheritance test.

Don’t forgot to check execution order in project setting bacause DefualtExecutionOrder effect only new class add, if unity generated .meta file attribute has no effect.

Script execution order in project setting. has ExecutionOrderTestB and EditModeTestB value 100 and 200 in order

and scene setup like this

Scene setup, In hierachy window has Scene A B C and Object AB, In inspector has component Execution OrderTest A B

RuntimeInitializeOnLoadMethod has one component to log all step here.

When press play button.

console log

For instantiate, destroy and coroutine test I has dedicate component for this work.

Component view in Inpector

For hot reload test I has a button for change value at runtime. when testing just put some space in code and save. Unity will recomplie and reload assembly.

Hot reload test in Inspector

Full project file upload at github for extend self testing

Have no Bug!

--

--

No responses yet