Conversation
|
It looks like your PR has been selected for a highlight in the next release blog post, but you didn't provide a release note. Please review the instructions for writing release notes, then expand or revise the content in the release notes directory to showcase your changes. |
Jondolf
left a comment
There was a problem hiding this comment.
I like this a lot! This has been something that I'd really like for Avian, as we've been planning to split the RigidBody enum into mutually exclusive DynamicBody, KinematicBody, and StaticBody components. This is already possible to hack together via hooks, but it's not ideal, and the lack of a first-party "mutual exclusiveness" invariant has kept me wary of using the pattern.
I did an initial cursory review of the code, and it looks pretty solid already. I like the tests! I'm not too familiar with the archetype code though, so I'll defer checking its correctness to the ECS wizards :)
Some general initial thoughts:
- I like starting minimal here, and a
WorldAPI is enough for my purposes. More user-facing derive shorthands orQueryintegration would be nice, but can totally be left to future PRs IMO. - I like the default behavior of removing existing components that are incompatible with a new insertion, and panicking when adding two exclusive components simultaneously. I can see others maybe wanting different behavior in some cases, like not inserting an incompatible component instead of replacing an existing one, or emitting a warning instead of panicking, but I think the behavior in this PR is the right default. If other options are strongly desired, we can consider adding them in other PRs.
- Some usage docs and examples could be nice! Though right now, this is not as user-facing as it's only a
WorldAPI.
I'll try to do a more thorough review later
Objective
Implement mutually exclusive invariant from #1481, allowing enum-like components that cannot co-exist on the same archetype.
Solution
Add
World::register_mutually_exclusive_componentsthat allows to register which components are incompatible with each other and would be removed if any of the others are inserted.This is a minimal implementation which just makes this pattern integrated with the ecs -
World::register_mutually_exclusive_componentsis the only public interface featured in this PR.Possible extensions that are left to future PRs:
#[derive(Component)]shortcut to define mutually exclusive components more ergonomicallyQueryfilters aware of mutually exclusive components so that entities with different mutually exclusive components don't cause conflicts.Testing
bundle/tests.rscontains new tests for basic functionality, miri passes.