Mutually Exclusive Components #17707
Labels
A-ECS
Entities, components, systems, and events
C-Feature
A new feature, making something new possible
S-Needs-Design
This issue requires design work to think about how it would best be accomplished
What problem does this solve or what need does it fill?
Provide a way to declare two or more components as "mutually exclusive". That is if
ComponentA
andComponentB
are mutually exclusive, only one ofComponentA
orComponentB
may exist on anEntity
at a given time.What solution would you like?
An annotation or derive macro that marks two or more components as xor, or another way to register the relationship with the application.
When a
ComponentA
is added to anEntity
that already has aComponentB
, thenComponentB
will be automatically & atomically removed, thus upholding the invariant.Queries could be made aware of mutually exclusive components, and add implicit
Without
filters as appropriate. That isQuery<.., With<ComponentA>>
is equivalent toQuery<.., (With<ComponentA>, Without<ComponentB>)>
.This works to allow a system to have both
Query<&mut T, With<ComponentA>>
andQuery<&mut T, With<ComponentB>>
, without the user needing to explicitly write theWithout
filters.It should be possible for the user to add a
ComponentC
to an existing set of mutually exclusive components defined by a 3rd party.What alternative(s) have you considered?
Enum Components provide similar xor behaviour, however the entire enum must be queried and then branched on inside systems. Additionally, it is not possible to add variants to an existing enum (point 4 of the previous section).
Additional context
This is kinda sorta the inverse of "Required Components", but it provides a stronger invariant (xor-ness should always be maintained) and can integrate more meaningfully into queries & systems, rather than acting only at bundle insertion time.
I'm sure I've seen this idea floating around before, so this is an attempt to formalise the feature request. (Maybe it should be an rfc?)
The text was updated successfully, but these errors were encountered: