Search Unity

All system stopped running except MeshInstanceRendererSystem

Discussion in 'Graphics for ECS' started by 5argon, Sep 25, 2018.

  1. 5argon

    5argon

    Joined:
    Jun 10, 2013
    Posts:
    1,555
    I just try upgrading to 2018.3.0b2 in order to use the new prefab system and upgraded Entities to preview 15, after all the fixes about .Concurrent needing job index and thing about zero-sized components I am able to run the game, but now all of my systems in the debugger has 0.00 time except MeshInstanceRendererSystem which the number is running.

    All of them seems to have the entities required for OnUpdate activation as seen on the right hand side of the debugger but OnUpdate does not activate at all. What could be the possible problem here? (Even a system with no injects which should always run does not run with perfectly constant 0.00ms)
     
  2. pcysl5edgo

    pcysl5edgo

    Joined:
    Jun 3, 2018
    Posts:
    65
    You should check 'RenderingSystemBootstrap.cs'.
    It registers rendering delegate to camera event handler.
     
  3. 5argon

    5argon

    Joined:
    Jun 10, 2013
    Posts:
    1,555
    Ah.. I know what's happening now. I have recently installed UniRx.Async. They have something like this :

    Code (CSharp):
    1.         [RuntimeInitializeOnLoadMethod(RuntimeInitializeLoadType.BeforeSceneLoad)]
    2.         static void Init()
    3.         {
    4.             // capture default(unity) sync-context.
    5.             unitySynchronizationContetext = SynchronizationContext.Current;
    6.             mainThreadId = Thread.CurrentThread.ManagedThreadId;
    7.  
    8.             if (runners != null) return; // already initialized
    9.  
    10.             var playerLoop = PlayerLoop.GetDefaultPlayerLoop();
    11.             Initialize(ref playerLoop);
    12.         }
    It has the same RuntimeInitializeLoadType.BeforeSceneLoad and this one runs after ECS's bootstrap, overriding the player loop with a default one + some modifications completely. (So all prepared systems disappeared, what's remaining is exactly because 'RenderingSystemBootstrap.cs' callback is independent of PlayerLoop) The ordering is not guaranteed according to Unity docs, so there is no way to "win" over ECS's bootstrap reliably.

    Also, it is a shame that this PlayerLoop API does not include how to get the current player loop (why not?) just default and set. If that is so any RuntimeInitializeOnLoadMethod that runs later can work on the loop in continuation from the prior one, without knowing about prior one. The only way now is that this library needs to know about Unity.Entities and grab the ECSified PlayerLoop via ScriptBehaviourUpdateOrder.CurrentPlayerLoop.

    (This public static field for safekeeping the PlayerLoop seems to acknowledge that getting the current PlayerLoop is not possible, either only currently or technically?)
     
  4. snacktime

    snacktime

    Joined:
    Apr 15, 2013
    Posts:
    3,356
    ScriptBehaviourUpdateOrder.CurrentPlayerLoop.
     
  5. isbdnt

    isbdnt

    Joined:
    May 16, 2017
    Posts:
    35
    you can manually active all your systems
    Code (CSharp):
    1. ScriptBehaviourUpdateOrder.UpdatePlayerLoop(World.Active);
     
  6. 5argon

    5argon

    Joined:
    Jun 10, 2013
    Posts:
    1,555
    That won't work. Imagine it goes like this :

    Enter play mode.

    DefaultWorldInitialization
    >
    ScriptBehaviourUpdateOrder.UpdatePlayerLoop


    - Get default player loop then make it includes all systems in all specified worlds.
    - Set that player loop as active with
    PlayerLoop.SetPlayerLoop

    - That modified player loop is stored in
    ScriptBehaviourUpdateOrder : public static PlayerLoopSystem CurrentPlayerLoop;

    - Some other ECS code are reading from this
    CurrentPlayerLoop
    static property, it is also open for anyone to use.

    UniRx or other libraries
    RuntimeInitializeOnLoadMethod
    with player loop modification

    - Get default player loop and make some modifications. Other libs has no knowledge of ECS
    ScriptBehaviourUpdateOrder.CurrentPlayerLoop
    . (nor it is guaranteed to run before or after ECS's modification)
    - The player loop now is that of the default plus some modifications, but without any systems from the ECS bootstrap.

    Call
    ScriptBehaviourUpdateOrder.UpdatePlayerLoop
    manually

    - Get default player loop then make it includes all systems in all specified worlds.
    - Then the same happen, but this time those modifications from other libs will disappear.

    Rather than having to store the current player loop externally the player loop API needs to be able to return the current loop for anyone to build additively on it. There is a chance that ECS will not be the only one that needs to modify the player loop in the future.
     
    isbdnt likes this.
  7. pcysl5edgo

    pcysl5edgo

    Joined:
    Jun 3, 2018
    Posts:
    65
    Here is the solution about UniRx.
    http://notargs.hateblo.jp/entry/ecs_unirx


    After the timing of RuntimeInitializeLoadType.BeforeSceneLoad
    You should re-Initialize UniRx playerloop with ECS playerloop.
    Code (CSharp):
    1. var playerLoop = ScriptBehaviourUpdateOrder.CurrentPlayerLoop;
    2. PlayerLoopHelper.Initialize(ref playerLoop);
     
  8. xVergilx

    xVergilx

    Joined:
    Dec 22, 2014
    Posts:
    3,296
    For the future readers, UniRx patched this, but if you've encountered this on 2019.3+ there's no ScriptBehaviourUpdateOrder.CurrentPlayerLoop anymore.

    So to fix this issue, go to PlayerLoopHelper.cs in UniRx.Async, and replace var playerLoop with the following:
    Code (CSharp):
    1.             var playerLoop =
    2. #if UNITY_2019_3_OR_NEWER
    3.                 PlayerLoop.GetCurrentPlayerLoop();
    4. #else
    5.                 PlayerLoop.GetDefaultPlayerLoop();
    6. #endif
    Or just... update UniRx