Hierarchy traversal and syntactic sugar for `EntityCommands`
- Dominant language
- Rust
- Stars
- 48.2k
- Forks
- 4.8k
- Avg merge
- 3d 22h
- Merged PRs (30d)
- 161
Description
## What problem does this solve or what need does it fill?
I love `EntityCommands` daisy chaining but to me, it doesn't work anymore when dealing with parent/children entities, since I have to stop the flow to get parent or child from queries (that could be get ridden of to unclutter the system signature).
Also, I think that in general, it could be easily improved by adding a bit of syntactic sugar.
## What solution would you like?
- A way to access parent/children directly from the `EntityCommands`:
- a `parent()` (and faillible `get_parent()`) method,
- and a `on_children(f)` method that would feel like an enumerator counterpart to `with_children(f)` BuildChildren ;
- Conditional counterparts for all entity operations, e.g `insert_if()`, `remove_if()`, `despawn_if()`…
As an example of what I mean, here is some pseudocode of how I think it would greatly improve concision and readability:
```rust
fn my_system_with_syntactic_sugar(
mut commands: Commands,
// -- SNIP --
) {
// -- SNIP --
let some_condition = false;
// -- SNIP --
commands
.entity(some_known_child_entity)
.insert(SomeMarker)
.parent()
.insert_if(some_condition, SomeRelatedMarker)
.on_children(|child_entity_commands| {
child_entity_commands
.remove_if::(!some_condition)
.despawn_recursive_if(some_condition)
;
})
;
}
```
Whereas today, in bevy 0.11, I'm writing this as:
```rust
fn my_system_without_syntactic_sugar(
mut commands: Commands,
parent_query: ,
children_query: ,
// -- SNIP --
) {
// -- SNIP --
let some_condition = false;
// -- SNIP --
commands
.entity(some_known_child_entity)
.insert(SomeMarker)
;
let parent_entity = parent_query.get(some_known_child_entity);
if some_condition {
commands
.entity(parent_entity)
.insert(SomeRelatedMarker)
;
}
children_query
.for_each(|child_entity| {
if (some_condition) {
commands
.entity(child_entity)
.despawn_recursive()
;
} else {
commands
.entity(child_entity)
.remove::
;
}
})
;
}
```
## Additional context
I'm still a Bevy newbie and still in the process of learning Rust, so there's maybe already a better way to express those kind of things that I don't know of, so please feel free to correct me!
## Performance?
Also, I'm not savy enough about bevy internals (and Rust in general☺) to evaluate the performance hit of storing references to parent/children entities in `EntityCommands`, so maybe making it optional would be better (e.g. a `HierarchyEntityCommands` that could be accessed using `commands.entity_in_hierarchy(some_known_child_entity)` ? (Although maybe maintenance cost would be too high…).
Thanks in advance for your input, have a nice day!
Contributor guide
Assessment
This issue has not been assessed yet.