Events
A CombatSystem deals damage and needs to tell an AudioSystem, a floating-damage-number UI, and an achievement tracker, without knowing any of them exist. That’s what events are for: emit once, let anyone interested read it.
Emitting
Section titled “Emitting”public struct DamageDealt : IEvent{ public Entity Target; public int Amount;}
world.Emit(new DamageDealt { Target = goblin, Amount = 5 });IEvent is a marker interface, same shape as IComponent. Emit is immediate, no CommandBuffer involved, and safe to call concurrently from several systems in the same parallel stage.
Reading
Section titled “Reading”public sealed partial class DamageNumbersSystem(World world) : QuerySystem{ private readonly EventReader<DamageDealt> _damageEvents = world.CreateEventReader<DamageDealt>();
protected override IQuery DefineQuery(Query query) => query.With<Position>();
public void Update(Time time) { foreach (var damage in _damageEvents.Read()) { // spawn a floating number at damage.Target's position } }}Create one EventReader<T> per system that cares, store it, call Read() once every tick. Each reader tracks its own position independently, one system reading DamageDealt doesn’t affect what another sees.
Events tell you something happened. For inspecting live world state directly, see Debugging.