entity_data/
state.rs

1use crate::private::ArchetypeMetadata;
2use smallvec::SmallVec;
3use std::alloc;
4use std::any::{Any, TypeId};
5use std::ops::Deref;
6
7/// Defines archetype objects (entity states) with definite components.
8pub trait ArchetypeState: Send + Sync + 'static {
9    fn ty(&self) -> TypeId;
10    fn as_ptr(&self) -> *const u8;
11    fn forget(self);
12    fn metadata(&self) -> ArchetypeMetadata;
13    fn as_any(&self) -> &dyn Any;
14    fn as_any_mut(&mut self) -> &mut dyn Any;
15    fn num_components(&self) -> usize;
16
17    fn component_ids(&self) -> SmallVec<[TypeId; 32]> {
18        let meta = self.metadata();
19        (meta.component_type_ids)()
20    }
21}
22
23/// Defines archetype objects (entity states).
24pub trait StaticArchetype: Sized + ArchetypeState {
25    const N_COMPONENTS: usize;
26
27    fn metadata() -> ArchetypeMetadata;
28
29    fn into_any(self) -> AnyState {
30        AnyState(Box::new(self))
31    }
32}
33
34pub struct AnyState(Box<dyn ArchetypeState>);
35
36/// Entity state with arbitrary components.
37impl AnyState {
38    /// Returns `&dyn` reference to the contained state.
39    pub fn downcast_ref<T: ArchetypeState>(&self) -> Option<&T> {
40        self.0.as_any().downcast_ref()
41    }
42
43    /// Returns `&mut dyn` reference to the contained state.
44    pub fn downcast_mut<T: ArchetypeState>(&mut self) -> Option<&mut T> {
45        self.0.as_any_mut().downcast_mut()
46    }
47
48    /// Returns the contained state.
49    pub fn downcast<T: ArchetypeState>(self) -> Option<T> {
50        if let Some(val) = self.downcast_ref::<T>() {
51            let val = unsafe { (val as *const T).read() };
52            self.forget();
53            Some(val)
54        } else {
55            None
56        }
57    }
58}
59
60impl<T: StaticArchetype> From<T> for AnyState {
61    fn from(state: T) -> Self {
62        state.into_any()
63    }
64}
65
66impl ArchetypeState for AnyState {
67    fn ty(&self) -> TypeId {
68        self.0.ty()
69    }
70
71    fn as_ptr(&self) -> *const u8 {
72        self.0.as_ptr()
73    }
74
75    fn forget(self) {
76        let val: &dyn ArchetypeState = self.0.deref();
77        let layout = alloc::Layout::for_value(val);
78        let ptr = Box::into_raw(self.0);
79
80        // Deallocate `Box` without dropping the state itself.
81        if layout.size() != 0 {
82            unsafe {
83                assert!(!ptr.is_null());
84                alloc::dealloc(ptr as *mut u8, layout);
85            };
86        }
87    }
88
89    fn metadata(&self) -> ArchetypeMetadata {
90        self.0.metadata()
91    }
92
93    fn as_any(&self) -> &dyn Any {
94        self.0.as_any()
95    }
96
97    fn as_any_mut(&mut self) -> &mut dyn Any {
98        self.0.as_any_mut()
99    }
100
101    fn num_components(&self) -> usize {
102        self.0.num_components()
103    }
104}
105
106impl ArchetypeState for () {
107    fn ty(&self) -> TypeId {
108        TypeId::of::<()>()
109    }
110
111    fn as_ptr(&self) -> *const u8 {
112        self as *const _ as *const u8
113    }
114
115    fn forget(self) {}
116
117    fn metadata(&self) -> ArchetypeMetadata {
118        ArchetypeMetadata {
119            type_id: TypeId::of::<Self>(),
120            component_type_ids: || Default::default(),
121            component_infos: || Default::default(),
122            size: 0,
123            needs_drop: false,
124            drop_fn: |_| {},
125        }
126    }
127
128    fn as_any(&self) -> &dyn Any {
129        self
130    }
131
132    fn as_any_mut(&mut self) -> &mut dyn Any {
133        self
134    }
135
136    fn num_components(&self) -> usize {
137        0
138    }
139}
140
141impl StaticArchetype for () {
142    const N_COMPONENTS: usize = 0;
143
144    fn metadata() -> ArchetypeMetadata {
145        ArchetypeMetadata {
146            type_id: TypeId::of::<Self>(),
147            component_type_ids: || Default::default(),
148            component_infos: || Default::default(),
149            size: 0,
150            needs_drop: false,
151            drop_fn: |_| {},
152        }
153    }
154}