diff --git a/crates/bevy_transform/src/hierarchy/child_builder.rs b/crates/bevy_transform/src/hierarchy/child_builder.rs index 9731c8c02b0e5..71fc54aeb24ce 100644 --- a/crates/bevy_transform/src/hierarchy/child_builder.rs +++ b/crates/bevy_transform/src/hierarchy/child_builder.rs @@ -219,7 +219,7 @@ impl<'w> BuildWorldChildren for EntityMut<'w> { fn push_children(&mut self, children: &[Entity]) -> &mut Self { let parent = self.id(); { - // SAFE: parent entity is not modified + // SAFE: parent entity is not modified and its location is updated manually let world = unsafe { self.world_mut() }; for child in children.iter() { world @@ -227,6 +227,8 @@ impl<'w> BuildWorldChildren for EntityMut<'w> { // FIXME: don't erase the previous parent (see #1545) .insert_bundle((Parent(parent), PreviousParent(parent))); } + // Inserting a bundle in the children entities may change the parent entity's location if they were of the same archetype + self.update_location(); } if let Some(mut children_component) = self.get_mut::() { children_component.0.extend(children.iter().cloned()); @@ -239,7 +241,7 @@ impl<'w> BuildWorldChildren for EntityMut<'w> { fn insert_children(&mut self, index: usize, children: &[Entity]) -> &mut Self { let parent = self.id(); { - // SAFE: parent entity is not modified + // SAFE: parent entity is not modified and its location is updated manually let world = unsafe { self.world_mut() }; for child in children.iter() { world @@ -247,6 +249,8 @@ impl<'w> BuildWorldChildren for EntityMut<'w> { // FIXME: don't erase the previous parent (see #1545) .insert_bundle((Parent(parent), PreviousParent(parent))); } + // Inserting a bundle in the children entities may change the parent entity's location if they were of the same archetype + self.update_location(); } if let Some(mut children_component) = self.get_mut::() { @@ -471,4 +475,11 @@ mod tests { PreviousParent(parent) ); } + + #[test] + fn regression_push_children_same_archetype() { + let mut world = World::new(); + let child = world.spawn().id(); + world.spawn().push_children(&[child]); + } }