despero_hecs_schedule/borrow/
component_borrow.rs

1use std::any::{type_name, TypeId};
2
3use super::Borrows;
4use crate::{Access, AllAccess, IntoAccess};
5use hecs::{Fetch, Query, World};
6pub use smallvec::smallvec;
7use smallvec::SmallVec;
8
9/// Trait for a set of component accesses
10pub trait ComponentBorrow {
11    /// Returns a list of all component accesses
12    fn borrows() -> Borrows;
13    /// Returns true if id exists in Self
14    fn has_dynamic(id: TypeId, exclusive: bool) -> bool;
15    /// Returns true if U exists in Self
16    fn has<U: IntoAccess>() -> bool;
17}
18
19impl<'a, Q: Query> ComponentBorrow for Q {
20    fn borrows() -> Borrows {
21        let mut borrows = SmallVec::with_capacity(8);
22
23        Q::Fetch::for_each_borrow(|id, exclusive| {
24            borrows.push(Access::new(type_name::<Q>(), id, exclusive))
25        });
26
27        borrows
28    }
29
30    fn has_dynamic(id: TypeId, exclusive: bool) -> bool {
31        let mut found = false;
32        Q::Fetch::for_each_borrow(|f_id, f_exclusive| {
33            if f_id == id && (!exclusive || exclusive == f_exclusive) {
34                found = true
35            }
36        });
37
38        found
39    }
40
41    fn has<U: IntoAccess>() -> bool {
42        let u = U::access();
43        Self::has_dynamic(u.id, u.exclusive)
44    }
45}
46
47impl ComponentBorrow for AllAccess {
48    fn borrows() -> Borrows {
49        smallvec![Access::of::<&mut World>()]
50    }
51
52    // Has everything
53    fn has<U: IntoAccess>() -> bool {
54        true
55    }
56
57    fn has_dynamic(_: TypeId, _: bool) -> bool {
58        true
59    }
60}