Exemplo n.º 1
0
        /// <summary>
        /// Enabled entities are processed by systems, disabled entities are not.
        /// Adds or removes the <see cref="Disabled"/> component. By default EntityQuery does not include entities containing the Disabled component.
        ///
        /// If the entity was converted from a prefab and thus has a <see cref="LinkedEntityGroup"/> component, the entire group will enabled or disabled.
        /// </summary>
        /// <param name="entity">The entity to enable or disable</param>
        /// <param name="enabled">True if the entity should be enabled</param>
        public void SetEnabled(Entity entity, bool enabled)
        {
            if (GetEnabled(entity) == enabled)
            {
                return;
            }

            var disabledType = ComponentType.ReadWrite <Disabled>();

            if (HasComponent <LinkedEntityGroup>(entity))
            {
                //@TODO: AddComponent / Remove component should support Allocator.Temp
                using (var linkedEntities = GetBuffer <LinkedEntityGroup>(entity).Reinterpret <Entity>().ToNativeArray(Allocator.TempJob))
                {
                    if (enabled)
                    {
                        RemoveComponent(linkedEntities, disabledType);
                    }
                    else
                    {
                        AddComponent(linkedEntities, disabledType);
                    }
                }
            }
            else
            {
                if (!enabled)
                {
                    AddComponent(entity, disabledType);
                }
                else
                {
                    RemoveComponent(entity, disabledType);
                }
            }
        }
Exemplo n.º 2
0
        internal EntityManager(World world)
        {
            TypeManager.Initialize();

            m_World = world;

            m_ComponentJobSafetyManager =
                (ComponentJobSafetyManager *)UnsafeUtility.Malloc(sizeof(ComponentJobSafetyManager), 64,
                                                                  Allocator.Persistent);
            m_ComponentJobSafetyManager->OnCreate();

            m_EntityComponentStore  = Entities.EntityComponentStore.Create(world.SequenceNumber << 32);
            m_ManagedComponentStore = new ManagedComponentStore();
            m_EntityQueryManager    = new EntityQueryManager(m_ComponentJobSafetyManager);

            m_ExclusiveEntityTransaction = new ExclusiveEntityTransaction(EntityQueryManager, m_ManagedComponentStore, EntityComponentStore);

            m_UniversalQuery = CreateEntityQuery(
                new EntityQueryDesc
            {
                Options = EntityQueryOptions.IncludePrefab | EntityQueryOptions.IncludeDisabled
            }
                );

            m_UniversalQueryWithChunks = CreateEntityQuery(
                new EntityQueryDesc
            {
                All     = new[] { ComponentType.ReadWrite <ChunkHeader>() },
                Options = EntityQueryOptions.IncludeDisabled | EntityQueryOptions.IncludePrefab
            },
                new EntityQueryDesc
            {
                Options = EntityQueryOptions.IncludeDisabled | EntityQueryOptions.IncludePrefab
            }
                );
        }
