Search Unity

How to update LocalToWorld translation?

Discussion in 'Entity Component System' started by HoHStudios, Aug 3, 2021.

  1. HoHStudios

    HoHStudios

    Joined:
    Nov 3, 2016
    Posts:
    20
    Hello guys,

    Sorry if this is a noob question, I'm new to DOTS

    I have this code shown below inside of an IJobParallelFor job

    Code (CSharp):
    1.                        
    2. var spawnedEntity = CommandBuffer.Instantiate(i, prefab);
    3. CommandBuffer.AddComponent<DataComponent>(i, spawnedEntity);
    4. CommandBuffer.SetComponent(i, spawnedEntity, new Translation()
    5. {
    6. Value = spawnData.InitialTransform.Position
    7. });
    Obviously all I'm trying to do is instantiate a bunch of entity prefabs at a specific world positions. To do this, I'm updating the Translation component which exists on each prefab. For about one frame, the entity spawns at an arbitrary spawn location (with the updated translation component) but the LocalToWorld component hasn't updated yet to reflect the new position, so the following frame it snaps to the newly set position. It seems to me that the LocalToWorld component gets updated the following frame AFTER it spawned. How do I force the immediate spawn position to the new translation position so there isn't a one frame position "snap"?

    Idk if it matters or not but my command buffer originates from the
    'EndSimulationEntityCommandBufferSystem' system.


    Thanks in advanced
     
  2. DreamingImLatios

    DreamingImLatios

    Joined:
    Jun 3, 2017
    Posts:
    4,266
    Makes all the difference actually! ;)

    If you used BeginInitializationCommandBuffer, then what would happen is your entity will spawn at the beginning of the next frame and have its LocalToWorld updated before it gets rendered for the first time. Personally, I like to make the TransformSystemGroup update a second time right after command buffer playback so that everything is fully updated.
     
    HoHStudios and Krajca like this.
  3. yinyinh

    yinyinh

    Joined:
    Oct 31, 2018
    Posts:
    17
    The Systems inspector will help, Window > DOTS > System.
    By default, LocalToWorld is updated once every loop by the sequence of systems under TransformSystemGroup.

    There are a few ways to ensure LocalToWorld gets updated.
    1. Update your Translation, Rotation, etc anywhere before TransformSystemGroup. Use UpdateBefore, UpdateAfter, UpdateInGroup for this. A common practice is to define your own SystemGroup, define its update order, put your own Systems under them and create CommandBuffers as needed.
    2. Manually compute your LocalToWorld. It's your standard TRS matrix (though not limited to it depending on what you want to achieve). Just do not forget to concatenate the entity's parent's (if any) transformation matrices too.
    3. Update TransformSystemGroup a second time. Of course, you will have to pay the cost of computing all transformations for every single entity in chunks that were considered to be changed according to their LastSystemVersion.
     
    Last edited: Aug 3, 2021
    HoHStudios likes this.
  4. HoHStudios

    HoHStudios

    Joined:
    Nov 3, 2016
    Posts:
    20
    Thanks for the replies guys! Couldn't have answered better!
     
  5. willy-kantana-alegrium

    willy-kantana-alegrium

    Joined:
    Sep 4, 2015
    Posts:
    2
    Hi @HoHStudios, we're currently stumbling with this same problem. If you do not mind can you tell us did you resolve this problem yet, and if it is can you share with us how to resolve that? cheers.