1use alloc::collections::{btree_set, BTreeSet};
2use core::{
3 hash::BuildHasher,
4 ops::{Deref, DerefMut},
5};
6
7use crate::entity::{Entity, EntityHashSet, EntityIndexSet};
8use alloc::vec::Vec;
9use indexmap::IndexSet;
10use smallvec::SmallVec;
11
12pub trait RelationshipSourceCollection {
15 type SourceIter<'a>: Iterator<Item = Entity>
23 where
24 Self: 'a;
25
26 fn new() -> Self;
28
29 fn with_capacity(capacity: usize) -> Self;
33
34 fn reserve(&mut self, additional: usize);
38
39 fn add(&mut self, entity: Entity) -> bool;
45
46 fn remove(&mut self, entity: Entity) -> bool;
51
52 fn iter(&self) -> Self::SourceIter<'_>;
54
55 fn len(&self) -> usize;
57
58 fn clear(&mut self);
60
61 fn shrink_to_fit(&mut self);
65
66 #[inline]
68 fn is_empty(&self) -> bool {
69 self.len() == 0
70 }
71
72 fn source_to_remove_before_add(&self) -> Option<Entity> {
75 None
76 }
77
78 fn extend_from_iter(&mut self, entities: impl IntoIterator<Item = Entity>);
82}
83
84pub trait OrderedRelationshipSourceCollection: RelationshipSourceCollection {
86 fn insert(&mut self, index: usize, entity: Entity);
89 fn remove_at(&mut self, index: usize) -> Option<Entity>;
91 fn insert_stable(&mut self, index: usize, entity: Entity);
95 fn remove_at_stable(&mut self, index: usize) -> Option<Entity>;
98 fn sort(&mut self);
100 fn insert_sorted(&mut self, entity: Entity);
102
103 fn place_most_recent(&mut self, index: usize);
105
106 fn place(&mut self, entity: Entity, index: usize);
110
111 fn push_front(&mut self, entity: Entity) {
113 self.insert(0, entity);
114 }
115
116 fn push_back(&mut self, entity: Entity) {
118 self.insert(usize::MAX, entity);
119 }
120
121 fn pop_front(&mut self) -> Option<Entity> {
123 self.remove_at(0)
124 }
125
126 fn pop_back(&mut self) -> Option<Entity> {
128 if self.is_empty() {
129 None
130 } else {
131 self.remove_at(self.len() - 1)
132 }
133 }
134}
135
136impl RelationshipSourceCollection for Vec<Entity> {
137 type SourceIter<'a> = core::iter::Copied<core::slice::Iter<'a, Entity>>;
138
139 fn new() -> Self {
140 Vec::new()
141 }
142
143 fn reserve(&mut self, additional: usize) {
144 Vec::reserve(self, additional);
145 }
146
147 fn with_capacity(capacity: usize) -> Self {
148 Vec::with_capacity(capacity)
149 }
150
151 fn add(&mut self, entity: Entity) -> bool {
152 Vec::push(self, entity);
153
154 true
155 }
156
157 fn remove(&mut self, entity: Entity) -> bool {
158 if let Some(index) = <[Entity]>::iter(self).rposition(|e| *e == entity) {
161 Vec::remove(self, index);
162 return true;
163 }
164
165 false
166 }
167
168 fn iter(&self) -> Self::SourceIter<'_> {
169 <[Entity]>::iter(self).copied()
170 }
171
172 fn len(&self) -> usize {
173 Vec::len(self)
174 }
175
176 fn clear(&mut self) {
177 self.clear();
178 }
179
180 fn shrink_to_fit(&mut self) {
181 Vec::shrink_to_fit(self);
182 }
183
184 fn extend_from_iter(&mut self, entities: impl IntoIterator<Item = Entity>) {
185 self.extend(entities);
186 }
187}
188
189impl OrderedRelationshipSourceCollection for Vec<Entity> {
190 fn insert(&mut self, index: usize, entity: Entity) {
191 self.push(entity);
192 let len = self.len();
193 if index < len {
194 self.swap(index, len - 1);
195 }
196 }
197
198 fn remove_at(&mut self, index: usize) -> Option<Entity> {
199 (index < self.len()).then(|| self.swap_remove(index))
200 }
201
202 fn insert_stable(&mut self, index: usize, entity: Entity) {
203 if index < self.len() {
204 Vec::insert(self, index, entity);
205 } else {
206 self.push(entity);
207 }
208 }
209
210 fn remove_at_stable(&mut self, index: usize) -> Option<Entity> {
211 (index < self.len()).then(|| self.remove(index))
212 }
213
214 fn sort(&mut self) {
215 self.sort_unstable();
216 }
217
218 fn insert_sorted(&mut self, entity: Entity) {
219 let index = self.partition_point(|e| e <= &entity);
220 self.insert_stable(index, entity);
221 }
222
223 fn place_most_recent(&mut self, index: usize) {
224 if let Some(entity) = self.pop() {
225 let index = index.min(self.len());
226 self.insert(index, entity);
227 }
228 }
229
230 fn place(&mut self, entity: Entity, index: usize) {
231 if let Some(current) = <[Entity]>::iter(self).position(|e| *e == entity) {
232 Vec::remove(self, current);
233 let index = index.min(self.len());
234 self.insert(index, entity);
235 };
236 }
237}
238
239impl RelationshipSourceCollection for EntityHashSet {
240 type SourceIter<'a> = core::iter::Copied<crate::entity::hash_set::Iter<'a, Entity>>;
241
242 fn new() -> Self {
243 EntityHashSet::new()
244 }
245
246 fn reserve(&mut self, additional: usize) {
247 self.deref_mut().reserve(additional);
248 }
249
250 fn with_capacity(capacity: usize) -> Self {
251 EntityHashSet::with_capacity(capacity)
252 }
253
254 fn add(&mut self, entity: Entity) -> bool {
255 self.insert(entity)
256 }
257
258 fn remove(&mut self, entity: Entity) -> bool {
259 self.deref_mut().remove(&entity)
260 }
261
262 fn iter(&self) -> Self::SourceIter<'_> {
263 self.iter().copied()
264 }
265
266 fn len(&self) -> usize {
267 self.deref().len()
268 }
269
270 fn clear(&mut self) {
271 self.deref_mut().clear();
272 }
273
274 fn shrink_to_fit(&mut self) {
275 self.deref_mut().shrink_to_fit();
276 }
277
278 fn extend_from_iter(&mut self, entities: impl IntoIterator<Item = Entity>) {
279 self.extend(entities);
280 }
281}
282
283impl<const N: usize> RelationshipSourceCollection for SmallVec<[Entity; N]> {
284 type SourceIter<'a> = core::iter::Copied<core::slice::Iter<'a, Entity>>;
285
286 fn new() -> Self {
287 SmallVec::new()
288 }
289
290 fn reserve(&mut self, additional: usize) {
291 SmallVec::reserve(self, additional);
292 }
293
294 fn with_capacity(capacity: usize) -> Self {
295 SmallVec::with_capacity(capacity)
296 }
297
298 fn add(&mut self, entity: Entity) -> bool {
299 SmallVec::push(self, entity);
300
301 true
302 }
303
304 fn remove(&mut self, entity: Entity) -> bool {
305 if let Some(index) = <[Entity]>::iter(self).position(|e| *e == entity) {
306 SmallVec::remove(self, index);
307 return true;
308 }
309
310 false
311 }
312
313 fn iter(&self) -> Self::SourceIter<'_> {
314 <[Entity]>::iter(self).copied()
315 }
316
317 fn len(&self) -> usize {
318 SmallVec::len(self)
319 }
320
321 fn clear(&mut self) {
322 self.clear();
323 }
324
325 fn shrink_to_fit(&mut self) {
326 SmallVec::shrink_to_fit(self);
327 }
328
329 fn extend_from_iter(&mut self, entities: impl IntoIterator<Item = Entity>) {
330 self.extend(entities);
331 }
332}
333
334impl RelationshipSourceCollection for Entity {
335 type SourceIter<'a> = core::option::IntoIter<Entity>;
336
337 fn new() -> Self {
338 Entity::PLACEHOLDER
339 }
340
341 fn reserve(&mut self, _: usize) {}
342
343 fn with_capacity(_capacity: usize) -> Self {
344 Self::new()
345 }
346
347 fn add(&mut self, entity: Entity) -> bool {
348 *self = entity;
349 true
350 }
351
352 fn remove(&mut self, entity: Entity) -> bool {
353 if *self == entity {
354 *self = Entity::PLACEHOLDER;
355
356 return true;
357 }
358
359 false
360 }
361
362 fn iter(&self) -> Self::SourceIter<'_> {
363 if *self == Entity::PLACEHOLDER {
364 None.into_iter()
365 } else {
366 Some(*self).into_iter()
367 }
368 }
369
370 fn len(&self) -> usize {
371 if *self == Entity::PLACEHOLDER {
372 return 0;
373 }
374 1
375 }
376
377 fn clear(&mut self) {
378 *self = Entity::PLACEHOLDER;
379 }
380
381 fn shrink_to_fit(&mut self) {}
382
383 fn extend_from_iter(&mut self, entities: impl IntoIterator<Item = Entity>) {
384 for entity in entities {
385 *self = entity;
386 }
387 }
388
389 fn source_to_remove_before_add(&self) -> Option<Entity> {
390 if *self != Entity::PLACEHOLDER {
391 Some(*self)
392 } else {
393 None
394 }
395 }
396}
397
398impl<const N: usize> OrderedRelationshipSourceCollection for SmallVec<[Entity; N]> {
399 fn insert(&mut self, index: usize, entity: Entity) {
400 self.push(entity);
401 let len = self.len();
402 if index < len {
403 self.swap(index, len - 1);
404 }
405 }
406
407 fn remove_at(&mut self, index: usize) -> Option<Entity> {
408 (index < self.len()).then(|| self.swap_remove(index))
409 }
410
411 fn insert_stable(&mut self, index: usize, entity: Entity) {
412 if index < self.len() {
413 SmallVec::<[Entity; N]>::insert(self, index, entity);
414 } else {
415 self.push(entity);
416 }
417 }
418
419 fn remove_at_stable(&mut self, index: usize) -> Option<Entity> {
420 (index < self.len()).then(|| self.remove(index))
421 }
422
423 fn sort(&mut self) {
424 self.sort_unstable();
425 }
426
427 fn insert_sorted(&mut self, entity: Entity) {
428 let index = self.partition_point(|e| e <= &entity);
429 self.insert_stable(index, entity);
430 }
431
432 fn place_most_recent(&mut self, index: usize) {
433 if let Some(entity) = self.pop() {
434 let index = index.min(self.len());
435 self.insert(index, entity);
436 }
437 }
438
439 fn place(&mut self, entity: Entity, index: usize) {
440 if let Some(current) = <[Entity]>::iter(self).position(|e| *e == entity) {
441 SmallVec::<[Entity; N]>::remove(self, current);
442 let index = index.min(self.len());
443 self.insert(index, entity);
444 };
445 }
446}
447
448impl<S: BuildHasher + Default> RelationshipSourceCollection for IndexSet<Entity, S> {
449 type SourceIter<'a>
450 = core::iter::Copied<indexmap::set::Iter<'a, Entity>>
451 where
452 S: 'a;
453
454 fn new() -> Self {
455 IndexSet::default()
456 }
457
458 fn reserve(&mut self, additional: usize) {
459 self.reserve(additional);
460 }
461
462 fn with_capacity(capacity: usize) -> Self {
463 IndexSet::with_capacity_and_hasher(capacity, S::default())
464 }
465
466 fn add(&mut self, entity: Entity) -> bool {
467 self.insert(entity)
468 }
469
470 fn remove(&mut self, entity: Entity) -> bool {
471 self.shift_remove(&entity)
472 }
473
474 fn iter(&self) -> Self::SourceIter<'_> {
475 self.iter().copied()
476 }
477
478 fn len(&self) -> usize {
479 self.len()
480 }
481
482 fn clear(&mut self) {
483 self.clear();
484 }
485
486 fn shrink_to_fit(&mut self) {
487 self.shrink_to_fit();
488 }
489
490 fn extend_from_iter(&mut self, entities: impl IntoIterator<Item = Entity>) {
491 self.extend(entities);
492 }
493}
494
495impl RelationshipSourceCollection for EntityIndexSet {
496 type SourceIter<'a> = core::iter::Copied<crate::entity::index_set::Iter<'a, Entity>>;
497
498 fn new() -> Self {
499 EntityIndexSet::new()
500 }
501
502 fn reserve(&mut self, additional: usize) {
503 self.deref_mut().reserve(additional);
504 }
505
506 fn with_capacity(capacity: usize) -> Self {
507 EntityIndexSet::with_capacity(capacity)
508 }
509
510 fn add(&mut self, entity: Entity) -> bool {
511 self.insert(entity)
512 }
513
514 fn remove(&mut self, entity: Entity) -> bool {
515 self.deref_mut().shift_remove(&entity)
516 }
517
518 fn iter(&self) -> Self::SourceIter<'_> {
519 self.iter().copied()
520 }
521
522 fn len(&self) -> usize {
523 self.deref().len()
524 }
525
526 fn clear(&mut self) {
527 self.deref_mut().clear();
528 }
529
530 fn shrink_to_fit(&mut self) {
531 self.deref_mut().shrink_to_fit();
532 }
533
534 fn extend_from_iter(&mut self, entities: impl IntoIterator<Item = Entity>) {
535 self.extend(entities);
536 }
537}
538
539impl RelationshipSourceCollection for BTreeSet<Entity> {
540 type SourceIter<'a> = core::iter::Copied<btree_set::Iter<'a, Entity>>;
541
542 fn new() -> Self {
543 BTreeSet::new()
544 }
545
546 fn with_capacity(_: usize) -> Self {
547 Self::new()
549 }
550
551 fn reserve(&mut self, _: usize) {
552 }
554
555 fn add(&mut self, entity: Entity) -> bool {
556 self.insert(entity)
557 }
558
559 fn remove(&mut self, entity: Entity) -> bool {
560 self.remove(&entity)
561 }
562
563 fn iter(&self) -> Self::SourceIter<'_> {
564 self.iter().copied()
565 }
566
567 fn len(&self) -> usize {
568 self.len()
569 }
570
571 fn clear(&mut self) {
572 self.clear();
573 }
574
575 fn shrink_to_fit(&mut self) {
576 }
578
579 fn extend_from_iter(&mut self, entities: impl IntoIterator<Item = Entity>) {
580 self.extend(entities);
581 }
582}
583
584#[cfg(test)]
585mod tests {
586 use super::*;
587 use crate::prelude::{Component, World};
588 use crate::relationship::RelationshipTarget;
589 use alloc::vec;
590
591 #[test]
592 fn vec_relationship_source_collection() {
593 #[derive(Component)]
594 #[relationship(relationship_target = RelTarget)]
595 struct Rel(Entity);
596
597 #[derive(Component)]
598 #[relationship_target(relationship = Rel, linked_spawn)]
599 struct RelTarget(Vec<Entity>);
600
601 let mut world = World::new();
602 let a = world.spawn_empty().id();
603 let b = world.spawn_empty().id();
604
605 world.entity_mut(a).insert(Rel(b));
606
607 let rel_target = world.get::<RelTarget>(b).unwrap();
608 let collection = rel_target.collection();
609 assert_eq!(collection, &alloc::vec!(a));
610 }
611
612 #[test]
613 fn smallvec_relationship_source_collection() {
614 #[derive(Component)]
615 #[relationship(relationship_target = RelTarget)]
616 struct Rel(Entity);
617
618 #[derive(Component)]
619 #[relationship_target(relationship = Rel, linked_spawn)]
620 struct RelTarget(SmallVec<[Entity; 4]>);
621
622 let mut world = World::new();
623 let a = world.spawn_empty().id();
624 let b = world.spawn_empty().id();
625
626 world.entity_mut(a).insert(Rel(b));
627
628 let rel_target = world.get::<RelTarget>(b).unwrap();
629 let collection = rel_target.collection();
630 assert_eq!(collection, &SmallVec::from_buf([a]));
631 }
632
633 #[test]
634 fn entity_relationship_source_collection() {
635 #[derive(Component)]
636 #[relationship(relationship_target = RelTarget)]
637 struct Rel(Entity);
638
639 #[derive(Component)]
640 #[relationship_target(relationship = Rel)]
641 struct RelTarget(Entity);
642
643 let mut world = World::new();
644 let a = world.spawn_empty().id();
645 let b = world.spawn_empty().id();
646
647 world.entity_mut(a).insert(Rel(b));
648
649 let rel_target = world.get::<RelTarget>(b).unwrap();
650 let collection = rel_target.collection();
651 assert_eq!(collection, &a);
652 }
653
654 #[test]
655 fn vec_ordered_relationship_source_collection() {
656 let mut world = World::new();
657 let a = world.spawn_empty().id();
658 let b = world.spawn_empty().id();
659
660 let mut v: Vec<Entity> = vec![];
661 OrderedRelationshipSourceCollection::insert_stable(&mut v, 10, a);
662 assert_eq!(v, vec![a]);
663 OrderedRelationshipSourceCollection::insert_stable(&mut v, 10, b);
664 assert_eq!(v, vec![a, b]);
665 OrderedRelationshipSourceCollection::place(&mut v, b, 0);
666 assert_eq!(v, vec![b, a]);
667 OrderedRelationshipSourceCollection::place(&mut v, b, 10);
668 assert_eq!(v, vec![a, b]);
669 OrderedRelationshipSourceCollection::place(&mut v, b, 10);
670 assert_eq!(v, vec![a, b]);
671 OrderedRelationshipSourceCollection::place_most_recent(&mut v, 0);
672 assert_eq!(v, vec![b, a]);
673 OrderedRelationshipSourceCollection::place_most_recent(&mut v, 10);
674 assert_eq!(v, vec![b, a]);
675 }
676
677 #[test]
678 fn smallvec_ordered_relationship_source_collection() {
679 let mut world = World::new();
680 let a = world.spawn_empty().id();
681 let b = world.spawn_empty().id();
682
683 let mut v = SmallVec::<[Entity; 2]>::new();
684 OrderedRelationshipSourceCollection::insert_stable(&mut v, 10, a);
685 assert_eq!(v.as_ref(), vec![a]);
686 OrderedRelationshipSourceCollection::insert_stable(&mut v, 10, b);
687 assert_eq!(v.as_ref(), vec![a, b]);
688 OrderedRelationshipSourceCollection::place(&mut v, b, 0);
689 assert_eq!(v.as_ref(), vec![b, a]);
690 OrderedRelationshipSourceCollection::place(&mut v, b, 10);
691 assert_eq!(v.as_ref(), vec![a, b]);
692 OrderedRelationshipSourceCollection::place(&mut v, b, 10);
693 assert_eq!(v.as_ref(), vec![a, b]);
694 OrderedRelationshipSourceCollection::place_most_recent(&mut v, 0);
695 assert_eq!(v.as_ref(), vec![b, a]);
696 OrderedRelationshipSourceCollection::place_most_recent(&mut v, 10);
697 assert_eq!(v.as_ref(), vec![b, a]);
698 }
699
700 #[test]
701 fn one_to_one_relationships() {
702 #[derive(Component)]
703 #[relationship(relationship_target = Below)]
704 struct Above(Entity);
705
706 #[derive(Component)]
707 #[relationship_target(relationship = Above)]
708 struct Below(Entity);
709
710 let mut world = World::new();
711 let a = world.spawn_empty().id();
712 let b = world.spawn_empty().id();
713
714 world.entity_mut(a).insert(Above(b));
715 assert_eq!(a, world.get::<Below>(b).unwrap().0);
716
717 world.entity_mut(b).remove::<Below>();
719 assert!(world.get::<Above>(a).is_none());
720
721 world.entity_mut(a).insert(Above(b));
723 world.entity_mut(a).remove::<Above>();
724 assert!(world.get::<Below>(b).is_none());
725
726 let c = world.spawn_empty().id();
728 world.entity_mut(a).insert(Above(c));
729 assert!(world.get::<Below>(b).is_none());
730 assert_eq!(a, world.get::<Below>(c).unwrap().0);
731 }
732
733 #[test]
734 fn entity_index_map() {
735 for add_before in [false, true] {
736 #[derive(Component)]
737 #[relationship(relationship_target = RelTarget)]
738 struct Rel(Entity);
739
740 #[derive(Component)]
741 #[relationship_target(relationship = Rel, linked_spawn)]
742 struct RelTarget(Vec<Entity>);
743
744 let mut world = World::new();
745 if add_before {
746 let _ = world.spawn_empty().id();
747 }
748 let a = world.spawn_empty().id();
749 let b = world.spawn_empty().id();
750 let c = world.spawn_empty().id();
751 let d = world.spawn_empty().id();
752
753 world.entity_mut(a).add_related::<Rel>(&[b, c, d]);
754
755 let rel_target = world.get::<RelTarget>(a).unwrap();
756 let collection = rel_target.collection();
757
758 assert!(collection.iter().eq([b, c, d]));
760
761 world.entity_mut(c).despawn();
762
763 let rel_target = world.get::<RelTarget>(a).unwrap();
764 let collection = rel_target.collection();
765
766 assert!(collection.iter().eq([b, d]));
768 }
769 }
770
771 #[test]
772 fn one_to_one_relationship_shared_target() {
773 #[derive(Component)]
774 #[relationship(relationship_target = Below)]
775 struct Above(Entity);
776
777 #[derive(Component)]
778 #[relationship_target(relationship = Above)]
779 struct Below(Entity);
780 let mut world = World::new();
781 let a = world.spawn_empty().id();
782 let b = world.spawn_empty().id();
783 let c = world.spawn_empty().id();
784
785 world.entity_mut(a).insert(Above(c));
786 world.entity_mut(b).insert(Above(c));
787
788 assert!(
790 world.get::<Above>(a).is_none(),
791 "Original relationship should be removed"
792 );
793 assert_eq!(
794 world.get::<Above>(b).unwrap().0,
795 c,
796 "New relationship should be established"
797 );
798 assert_eq!(
799 world.get::<Below>(c).unwrap().0,
800 b,
801 "Target should point to new source"
802 );
803 }
804
805 #[test]
806 fn one_to_one_relationship_reinsert() {
807 #[derive(Component)]
808 #[relationship(relationship_target = Below)]
809 struct Above(Entity);
810
811 #[derive(Component)]
812 #[relationship_target(relationship = Above)]
813 struct Below(Entity);
814
815 let mut world = World::new();
816 let a = world.spawn_empty().id();
817 let b = world.spawn_empty().id();
818
819 world.entity_mut(a).insert(Above(b));
820 world.entity_mut(a).insert(Above(b));
821 }
822}