Exemplo n.º 3
0
 /// <summary>
 /// Gets the run-time type information required to access an array of component data in a chunk.
 /// </summary>
 /// <param name="isReadOnly">Whether the component data is only read, not written. Access components as
 /// read-only whenever possible.</param>
 /// <typeparam name="T">A struct that implements <see cref="IComponentData"/>.</typeparam>
 /// <returns>An object representing the type information required to safely access component data stored in a
 /// chunk.</returns>
 /// <remarks>Pass an <see cref="ArchetypeChunkComponentType"/> instance to a job that has access to chunk data,
 /// such as an <see cref="IJobChunk"/> job, to access that type of component inside the job.</remarks>
 public ArchetypeChunkComponentType <T> GetArchetypeChunkComponentType <T>(bool isReadOnly = false) where T : struct, IComponentData
 {
     AddReaderWriter(isReadOnly ? ComponentType.ReadOnly <T>() : ComponentType.ReadWrite <T>());
     return(EntityManager.GetArchetypeChunkComponentType <T>(isReadOnly));
 }
        // ----------------------------------------------------------------------------------------------------------
        // PUBLIC
        // ----------------------------------------------------------------------------------------------------------

        public static Archetype *GetOrCreateArchetype(ComponentTypeInArchetype *inTypesSorted, int count,
                                                      EntityComponentStore *entityComponentStore)
        {
            var srcArchetype = entityComponentStore->GetExistingArchetype(inTypesSorted, count);

            if (srcArchetype != null)
            {
                return(srcArchetype);
            }

            srcArchetype = entityComponentStore->CreateArchetype(inTypesSorted, count);
            var types = stackalloc ComponentTypeInArchetype[count + 1];

            // Setup Instantiable archetype
            {
                UnsafeUtility.MemCpy(types, inTypesSorted, sizeof(ComponentTypeInArchetype) * count);

                var hasCleanup       = false;
                var removedTypes     = 0;
                var prefabTypeIndex  = TypeManager.GetTypeIndex <Prefab>();
                var cleanupTypeIndex = TypeManager.GetTypeIndex <CleanupEntity>();
                for (var t = 0; t < srcArchetype->TypesCount; ++t)
                {
                    var type = srcArchetype->Types[t];

                    hasCleanup |= type.TypeIndex == cleanupTypeIndex;

                    var skip = type.IsSystemStateComponent || type.TypeIndex == prefabTypeIndex;
                    if (skip)
                    {
                        ++removedTypes;
                    }
                    else
                    {
                        types[t - removedTypes] = srcArchetype->Types[t];
                    }
                }

                // Entity has already been destroyed, so it shouldn't be instantiated anymore
                if (hasCleanup)
                {
                    srcArchetype->InstantiableArchetype = null;
                }
                else if (removedTypes > 0)
                {
                    var instantiableArchetype = GetOrCreateArchetype(types, count - removedTypes, entityComponentStore);

                    srcArchetype->InstantiableArchetype = instantiableArchetype;
                    Assert.IsTrue(instantiableArchetype->InstantiableArchetype == instantiableArchetype);
                    Assert.IsTrue(instantiableArchetype->SystemStateResidueArchetype == null);
                }
                else
                {
                    srcArchetype->InstantiableArchetype = srcArchetype;
                }
            }


            // Setup System state cleanup archetype
            if (srcArchetype->SystemStateCleanupNeeded)
            {
                var  cleanupEntityType = new ComponentTypeInArchetype(ComponentType.ReadWrite <CleanupEntity>());
                bool cleanupAdded      = false;

                types[0] = inTypesSorted[0];
                var newTypeCount = 1;

                for (var t = 1; t < srcArchetype->TypesCount; ++t)
                {
                    var type = srcArchetype->Types[t];

                    if (type.IsSystemStateComponent)
                    {
                        if (!cleanupAdded && (cleanupEntityType < srcArchetype->Types[t]))
                        {
                            types[newTypeCount++] = cleanupEntityType;
                            cleanupAdded          = true;
                        }

                        types[newTypeCount++] = srcArchetype->Types[t];
                    }
                }

                if (!cleanupAdded)
                {
                    types[newTypeCount++] = cleanupEntityType;
                }

                var systemStateResidueArchetype = GetOrCreateArchetype(types, newTypeCount, entityComponentStore);
                srcArchetype->SystemStateResidueArchetype = systemStateResidueArchetype;

                Assert.IsTrue(systemStateResidueArchetype->SystemStateResidueArchetype == systemStateResidueArchetype);
                Assert.IsTrue(systemStateResidueArchetype->InstantiableArchetype == null);
            }

            // Setup meta chunk archetype
            if (count > 1)
            {
                types[0] = new ComponentTypeInArchetype(typeof(Entity));
                int metaArchetypeTypeCount = 1;
                for (int i = 1; i < count; ++i)
                {
                    var           t = inTypesSorted[i];
                    ComponentType typeToInsert;
                    if (inTypesSorted[i].IsChunkComponent)
                    {
                        typeToInsert = new ComponentType
                        {
                            TypeIndex = TypeManager.ChunkComponentToNormalTypeIndex(t.TypeIndex)
                        };
                        SortingUtilities.InsertSorted(types, metaArchetypeTypeCount++, typeToInsert);
                    }
                }

                if (metaArchetypeTypeCount > 1)
                {
                    SortingUtilities.InsertSorted(types, metaArchetypeTypeCount++, new ComponentType(typeof(ChunkHeader)));
                    srcArchetype->MetaChunkArchetype = GetOrCreateArchetype(types, metaArchetypeTypeCount, entityComponentStore);
                }
            }

            return(srcArchetype);
        }
Exemplo n.º 5
0
        /// <summary>
        /// Gets the managed [UnityEngine.Component](https://docs.unity3d.com/ScriptReference/Component.html) object
        /// from an entity.
        /// </summary>
        /// <param name="entity">The entity.</param>
        /// <typeparam name="T">The type of the managed object.</typeparam>
        /// <returns>The managed object, cast to type T.</returns>
        public T GetComponentObject <T>(Entity entity)
        {
            var componentType = ComponentType.ReadWrite <T>();

            return(GetComponentObject <T>(entity, componentType));
        }
