Game.Events.SpectateSystem
Assembly: Game
Namespace: Game.Events
Type: class
Base: GameSystemBase
Summary: SpectateSystem is an ECS system that processes entities with the Spectate component and creates/attaches SpectatorSite components to the referenced target prefab entities. It also updates target event buffers (TargetElement) so the event/entity that requested spectating is recorded on the target. The system schedules a Burst-compiled IJob (SpectateJob) to gather requests in parallel, uses a NativeParallelHashMap to deduplicate targets, and then issues structural changes via a ModificationBarrier4 command buffer so component additions happen safely on the main thread.
Fields
-
private ModificationBarrier4 m_ModificationBarrier
Used to obtain an EntityCommandBuffer for safe structural changes (adding SpectatorSite components) from a job producer. The command buffer is created per update and the produced JobHandle is registered with the barrier. -
private EntityQuery m_SpectateQuery
EntityQuery selecting entities that contain a Spectate component (and an Event component). The query is required for the system to run (RequireForUpdate). -
private TypeHandle __TypeHandle
Holds component type/lookups (ComponentTypeHandle, ComponentLookup and BufferLookup) required by the scheduled job. Populated in OnCreateForCompiler.
Properties
- None
Constructors
public SpectateSystem()
Default constructor. The system uses the ECS lifecycle methods (OnCreate, OnUpdate, etc.) for initialization and work scheduling.
Methods
-
protected override void OnCreate()
: System.Void
Initializes the system: obtains the ModificationBarrier4 system, constructs the m_SpectateQuery to find entities with Spectate (and Event) components, and calls RequireForUpdate to ensure the system only runs when there are matching entities. -
protected override void OnUpdate()
: System.Void
Main update: converts the m_SpectateQuery to an archetype chunk list asynchronously, prepares a SpectateJob instance with component handles/lookups and a command buffer, schedules the job (Burst-compiled), disposes the chunk list when the job completes, registers the job handle with m_ModificationBarrier and updates base.Dependency.
Key behaviors performed by the scheduled job: - Iterates all matching chunks and reads Spectate components. - Uses PrefabRef lookup to verify the referenced target is a prefab entity. - Builds a NativeParallelHashMap of unique target entities -> SpectatorSite (carrying the originating event). - For each unique target not already having a SpectatorSite, adds the TargetElement to the event's buffer (if the event entity has a TargetElement buffer) and enqueues an AddComponent(SpectatorSite) on the target via the command buffer.
-
private void __AssignQueries(ref SystemState state)
: System.Void
Internal helper used during compiler-time setup. In this implementation it currently creates and disposes an empty EntityQueryBuilder (placeholder used in compile-time wiring). -
protected override void OnCreateForCompiler()
: System.Void
Called by generated/compiled code paths to assign queries and type handles used by the job (calls __AssignQueries and __TypeHandle.__AssignHandles).
Nested types (high level):
SpectateJob : IJob
- Attributes: [BurstCompile]
- Fields:
- ReadOnly NativeList
m_Chunks - ReadOnly ComponentTypeHandle
m_SpectateType - ReadOnly ComponentLookup
m_PrefabRefData - ComponentLookup
m_SpectatorSiteData - BufferLookup
m_TargetElements - EntityCommandBuffer m_CommandBuffer
- ReadOnly NativeList
-
Method:
public void Execute()
Job logic described above: gathers all Spectate components, builds a deduplicated map of target => SpectatorSite, updates event buffers and enqueues AddComponent calls through m_CommandBuffer. -
TypeHandle
Internal struct that stores and assigns the component handles/lookups required by SpectateJob: - ComponentTypeHandle
(read-only) - ComponentLookup
(read-only) - ComponentLookup
(read/write) - BufferLookup
(read/write) - Method:
__AssignHandles(ref SystemState state)
to populate the handles from the SystemState.
Usage Example
// Example: create an event entity that requests spectating a target entity.
// Assumes Spectate is a struct with fields: Entity m_Target; Entity m_Event;
var em = World.DefaultGameObjectInjectionWorld.EntityManager;
// Create an "event" entity (type and components depend on mod code; this is illustrative)
Entity eventEntity = em.CreateEntity(typeof(Game.Common.Event), typeof(Unity.Entities.DynamicBuffer<Game.Events.TargetElement>));
// Suppose targetEntity is an existing prefab entity with a PrefabRef component
Entity targetEntity = /* get or create target prefab entity */;
// Create a spectate request entity that references the event and target
Entity spectateRequest = em.CreateEntity(typeof(Game.Events.Spectate));
em.SetComponentData(spectateRequest, new Game.Events.Spectate { m_Target = targetEntity, m_Event = eventEntity });
// On the next system tick, SpectateSystem will process the Spectate component,
// add a SpectatorSite to the target (if appropriate) and append a TargetElement to the event buffer.
Notes and caveats: - The system relies on PrefabRef being present on the referenced target entity to verify it is a valid prefab. - Structural changes (AddComponent) are done through the ModificationBarrier4 command buffer; the actual addition will occur when the command buffer is played back. - The system uses Burst and parallel native collections to reduce GC and improve performance; ensure access patterns and lifetimes are respected if adapting code.