diff options
Diffstat (limited to 'ecs/src/component.rs')
-rw-r--r-- | ecs/src/component.rs | 42 |
1 files changed, 38 insertions, 4 deletions
diff --git a/ecs/src/component.rs b/ecs/src/component.rs index 70ce9ba..023be86 100644 --- a/ecs/src/component.rs +++ b/ecs/src/component.rs @@ -23,6 +23,11 @@ impl dyn Component self.as_any_mut().downcast_mut() } + pub fn downcast_ref<Real: 'static>(&self) -> Option<&Real> + { + self.as_any().downcast_ref() + } + pub fn is<Other: 'static>(&self) -> bool { self.as_any().is::<Other>() @@ -40,6 +45,10 @@ impl Debug for dyn Component /// A sequence of components. pub trait Sequence { + type Refs<'component> + where + Self: 'component; + type MutRefs<'component> where Self: 'component; @@ -48,16 +57,22 @@ pub trait Sequence fn type_ids() -> Vec<TypeId>; - fn from_components(components: &mut [Box<dyn Component>]) -> Self::MutRefs<'_>; + fn from_components(components: &[Box<dyn Component>]) -> Self::Refs<'_>; + + fn from_components_mut(components: &mut [Box<dyn Component>]) -> Self::MutRefs<'_>; } macro_rules! inner { ($c: tt) => { seq!(I in 0..=$c { impl<#(Comp~I: Component,)*> Sequence for (#(Comp~I,)*) { + type Refs<'component> = (#(&'component Comp~I,)*) + where Self: 'component; + type MutRefs<'component> = (#(&'component mut Comp~I,)*) where Self: 'component; + fn into_vec(self) -> Vec<Box<dyn Component>> { Vec::from_iter([#(Box::new(self.I) as Box<dyn Component>,)*]) } @@ -70,7 +85,28 @@ macro_rules! inner { ] } - fn from_components( + fn from_components(components: &[Box<dyn Component>]) -> Self::Refs<'_> + { + #( + let mut comp_~I = None; + )* + + for comp in components { + #( + if comp.is::<Comp~I>() { + comp_~I = Some(comp); + continue; + } + )* + } + + (#( + comp_~I.unwrap().downcast_ref::<Comp~I>().unwrap(), + )*) + + } + + fn from_components_mut( components: &mut [Box<dyn Component>], ) -> Self::MutRefs<'_> { @@ -84,11 +120,9 @@ macro_rules! inner { comp_~I = Some(comp); continue; } - )* } - (#( comp_~I.unwrap().downcast_mut::<Comp~I>().unwrap(), )*) |