Search Unity

When is OnDestroy() called?

Discussion in 'Scripting' started by angrypenguin, Nov 15, 2014.

  1. angrypenguin

    angrypenguin

    Joined:
    Dec 29, 2011
    Posts:
    15,620
    Is OnDestroy() called on a MonoBehaviour immediately when Destroy(...) is called for its GameObject, or is it delayed until later in the frame when the destruction actually happens?

    I've got a few properties I've got to change when certain objects are destroyed. Since other stuff in the same frame will rely upon those changes I need to know whether OnDestroy() gets called immediately (and will thus do the job without any extra effort) or if I need to wrap it to make sure the changes are made when the destruction is flagged.
     
  2. orb

    orb

    Joined:
    Nov 24, 2010
    Posts:
    3,037
    From what I've gathered, it's called in the same frame an object is marked for destruction, at the end of Update(). So basically "immediately".
     
  3. GarthSmith

    GarthSmith

    Joined:
    Apr 26, 2012
    Posts:
    1,240
    If you need the object to be destroyed immediately, then use DestroyImmediate even though it's slower than Destroy. Destroy will destroy the object sometime during this frame, but you cannot expect the object to be destroyed during another object's Update.
     
  4. angrypenguin

    angrypenguin

    Joined:
    Dec 29, 2011
    Posts:
    15,620
    I don't care when the object is destroyed. There's stuff I want to happen when the destruction is queued. If OnDestroy is called actually immediately then I can use that and it'll be transparent to other coders. If OnDestroy is not immediate (and the end of the same frame isn't immediate enough for me) then I'll have to wrap the Destroy method, and tell people not to use Destroy immediately for these particular objects.

    I'd rather the former approach, but it looks like I'll have to do an experiment first to ensure it works that way before relying on it.
     
    Westland likes this.
  5. MUGIK

    MUGIK

    Joined:
    Jul 2, 2015
    Posts:
    481
    So the answer is: OnDestroy called NOT immediatelly after Destroy();

    Proofs:
    Code (CSharp):
    1.  
    2. using UnityEngine;
    3.  
    4. public class test_script : MonoBehaviour
    5. {
    6.     void Start()
    7.     {
    8.         Debug.Log("Start1");
    9.         Destroy(gameObject);
    10.         Debug.Log("Start2");
    11.     }
    12.  
    13.     private void Update()
    14.     {
    15.         Debug.Log("Update");
    16.     }
    17.  
    18.     private void OnDisable()
    19.     {
    20.         Debug.Log("OnDisable");
    21.     }
    22.  
    23.     private void OnDestroy()
    24.     {
    25.         Debug.Log("OnDestroy");
    26.     }
    27. }
    28.  
    And the result:
    upload_2020-9-19_17-46-45.png
     
    odaimoko, ailuropoda0 and davidrochin like this.