@@ -46,11 +46,6 @@ pub struct PushChildren {
4646    children :  SmallVec < [ Entity ;  8 ] > , 
4747} 
4848
49- pub  struct  ChildBuilder < ' a ,  ' b >  { 
50-     commands :  & ' b  mut  Commands < ' a > , 
51-     push_children :  PushChildren , 
52- } 
53- 
5449impl  Command  for  PushChildren  { 
5550    fn  write ( self :  Box < Self > ,  world :  & mut  World )  { 
5651        for  child in  self . children . iter ( )  { 
@@ -77,6 +72,46 @@ impl Command for PushChildren {
7772    } 
7873} 
7974
75+ pub  struct  RemoveChildren  { 
76+     parent :  Entity , 
77+     children :  SmallVec < [ Entity ;  8 ] > , 
78+ } 
79+ 
80+ fn  remove_children ( parent :  Entity ,  children :  & [ Entity ] ,  world :  & mut  World )  { 
81+     for  child in  children. iter ( )  { 
82+         let  mut  child = world. entity_mut ( * child) ; 
83+         let  mut  remove_parent = false ; 
84+         if  let  Some ( child_parent)  = child. get_mut :: < Parent > ( )  { 
85+             if  child_parent. 0  == parent { 
86+                 remove_parent = true ; 
87+             } 
88+         } 
89+         if  remove_parent { 
90+             if  let  Some ( parent)  = child. remove :: < Parent > ( )  { 
91+                 child. insert ( PreviousParent ( parent. 0 ) ) ; 
92+             } 
93+         } 
94+     } 
95+     // Remove the children from the parents. 
96+     if  let  Some ( mut  parent_children)  = world. get_mut :: < Children > ( parent)  { 
97+         parent_children
98+             . 0 
99+             . retain ( |parent_child| !children. contains ( parent_child) ) ; 
100+     } 
101+ } 
102+ 
103+ impl  Command  for  RemoveChildren  { 
104+     fn  write ( self :  Box < Self > ,  world :  & mut  World )  { 
105+         // Remove any matching Parent components from the children 
106+         remove_children ( self . parent ,  & self . children ,  world) ; 
107+     } 
108+ } 
109+ 
110+ pub  struct  ChildBuilder < ' a ,  ' b >  { 
111+     commands :  & ' b  mut  Commands < ' a > , 
112+     push_children :  PushChildren , 
113+ } 
114+ 
80115impl < ' a ,  ' b >  ChildBuilder < ' a ,  ' b >  { 
81116    pub  fn  spawn_bundle ( & mut  self ,  bundle :  impl  Bundle )  -> EntityCommands < ' a ,  ' _ >  { 
82117        let  e = self . commands . spawn_bundle ( bundle) ; 
@@ -104,6 +139,7 @@ pub trait BuildChildren {
104139    fn  with_children ( & mut  self ,  f :  impl  FnOnce ( & mut  ChildBuilder ) )  -> & mut  Self ; 
105140    fn  push_children ( & mut  self ,  children :  & [ Entity ] )  -> & mut  Self ; 
106141    fn  insert_children ( & mut  self ,  index :  usize ,  children :  & [ Entity ] )  -> & mut  Self ; 
142+     fn  remove_children ( & mut  self ,  children :  & [ Entity ] )  -> & mut  Self ; 
107143} 
108144
109145impl < ' a ,  ' b >  BuildChildren  for  EntityCommands < ' a ,  ' b >  { 
@@ -143,6 +179,15 @@ impl<'a, 'b> BuildChildren for EntityCommands<'a, 'b> {
143179        } ) ; 
144180        self 
145181    } 
182+ 
183+     fn  remove_children ( & mut  self ,  children :  & [ Entity ] )  -> & mut  Self  { 
184+         let  parent = self . id ( ) ; 
185+         self . commands ( ) . add ( RemoveChildren  { 
186+             children :  SmallVec :: from ( children) , 
187+             parent, 
188+         } ) ; 
189+         self 
190+     } 
146191} 
147192
148193#[ derive( Debug ) ]  
@@ -202,6 +247,7 @@ pub trait BuildWorldChildren {
202247    fn  with_children ( & mut  self ,  spawn_children :  impl  FnOnce ( & mut  WorldChildBuilder ) )  -> & mut  Self ; 
203248    fn  push_children ( & mut  self ,  children :  & [ Entity ] )  -> & mut  Self ; 
204249    fn  insert_children ( & mut  self ,  index :  usize ,  children :  & [ Entity ] )  -> & mut  Self ; 
250+     fn  remove_children ( & mut  self ,  children :  & [ Entity ] )  -> & mut  Self ; 
205251} 
206252
207253impl < ' w >  BuildWorldChildren  for  EntityMut < ' w >  { 
@@ -262,6 +308,33 @@ impl<'w> BuildWorldChildren for EntityMut<'w> {
262308        } 
263309        self 
264310    } 
311+ 
312+     fn  remove_children ( & mut  self ,  children :  & [ Entity ] )  -> & mut  Self  { 
313+         let  parent = self . id ( ) ; 
314+         // SAFE: This doesn't change the parent's location 
315+         let  world = unsafe  {  self . world_mut ( )  } ; 
316+         for  child in  children. iter ( )  { 
317+             let  mut  child = world. entity_mut ( * child) ; 
318+             let  mut  remove_parent = false ; 
319+             if  let  Some ( child_parent)  = child. get_mut :: < Parent > ( )  { 
320+                 if  child_parent. 0  == parent { 
321+                     remove_parent = true ; 
322+                 } 
323+             } 
324+             if  remove_parent { 
325+                 if  let  Some ( parent)  = child. remove :: < Parent > ( )  { 
326+                     child. insert ( PreviousParent ( parent. 0 ) ) ; 
327+                 } 
328+             } 
329+         } 
330+         // Remove the children from the parents. 
331+         if  let  Some ( mut  parent_children)  = world. get_mut :: < Children > ( parent)  { 
332+             parent_children
333+                 . 0 
334+                 . retain ( |parent_child| !children. contains ( parent_child) ) ; 
335+         } 
336+         self 
337+     } 
265338} 
266339
267340impl < ' w >  BuildWorldChildren  for  WorldChildBuilder < ' w >  { 
@@ -321,6 +394,15 @@ impl<'w> BuildWorldChildren for WorldChildBuilder<'w> {
321394        } 
322395        self 
323396    } 
397+ 
398+     fn  remove_children ( & mut  self ,  children :  & [ Entity ] )  -> & mut  Self  { 
399+         let  parent = self 
400+             . current_entity 
401+             . expect ( "Cannot remove children without a parent. Try creating an entity first." ) ; 
402+ 
403+         remove_children ( parent,  children,  self . world ) ; 
404+         self 
405+     } 
324406} 
325407
326408#[ cfg( test) ]  
@@ -367,7 +449,7 @@ mod tests {
367449    } 
368450
369451    #[ test]  
370-     fn  push_and_insert_children_commands ( )  { 
452+     fn  push_and_insert_and_remove_children_commands ( )  { 
371453        let  mut  world = World :: default ( ) ; 
372454
373455        let  entities = world
@@ -425,10 +507,33 @@ mod tests {
425507            * world. get:: <PreviousParent >( child4) . unwrap( ) , 
426508            PreviousParent ( parent) 
427509        ) ; 
510+ 
511+         let  remove_children = [ child1,  child4] ; 
512+         { 
513+             let  mut  commands = Commands :: new ( & mut  queue,  & world) ; 
514+             commands. entity ( parent) . remove_children ( & remove_children) ; 
515+         } 
516+         queue. apply ( & mut  world) ; 
517+ 
518+         let  expected_children:  SmallVec < [ Entity ;  8 ] >  = smallvec ! [ child3,  child2] ; 
519+         assert_eq ! ( 
520+             world. get:: <Children >( parent) . unwrap( ) . 0 . clone( ) , 
521+             expected_children
522+         ) ; 
523+         assert ! ( world. get:: <Parent >( child1) . is_none( ) ) ; 
524+         assert ! ( world. get:: <Parent >( child4) . is_none( ) ) ; 
525+         assert_eq ! ( 
526+             * world. get:: <PreviousParent >( child1) . unwrap( ) , 
527+             PreviousParent ( parent) 
528+         ) ; 
529+         assert_eq ! ( 
530+             * world. get:: <PreviousParent >( child4) . unwrap( ) , 
531+             PreviousParent ( parent) 
532+         ) ; 
428533    } 
429534
430535    #[ test]  
431-     fn  push_and_insert_children_world ( )  { 
536+     fn  push_and_insert_and_remove_children_world ( )  { 
432537        let  mut  world = World :: default ( ) ; 
433538
434539        let  entities = world
@@ -476,5 +581,23 @@ mod tests {
476581            * world. get:: <PreviousParent >( child4) . unwrap( ) , 
477582            PreviousParent ( parent) 
478583        ) ; 
584+ 
585+         let  remove_children = [ child1,  child4] ; 
586+         world. entity_mut ( parent) . remove_children ( & remove_children) ; 
587+         let  expected_children:  SmallVec < [ Entity ;  8 ] >  = smallvec ! [ child3,  child2] ; 
588+         assert_eq ! ( 
589+             world. get:: <Children >( parent) . unwrap( ) . 0 . clone( ) , 
590+             expected_children
591+         ) ; 
592+         assert ! ( world. get:: <Parent >( child1) . is_none( ) ) ; 
593+         assert ! ( world. get:: <Parent >( child4) . is_none( ) ) ; 
594+         assert_eq ! ( 
595+             * world. get:: <PreviousParent >( child1) . unwrap( ) , 
596+             PreviousParent ( parent) 
597+         ) ; 
598+         assert_eq ! ( 
599+             * world. get:: <PreviousParent >( child4) . unwrap( ) , 
600+             PreviousParent ( parent) 
601+         ) ; 
479602    } 
480603} 
0 commit comments