Search Unity

  1. Welcome to the Unity Forums! Please take the time to read our Code of Conduct to familiarize yourself with the forum rules and how to post constructively.
  2. We have updated the language to the Editor Terms based on feedback from our employees and community. Learn more.
    Dismiss Notice

"SetActive can only be called from the main thread"

Discussion in 'Windows' started by K1kk0z90_Unity, Feb 18, 2015.

  1. K1kk0z90_Unity

    K1kk0z90_Unity

    Joined:
    Jun 2, 2013
    Posts:
    90
    Hi all!
    I'm trying to port my Unity game to Windows Store. Sometimes, running the Visual Studio project generated by Unity, the game crashes with the following error:
    This error raises just sometimes, while other times the game runs without crashing. Here is the piece of code that raises the exception:
    Code (CSharp):
    1. #if NETFX_CORE
    2.     async
    3. #endif
    4.     public void Foo()
    5.     {
    6.         ...
    7. #if !NETFX_CORE
    8.         if (Bar())
    9. #else
    10.         if (await Bar())
    11. #endif
    12.         {
    13.             myGameObject.SetActive(true); // THIS INSTRUCTION RAISES THE EXCEPTION
    14.         }
    15.  
    16.         ...
    17.     }
    It seems to me that the problem is that sometimes the "myGameObject.SetActive(true)" instruction is executed into another thread, but I don't understand how it can happen.
    What's wrong with my code?
    Thank you in advance for your help!
     
  2. Tomas1856

    Tomas1856

    Unity Technologies

    Joined:
    Sep 21, 2012
    Posts:
    3,687
    As the error says you're calling "myGameObject.SetActive(true); " from the wrong thread, to fix this you must use InvokeOnAppThread, something like this:
    Code (csharp):
    1.  
    2. WSAApplication.InvokeOnAppThread(()=>
    3. {
    4.    myGameObject.SetActive(true);
    5. }
    6.  
     
    ZoraMikau and K1kk0z90_Unity like this.
  3. Tautvydas-Zilys

    Tautvydas-Zilys

    Unity Technologies

    Joined:
    Jul 25, 2013
    Posts:
    10,522
    await transfers control to another thread.
     
    K1kk0z90_Unity likes this.
  4. K1kk0z90_Unity

    K1kk0z90_Unity

    Joined:
    Jun 2, 2013
    Posts:
    90
    Thank you both for your answers! :)
    So, if I understood correctly, inside an async method every UnityEngine's method call must be wrapped into InvokeOnAppThread()?
     
    Simic13 likes this.
  5. Tomas1856

    Tomas1856

    Unity Technologies

    Joined:
    Sep 21, 2012
    Posts:
    3,687
    Yes, because most of the UnityEngine API is not thread-safe, so you must call them in the correct thread - also known as app thread in this case.
     
    Simic13 and K1kk0z90_Unity like this.
  6. K1kk0z90_Unity

    K1kk0z90_Unity

    Joined:
    Jun 2, 2013
    Posts:
    90
    Ok, good to know. Thank you very much for your precious help! :)