Search Unity

  1. Megacity Metro Demo now available. Download now.
    Dismiss Notice
  2. Unity support for visionOS is now available. Learn more in our blog post.
    Dismiss Notice

Packages and System Update Order

Discussion in 'Entity Component System' started by Jawsarn, Feb 3, 2020.

  1. Jawsarn

    Jawsarn

    Joined:
    Jan 12, 2017
    Posts:
    245
    Is the end goal to create empty systems to order systems from different packages? E.g. PredictionSystemGroup and BuildPhysicsWorld, since the code of "UpdateBefore/After" resides in the packages I'll either need to extract and modify, or use an empty system with the attributes to sort it out. Or have I missed some magic out there?
     
  2. alexandre-fiset

    alexandre-fiset

    Joined:
    Mar 19, 2012
    Posts:
    714
    The thing is, if you really need these systems to update before/after each other, it means there is some sort of dependency between them, no?

    If package A relies on package B, what I would do is to add package B to the manifest.json, package.json and assembly definition of project A, and set the order there.

    If A and B are agnostic to each other, but you need a C that updates after B and before A, you just set UpdateBefore(typeof(A)) and UpdateAfter(typeof(B) on your C-systems, and then it should place itselfs at the right place at runtime.

    To make things easier you can use ComponentSystemGroup to group systems that need to stay together. It also improves lisibility in the EntityDebugger and also allows you to just update these systems only if a query returns something.
     
    Chebn likes this.
  3. 5argon

    5argon

    Joined:
    Jun 10, 2013
    Posts:
    1,555
    Best practice in the docs says you should always add your systems to your own defined group. If everyone including package author followed this then the Before/After to sort only have to mention the package's group. At most packages would define 3 top groups if it uses all 3 default top groups.
     
  4. snacktime

    snacktime

    Joined:
    Apr 15, 2013
    Posts:
    3,356
    Are player loops still the only way to order your own groups relative to the built in ones? Haven't had the time to look at that recently but I'd love to get rid of our custom player loop stuff. Using that to order groups depends on internal ECS logic as to when and where which I really don't like.
     
  5. Jawsarn

    Jawsarn

    Joined:
    Jan 12, 2017
    Posts:
    245
    Yes, indirectly. I'm adding a system that resides in an existing SystemGroup from package A, where this group from package A is on the same "level" (in same group) as another group from package B, but which doesn't have any already defined order, but which I require from logic inside my system to have.


    I've never heard of setting order of systems by assembly definition, can you elaborate or give a link? As side question, doesn't this require you to not use manifest for one of the packages - which was one of the things I didn't want in my question?

    As I said I can't do this if you regard C as my own system, as it is within A and not on the same level. And the other note I wrote in the question was that you could create an empty system to do above, which seems more of a hack than anything else.


    I don't see how adding another layer of groups beside my own would solve this case. I'm talking of deciding order of SystemGroups which I don't directly have "control" over, as they reside in packages.
     
  6. e199

    e199

    Joined:
    Mar 24, 2015
    Posts:
    101
    The best way would be to have a class define the order in this way:

    Code (CSharp):
    1. public CreateSystems(){
    2.   Add(new SystemA);
    3.   Add(new SystemB);
    4.   Add(new FeatureA);  //FeatureA adds SystemC and SystemD
    5.   Add(new SystemT);
    6. }

    `Feature` is just a collection of systems AND `Features`, that way you can group systems together, but it doesn't stop you from adding systems one by one

    And that way you can define the order in any way you want for plugins too

    The magic approach unity has chosen is pathetic and not reliable
     
  7. snacktime

    snacktime

    Joined:
    Apr 15, 2013
    Posts:
    3,356
    Instead of setting the order of system groups, you arrange your groups relative to those groups. So you can create your own group that say runs in SimulationSystemGroup. And you can specify that the entire group runs before or after built in systems that are running in SimulationSystemGroup.

    You should not change the order of built in systems relative to each other within a specific feature, only relative to your own systems. A feature's systems should define their own order and if that is causing problems, it's a bug pretty much by definition. But you can order your systems relative to systems within a feature. Like we do that for Unity.Physics we have a group that runs before all physics systems, and another that runs sort of in the middle of them.

    So most things you can solve as far as order with groups.

    What you can't always solve is timing. Like a classic issue is PresentationSystemGroup running immediately after SimulationSystemGroup. Just one dependency between the two can chain into more and basically force complete stuff early wasting tons of main thread time unnecessarily. In that case as far as I know you have to use custom player loops. With those you can reorder whatever you want including built in groups.
     
  8. Jawsarn

    Jawsarn

    Joined:
    Jan 12, 2017
    Posts:
    245
    I assume this is something you would want and not existing? I think this is similar to what you can do in bootstrap, and you could I guess manually order the systems if you want like that.


    Not sure if I should regard it as bug or not, but to further explain my existing problem. The
    GhostSimulationSystemGroup which updates in the SimulationGroup runs a
    GhostPredictionSystemGroup X times each frame on client, you can add systems to be in this group that predict entities for X frames forward, usually done with some physics calculations. If you want to use the current simulation frames physics, you would want the BuildPhysicsWorld to be run before the GhostSimulationSystemGroup, but if you would want to add and modify velocities which are extracted in the build step from the entities into the physics world, you would want it to be updated after. Now both BuildPhysicsWorld and GhostSimulationSystemGroup are from different packages and doesn't have any relation in between.

    Now I know you can solve this specific problem by modifying velocities directly of the physics world instead of entities or doing approximation of physics within the prediction tick itself, but it shows that there are some problematic to the current approach of packages, structure with ease of use.
     
    Mikael-H and Chebn like this.