Skip to content

Make lifecycle events ordering and meaning more intuitive #20729

@SkiFire13

Description

@SkiFire13

What problem does this solve or what need does it fill?

I was looking at the various lifecycle events we have and IMO they are quite confusing. Apart from having events that kinda overlap (e.g. Insert/Add, or Replace/Remove), the documentation for when they run is not very clear. Consider for example if we wanted to understand when Remove runs without looking at bevy_ecs's source code, you can go look at the documentation and this is what you see (the (N) were added by me):

- Replace: Triggered when a component is removed from an entity, regardless if it is then replaced with a new value. (1)
- Remove: Triggered when a component is removed from an entity and not replaced, before the component is removed. (3)
- Despawn: Triggered for each component on an entity when it is despawned.

Replace hooks are evaluated before Remove, then finally Despawn hooks are evaluated. (2)

I would first look at (1), but there's no indication of this there. To actually understand when it runs I have to go down until (2) to see that it runs before Remove, then go back to (3) to see that Remove runs before a component is removed, and hence by transitivity conclude that Replace also runs before.

You can argue it's kinda intuitive because otherwise you likely want to observe the component being removed... but not everything is intuitive, for example Replace runs regardless if the component is then replaced (????) and an event when a component is actually replaced doesn't seem to exist.

Can we make these events a bit configurable, so the user can choose to e.g. run before or after the event happens, or when any of a group of events happens (e.g. to allow Replace to actually run only on replace)?

What solution would you like?

I'd like a more structured approach where each lifecycle event has a Before and After variant which gets fired respectively before and after a component is modified. This would make it clear at the use-site when that observer/hook will run.

I'd also like to see some clearer names for the lifecycle events, with for example Replace running only when a component is actualy replaced. This might not be possible in general, but maybe we could build a more generic system where people can write observers that run when any of two or more lifecycle events happen?

What alternative(s) have you considered?

Improve documentation, but I would argue it's generally better if this was so obvious that you don't need to go look at its documentation.

Additional context

See this discussion on discord

Metadata

Metadata

Assignees

No one assigned

    Labels

    A-ECSEntities, components, systems, and eventsC-FeatureA new feature, making something new possibleD-ComplexQuite challenging from either a design or technical perspective. Ask for help!S-Needs-BenchmarkingThis set of changes needs performance benchmarking to double-check that they helpS-Needs-DesignThis issue requires design work to think about how it would best be accomplished

    Type

    No type

    Projects

    No projects

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions