1use core::{
6 cmp::Ordering,
7 fmt::{self, Debug, Formatter},
8 hash::BuildHasher,
9 hash::{Hash, Hasher},
10 iter::FusedIterator,
11 marker::PhantomData,
12 ops::{
13 BitAnd, BitOr, BitXor, Bound, Deref, DerefMut, Index, Range, RangeBounds, RangeFrom,
14 RangeFull, RangeInclusive, RangeTo, RangeToInclusive, Sub,
15 },
16 ptr,
17};
18
19use indexmap::set::{self, IndexSet};
20
21use super::{Entity, EntityHash, EntitySetIterator};
22
23use bevy_platform::prelude::Box;
24
25#[cfg_attr(feature = "serialize", derive(serde::Deserialize, serde::Serialize))]
27#[derive(Debug, Clone, Default)]
28pub struct EntityIndexSet(pub(crate) IndexSet<Entity, EntityHash>);
29
30impl EntityIndexSet {
31 pub const fn new() -> Self {
37 Self(IndexSet::with_hasher(EntityHash))
38 }
39
40 pub fn with_capacity(n: usize) -> Self {
46 Self(IndexSet::with_capacity_and_hasher(n, EntityHash))
47 }
48
49 pub fn into_inner(self) -> IndexSet<Entity, EntityHash> {
51 self.0
52 }
53
54 pub fn as_slice(&self) -> &Slice {
58 unsafe { Slice::from_slice_unchecked(self.0.as_slice()) }
60 }
61
62 pub fn drain<R: RangeBounds<usize>>(&mut self, range: R) -> Drain<'_> {
67 Drain(self.0.drain(range), PhantomData)
68 }
69
70 pub fn get_range<R: RangeBounds<usize>>(&self, range: R) -> Option<&Slice> {
74 self.0.get_range(range).map(|slice|
75 unsafe { Slice::from_slice_unchecked(slice) })
77 }
78
79 pub fn iter(&self) -> Iter<'_> {
83 Iter(self.0.iter(), PhantomData)
84 }
85
86 pub fn into_boxed_slice(self) -> Box<Slice> {
90 unsafe { Slice::from_boxed_slice_unchecked(self.0.into_boxed_slice()) }
92 }
93}
94
95impl Deref for EntityIndexSet {
96 type Target = IndexSet<Entity, EntityHash>;
97
98 fn deref(&self) -> &Self::Target {
99 &self.0
100 }
101}
102
103impl DerefMut for EntityIndexSet {
104 fn deref_mut(&mut self) -> &mut Self::Target {
105 &mut self.0
106 }
107}
108
109impl<'a> IntoIterator for &'a EntityIndexSet {
110 type Item = &'a Entity;
111
112 type IntoIter = Iter<'a>;
113
114 fn into_iter(self) -> Self::IntoIter {
115 Iter((&self.0).into_iter(), PhantomData)
116 }
117}
118
119impl IntoIterator for EntityIndexSet {
120 type Item = Entity;
121
122 type IntoIter = IntoIter;
123
124 fn into_iter(self) -> Self::IntoIter {
125 IntoIter(self.0.into_iter(), PhantomData)
126 }
127}
128
129impl BitAnd for &EntityIndexSet {
130 type Output = EntityIndexSet;
131
132 fn bitand(self, rhs: Self) -> Self::Output {
133 EntityIndexSet(self.0.bitand(&rhs.0))
134 }
135}
136
137impl BitOr for &EntityIndexSet {
138 type Output = EntityIndexSet;
139
140 fn bitor(self, rhs: Self) -> Self::Output {
141 EntityIndexSet(self.0.bitor(&rhs.0))
142 }
143}
144
145impl BitXor for &EntityIndexSet {
146 type Output = EntityIndexSet;
147
148 fn bitxor(self, rhs: Self) -> Self::Output {
149 EntityIndexSet(self.0.bitxor(&rhs.0))
150 }
151}
152
153impl Sub for &EntityIndexSet {
154 type Output = EntityIndexSet;
155
156 fn sub(self, rhs: Self) -> Self::Output {
157 EntityIndexSet(self.0.sub(&rhs.0))
158 }
159}
160
161impl<'a> Extend<&'a Entity> for EntityIndexSet {
162 fn extend<T: IntoIterator<Item = &'a Entity>>(&mut self, iter: T) {
163 self.0.extend(iter);
164 }
165}
166
167impl Extend<Entity> for EntityIndexSet {
168 fn extend<T: IntoIterator<Item = Entity>>(&mut self, iter: T) {
169 self.0.extend(iter);
170 }
171}
172
173impl<const N: usize> From<[Entity; N]> for EntityIndexSet {
174 fn from(value: [Entity; N]) -> Self {
175 Self(IndexSet::from_iter(value))
176 }
177}
178
179impl FromIterator<Entity> for EntityIndexSet {
180 fn from_iter<I: IntoIterator<Item = Entity>>(iterable: I) -> Self {
181 Self(IndexSet::from_iter(iterable))
182 }
183}
184
185impl<S2> PartialEq<IndexSet<Entity, S2>> for EntityIndexSet
186where
187 S2: BuildHasher,
188{
189 fn eq(&self, other: &IndexSet<Entity, S2>) -> bool {
190 self.0.eq(other)
191 }
192}
193
194impl PartialEq for EntityIndexSet {
195 fn eq(&self, other: &EntityIndexSet) -> bool {
196 self.0.eq(other)
197 }
198}
199
200impl Eq for EntityIndexSet {}
201
202impl Index<(Bound<usize>, Bound<usize>)> for EntityIndexSet {
203 type Output = Slice;
204 fn index(&self, key: (Bound<usize>, Bound<usize>)) -> &Self::Output {
205 unsafe { Slice::from_slice_unchecked(self.0.index(key)) }
207 }
208}
209
210impl Index<Range<usize>> for EntityIndexSet {
211 type Output = Slice;
212 fn index(&self, key: Range<usize>) -> &Self::Output {
213 unsafe { Slice::from_slice_unchecked(self.0.index(key)) }
215 }
216}
217
218impl Index<RangeFrom<usize>> for EntityIndexSet {
219 type Output = Slice;
220 fn index(&self, key: RangeFrom<usize>) -> &Self::Output {
221 unsafe { Slice::from_slice_unchecked(self.0.index(key)) }
223 }
224}
225
226impl Index<RangeFull> for EntityIndexSet {
227 type Output = Slice;
228 fn index(&self, key: RangeFull) -> &Self::Output {
229 unsafe { Slice::from_slice_unchecked(self.0.index(key)) }
231 }
232}
233
234impl Index<RangeInclusive<usize>> for EntityIndexSet {
235 type Output = Slice;
236 fn index(&self, key: RangeInclusive<usize>) -> &Self::Output {
237 unsafe { Slice::from_slice_unchecked(self.0.index(key)) }
239 }
240}
241
242impl Index<RangeTo<usize>> for EntityIndexSet {
243 type Output = Slice;
244 fn index(&self, key: RangeTo<usize>) -> &Self::Output {
245 unsafe { Slice::from_slice_unchecked(self.0.index(key)) }
247 }
248}
249
250impl Index<RangeToInclusive<usize>> for EntityIndexSet {
251 type Output = Slice;
252 fn index(&self, key: RangeToInclusive<usize>) -> &Self::Output {
253 unsafe { Slice::from_slice_unchecked(self.0.index(key)) }
255 }
256}
257
258impl Index<usize> for EntityIndexSet {
259 type Output = Entity;
260 fn index(&self, key: usize) -> &Entity {
261 self.0.index(key)
262 }
263}
264
265#[repr(transparent)]
270pub struct Slice<S = EntityHash>(PhantomData<S>, set::Slice<Entity>);
271
272impl Slice {
273 pub const fn new<'a>() -> &'a Self {
277 unsafe { Self::from_slice_unchecked(set::Slice::new()) }
279 }
280
281 pub const unsafe fn from_slice_unchecked(slice: &set::Slice<Entity>) -> &Self {
289 unsafe { &*(ptr::from_ref(slice) as *const Self) }
291 }
292
293 pub const unsafe fn from_slice_unchecked_mut(slice: &mut set::Slice<Entity>) -> &mut Self {
301 unsafe { &mut *(ptr::from_mut(slice) as *mut Self) }
303 }
304
305 pub const fn as_inner(&self) -> &set::Slice<Entity> {
307 &self.1
308 }
309
310 pub unsafe fn from_boxed_slice_unchecked(slice: Box<set::Slice<Entity>>) -> Box<Self> {
318 unsafe { Box::from_raw(Box::into_raw(slice) as *mut Self) }
320 }
321
322 #[expect(
324 clippy::borrowed_box,
325 reason = "We wish to access the Box API of the inner type, without consuming it."
326 )]
327 pub fn as_boxed_inner(self: &Box<Self>) -> &Box<set::Slice<Entity>> {
328 unsafe { &*(ptr::from_ref(self).cast::<Box<set::Slice<Entity>>>()) }
330 }
331
332 pub fn into_boxed_inner(self: Box<Self>) -> Box<set::Slice<Entity>> {
334 unsafe { Box::from_raw(Box::into_raw(self) as *mut set::Slice<Entity>) }
336 }
337
338 pub fn get_range<R: RangeBounds<usize>>(&self, range: R) -> Option<&Self> {
342 self.1.get_range(range).map(|slice|
343 unsafe { Self::from_slice_unchecked(slice) })
345 }
346
347 pub fn split_at(&self, index: usize) -> (&Self, &Self) {
351 let (slice_1, slice_2) = self.1.split_at(index);
352 unsafe {
354 (
355 Self::from_slice_unchecked(slice_1),
356 Self::from_slice_unchecked(slice_2),
357 )
358 }
359 }
360
361 pub fn split_first(&self) -> Option<(&Entity, &Self)> {
366 self.1.split_first().map(|(first, rest)| {
367 (
368 first,
369 unsafe { Self::from_slice_unchecked(rest) },
371 )
372 })
373 }
374
375 pub fn split_last(&self) -> Option<(&Entity, &Self)> {
380 self.1.split_last().map(|(last, rest)| {
381 (
382 last,
383 unsafe { Self::from_slice_unchecked(rest) },
385 )
386 })
387 }
388
389 pub fn iter(&self) -> Iter<'_> {
393 Iter(self.1.iter(), PhantomData)
394 }
395}
396
397impl Deref for Slice {
398 type Target = set::Slice<Entity>;
399
400 fn deref(&self) -> &Self::Target {
401 &self.1
402 }
403}
404
405impl<'a> IntoIterator for &'a Slice {
406 type IntoIter = Iter<'a>;
407 type Item = &'a Entity;
408
409 fn into_iter(self) -> Self::IntoIter {
410 self.iter()
411 }
412}
413
414impl IntoIterator for Box<Slice> {
415 type IntoIter = IntoIter;
416 type Item = Entity;
417
418 fn into_iter(self) -> Self::IntoIter {
419 IntoIter(self.into_boxed_inner().into_iter(), PhantomData)
420 }
421}
422
423impl Clone for Box<Slice> {
424 fn clone(&self) -> Self {
425 unsafe { Slice::from_boxed_slice_unchecked(self.as_boxed_inner().clone()) }
427 }
428}
429
430impl Default for &Slice {
431 fn default() -> Self {
432 unsafe { Slice::from_slice_unchecked(<&set::Slice<Entity>>::default()) }
434 }
435}
436
437impl Default for Box<Slice> {
438 fn default() -> Self {
439 unsafe { Slice::from_boxed_slice_unchecked(<Box<set::Slice<Entity>>>::default()) }
441 }
442}
443
444impl<V: Debug> Debug for Slice<V> {
445 fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
446 f.debug_tuple("Slice")
447 .field(&self.0)
448 .field(&&self.1)
449 .finish()
450 }
451}
452
453impl From<&Slice> for Box<Slice> {
454 fn from(value: &Slice) -> Self {
455 unsafe { Slice::from_boxed_slice_unchecked(value.1.into()) }
457 }
458}
459
460impl Hash for Slice {
461 fn hash<H: Hasher>(&self, state: &mut H) {
462 self.1.hash(state);
463 }
464}
465
466impl PartialOrd for Slice {
467 fn partial_cmp(&self, other: &Self) -> Option<Ordering> {
468 Some(self.cmp(other))
469 }
470}
471
472impl Ord for Slice {
473 fn cmp(&self, other: &Self) -> Ordering {
474 self.1.cmp(other)
475 }
476}
477
478impl PartialEq for Slice {
479 fn eq(&self, other: &Self) -> bool {
480 self.1 == other.1
481 }
482}
483
484impl Eq for Slice {}
485
486impl Index<(Bound<usize>, Bound<usize>)> for Slice {
487 type Output = Self;
488 fn index(&self, key: (Bound<usize>, Bound<usize>)) -> &Self {
489 unsafe { Self::from_slice_unchecked(self.1.index(key)) }
491 }
492}
493
494impl Index<Range<usize>> for Slice {
495 type Output = Self;
496 fn index(&self, key: Range<usize>) -> &Self {
497 unsafe { Self::from_slice_unchecked(self.1.index(key)) }
499 }
500}
501
502impl Index<RangeFrom<usize>> for Slice {
503 type Output = Slice;
504 fn index(&self, key: RangeFrom<usize>) -> &Self {
505 unsafe { Self::from_slice_unchecked(self.1.index(key)) }
507 }
508}
509
510impl Index<RangeFull> for Slice {
511 type Output = Self;
512 fn index(&self, key: RangeFull) -> &Self {
513 unsafe { Self::from_slice_unchecked(self.1.index(key)) }
515 }
516}
517
518impl Index<RangeInclusive<usize>> for Slice {
519 type Output = Self;
520 fn index(&self, key: RangeInclusive<usize>) -> &Self {
521 unsafe { Self::from_slice_unchecked(self.1.index(key)) }
523 }
524}
525
526impl Index<RangeTo<usize>> for Slice {
527 type Output = Self;
528 fn index(&self, key: RangeTo<usize>) -> &Self {
529 unsafe { Self::from_slice_unchecked(self.1.index(key)) }
531 }
532}
533
534impl Index<RangeToInclusive<usize>> for Slice {
535 type Output = Self;
536 fn index(&self, key: RangeToInclusive<usize>) -> &Self {
537 unsafe { Self::from_slice_unchecked(self.1.index(key)) }
539 }
540}
541
542impl Index<usize> for Slice {
543 type Output = Entity;
544 fn index(&self, key: usize) -> &Entity {
545 self.1.index(key)
546 }
547}
548
549pub struct Iter<'a, S = EntityHash>(set::Iter<'a, Entity>, PhantomData<S>);
555
556impl<'a> Iter<'a> {
557 pub fn into_inner(self) -> set::Iter<'a, Entity> {
559 self.0
560 }
561
562 pub fn as_slice(&self) -> &Slice {
566 unsafe { Slice::from_slice_unchecked(self.0.as_slice()) }
568 }
569}
570
571impl<'a> Deref for Iter<'a> {
572 type Target = set::Iter<'a, Entity>;
573
574 fn deref(&self) -> &Self::Target {
575 &self.0
576 }
577}
578
579impl<'a> Iterator for Iter<'a> {
580 type Item = &'a Entity;
581
582 fn next(&mut self) -> Option<Self::Item> {
583 self.0.next()
584 }
585}
586
587impl DoubleEndedIterator for Iter<'_> {
588 fn next_back(&mut self) -> Option<Self::Item> {
589 self.0.next_back()
590 }
591}
592
593impl ExactSizeIterator for Iter<'_> {}
594
595impl FusedIterator for Iter<'_> {}
596
597impl Clone for Iter<'_> {
598 fn clone(&self) -> Self {
599 Self(self.0.clone(), PhantomData)
600 }
601}
602
603impl Debug for Iter<'_> {
604 fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
605 f.debug_tuple("Iter").field(&self.0).field(&self.1).finish()
606 }
607}
608
609impl Default for Iter<'_> {
610 fn default() -> Self {
611 Self(Default::default(), PhantomData)
612 }
613}
614
615unsafe impl EntitySetIterator for Iter<'_> {}
617
618pub struct IntoIter<S = EntityHash>(set::IntoIter<Entity>, PhantomData<S>);
624
625impl IntoIter {
626 pub fn into_inner(self) -> set::IntoIter<Entity> {
628 self.0
629 }
630
631 pub fn as_slice(&self) -> &Slice {
635 unsafe { Slice::from_slice_unchecked(self.0.as_slice()) }
637 }
638}
639
640impl Deref for IntoIter {
641 type Target = set::IntoIter<Entity>;
642
643 fn deref(&self) -> &Self::Target {
644 &self.0
645 }
646}
647
648impl Iterator for IntoIter {
649 type Item = Entity;
650
651 fn next(&mut self) -> Option<Self::Item> {
652 self.0.next()
653 }
654}
655
656impl DoubleEndedIterator for IntoIter {
657 fn next_back(&mut self) -> Option<Self::Item> {
658 self.0.next_back()
659 }
660}
661
662impl ExactSizeIterator for IntoIter {}
663
664impl FusedIterator for IntoIter {}
665
666impl Clone for IntoIter {
667 fn clone(&self) -> Self {
668 Self(self.0.clone(), PhantomData)
669 }
670}
671
672impl Debug for IntoIter {
673 fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
674 f.debug_tuple("IntoIter")
675 .field(&self.0)
676 .field(&self.1)
677 .finish()
678 }
679}
680
681impl Default for IntoIter {
682 fn default() -> Self {
683 Self(Default::default(), PhantomData)
684 }
685}
686
687unsafe impl EntitySetIterator for IntoIter {}
689
690pub struct Drain<'a, S = EntityHash>(set::Drain<'a, Entity>, PhantomData<S>);
696
697impl<'a> Drain<'a> {
698 pub fn into_inner(self) -> set::Drain<'a, Entity> {
700 self.0
701 }
702
703 pub fn as_slice(&self) -> &Slice {
707 unsafe { Slice::from_slice_unchecked(self.0.as_slice()) }
709 }
710}
711
712impl<'a> Deref for Drain<'a> {
713 type Target = set::Drain<'a, Entity>;
714
715 fn deref(&self) -> &Self::Target {
716 &self.0
717 }
718}
719
720impl<'a> Iterator for Drain<'a> {
721 type Item = Entity;
722
723 fn next(&mut self) -> Option<Self::Item> {
724 self.0.next()
725 }
726}
727
728impl DoubleEndedIterator for Drain<'_> {
729 fn next_back(&mut self) -> Option<Self::Item> {
730 self.0.next_back()
731 }
732}
733
734impl ExactSizeIterator for Drain<'_> {}
735
736impl FusedIterator for Drain<'_> {}
737
738impl Debug for Drain<'_> {
739 fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
740 f.debug_tuple("Drain")
741 .field(&self.0)
742 .field(&self.1)
743 .finish()
744 }
745}
746
747unsafe impl EntitySetIterator for Drain<'_> {}
749
750unsafe impl EntitySetIterator for set::Difference<'_, Entity, EntityHash> {}
752
753unsafe impl EntitySetIterator for set::Intersection<'_, Entity, EntityHash> {}
755
756unsafe impl EntitySetIterator for set::SymmetricDifference<'_, Entity, EntityHash, EntityHash> {}
758
759unsafe impl EntitySetIterator for set::Union<'_, Entity, EntityHash> {}
761
762unsafe impl<I: Iterator<Item = Entity>> EntitySetIterator
764 for set::Splice<'_, I, Entity, EntityHash>
765{
766}