Search Unity

Question Multi world systems?

Discussion in 'Entity Component System' started by Guedez, May 8, 2020.

  1. Guedez

    Guedez

    Joined:
    Jun 1, 2012
    Posts:
    827
    Is it possible to have a single system operate on two worlds at once?
    For instance, check EntityA positon in world1 and world 2? Like this
    Update(Entity ea, ref Position world1, ref Position world2);

    Of course, if possible, I expect that it would require manual chunk iteration or something like that, so there would be tons of code before getting that neat and clean update above.
    I just want to know if it's currently possible to do so performantly (about as costly as running the same system on a single world twice), with burst preferably, so I can start figuring out how to.,

    The intent is to have a world for current simulation, and a world for 'previous state', where you can check if the current simulation is 'different enough' to warrant updating the previous state and sending it to the network to other players, so you can have more or less automated syncing and per-component logic to determine if it is worth sending the changes over the network.
     
    nixiaozi likes this.
  2. Guedez

    Guedez

    Joined:
    Jun 1, 2012
    Posts:
    827
    So it's not possible? Not with burst at least?
     
  3. WAYNGames

    WAYNGames

    Joined:
    Mar 16, 2019
    Posts:
    992
    Hello,

    I think that the FPS sample use another IComponentData on the same entity to store the previous value of the data. The delta compression then only sych the changes, you could probably add a threshold of change and consider taht under a certain amount of change, the delta compression result in no change at all (in tha case, you should not update the previous state of the data).

    I don't know the impact this would have on the all state at a previous tick logic.
     
  4. Guedez

    Guedez

    Joined:
    Jun 1, 2012
    Posts:
    827
    The issues with having a "Thing I want to sync" and a "Copy of thing I want to sync",
    1. It inflates the entity size, and big entities are slower than small entities, for all uses at all times.
    2. The "Copy of thing I want to sync" need to be manually created
    Although that certainly is the fastest method of comparing if the current and previous state is different enough, it creates management issues (needing to have two copies of the same component, with different names, for all things I want to sync), and a hard to measure efficiency decrease by inflating the entity size, which will probably not be an issue 99% of the time, but I have no way to be sure of that.

    I wanted to fix that by having two worlds, one for the entity as is, and another for just the things I want to sync from said entity, so entity sizes don't inflate, and I don't need to create two copies of the same component.
    But the more I think about it, the more it seems this 'sync world' concept needs to be a made-for-purpose thing in the very core of the ECS system, as not only it would not run systems, it's only reason to exist is to be compared to the non-sync version of itself, ensuring that there is a 1-1 match of chunks so that both copies of the components are always aligned and whatnot seem to be all completely out of scope of what the current worlds are meant to be used for
     
  5. WAYNGames

    WAYNGames

    Joined:
    Mar 16, 2019
    Posts:
    992
    Then maybe start by creating a copy entity that reference its original. On that copied entity you can have the same. Component as on the original entity but with the previous value.
    In that case your entities don't inflate, you can use the same component structure. But you'll have an indirection to get the original component values on it.
     
  6. Guedez

    Guedez

    Joined:
    Jun 1, 2012
    Posts:
    827
    but then I am quite sure either burst or simd is impossible, which are pretty significant speed factors, since I will be basically doing random access for each pair of entities
     
  7. WAYNGames

    WAYNGames

    Joined:
    Mar 16, 2019
    Posts:
    992
    The only constrain I see are the safety check on the alliasing since you would be using the same component types but I'm pretty sure you can use attributes to disable those since you now you won't be reading and writing to the same entities or another work arround. So burst should be fine.

    As for the performance of the indirection it's a O(1) look up using component data from entity and apparently it's not as bad I one might initially think.


    It may be worth the shot if you really don't want to define duplicate component data.

    First you'll get the convinence of not defining duplicate component data and second you said small entites are faster so maybe the performance drawback of the indirection in the delta compression job will be well compensated by other systems running faster.

    It may not be such a bad tradeof depending on the amount of data to synchronize between the server and client.
     
  8. Guedez

    Guedez

    Joined:
    Jun 1, 2012
    Posts:
    827
    I guess I might as well try