Skip to main content

bevy_ecs/
hierarchy.rs

1//! The canonical "parent-child" [`Relationship`] for entities, driven by
2//! the [`ChildOf`] [`Relationship`] and the [`Children`] [`RelationshipTarget`].
3//!
4//! See [`ChildOf`] for a full description of the relationship and how to use it.
5//!
6//! [`Relationship`]: crate::relationship::Relationship
7//! [`RelationshipTarget`]: crate::relationship::RelationshipTarget
8
9#[cfg(feature = "bevy_reflect")]
10use crate::reflect::{ReflectComponent, ReflectFromWorld};
11use crate::{
12    bundle::Bundle,
13    component::Component,
14    entity::Entity,
15    relationship::{RelatedSpawner, RelatedSpawnerCommands},
16    system::EntityCommands,
17    template::FromTemplate,
18    world::{EntityWorldMut, FromWorld, World},
19};
20use alloc::vec::Vec;
21#[cfg(feature = "bevy_reflect")]
22use bevy_reflect::std_traits::ReflectDefault;
23#[cfg(all(feature = "serialize", feature = "bevy_reflect"))]
24use bevy_reflect::{ReflectDeserialize, ReflectSerialize};
25use core::ops::Deref;
26use core::slice;
27
28/// Stores the parent entity of this child entity with this component.
29///
30/// This is a [`Relationship`] component, and creates the canonical
31/// "parent / child" hierarchy. This is the "source of truth" component, and it pairs with
32/// the [`Children`] [`RelationshipTarget`](crate::relationship::RelationshipTarget).
33///
34/// This relationship should be used for things like:
35///
36/// 1. Organizing entities in a scene
37/// 2. Propagating configuration or data inherited from a parent, such as "visibility" or "world-space global transforms".
38/// 3. Ensuring a hierarchy is despawned when an entity is despawned.
39///
40/// [`ChildOf`] contains a single "target" [`Entity`]. When [`ChildOf`] is inserted on a "source" entity,
41/// the "target" entity will automatically (and immediately, via a component hook) have a [`Children`]
42/// component inserted, and the "source" entity will be added to that [`Children`] instance.
43///
44/// If the [`ChildOf`] component is replaced with a different "target" entity, the old target's [`Children`]
45/// will be automatically (and immediately, via a component hook) be updated to reflect that change.
46///
47/// Likewise, when the [`ChildOf`] component is removed, the "source" entity will be removed from the old
48/// target's [`Children`]. If this results in [`Children`] being empty, [`Children`] will be automatically removed.
49///
50/// When a parent is despawned, all children (and their descendants) will _also_ be despawned.
51///
52/// You can create parent-child relationships in a variety of ways. The most direct way is to insert a [`ChildOf`] component:
53///
54/// ```
55/// # use bevy_ecs::prelude::*;
56/// # let mut world = World::new();
57/// let root = world.spawn_empty().id();
58/// let child1 = world.spawn(ChildOf(root)).id();
59/// let child2 = world.spawn(ChildOf(root)).id();
60/// let grandchild = world.spawn(ChildOf(child1)).id();
61///
62/// assert_eq!(&**world.entity(root).get::<Children>().unwrap(), &[child1, child2]);
63/// assert_eq!(&**world.entity(child1).get::<Children>().unwrap(), &[grandchild]);
64///
65/// world.entity_mut(child2).remove::<ChildOf>();
66/// assert_eq!(&**world.entity(root).get::<Children>().unwrap(), &[child1]);
67///
68/// world.entity_mut(root).despawn();
69/// assert!(world.get_entity(root).is_err());
70/// assert!(world.get_entity(child1).is_err());
71/// assert!(world.get_entity(grandchild).is_err());
72/// ```
73///
74/// However if you are spawning many children, you might want to use the [`EntityWorldMut::with_children`] helper instead:
75///
76/// ```
77/// # use bevy_ecs::prelude::*;
78/// # let mut world = World::new();
79/// let mut child1 = None;
80/// let mut child2 = None;
81/// let mut grandchild = None;
82/// let root = world.spawn_empty().with_children(|p| {
83///     child1 = Some(p.spawn_empty().with_children(|p| {
84///         grandchild = Some(p.spawn_empty().id());
85///     }).id());
86///     child2 = Some(p.spawn_empty().id());
87/// }).id();
88///
89/// assert_eq!(&**world.entity(root).get::<Children>().unwrap(), &[child1.unwrap(), child2.unwrap()]);
90/// assert_eq!(&**world.entity(child1.unwrap()).get::<Children>().unwrap(), &[grandchild.unwrap()]);
91/// ```
92///
93/// [`Relationship`]: crate::relationship::Relationship
94#[derive(Component, FromTemplate, Clone, PartialEq, Eq, Debug)]
95#[cfg_attr(feature = "bevy_reflect", derive(bevy_reflect::Reflect))]
96#[cfg_attr(
97    feature = "bevy_reflect",
98    reflect(Component, PartialEq, Debug, FromWorld, Clone)
99)]
100#[cfg_attr(feature = "serialize", derive(serde::Serialize, serde::Deserialize))]
101#[cfg_attr(
102    all(feature = "serialize", feature = "bevy_reflect"),
103    reflect(Serialize, Deserialize)
104)]
105#[relationship(relationship_target = Children)]
106#[doc(alias = "IsChild", alias = "Parent")]
107pub struct ChildOf(#[entities] pub Entity);
108
109impl ChildOf {
110    /// The parent entity of this child entity.
111    #[inline]
112    pub fn parent(&self) -> Entity {
113        self.0
114    }
115}
116
117// TODO: We need to impl either FromWorld or Default so ChildOf can be registered as Reflect.
118// This is because Reflect deserialize by creating an instance and apply a patch on top.
119// However ChildOf should only ever be set with a real user-defined entity.  Its worth looking into
120// better ways to handle cases like this.
121impl FromWorld for ChildOf {
122    #[inline(always)]
123    fn from_world(_world: &mut World) -> Self {
124        ChildOf(Entity::PLACEHOLDER)
125    }
126}
127
128/// Tracks which entities are children of this parent entity.
129///
130/// A [`RelationshipTarget`] collection component that is populated
131/// with entities that "target" this entity with the [`ChildOf`] [`Relationship`] component.
132///
133/// Together, these components form the "canonical parent-child hierarchy". See the [`ChildOf`] component for the full
134/// description of this relationship and instructions on how to use it.
135///
136/// # Usage
137///
138/// Like all [`RelationshipTarget`] components, this data should not be directly manipulated to avoid desynchronization.
139/// Instead, modify the [`ChildOf`] components on the "source" entities.
140///
141/// To access the children of an entity, you can iterate over the [`Children`] component,
142/// using the [`IntoIterator`] trait.
143/// For more complex access patterns, see the [`RelationshipTarget`] trait.
144///
145/// [`Relationship`]: crate::relationship::Relationship
146/// [`RelationshipTarget`]: crate::relationship::RelationshipTarget
147#[derive(Component, Default, Debug, PartialEq, Eq)]
148#[relationship_target(relationship = ChildOf, linked_spawn)]
149#[cfg_attr(feature = "bevy_reflect", derive(bevy_reflect::Reflect))]
150#[cfg_attr(feature = "bevy_reflect", reflect(Component, FromWorld, Default))]
151#[doc(alias = "IsParent")]
152pub struct Children(Vec<Entity>);
153
154impl Children {
155    /// Swaps the child at `a_index` with the child at `b_index`.
156    #[inline]
157    pub fn swap(&mut self, a_index: usize, b_index: usize) {
158        self.0.swap(a_index, b_index);
159    }
160
161    /// Sorts children [stably](https://en.wikipedia.org/wiki/Sorting_algorithm#Stability)
162    /// in place using the provided comparator function.
163    ///
164    /// For the underlying implementation, see [`slice::sort_by`].
165    ///
166    /// For the unstable version, see [`sort_unstable_by`](Children::sort_unstable_by).
167    ///
168    /// See also [`sort_by_key`](Children::sort_by_key), [`sort_by_cached_key`](Children::sort_by_cached_key).
169    #[inline]
170    pub fn sort_by<F>(&mut self, compare: F)
171    where
172        F: FnMut(&Entity, &Entity) -> core::cmp::Ordering,
173    {
174        self.0.sort_by(compare);
175    }
176
177    /// Sorts children [stably](https://en.wikipedia.org/wiki/Sorting_algorithm#Stability)
178    /// in place using the provided key extraction function.
179    ///
180    /// For the underlying implementation, see [`slice::sort_by_key`].
181    ///
182    /// For the unstable version, see [`sort_unstable_by_key`](Children::sort_unstable_by_key).
183    ///
184    /// See also [`sort_by`](Children::sort_by), [`sort_by_cached_key`](Children::sort_by_cached_key).
185    #[inline]
186    pub fn sort_by_key<K, F>(&mut self, compare: F)
187    where
188        F: FnMut(&Entity) -> K,
189        K: Ord,
190    {
191        self.0.sort_by_key(compare);
192    }
193
194    /// Sorts children [stably](https://en.wikipedia.org/wiki/Sorting_algorithm#Stability)
195    /// in place using the provided key extraction function. Only evaluates each key at most
196    /// once per sort, caching the intermediate results in memory.
197    ///
198    /// For the underlying implementation, see [`slice::sort_by_cached_key`].
199    ///
200    /// See also [`sort_by`](Children::sort_by), [`sort_by_key`](Children::sort_by_key).
201    #[inline]
202    pub fn sort_by_cached_key<K, F>(&mut self, compare: F)
203    where
204        F: FnMut(&Entity) -> K,
205        K: Ord,
206    {
207        self.0.sort_by_cached_key(compare);
208    }
209
210    /// Sorts children [unstably](https://en.wikipedia.org/wiki/Sorting_algorithm#Stability)
211    /// in place using the provided comparator function.
212    ///
213    /// For the underlying implementation, see [`slice::sort_unstable_by`].
214    ///
215    /// For the stable version, see [`sort_by`](Children::sort_by).
216    ///
217    /// See also [`sort_unstable_by_key`](Children::sort_unstable_by_key).
218    #[inline]
219    pub fn sort_unstable_by<F>(&mut self, compare: F)
220    where
221        F: FnMut(&Entity, &Entity) -> core::cmp::Ordering,
222    {
223        self.0.sort_unstable_by(compare);
224    }
225
226    /// Sorts children [unstably](https://en.wikipedia.org/wiki/Sorting_algorithm#Stability)
227    /// in place using the provided key extraction function.
228    ///
229    /// For the underlying implementation, see [`slice::sort_unstable_by_key`].
230    ///
231    /// For the stable version, see [`sort_by_key`](Children::sort_by_key).
232    ///
233    /// See also [`sort_unstable_by`](Children::sort_unstable_by).
234    #[inline]
235    pub fn sort_unstable_by_key<K, F>(&mut self, compare: F)
236    where
237        F: FnMut(&Entity) -> K,
238        K: Ord,
239    {
240        self.0.sort_unstable_by_key(compare);
241    }
242}
243
244impl<'a> IntoIterator for &'a Children {
245    type Item = <Self::IntoIter as Iterator>::Item;
246
247    type IntoIter = slice::Iter<'a, Entity>;
248
249    #[inline(always)]
250    fn into_iter(self) -> Self::IntoIter {
251        self.0.iter()
252    }
253}
254
255impl Deref for Children {
256    type Target = [Entity];
257
258    fn deref(&self) -> &Self::Target {
259        &self.0
260    }
261}
262
263/// A type alias over [`RelatedSpawner`] used to spawn child entities containing a [`ChildOf`] relationship.
264pub type ChildSpawner<'w> = RelatedSpawner<'w, ChildOf>;
265
266/// A type alias over [`RelatedSpawnerCommands`] used to spawn child entities containing a [`ChildOf`] relationship.
267pub type ChildSpawnerCommands<'w> = RelatedSpawnerCommands<'w, ChildOf>;
268
269impl<'w> EntityWorldMut<'w> {
270    /// Spawns children of this entity (with a [`ChildOf`] relationship) by taking a function that operates on a [`ChildSpawner`].
271    /// See also [`with_related`](Self::with_related).
272    pub fn with_children(&mut self, func: impl FnOnce(&mut ChildSpawner)) -> &mut Self {
273        self.with_related_entities(func);
274        self
275    }
276
277    /// Adds the given children to this entity.
278    /// See also [`add_related`](Self::add_related).
279    pub fn add_children(&mut self, children: &[Entity]) -> &mut Self {
280        self.add_related::<ChildOf>(children)
281    }
282
283    /// Removes all the parent-child relationships from this entity.
284    /// To despawn the child entities, instead use [`EntityWorldMut::despawn_children`](EntityWorldMut::despawn_children).
285    /// See also [`detach_all_related`](Self::detach_all_related)
286    pub fn detach_all_children(&mut self) -> &mut Self {
287        self.detach_all_related::<ChildOf>()
288    }
289
290    /// Insert children at specific index.
291    /// See also [`insert_related`](Self::insert_related).
292    pub fn insert_children(&mut self, index: usize, children: &[Entity]) -> &mut Self {
293        self.insert_related::<ChildOf>(index, children)
294    }
295
296    /// Insert child at specific index.
297    /// See also [`insert_related`](Self::insert_related).
298    pub fn insert_child(&mut self, index: usize, child: Entity) -> &mut Self {
299        self.insert_related::<ChildOf>(index, &[child])
300    }
301
302    /// Adds the given child to this entity.
303    /// See also [`add_related`](Self::add_related).
304    pub fn add_child(&mut self, child: Entity) -> &mut Self {
305        self.add_related::<ChildOf>(&[child])
306    }
307
308    /// Removes the parent-child relationship between this entity and the given entities.
309    /// Does not despawn the children.
310    pub fn detach_children(&mut self, children: &[Entity]) -> &mut Self {
311        self.remove_related::<ChildOf>(children)
312    }
313
314    /// Removes the parent-child relationship between this entity and the given entity.
315    /// Does not despawn the child.
316    pub fn detach_child(&mut self, child: Entity) -> &mut Self {
317        self.remove_related::<ChildOf>(&[child])
318    }
319
320    /// Replaces all the related children with a new set of children.
321    ///
322    /// Duplicated children are removed, leaving only their first occurrence.
323    pub fn replace_children(&mut self, children: &[Entity]) -> &mut Self {
324        self.replace_related::<ChildOf>(children)
325    }
326
327    /// Replaces all the related children with a new set of children.
328    ///
329    /// # Warning
330    ///
331    /// Failing to maintain the functions invariants may lead to erratic engine behavior including random crashes.
332    /// Refer to [`Self::replace_related_with_difference`] for a list of these invariants.
333    ///
334    /// # Panics
335    ///
336    /// Panics when debug assertions are enabled if an invariant is broken and the command is executed.
337    pub fn replace_children_with_difference(
338        &mut self,
339        entities_to_unrelate: &[Entity],
340        entities_to_relate: &[Entity],
341        newly_related_entities: &[Entity],
342    ) -> &mut Self {
343        self.replace_related_with_difference::<ChildOf>(
344            entities_to_unrelate,
345            entities_to_relate,
346            newly_related_entities,
347        )
348    }
349
350    /// Spawns the passed bundle and adds it to this entity as a child.
351    ///
352    /// For efficient spawning of multiple children, use [`with_children`].
353    ///
354    /// [`with_children`]: EntityWorldMut::with_children
355    pub fn with_child(&mut self, bundle: impl Bundle) -> &mut Self {
356        let parent = self.id();
357        self.world_scope(|world| {
358            world.spawn((bundle, ChildOf(parent)));
359        });
360        self
361    }
362}
363
364impl<'a> EntityCommands<'a> {
365    /// Spawns children of this entity (with a [`ChildOf`] relationship) by taking a function that operates on a [`ChildSpawner`].
366    pub fn with_children(
367        &mut self,
368        func: impl FnOnce(&mut RelatedSpawnerCommands<ChildOf>),
369    ) -> &mut Self {
370        self.with_related_entities(func);
371        self
372    }
373
374    /// Adds the given children to this entity.
375    pub fn add_children(&mut self, children: &[Entity]) -> &mut Self {
376        self.add_related::<ChildOf>(children)
377    }
378
379    /// Removes all the parent-child relationships from this entity.
380    /// To despawn the child entities, instead use [`EntityWorldMut::despawn_children`](EntityWorldMut::despawn_children).
381    /// See also [`detach_all_related`](Self::detach_all_related)
382    pub fn detach_all_children(&mut self) -> &mut Self {
383        self.detach_all_related::<ChildOf>()
384    }
385
386    /// Insert children at specific index.
387    /// See also [`insert_related`](Self::insert_related).
388    pub fn insert_children(&mut self, index: usize, children: &[Entity]) -> &mut Self {
389        self.insert_related::<ChildOf>(index, children)
390    }
391
392    /// Insert children at specific index.
393    /// See also [`insert_related`](Self::insert_related).
394    pub fn insert_child(&mut self, index: usize, child: Entity) -> &mut Self {
395        self.insert_related::<ChildOf>(index, &[child])
396    }
397
398    /// Adds the given child to this entity.
399    pub fn add_child(&mut self, child: Entity) -> &mut Self {
400        self.add_related::<ChildOf>(&[child])
401    }
402
403    /// Removes the parent-child relationship between this entity and the given entities.
404    /// Does not despawn the children.
405    pub fn detach_children(&mut self, children: &[Entity]) -> &mut Self {
406        self.remove_related::<ChildOf>(children)
407    }
408
409    /// Removes the parent-child relationship between this entity and the given entity.
410    /// Does not despawn the child.
411    pub fn detach_child(&mut self, child: Entity) -> &mut Self {
412        self.remove_related::<ChildOf>(&[child])
413    }
414
415    /// Replaces the children on this entity with a new list of children.
416    ///
417    /// Duplicated children are removed, leaving only their first occurrence.
418    pub fn replace_children(&mut self, children: &[Entity]) -> &mut Self {
419        self.replace_related::<ChildOf>(children)
420    }
421
422    /// Replaces all the related entities with a new set of entities.
423    ///
424    /// # Warning
425    ///
426    /// Failing to maintain the functions invariants may lead to erratic engine behavior including random crashes.
427    /// Refer to [`EntityWorldMut::replace_related_with_difference`] for a list of these invariants.
428    ///
429    /// # Panics
430    ///
431    /// Panics when debug assertions are enabled if an invariant is broken and the command is executed.
432    pub fn replace_children_with_difference(
433        &mut self,
434        entities_to_unrelate: &[Entity],
435        entities_to_relate: &[Entity],
436        newly_related_entities: &[Entity],
437    ) -> &mut Self {
438        self.replace_related_with_difference::<ChildOf>(
439            entities_to_unrelate,
440            entities_to_relate,
441            newly_related_entities,
442        )
443    }
444
445    /// Spawns the passed bundle and adds it to this entity as a child.
446    ///
447    /// For efficient spawning of multiple children, use [`with_children`].
448    ///
449    /// [`with_children`]: EntityCommands::with_children
450    pub fn with_child(&mut self, bundle: impl Bundle) -> &mut Self {
451        self.with_related::<ChildOf>(bundle);
452        self
453    }
454}
455
456/// Returns a [`SpawnRelatedBundle`] that will insert the [`Children`] component, spawn a [`SpawnableList`] of entities with given bundles that
457/// relate to the [`Children`] entity via the [`ChildOf`] component, and reserve space in the [`Children`] for each spawned entity.
458///
459/// Any additional arguments will be interpreted as bundles to be spawned.
460///
461/// Also see [`related`](crate::related) for a version of this that works with any [`RelationshipTarget`] type.
462///
463/// ```
464/// # use bevy_ecs::hierarchy::Children;
465/// # use bevy_ecs::name::Name;
466/// # use bevy_ecs::world::World;
467/// # use bevy_ecs::children;
468/// let mut world = World::new();
469/// world.spawn((
470///     Name::new("Root"),
471///     children![
472///         Name::new("Child1"),
473///         (
474///             Name::new("Child2"),
475///             children![Name::new("Grandchild")]
476///         )
477///     ]
478/// ));
479/// ```
480///
481/// [`RelationshipTarget`]: crate::relationship::RelationshipTarget
482/// [`SpawnRelatedBundle`]: crate::spawn::SpawnRelatedBundle
483/// [`SpawnableList`]: crate::spawn::SpawnableList
484#[macro_export]
485macro_rules! children {
486    [$($child:expr),*$(,)?] => {
487        $crate::related!($crate::hierarchy::Children [$($child),*])
488    };
489}
490
491#[cfg(test)]
492mod tests {
493    use crate::{
494        entity::Entity,
495        hierarchy::{ChildOf, Children},
496        relationship::{RelationshipHookMode, RelationshipTarget},
497        spawn::{Spawn, SpawnRelated},
498        world::World,
499    };
500    use alloc::{vec, vec::Vec};
501
502    #[derive(PartialEq, Eq, Debug)]
503    struct Node {
504        entity: Entity,
505        children: Vec<Node>,
506    }
507
508    impl Node {
509        fn new(entity: Entity) -> Self {
510            Self {
511                entity,
512                children: Vec::new(),
513            }
514        }
515
516        fn new_with(entity: Entity, children: Vec<Node>) -> Self {
517            Self { entity, children }
518        }
519    }
520
521    fn get_hierarchy(world: &World, entity: Entity) -> Node {
522        Node {
523            entity,
524            children: world
525                .entity(entity)
526                .get::<Children>()
527                .map_or_else(Default::default, |c| {
528                    c.iter().map(|e| get_hierarchy(world, e)).collect()
529                }),
530        }
531    }
532
533    #[test]
534    fn hierarchy() {
535        let mut world = World::new();
536        let root = world.spawn_empty().id();
537        let child1 = world.spawn(ChildOf(root)).id();
538        let grandchild = world.spawn(ChildOf(child1)).id();
539        let child2 = world.spawn(ChildOf(root)).id();
540
541        // Spawn
542        let hierarchy = get_hierarchy(&world, root);
543        assert_eq!(
544            hierarchy,
545            Node::new_with(
546                root,
547                vec![
548                    Node::new_with(child1, vec![Node::new(grandchild)]),
549                    Node::new(child2)
550                ]
551            )
552        );
553
554        // Removal
555        world.entity_mut(child1).remove::<ChildOf>();
556        let hierarchy = get_hierarchy(&world, root);
557        assert_eq!(hierarchy, Node::new_with(root, vec![Node::new(child2)]));
558
559        // Insert
560        world.entity_mut(child1).insert(ChildOf(root));
561        let hierarchy = get_hierarchy(&world, root);
562        assert_eq!(
563            hierarchy,
564            Node::new_with(
565                root,
566                vec![
567                    Node::new(child2),
568                    Node::new_with(child1, vec![Node::new(grandchild)])
569                ]
570            )
571        );
572
573        // Recursive Despawn
574        world.entity_mut(root).despawn();
575        assert!(world.get_entity(root).is_err());
576        assert!(world.get_entity(child1).is_err());
577        assert!(world.get_entity(child2).is_err());
578        assert!(world.get_entity(grandchild).is_err());
579    }
580
581    #[test]
582    fn with_children() {
583        let mut world = World::new();
584        let mut child1 = None;
585        let mut child2 = None;
586        let root = world
587            .spawn_empty()
588            .with_children(|p| {
589                child1 = Some(p.spawn_empty().id());
590                child2 = Some(p.spawn_empty().id());
591            })
592            .id();
593
594        let hierarchy = get_hierarchy(&world, root);
595        assert_eq!(
596            hierarchy,
597            Node::new_with(
598                root,
599                vec![Node::new(child1.unwrap()), Node::new(child2.unwrap())]
600            )
601        );
602    }
603
604    #[test]
605    fn add_children() {
606        let mut world = World::new();
607        let child1 = world.spawn_empty().id();
608        let child2 = world.spawn_empty().id();
609        let root = world.spawn_empty().add_children(&[child1, child2]).id();
610
611        let hierarchy = get_hierarchy(&world, root);
612        assert_eq!(
613            hierarchy,
614            Node::new_with(root, vec![Node::new(child1), Node::new(child2)])
615        );
616    }
617
618    #[test]
619    fn insert_children() {
620        let mut world = World::new();
621        let child1 = world.spawn_empty().id();
622        let child2 = world.spawn_empty().id();
623        let child3 = world.spawn_empty().id();
624        let child4 = world.spawn_empty().id();
625
626        let mut entity_world_mut = world.spawn_empty();
627
628        let first_children = entity_world_mut.add_children(&[child1, child2]);
629
630        let root = first_children.insert_children(1, &[child3, child4]).id();
631
632        let hierarchy = get_hierarchy(&world, root);
633        assert_eq!(
634            hierarchy,
635            Node::new_with(
636                root,
637                vec![
638                    Node::new(child1),
639                    Node::new(child3),
640                    Node::new(child4),
641                    Node::new(child2)
642                ]
643            )
644        );
645    }
646
647    #[test]
648    fn insert_child() {
649        let mut world = World::new();
650        let child1 = world.spawn_empty().id();
651        let child2 = world.spawn_empty().id();
652        let child3 = world.spawn_empty().id();
653
654        let mut entity_world_mut = world.spawn_empty();
655
656        let first_children = entity_world_mut.add_children(&[child1, child2]);
657
658        let root = first_children.insert_child(1, child3).id();
659
660        let hierarchy = get_hierarchy(&world, root);
661        assert_eq!(
662            hierarchy,
663            Node::new_with(
664                root,
665                vec![Node::new(child1), Node::new(child3), Node::new(child2)]
666            )
667        );
668    }
669
670    // regression test for https://github.com/bevyengine/bevy/pull/19134
671    #[test]
672    fn insert_children_index_bound() {
673        let mut world = World::new();
674        let child1 = world.spawn_empty().id();
675        let child2 = world.spawn_empty().id();
676        let child3 = world.spawn_empty().id();
677        let child4 = world.spawn_empty().id();
678
679        let mut entity_world_mut = world.spawn_empty();
680
681        let first_children = entity_world_mut.add_children(&[child1, child2]).id();
682        let hierarchy = get_hierarchy(&world, first_children);
683        assert_eq!(
684            hierarchy,
685            Node::new_with(first_children, vec![Node::new(child1), Node::new(child2)])
686        );
687
688        let root = world
689            .entity_mut(first_children)
690            .insert_children(usize::MAX, &[child3, child4])
691            .id();
692        let hierarchy = get_hierarchy(&world, root);
693        assert_eq!(
694            hierarchy,
695            Node::new_with(
696                root,
697                vec![
698                    Node::new(child1),
699                    Node::new(child2),
700                    Node::new(child3),
701                    Node::new(child4),
702                ]
703            )
704        );
705    }
706
707    #[test]
708    fn detach_children() {
709        let mut world = World::new();
710        let child1 = world.spawn_empty().id();
711        let child2 = world.spawn_empty().id();
712        let child3 = world.spawn_empty().id();
713        let child4 = world.spawn_empty().id();
714
715        let mut root = world.spawn_empty();
716        root.add_children(&[child1, child2, child3, child4]);
717        root.detach_children(&[child2, child3]);
718        let root = root.id();
719
720        let hierarchy = get_hierarchy(&world, root);
721        assert_eq!(
722            hierarchy,
723            Node::new_with(root, vec![Node::new(child1), Node::new(child4)])
724        );
725    }
726
727    #[test]
728    fn detach_child() {
729        let mut world = World::new();
730        let child1 = world.spawn_empty().id();
731        let child2 = world.spawn_empty().id();
732        let child3 = world.spawn_empty().id();
733
734        let mut root = world.spawn_empty();
735        root.add_children(&[child1, child2, child3]);
736        root.detach_child(child2);
737        let root = root.id();
738
739        let hierarchy = get_hierarchy(&world, root);
740        assert_eq!(
741            hierarchy,
742            Node::new_with(root, vec![Node::new(child1), Node::new(child3)])
743        );
744    }
745
746    #[test]
747    fn self_parenting_invalid() {
748        let mut world = World::new();
749        let id = world.spawn_empty().id();
750        world.entity_mut(id).insert(ChildOf(id));
751        assert!(
752            world.entity(id).get::<ChildOf>().is_none(),
753            "invalid ChildOf relationships should self-remove"
754        );
755    }
756
757    #[test]
758    fn missing_parent_invalid() {
759        let mut world = World::new();
760        let parent = world.spawn_empty().id();
761        world.entity_mut(parent).despawn();
762        let id = world.spawn(ChildOf(parent)).id();
763        assert!(
764            world.entity(id).get::<ChildOf>().is_none(),
765            "invalid ChildOf relationships should self-remove"
766        );
767    }
768
769    #[test]
770    fn reinsert_same_parent() {
771        let mut world = World::new();
772        let parent = world.spawn_empty().id();
773        let id = world.spawn(ChildOf(parent)).id();
774        world.entity_mut(id).insert(ChildOf(parent));
775        assert_eq!(
776            Some(&ChildOf(parent)),
777            world.entity(id).get::<ChildOf>(),
778            "ChildOf should still be there"
779        );
780    }
781
782    #[test]
783    fn spawn_children() {
784        let mut world = World::new();
785        let id = world.spawn(Children::spawn((Spawn(()), Spawn(())))).id();
786        assert_eq!(world.entity(id).get::<Children>().unwrap().len(), 2,);
787    }
788
789    #[test]
790    fn spawn_many_children() {
791        let mut world = World::new();
792
793        // ensure an empty set can be mentioned
794        world.spawn(children![]);
795
796        // 12 children should result in a flat tuple
797        let id = world
798            .spawn(children![(), (), (), (), (), (), (), (), (), (), (), ()])
799            .id();
800
801        assert_eq!(world.entity(id).get::<Children>().unwrap().len(), 12,);
802
803        // 13 will start nesting, but should nonetheless produce a flat hierarchy
804        let id = world
805            .spawn(children![
806                (),
807                (),
808                (),
809                (),
810                (),
811                (),
812                (),
813                (),
814                (),
815                (),
816                (),
817                (),
818                (),
819            ])
820            .id();
821
822        assert_eq!(world.entity(id).get::<Children>().unwrap().len(), 13,);
823    }
824
825    #[test]
826    fn replace_children() {
827        let mut world = World::new();
828        let parent = world.spawn(Children::spawn((Spawn(()), Spawn(())))).id();
829        let &[child_a, child_b] = &world.entity(parent).get::<Children>().unwrap().0[..] else {
830            panic!("Tried to spawn 2 children on an entity and didn't get 2 children");
831        };
832
833        let child_c = world.spawn_empty().id();
834
835        world
836            .entity_mut(parent)
837            .replace_children(&[child_a, child_c]);
838
839        let children = world.entity(parent).get::<Children>().unwrap();
840
841        assert!(children.contains(&child_a));
842        assert!(children.contains(&child_c));
843        assert!(!children.contains(&child_b));
844
845        assert_eq!(
846            world.entity(child_a).get::<ChildOf>().unwrap(),
847            &ChildOf(parent)
848        );
849        assert_eq!(
850            world.entity(child_c).get::<ChildOf>().unwrap(),
851            &ChildOf(parent)
852        );
853        assert!(world.entity(child_b).get::<ChildOf>().is_none());
854    }
855
856    #[test]
857    fn replace_children_with_nothing() {
858        let mut world = World::new();
859        let parent = world.spawn_empty().id();
860        let child_a = world.spawn_empty().id();
861        let child_b = world.spawn_empty().id();
862
863        world.entity_mut(parent).add_children(&[child_a, child_b]);
864
865        assert_eq!(world.entity(parent).get::<Children>().unwrap().len(), 2);
866
867        world.entity_mut(parent).replace_children(&[]);
868
869        assert!(world.entity(child_a).get::<ChildOf>().is_none());
870        assert!(world.entity(child_b).get::<ChildOf>().is_none());
871    }
872
873    #[test]
874    fn insert_same_child_twice() {
875        let mut world = World::new();
876
877        let parent = world.spawn_empty().id();
878        let child = world.spawn_empty().id();
879
880        world.entity_mut(parent).add_child(child);
881        world.entity_mut(parent).add_child(child);
882
883        let children = world.get::<Children>(parent).unwrap();
884        assert_eq!(children.0, [child]);
885        assert_eq!(
886            world.entity(child).get::<ChildOf>().unwrap(),
887            &ChildOf(parent)
888        );
889    }
890
891    #[test]
892    fn replace_with_difference() {
893        let mut world = World::new();
894
895        let parent = world.spawn_empty().id();
896        let child_a = world.spawn_empty().id();
897        let child_b = world.spawn_empty().id();
898        let child_c = world.spawn_empty().id();
899        let child_d = world.spawn_empty().id();
900
901        // Test inserting new relations
902        world.entity_mut(parent).replace_children_with_difference(
903            &[],
904            &[child_a, child_b],
905            &[child_a, child_b],
906        );
907
908        assert_eq!(
909            world.entity(child_a).get::<ChildOf>().unwrap(),
910            &ChildOf(parent)
911        );
912        assert_eq!(
913            world.entity(child_b).get::<ChildOf>().unwrap(),
914            &ChildOf(parent)
915        );
916        assert_eq!(
917            world.entity(parent).get::<Children>().unwrap().0,
918            [child_a, child_b]
919        );
920
921        // Test replacing relations and changing order
922        world.entity_mut(parent).replace_children_with_difference(
923            &[child_b],
924            &[child_d, child_c, child_a],
925            &[child_c, child_d],
926        );
927        assert_eq!(
928            world.entity(child_a).get::<ChildOf>().unwrap(),
929            &ChildOf(parent)
930        );
931        assert_eq!(
932            world.entity(child_c).get::<ChildOf>().unwrap(),
933            &ChildOf(parent)
934        );
935        assert_eq!(
936            world.entity(child_d).get::<ChildOf>().unwrap(),
937            &ChildOf(parent)
938        );
939        assert_eq!(
940            world.entity(parent).get::<Children>().unwrap().0,
941            [child_d, child_c, child_a]
942        );
943        assert!(!world.entity(child_b).contains::<ChildOf>());
944
945        // Test removing relationships
946        world.entity_mut(parent).replace_children_with_difference(
947            &[child_a, child_d, child_c],
948            &[],
949            &[],
950        );
951        assert!(!world.entity(parent).contains::<Children>());
952        assert!(!world.entity(child_a).contains::<ChildOf>());
953        assert!(!world.entity(child_b).contains::<ChildOf>());
954        assert!(!world.entity(child_c).contains::<ChildOf>());
955        assert!(!world.entity(child_d).contains::<ChildOf>());
956    }
957
958    #[test]
959    fn replace_with_difference_on_empty() {
960        let mut world = World::new();
961
962        let parent = world.spawn_empty().id();
963        let child_a = world.spawn_empty().id();
964
965        world
966            .entity_mut(parent)
967            .replace_children_with_difference(&[child_a], &[], &[]);
968
969        assert!(!world.entity(parent).contains::<Children>());
970        assert!(!world.entity(child_a).contains::<ChildOf>());
971    }
972
973    #[test]
974    fn replace_with_difference_totally_new_children() {
975        let mut world = World::new();
976
977        let parent = world.spawn_empty().id();
978        let child_a = world.spawn_empty().id();
979        let child_b = world.spawn_empty().id();
980        let child_c = world.spawn_empty().id();
981        let child_d = world.spawn_empty().id();
982
983        // Test inserting new relations
984        world.entity_mut(parent).replace_children_with_difference(
985            &[],
986            &[child_a, child_b],
987            &[child_a, child_b],
988        );
989
990        assert_eq!(
991            world.entity(child_a).get::<ChildOf>().unwrap(),
992            &ChildOf(parent)
993        );
994        assert_eq!(
995            world.entity(child_b).get::<ChildOf>().unwrap(),
996            &ChildOf(parent)
997        );
998        assert_eq!(
999            world.entity(parent).get::<Children>().unwrap().0,
1000            [child_a, child_b]
1001        );
1002
1003        // Test replacing relations and changing order
1004        world.entity_mut(parent).replace_children_with_difference(
1005            &[child_b, child_a],
1006            &[child_d, child_c],
1007            &[child_c, child_d],
1008        );
1009        assert_eq!(
1010            world.entity(child_c).get::<ChildOf>().unwrap(),
1011            &ChildOf(parent)
1012        );
1013        assert_eq!(
1014            world.entity(child_d).get::<ChildOf>().unwrap(),
1015            &ChildOf(parent)
1016        );
1017        assert_eq!(
1018            world.entity(parent).get::<Children>().unwrap().0,
1019            [child_d, child_c]
1020        );
1021        assert!(!world.entity(child_a).contains::<ChildOf>());
1022        assert!(!world.entity(child_b).contains::<ChildOf>());
1023    }
1024
1025    #[test]
1026    fn replace_children_order() {
1027        let mut world = World::new();
1028
1029        let parent = world.spawn_empty().id();
1030        let child_a = world.spawn_empty().id();
1031        let child_b = world.spawn_empty().id();
1032        let child_c = world.spawn_empty().id();
1033        let child_d = world.spawn_empty().id();
1034
1035        let initial_order = [child_a, child_b, child_c, child_d];
1036        world.entity_mut(parent).add_children(&initial_order);
1037
1038        assert_eq!(
1039            world.entity_mut(parent).get::<Children>().unwrap().0,
1040            initial_order
1041        );
1042
1043        let new_order = [child_d, child_b, child_a, child_c];
1044        world.entity_mut(parent).replace_children(&new_order);
1045
1046        assert_eq!(world.entity(parent).get::<Children>().unwrap().0, new_order);
1047    }
1048
1049    #[test]
1050    fn replace_children_duplicates() {
1051        let mut world = World::new();
1052
1053        let parent = world.spawn_empty().id();
1054        let child_a = world.spawn_empty().id();
1055        let child_b = world.spawn_empty().id();
1056
1057        world
1058            .entity_mut(parent)
1059            .add_children(&[child_a])
1060            .replace_children(&[child_a, child_a]);
1061
1062        assert_eq!(world.entity(parent).get::<Children>().unwrap().0, [child_a]);
1063
1064        world.entity_mut(parent).clear();
1065
1066        // Ensure the order is correct (child_a before child_b, irrespective of which is already inserted).
1067
1068        world
1069            .entity_mut(parent)
1070            .add_children(&[child_b])
1071            .replace_children(&[child_a, child_b, child_a]);
1072
1073        assert_eq!(
1074            world.entity(parent).get::<Children>().unwrap().0,
1075            [child_a, child_b]
1076        );
1077
1078        world.entity_mut(parent).clear();
1079
1080        world
1081            .entity_mut(parent)
1082            .add_children(&[child_a])
1083            .replace_children(&[child_a, child_b, child_a]);
1084
1085        assert_eq!(
1086            world.entity(parent).get::<Children>().unwrap().0,
1087            [child_a, child_b]
1088        );
1089    }
1090
1091    #[test]
1092    #[should_panic]
1093    #[cfg_attr(
1094        not(debug_assertions),
1095        ignore = "we don't check invariants if debug assertions are off"
1096    )]
1097    fn replace_diff_invariant_overlapping_unrelate_with_relate() {
1098        let mut world = World::new();
1099
1100        let parent = world.spawn_empty().id();
1101        let child_a = world.spawn_empty().id();
1102
1103        world
1104            .entity_mut(parent)
1105            .replace_children_with_difference(&[], &[child_a], &[child_a]);
1106
1107        // This should panic
1108        world
1109            .entity_mut(parent)
1110            .replace_children_with_difference(&[child_a], &[child_a], &[]);
1111    }
1112
1113    #[test]
1114    #[should_panic]
1115    #[cfg_attr(
1116        not(debug_assertions),
1117        ignore = "we don't check invariants if debug assertions are off"
1118    )]
1119    fn replace_diff_invariant_overlapping_unrelate_with_newly() {
1120        let mut world = World::new();
1121
1122        let parent = world.spawn_empty().id();
1123        let child_a = world.spawn_empty().id();
1124        let child_b = world.spawn_empty().id();
1125
1126        world
1127            .entity_mut(parent)
1128            .replace_children_with_difference(&[], &[child_a], &[child_a]);
1129
1130        // This should panic
1131        world.entity_mut(parent).replace_children_with_difference(
1132            &[child_b],
1133            &[child_a, child_b],
1134            &[child_b],
1135        );
1136    }
1137
1138    #[test]
1139    #[should_panic]
1140    #[cfg_attr(
1141        not(debug_assertions),
1142        ignore = "we don't check invariants if debug assertions are off"
1143    )]
1144    fn replace_diff_invariant_newly_not_subset() {
1145        let mut world = World::new();
1146
1147        let parent = world.spawn_empty().id();
1148        let child_a = world.spawn_empty().id();
1149        let child_b = world.spawn_empty().id();
1150
1151        // This should panic
1152        world.entity_mut(parent).replace_children_with_difference(
1153            &[],
1154            &[child_a, child_b],
1155            &[child_a],
1156        );
1157    }
1158
1159    #[test]
1160    fn child_replace_hook_skip() {
1161        let mut world = World::new();
1162        let parent = world.spawn_empty().id();
1163        let other = world.spawn_empty().id();
1164        let child = world.spawn(ChildOf(parent)).id();
1165        world
1166            .entity_mut(child)
1167            .insert_with_relationship_hook_mode(ChildOf(other), RelationshipHookMode::Skip);
1168        assert_eq!(
1169            &**world.entity(parent).get::<Children>().unwrap(),
1170            &[child],
1171            "Children should still have the old value, as on_insert/on_discard didn't run"
1172        );
1173    }
1174}