Exemplo n.º 6
0
 public DynamicBuffer <T> AddBuffer <T>(Entity entity) where T : struct, IBufferElementData
 {
     AddComponent(entity, ComponentType.ReadWrite <T>());
     return(GetBuffer <T>(entity));
 }
        /// <summary>
        /// Sets the value of a component of an entity.
        /// </summary>
        /// <param name="entity">The entity.</param>
        /// <param name="componentData">The data to set.</param>
        /// <typeparam name="T">The component type.</typeparam>
        /// <exception cref="ArgumentException">Thrown if the component type has no fields.</exception>
        public static void SetComponentData <T>(this EntityManager manager, Entity entity, T componentData) where T : class, IComponentData
        {
            var type = ComponentType.ReadWrite <T>();

            manager.SetComponentObject(entity, type, componentData);
        }
 public DynamicBuffer <T> AddBuffer <T>(Entity entity) where T : struct, IBufferElementData
 {
     CheckWriteAccess();
     m_EntityDataAccess.AddComponent(entity, ComponentType.ReadWrite <T>());
     return(GetBuffer <T>(entity));
 }
        /// <summary>
        /// Gets the value of a component for an entity.
        /// </summary>
        /// <param name="entity">The entity.</param>
        /// <typeparam name="T">The type of component to retrieve.</typeparam>
        /// <returns>A struct of type T containing the component value.</returns>
        /// <exception cref="ArgumentException">Thrown if the component type has no fields.</exception>
        public static T GetComponentData <T>(this EntityManager manager, Entity entity) where T : class, IComponentData
        {
            var componentType = ComponentType.ReadWrite <T>();

            return((T)manager.GetManagedComponentDataAsObject(entity, componentType));
        }
Exemplo n.º 10
0
 /// <summary>
 /// Adds a shared component to an entity.
 /// </summary>
 /// <remarks>
 /// The fields of the `componentData` parameter are assigned to the added shared component.
 ///
 /// Adding a component to an entity changes its archetype and results in the entity being moved to a
 /// different chunk. The entity moves to a chunk with other entities that have the same shared component values.
 /// A new chunk is created if no chunk with the same archetype and shared component values currently exists.
 ///
 /// **Important:** This function creates a sync point, which means that the EntityManager waits for all
 /// currently running Jobs to complete before adding the component and no additional Jobs can start before
 /// the function is finished. A sync point can cause a drop in performance because the ECS framework may not
 /// be able to make use of the processing power of all available cores.
 /// </remarks>
 /// <param name="entity">The entity.</param>
 /// <param name="componentData">An instance of the shared component having the values to set.</param>
 /// <typeparam name="T">The shared component type.</typeparam>
 public void AddSharedComponentData <T>(Entity entity, T componentData) where T : struct, ISharedComponentData
 {
     //TODO: optimize this (no need to move the entity to a new chunk twice)
     AddComponent(entity, ComponentType.ReadWrite <T>(), false);
     SetSharedComponentData(entity, componentData);
 }
Exemplo n.º 11
0
 /// <summary>
 /// Removes a component from a set of entities.
 /// </summary>
 /// <remarks>
 /// Removing a component changes an entity's archetype and results in the entity being moved to a different
 /// chunk.
 ///
 /// **Important:** This function creates a sync point, which means that the EntityManager waits for all
 /// currently running Jobs to complete before removing the component and no additional Jobs can start before
 /// the function is finished. A sync point can cause a drop in performance because the ECS framework may not
 /// be able to make use of the processing power of all available cores.
 /// </remarks>
 /// <param name="entities">An array identifying the entities to modify.</param>
 /// <typeparam name="T">The type of component to remove.</typeparam>
 public void RemoveComponent <T>(NativeArray <Entity> entities)
 {
     RemoveComponent(entities, ComponentType.ReadWrite <T>());
 }
