sparsey/query/
query_part.rs

1use crate::component::{Component, View, ViewGroupInfo, ViewMut};
2use crate::entity::{Entity, SparseVec};
3use crate::World;
4use core::ops::Range;
5use core::ptr::NonNull;
6use core::slice;
7
8/// Trait for querying and iterating a view.
9///
10/// # Safety
11///
12/// This trait is considered an implementation detail and cannot be safely
13/// implemented outside the crate.
14pub unsafe trait QueryPart {
15    /// View borrowed from a [`World`].
16    type View<'a>;
17
18    /// Item type returned by queries.
19    type Item<'a>: Send;
20
21    /// Slice returned by [`slice`](Self::slice_raw) operations.
22    type Slice<'a>;
23
24    /// [`SparseVec`](crate::entity::SparseVec) type used for sparse iteration.
25    type Sparse<'a>: Copy;
26
27    /// Key used to access dense data.
28    type SparseKey;
29
30    /// Data used for sparse and dense iteration.
31    type Data<'a>: Copy;
32
33    /// Borrows a view from the `world`.
34    #[must_use]
35    fn borrow(world: &World) -> Self::View<'_>;
36
37    /// Borrows a view from the `world` along with grouping information.
38    #[must_use]
39    fn borrow_with_group_info(world: &World) -> (Self::View<'_>, Option<ViewGroupInfo>);
40
41    /// Returns whether `entity` is present in the view.
42    #[must_use]
43    fn contains(view: &Self::View<'_>, entity: Entity) -> bool;
44
45    /// Returns the sparse key mapped to `entity`, if any.
46    #[must_use]
47    fn get_sparse_key(view: &Self::View<'_>, entity: Entity) -> Option<Self::SparseKey>;
48
49    /// Returns the item mapped to `key`, if any.
50    #[must_use]
51    unsafe fn get_sparse<'a>(view: &'a mut Self::View<'_>, key: Self::SparseKey) -> Self::Item<'a>;
52
53    /// Splits the view into its entities and sparse vecs.
54    #[must_use]
55    fn split_filter_parts<'a>(view: &'a Self::View<'_>)
56        -> (Option<&'a [Entity]>, Self::Sparse<'a>);
57
58    /// Splits the view into its entities, sparse vecs and data.
59    #[must_use]
60    fn split_sparse_parts<'a>(
61        view: &'a Self::View<'_>,
62    ) -> (Option<&'a [Entity]>, Self::Sparse<'a>, Self::Data<'a>);
63
64    /// Splits the view into its entities and data.
65    #[must_use]
66    fn split_dense_parts<'a>(view: &'a Self::View<'_>) -> (Option<&'a [Entity]>, Self::Data<'a>);
67
68    /// Returns whether the sparse index is present in the sparse vecs.
69    #[must_use]
70    fn contains_raw(sparse: Self::Sparse<'_>, sparse_index: usize) -> bool;
71
72    /// Returns the sparse key extracted from the sparse vecs.
73    #[must_use]
74    fn get_sparse_key_raw(sparse: Self::Sparse<'_>, entity: Entity) -> Option<Self::SparseKey>;
75
76    /// Returns the sparse data that can be accessed with the dense key.
77    #[must_use]
78    unsafe fn get_sparse_raw(data: Self::Data<'_>, key: Self::SparseKey) -> Self::Item<'_>;
79
80    /// Returns the item at the given `index` or `entity`.
81    #[must_use]
82    unsafe fn get_dense_raw(data: Self::Data<'_>, index: usize, entity: Entity) -> Self::Item<'_>;
83
84    /// Slices the data at the given `range`.
85    #[must_use]
86    unsafe fn slice_raw<'a>(
87        data: Self::Data<'a>,
88        entities: &'a [Entity],
89        range: Range<usize>,
90    ) -> Self::Slice<'a>;
91}
92
93unsafe impl QueryPart for Entity {
94    type View<'a> = ();
95    type Item<'a> = Entity;
96    type Slice<'a> = &'a [Entity];
97    type Sparse<'a> = ();
98    type SparseKey = Entity;
99    type Data<'a> = ();
100
101    #[inline]
102    fn borrow(_world: &World) -> Self::View<'_> {
103        // Empty
104    }
105
106    #[inline]
107    fn borrow_with_group_info(_world: &World) -> (Self::View<'_>, Option<ViewGroupInfo>) {
108        ((), None)
109    }
110
111    #[inline]
112    fn contains(_view: &Self::View<'_>, _entity: Entity) -> bool {
113        true
114    }
115
116    #[inline]
117    fn get_sparse_key(_view: &Self::View<'_>, entity: Entity) -> Option<Self::SparseKey> {
118        Some(entity)
119    }
120
121    #[inline]
122    unsafe fn get_sparse<'a>(
123        _view: &'a mut Self::View<'_>,
124        key: Self::SparseKey,
125    ) -> Self::Item<'a> {
126        key
127    }
128
129    #[inline]
130    fn split_filter_parts<'a>(
131        _view: &'a Self::View<'_>,
132    ) -> (Option<&'a [Entity]>, Self::Sparse<'a>) {
133        (None, ())
134    }
135
136    #[inline]
137    fn split_sparse_parts<'a>(
138        _view: &'a Self::View<'_>,
139    ) -> (Option<&'a [Entity]>, Self::Sparse<'a>, Self::Data<'a>) {
140        (None, (), ())
141    }
142
143    #[inline]
144    fn split_dense_parts<'a>(_view: &'a Self::View<'_>) -> (Option<&'a [Entity]>, Self::Data<'a>) {
145        (None, ())
146    }
147
148    #[inline]
149    fn contains_raw(_sparse: Self::Sparse<'_>, _sparse_index: usize) -> bool {
150        true
151    }
152
153    #[inline]
154    fn get_sparse_key_raw<'a>(
155        _sparse: Self::Sparse<'_>,
156        entity: Entity,
157    ) -> Option<Self::SparseKey> {
158        Some(entity)
159    }
160
161    #[inline]
162    unsafe fn get_sparse_raw(_data: Self::Data<'_>, key: Self::SparseKey) -> Self::Item<'_> {
163        key
164    }
165
166    #[inline]
167    unsafe fn get_dense_raw(
168        _part: Self::Data<'_>,
169        _index: usize,
170        entity: Entity,
171    ) -> Self::Item<'_> {
172        entity
173    }
174
175    #[inline]
176    unsafe fn slice_raw<'a>(
177        _data: Self::Data<'a>,
178        entities: &'a [Entity],
179        range: Range<usize>,
180    ) -> Self::Slice<'a> {
181        entities.get_unchecked(range)
182    }
183}
184
185unsafe impl<T> QueryPart for &'_ T
186where
187    T: Component,
188{
189    type View<'a> = View<'a, T>;
190    type Item<'a> = &'a T;
191    type Slice<'a> = &'a [T];
192    type Sparse<'a> = &'a SparseVec;
193    type SparseKey = usize;
194    type Data<'a> = NonNull<T>;
195
196    fn borrow(world: &World) -> Self::View<'_> {
197        world.borrow::<T>()
198    }
199
200    fn borrow_with_group_info(world: &World) -> (Self::View<'_>, Option<ViewGroupInfo>) {
201        let (view, info) = world.borrow_with_group_info::<T>();
202
203        let info = ViewGroupInfo {
204            info,
205            len: view.len(),
206        };
207
208        (view, Some(info))
209    }
210
211    fn contains(view: &Self::View<'_>, entity: Entity) -> bool {
212        view.contains(entity)
213    }
214
215    fn get_sparse_key(view: &Self::View<'_>, entity: Entity) -> Option<Self::SparseKey> {
216        view.sparse().get(entity).map(|i| i as usize)
217    }
218
219    unsafe fn get_sparse<'a>(view: &'a mut Self::View<'_>, key: Self::SparseKey) -> Self::Item<'a> {
220        view.as_non_null_ptr().add(key).as_ref()
221    }
222
223    fn split_filter_parts<'a>(
224        view: &'a Self::View<'_>,
225    ) -> (Option<&'a [Entity]>, Self::Sparse<'a>) {
226        (Some(view.entities()), view.sparse())
227    }
228
229    fn split_sparse_parts<'a>(
230        view: &'a Self::View<'_>,
231    ) -> (Option<&'a [Entity]>, Self::Sparse<'a>, Self::Data<'a>) {
232        (Some(view.entities()), view.sparse(), view.as_non_null_ptr())
233    }
234
235    fn split_dense_parts<'a>(view: &'a Self::View<'_>) -> (Option<&'a [Entity]>, Self::Data<'a>) {
236        (Some(view.entities()), view.as_non_null_ptr())
237    }
238
239    fn contains_raw(sparse: Self::Sparse<'_>, sparse_index: usize) -> bool {
240        sparse.contains_sparse(sparse_index)
241    }
242
243    fn get_sparse_key_raw<'a>(sparse: Self::Sparse<'_>, entity: Entity) -> Option<Self::SparseKey> {
244        Some(sparse.get_sparse(entity.sparse())? as usize)
245    }
246
247    unsafe fn get_sparse_raw(data: Self::Data<'_>, key: Self::SparseKey) -> Self::Item<'_> {
248        data.add(key).as_ref()
249    }
250
251    unsafe fn get_dense_raw(ptr: Self::Data<'_>, index: usize, _entity: Entity) -> Self::Item<'_> {
252        ptr.add(index).as_ref()
253    }
254
255    unsafe fn slice_raw<'a>(
256        data: Self::Data<'a>,
257        _entities: &'a [Entity],
258        range: Range<usize>,
259    ) -> Self::Slice<'a> {
260        slice::from_raw_parts(data.as_ptr(), range.end - range.start)
261    }
262}
263
264unsafe impl<T> QueryPart for &'_ mut T
265where
266    T: Component,
267{
268    type View<'a> = ViewMut<'a, T>;
269    type Item<'a> = &'a mut T;
270    type Slice<'a> = &'a mut [T];
271    type Sparse<'a> = &'a SparseVec;
272    type SparseKey = usize;
273    type Data<'a> = NonNull<T>;
274
275    fn borrow(world: &World) -> Self::View<'_> {
276        world.borrow_mut::<T>()
277    }
278
279    fn borrow_with_group_info(world: &World) -> (Self::View<'_>, Option<ViewGroupInfo>) {
280        let (view, info) = world.borrow_with_group_info_mut::<T>();
281
282        let info = ViewGroupInfo {
283            info,
284            len: view.len(),
285        };
286
287        (view, Some(info))
288    }
289
290    fn contains(view: &Self::View<'_>, entity: Entity) -> bool {
291        view.contains(entity)
292    }
293
294    fn get_sparse_key(view: &Self::View<'_>, entity: Entity) -> Option<Self::SparseKey> {
295        view.sparse().get(entity).map(|i| i as usize)
296    }
297
298    unsafe fn get_sparse<'a>(view: &'a mut Self::View<'_>, key: Self::SparseKey) -> Self::Item<'a> {
299        view.as_non_null_ptr().add(key).as_mut()
300    }
301
302    fn split_filter_parts<'a>(
303        view: &'a Self::View<'_>,
304    ) -> (Option<&'a [Entity]>, Self::Sparse<'a>) {
305        (Some(view.entities()), view.sparse())
306    }
307
308    fn split_sparse_parts<'a>(
309        view: &'a Self::View<'_>,
310    ) -> (Option<&'a [Entity]>, Self::Sparse<'a>, Self::Data<'a>) {
311        (Some(view.entities()), view.sparse(), view.as_non_null_ptr())
312    }
313
314    fn split_dense_parts<'a>(view: &'a Self::View<'_>) -> (Option<&'a [Entity]>, Self::Data<'a>) {
315        (Some(view.entities()), view.as_non_null_ptr())
316    }
317
318    fn contains_raw(sparse: Self::Sparse<'_>, sparse_index: usize) -> bool {
319        sparse.contains_sparse(sparse_index)
320    }
321
322    fn get_sparse_key_raw(sparse: Self::Sparse<'_>, entity: Entity) -> Option<Self::SparseKey> {
323        Some(sparse.get_sparse(entity.sparse())? as usize)
324    }
325
326    unsafe fn get_sparse_raw(data: Self::Data<'_>, key: Self::SparseKey) -> Self::Item<'_> {
327        data.add(key).as_mut()
328    }
329
330    unsafe fn get_dense_raw(ptr: Self::Data<'_>, index: usize, _entity: Entity) -> Self::Item<'_> {
331        ptr.add(index).as_mut()
332    }
333
334    unsafe fn slice_raw<'a>(
335        data: Self::Data<'a>,
336        _entities: &'a [Entity],
337        range: Range<usize>,
338    ) -> Self::Slice<'a> {
339        slice::from_raw_parts_mut(data.as_ptr(), range.end - range.start)
340    }
341}
342
343unsafe impl<T> QueryPart for Option<&'_ T>
344where
345    T: Component,
346{
347    type View<'a> = View<'a, T>;
348    type Item<'a> = Option<&'a T>;
349    type Slice<'a> = ();
350    type Sparse<'a> = ();
351    type SparseKey = Entity;
352    type Data<'a> = (&'a SparseVec, NonNull<T>);
353
354    fn borrow(world: &World) -> Self::View<'_> {
355        world.borrow::<T>()
356    }
357
358    fn borrow_with_group_info(world: &World) -> (Self::View<'_>, Option<ViewGroupInfo>) {
359        (world.borrow::<T>(), None)
360    }
361
362    fn contains(_view: &Self::View<'_>, _entity: Entity) -> bool {
363        true
364    }
365
366    fn get_sparse_key(_view: &Self::View<'_>, entity: Entity) -> Option<Self::SparseKey> {
367        Some(entity)
368    }
369
370    unsafe fn get_sparse<'a>(view: &'a mut Self::View<'_>, key: Self::SparseKey) -> Self::Item<'a> {
371        view.get(key)
372    }
373
374    fn split_filter_parts<'a>(
375        _view: &'a Self::View<'_>,
376    ) -> (Option<&'a [Entity]>, Self::Sparse<'a>) {
377        (None, ())
378    }
379
380    fn split_sparse_parts<'a>(
381        view: &'a Self::View<'_>,
382    ) -> (Option<&'a [Entity]>, Self::Sparse<'a>, Self::Data<'a>) {
383        (None, (), (view.sparse(), view.as_non_null_ptr()))
384    }
385
386    fn split_dense_parts<'a>(view: &'a Self::View<'_>) -> (Option<&'a [Entity]>, Self::Data<'a>) {
387        (None, (view.sparse(), view.as_non_null_ptr()))
388    }
389
390    fn contains_raw(_sparse: Self::Sparse<'_>, _sparse_index: usize) -> bool {
391        true
392    }
393
394    fn get_sparse_key_raw(_sparse: Self::Sparse<'_>, entity: Entity) -> Option<Self::SparseKey> {
395        Some(entity)
396    }
397
398    unsafe fn get_sparse_raw(
399        (sparse, ptr): Self::Data<'_>,
400        entity: Self::SparseKey,
401    ) -> Self::Item<'_> {
402        sparse
403            .get_sparse(entity.sparse())
404            .map(|dense| ptr.add(dense as usize).as_ref())
405    }
406
407    unsafe fn get_dense_raw(
408        (sparse, ptr): Self::Data<'_>,
409        _index: usize,
410        entity: Entity,
411    ) -> Self::Item<'_> {
412        sparse
413            .get_sparse(entity.sparse())
414            .map(|dense| ptr.add(dense as usize).as_ref())
415    }
416
417    unsafe fn slice_raw<'a>(
418        _data: Self::Data<'_>,
419        _entities: &'a [Entity],
420        _range: Range<usize>,
421    ) -> Self::Slice<'a> {
422        // Empty
423    }
424}
425
426unsafe impl<T> QueryPart for Option<&'_ mut T>
427where
428    T: Component,
429{
430    type View<'a> = ViewMut<'a, T>;
431    type Item<'a> = Option<&'a mut T>;
432    type Slice<'a> = ();
433    type Sparse<'a> = ();
434    type SparseKey = Entity;
435    type Data<'a> = (&'a SparseVec, NonNull<T>);
436
437    fn borrow(world: &World) -> Self::View<'_> {
438        world.borrow_mut::<T>()
439    }
440
441    fn borrow_with_group_info(world: &World) -> (Self::View<'_>, Option<ViewGroupInfo>) {
442        (world.borrow_mut::<T>(), None)
443    }
444
445    fn contains(_view: &Self::View<'_>, _entity: Entity) -> bool {
446        true
447    }
448
449    fn get_sparse_key(_view: &Self::View<'_>, entity: Entity) -> Option<Self::SparseKey> {
450        Some(entity)
451    }
452
453    unsafe fn get_sparse<'a>(view: &'a mut Self::View<'_>, key: Self::SparseKey) -> Self::Item<'a> {
454        view.get_mut(key)
455    }
456
457    fn split_filter_parts<'a>(
458        _view: &'a Self::View<'_>,
459    ) -> (Option<&'a [Entity]>, Self::Sparse<'a>) {
460        (None, ())
461    }
462
463    fn split_sparse_parts<'a>(
464        view: &'a Self::View<'_>,
465    ) -> (Option<&'a [Entity]>, Self::Sparse<'a>, Self::Data<'a>) {
466        (None, (), (view.sparse(), view.as_non_null_ptr()))
467    }
468
469    fn split_dense_parts<'a>(view: &'a Self::View<'_>) -> (Option<&'a [Entity]>, Self::Data<'a>) {
470        (None, (view.sparse(), view.as_non_null_ptr()))
471    }
472
473    fn contains_raw(_sparse: Self::Sparse<'_>, _sparse_index: usize) -> bool {
474        true
475    }
476
477    fn get_sparse_key_raw<'a>(
478        _sparse: Self::Sparse<'_>,
479        entity: Entity,
480    ) -> Option<Self::SparseKey> {
481        Some(entity)
482    }
483
484    unsafe fn get_sparse_raw(
485        (sparse, ptr): Self::Data<'_>,
486        entity: Self::SparseKey,
487    ) -> Self::Item<'_> {
488        sparse
489            .get_sparse(entity.sparse())
490            .map(|dense| ptr.add(dense as usize).as_mut())
491    }
492
493    unsafe fn get_dense_raw(
494        (sparse, ptr): Self::Data<'_>,
495        _index: usize,
496        entity: Entity,
497    ) -> Self::Item<'_> {
498        sparse
499            .get_sparse(entity.sparse())
500            .map(|dense| ptr.add(dense as usize).as_mut())
501    }
502
503    unsafe fn slice_raw<'a>(
504        _data: Self::Data<'_>,
505        _entities: &'a [Entity],
506        _range: Range<usize>,
507    ) -> Self::Slice<'a> {
508        // Empty
509    }
510}