Search Unity

API Deprecation FAQ (0.0.23)

Discussion in 'Data Oriented Technology Stack' started by AriaBonczek, Feb 28, 2019.

  1. tertle

    tertle

    Joined:
    Jan 25, 2011
    Posts:
    1,560
    The singleton api isn't anything magic, it just does a regular entity lookup and an Assert Length == 1 kind of check.
    Honestly, the Singleton api is a bit meh at the moment and I avoid it most of the time. I only use RequireSingletonForUpdate to do checks like this.

    Code (CSharp):
    1.         /// <inheritdoc/>
    2.         protected override void OnCreateManager()
    3.         {
    4.             // Ensure only a single ActiveFaction is present.
    5.             this.RequireSingletonForUpdate<ActiveFaction>();
    6.         }
    7.  
    8.         /// <inheritdoc/>
    9.         protected override void OnUpdate()
    10.         {
    11.                 // Because the RequireSingletonForUpdate<ActiveFaction> this will only ever have 1 entity.
    12.                 this.Entities
    13.                     .WithAll<ActiveFaction>()
    14.                     .ForEach((ref Faction faction, DynamicBuffer<FactionFogData> fogData) =>
     
    psuong, leni8ec and optimise like this.
  2. Skyblade

    Skyblade

    Joined:
    Nov 19, 2013
    Posts:
    71
    After upgrading to the latest preview 30 - 0.0.12 package version I get this error on game start:
    and this
    What does it mean?
     
  3. DreamingImLatios

    DreamingImLatios

    Joined:
    Jun 3, 2017
    Posts:
    377
    That's usually an issue with Unity's Package Manager and Burst. Restarting the editor fixes it. If you still have problems, that might be a Burst compile error in your code.
     
    Skyblade likes this.
  4. Skyblade

    Skyblade

    Joined:
    Nov 19, 2013
    Posts:
    71
    @DreamingImLatios

    Thanks a lot, that fixed the issue.
    However, I can not make generic JobComponentSystem running after upgrade:

    Code (CSharp):
    1. public class NodeSharedSpriteRenderingSystem : SharedSpriteRenderingSystem<NodeSharedSprite> { ... }
    2.  
    3. public class SharedSpriteRenderingSystem<T> : JobComponentSystem where T : struct, ISharedComponentData, ISprite { ... }
    4.  
    , where ISprite is my custom interface.

    OnCreateManager is the only method that is called. After that, no trace in the Entity debugger or any OnUpdate call.
    When I exit the game the OnDestroy is called once.

    What happens to this system?
     
  5. DreamingImLatios

    DreamingImLatios

    Joined:
    Jun 3, 2017
    Posts:
    377
    It sounds like the EntityQueries you specify in OnCreate and the EntityQueries derived from nested IJobForEach jobs in the class do not match any chunks in your world. Thus Unity won't call OnUpdate.
     
    Skyblade likes this.
  6. Skyblade

    Skyblade

    Joined:
    Nov 19, 2013
    Posts:
    71
    Thank you!
    For some reason (Job)ComponentSystem can not catch LocalToWorld component, so I can't render anything. I tried to add LocalToWorld to existing system which already uses Translation, and after that it breaks.
    Is this known issue?

    I attached sample project:
    _LocalToWorldIssue.zip

    If you run it, you will see CoordsToPositionSystem running:
    upload_2019-4-22_1-42-39.png

    But if you add LocalToWorld component in that way:
    Code (CSharp):
    1. public class CoordsToPositionSystem : ComponentSystem {
    2.     ...
    3.     protected override void OnUpdate(){
    4.         ...
    5.        Entities.ForEach((ref Coords coords, ref Translation position, ref LocalToWorld local) => {
    6.             ...
    7.        }
    8.     }
    9. }
    then CoordsToPositionSystem will not run:
    upload_2019-4-22_2-4-39.png
     

    Attached Files:

    Last edited: Apr 22, 2019
  7. Septimus

    Septimus

    Joined:
    Nov 23, 2011
    Posts:
    33
    Trying to understand these new changes. In the FPS Sample they have:
    Code (CSharp):
    1.     int FindPlayerControlling(ref ComponentArray<PlayerState> players, Entity entity)
    2.     {
    3.         if (entity == Entity.Null)
    4.             return -1;
    5.  
    6.         for (int i = 0, c = players.Length; i < c; ++i)
    7.         {
    8.             var playerState = players[i];
    9.             if (playerState.controlledEntity == entity)
    10.                 return i;
    11.         }
    12.         return -1;
    13.     }
    How would this be converted using the new ForEach stuff?
     
  8. Tony_Max

    Tony_Max

    Joined:
    Feb 7, 2017
    Posts:
    50
    The only way we can access IBufferElementData in parallel now is to use IJobChunk, right?

    So to access inside IJobChunkExecute we should initialize ArchetypeChunkBufferType wich can be get by EntityManager.GetArchetypeChunkBufferType(bool) where bool tells is it RO. But when you call ArchetypeChunk.GetBufferAccessor(ArchetypeChunkBufferType) chunk changes his version.

    In my case i have NativeMultiHashMap<int, Data> that contains some index that matches the cell on a map and some Data that i need to update on matching cell. In Execute() of IJobChunk i need to iterate through all cells and call TryGetFirstValue(...) on hashmap. But befor call it i also need to call ArchetypeChunk.GetBufferAccessor(ArchetypeBufferType). And that produce changes of whole chunk. I understand that i can write complex logic inside which i will get BufferAccessors only at fist successfull hit in hashmap iteration. But this approach seems very dirty to me.

    The question is: can it be done without changing whole chunk version?
     
  9. eizenhorn

    eizenhorn

    Joined:
    Oct 17, 2016
    Posts:
    1,370
    No. You also can use GetBufferFromEntity.
     
  10. Tony_Max

    Tony_Max

    Joined:
    Feb 7, 2017
    Posts:
    50
    Is it as efficient?
     
  11. eizenhorn

    eizenhorn

    Joined:
    Oct 17, 2016
    Posts:
    1,370
    Yes. It’s lookup.
     
  12. kazumio

    kazumio

    Joined:
    Mar 9, 2017
    Posts:
    5
    Is it still possible to work with hybrid ecs after these changes?
    How would you iterate over a entity with a transform and some costume script on it first example?
     
  13. eizenhorn

    eizenhorn

    Joined:
    Oct 17, 2016
    Posts:
    1,370
    Yep you can work with hybrid fine. Use latest .ForEach syntax for that on main thread. Also IJobForEachTransform still exists untill Unity find better replacement.
     
    kazumio likes this.
  14. kazumio

    kazumio

    Joined:
    Mar 9, 2017
    Posts:
    5

    Hey thanks for the reply any chance for an example ,or maybe you can correct what im doing wrong here?

    the SetOrientationToGroundNormal is a monobeahviour and i've tried coupling it with a transform to create a type so i can iterate over everything that has those two things


    using UnityEngine;
    using Unity.Entities;
    public class SystemSetOrientation : ComponentSystem
    {

    struct Data : IJobForEach<Transform,SetOrientationToGroundNormal>
    {
    public Transform transform;
    public SetOrientationToGroundNormal orientation;
    }


    protected override void OnUpdate()
    {


    Entities.ForEach((IJobForEach<Transform> trans)=>
    {
    //do somehting
    });
    }
    }
     
  15. eizenhorn

    eizenhorn

    Joined:
    Oct 17, 2016
    Posts:
    1,370
    Code (CSharp):
    1. using Unity.Entities;
    2. using UnityEngine;
    3.  
    4. public struct MyComponent : IComponentData
    5. {
    6.     public int Val;
    7. }
    8.  
    9. public class NewBehaviourScript : MonoBehaviour
    10. {
    11.     public int Val;
    12. }
    13.  
    14. public class SystemIterator : ComponentSystem
    15. {
    16.     protected override void OnCreate()
    17.     {
    18.         var e = EntityManager.CreateEntity(typeof(MyComponent));
    19.         EntityManager.SetComponentData(e, new MyComponent()
    20.         {
    21.             Val = 10
    22.         });
    23.      
    24.         var go = new GameObject();
    25.         go.transform.position = new Vector3(10, 11, 12);
    26.      
    27.         var monoComponent = (NewBehaviourScript)go.AddComponent(typeof(NewBehaviourScript));
    28.         monoComponent.Val = 555;
    29.      
    30.         EntityManager.AddComponentObject(e, monoComponent);
    31.         EntityManager.AddComponentObject(e, go.transform);
    32.  
    33.         monoComponent.Val = 999;
    34.     }
    35.  
    36.     protected override void OnUpdate()
    37.     {
    38.         Entities.ForEach((Entity Entities, ref MyComponent c, Transform t, NewBehaviourScript m)=>
    39.         {
    40.             Debug.Log($"{t.position} - {m.Val} - {c.Val}");
    41.             t.position += Vector3.up;
    42.             m.Val += 10;
    43.         });
    44.     }
    45. }
    46.  
    upload_2019-4-28_17-37-6.png
    upload_2019-4-28_17-37-39.png

    You of couse should use conversion workflow, I'm create GO from scratch just for showing example how ForEach works.

    For access and change transform in job you should use IJobParallelForTransform with TransormAccessArray
     
    kazumio likes this.
  16. kazumio

    kazumio

    Joined:
    Mar 9, 2017
    Posts:
    5
    Thanks so much for your help and time eizenhorn i really appreciate it :) , i understand what my mistake was, i kept doing a ref before component in the foreach paramaters and then i got the cannot put something that can be null error.
    so i see now i only need to put the ref before the structs.

    again thanks so much :)
     
  17. jae_yoo

    jae_yoo

    Joined:
    Apr 22, 2019
    Posts:
    2
    How do I do this now?
    Code (CSharp):
    1. foreach(var e in GetEntities<Components>())
    2. {
    3.     // do something?
    4. }
     
  18. eizenhorn

    eizenhorn

    Joined:
    Oct 17, 2016
    Posts:
    1,370
  19. Tony_Max

    Tony_Max

    Joined:
    Feb 7, 2017
    Posts:
    50
    But direct access to buffer through chunks is more optimal then lookup through BufferFromEntity i guess.
     
  20. Ashkan_gc

    Ashkan_gc

    Joined:
    Aug 12, 2009
    Posts:
    903
    1. @AriaBonczek or @Joachim_Ante I asked about determinism of GameObjectEntity in another thread. Some people mentioned there that GameobjectEntity is deprecated because things it relied on got deprecated. Is it true? If yes is there any built-in feature to keep the Gameobject and also a mapping between entity and gameobject.

      My main interest lies in making a deterministic simulation using a simple fixed point math lib and ECS and even hybrid mode is good enough for us and makes our job easier as well.

      How well it will be supported down the road and what approach should be used?

      We want to use ECS only for the simulation and not presentation of the game and the game has less than 20 units in the match at all points in time so memory / performance is not our explicit concern and determinism is.

      I know that we are not the most usual use-case but I want to see how much of the built-in infrastructure we can leverage and for example hopefully later on switch to burst deterministic floats instead of our fix64.
      Thanks
     
  21. Antypodish

    Antypodish

    Joined:
    Apr 29, 2014
    Posts:
    5,197