Exemplo n.º 12
0
 /// <summary>
 /// Removes a component from a set of entities defined by a EntityQuery.
 /// </summary>
 /// <remarks>
 /// Removing a component changes an entity's archetype and results in the entity being moved to a different
 /// chunk.
 ///
 /// **Important:** This function creates a sync point, which means that the EntityManager waits for all
 /// currently running Jobs to complete before removing the component and no additional Jobs can start before
 /// the function is finished. A sync point can cause a drop in performance because the ECS framework may not
 /// be able to make use of the processing power of all available cores.
 /// </remarks>
 /// <param name="entityQuery">The EntityQuery defining the entities to modify.</param>
 /// <typeparam name="T">The type of component to remove.</typeparam>
 public void RemoveComponent <T>(EntityQuery entityQuery)
 {
     RemoveComponent(entityQuery, ComponentType.ReadWrite <T>());
 }
 /// <summary>
 /// Gets the managed [UnityEngine.Component](https://docs.unity3d.com/ScriptReference/Component.html) object
 /// from an entity.
 /// </summary>
 /// <param name="entity">The entity.</param>
 /// <typeparam name="T">The type of the managed object.</typeparam>
 /// <returns>The managed object, cast to type T.</returns>
 public T GetComponentObject <T>(Entity entity)
 {
     return(m_EntityDataAccess.GetComponentObject <T>(entity, ComponentType.ReadWrite <T>(), m_ManagedComponentStore));
 }
Exemplo n.º 14
0
 /// <summary>
 /// Gets a BufferFromEntity&lt;T&gt; object that can access a <seealso cref="DynamicBuffer{T}"/>.
 /// </summary>
 /// <remarks>Assign the returned object to a field of your Job struct so that you can access the
 /// contents of the buffer in a Job.</remarks>
 /// <param name="isReadOnly">Whether the buffer data is only read or is also written. Access data in
 /// a read-only fashion whenever possible.</param>
 /// <typeparam name="T">The type of <see cref="IBufferElementData"/> stored in the buffer.</typeparam>
 /// <returns>An array-like object that provides access to buffers, indexed by <see cref="Entity"/>.</returns>
 /// <seealso cref="ComponentDataFromEntity{T}"/>
 public BufferFromEntity <T> GetBufferFromEntity <T>(bool isReadOnly = false) where T : struct, IBufferElementData
 {
     AddReaderWriter(isReadOnly ? ComponentType.ReadOnly <T>() : ComponentType.ReadWrite <T>());
     return(EntityManager.GetBufferFromEntity <T>(isReadOnly));
 }
Exemplo n.º 15
0
        public void ReleaseBlobAsset(EntityManager entityManager, ulong hash)
        {
            var blobAssets = (BlobAssetPtr *)m_BlobAssets->Ptr;

            for (var i = 0; i < m_BlobAssets->Length; i++)
            {
                if (blobAssets[i].Hash != hash)
                {
                    continue;
                }

                var entity = entityManager.CreateEntity(ComponentType.ReadWrite <RetainBlobAssets>(), ComponentType.ReadWrite <RetainBlobAssetPtr>());
                entityManager.SetComponentData(entity, new RetainBlobAssets {
                    FramesToRetainBlobAssets = m_FramesToRetainBlobAssets
                });
                entityManager.SetComponentData(entity, new RetainBlobAssetPtr {
                    BlobAsset = blobAssets[i].Header
                });

                // Entity lifetime will be bound to the SystemStateComponents we added above, we can safely call DestroyEntity(),
                //  it will be actually destroyed when both components will be removed at cleanup.
                entityManager.DestroyEntity(entity);

                m_BlobAssets->RemoveAtSwapBack <BlobAssetPtr>(i);
                return;
            }
        }
Exemplo n.º 16
0
 internal override ComponentType GetComponentType()
 {
     return(ComponentType.ReadWrite <T>());
 }
 /// <summary>
 /// Adds a component to an entity.
 /// </summary>
 /// <remarks>
 /// Adding a component changes the entity's archetype and results in the entity being moved to a different
 /// chunk.
 ///
 /// The added component has the default values for the type.
 ///
 /// If the <see cref="Entity"/> object refers to an entity that has been destroyed, this function throws an ArgumentError
 /// exception.
 ///
 /// **Important:** This function creates a sync point, which means that the EntityManager waits for all
 /// currently running Jobs to complete before adding thes component and no additional Jobs can start before
 /// the function is finished. A sync point can cause a drop in performance because the ECS framework may not
 /// be able to make use of the processing power of all available cores.
 /// </remarks>
 /// <param name="entity">The Entity object.</param>
 /// <typeparam name="T">The type of component to add.</typeparam>
 public void AddComponent <T>(Entity entity)
 {
     AddComponent(entity, ComponentType.ReadWrite <T>());
 }