Fix proc macro
This commit is contained in:
parent
7ee6ef0a08
commit
d730eb586b
2 changed files with 136 additions and 908 deletions
|
@ -7,871 +7,10 @@ use std::collections::HashMap;
|
||||||
|
|
||||||
use anyhow::Result;
|
use anyhow::Result;
|
||||||
use indexmap::IndexMap;
|
use indexmap::IndexMap;
|
||||||
|
use update_macros::implement_updates;
|
||||||
|
|
||||||
use crate::resources::Resource as ResourceTrait;
|
use crate::resources::Resource as ResourceTrait;
|
||||||
use crate::*;
|
use crate::*;
|
||||||
use update_macros::{implement_pair_update, implement_single_update};
|
|
||||||
|
|
||||||
macro_rules! impl_singleton_update {
|
|
||||||
// single without resources
|
|
||||||
( $s:ident, ) => {
|
|
||||||
impl<Func, Filter, $s> CreateArchetype<$s, (), Func, Filter> for Archetype
|
|
||||||
where
|
|
||||||
Func: Fn(&mut Commands, Query<&mut $s, Filter>) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
Filter: CheckFilter + 'static,
|
|
||||||
$s: EntityComponent + ComponentDebug,
|
|
||||||
{
|
|
||||||
paste::item! {
|
|
||||||
fn create(f: Func) -> Self {
|
|
||||||
Filter::verify_dedup::<$s>();
|
|
||||||
|
|
||||||
Self {
|
|
||||||
check_entity: Box::new({
|
|
||||||
move |entity| {
|
|
||||||
if !entity.components.contains::<$s>() {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if !Filter::check(entity) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
true
|
|
||||||
}
|
|
||||||
}),
|
|
||||||
|
|
||||||
create_callback: Box::new(move |entity| {
|
|
||||||
let [< $s:lower >] = UnsafeComponentStore::from(
|
|
||||||
entity.get_component::<$s>()?
|
|
||||||
);
|
|
||||||
|
|
||||||
let e = entity.as_entity();
|
|
||||||
let f = f.clone();
|
|
||||||
|
|
||||||
Ok(Box::new(move |commands, _world| {
|
|
||||||
let query = Query {
|
|
||||||
entity: e,
|
|
||||||
c: unsafe { [< $s:lower >].as_mut() },
|
|
||||||
filter: PhantomData,
|
|
||||||
};
|
|
||||||
|
|
||||||
f(commands, query)
|
|
||||||
}))
|
|
||||||
}),
|
|
||||||
|
|
||||||
entities: IndexMap::new(),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<Func, Filter, $s> AddUpdates<$s, (), Func, Filter> for Updates
|
|
||||||
where
|
|
||||||
$s: EntityComponent + ComponentDebug,
|
|
||||||
Func: Fn(&mut Commands, Query<&mut $s, Filter>) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
Filter: CheckFilter + 'static
|
|
||||||
{
|
|
||||||
fn add_update(
|
|
||||||
&mut self,
|
|
||||||
name: &str,
|
|
||||||
priority: u32,
|
|
||||||
func: Func,
|
|
||||||
) -> Result<()> {
|
|
||||||
paste::item! {
|
|
||||||
self.add(name, priority, Update::Single(Archetype::create(func)))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<Func, Filter, $s> AddUpdates<$s, (), Func, Filter> for WorldBuilder
|
|
||||||
where
|
|
||||||
$s: EntityComponent + ComponentDebug,
|
|
||||||
Func: Fn(&mut Commands, Query<&mut $s, Filter>) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
Filter: CheckFilter + 'static
|
|
||||||
{
|
|
||||||
fn add_update(
|
|
||||||
&mut self,
|
|
||||||
name: &str,
|
|
||||||
priority: u32,
|
|
||||||
func: Func,
|
|
||||||
) -> Result<()> {
|
|
||||||
self.updates.add_update(name, priority, func)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
// single with resources
|
|
||||||
( $s:ident, [$($res:ident $(,)?)+] ) => {
|
|
||||||
impl<Func, Filter, $s, $( $res, )+> CreateArchetype<$s, ( $( $res, )+ ), Func, Filter> for Archetype
|
|
||||||
where
|
|
||||||
Func: Fn(&mut Commands, Query<&mut $s, Filter>, $(&mut $res,)+) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
Filter: CheckFilter + 'static,
|
|
||||||
$s: EntityComponent + ComponentDebug,
|
|
||||||
$(
|
|
||||||
$res: ResourceTrait,
|
|
||||||
)+
|
|
||||||
{
|
|
||||||
paste::item! {
|
|
||||||
fn create(f: Func) -> Self {
|
|
||||||
Filter::verify_dedup::<$s>();
|
|
||||||
|
|
||||||
Self {
|
|
||||||
check_entity: Box::new({
|
|
||||||
move |entity| {
|
|
||||||
if !entity.components.contains::<$s>() {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if !Filter::check(entity) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
true
|
|
||||||
}
|
|
||||||
}),
|
|
||||||
|
|
||||||
create_callback: Box::new(move |entity| {
|
|
||||||
let [< $s:lower >] = UnsafeComponentStore::from(
|
|
||||||
entity.get_component::<$s>()?
|
|
||||||
);
|
|
||||||
|
|
||||||
let e = entity.as_entity();
|
|
||||||
let f = f.clone();
|
|
||||||
|
|
||||||
Ok(Box::new(move |commands, world| {
|
|
||||||
let (
|
|
||||||
$(
|
|
||||||
[< $res:lower _var >],
|
|
||||||
)+
|
|
||||||
): (
|
|
||||||
$(
|
|
||||||
&mut $res,
|
|
||||||
)+
|
|
||||||
) = world.resources.get_mut()?;
|
|
||||||
|
|
||||||
let query = Query {
|
|
||||||
entity: e,
|
|
||||||
c: unsafe { [< $s:lower >].as_mut() },
|
|
||||||
filter: PhantomData,
|
|
||||||
};
|
|
||||||
|
|
||||||
f(commands, query, $([< $res:lower _var >],)+)
|
|
||||||
}))
|
|
||||||
}),
|
|
||||||
|
|
||||||
entities: IndexMap::new(),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<Func, Filter, $s, $( $res, )+> AddUpdates<$s, ( $( $res, )+ ), Func, Filter> for Updates
|
|
||||||
where
|
|
||||||
$s: EntityComponent + ComponentDebug,
|
|
||||||
$(
|
|
||||||
$res: ResourceTrait,
|
|
||||||
)+
|
|
||||||
Func: Fn(& mut Commands, Query<&mut $s, Filter>, $(&mut $res,)+) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
Filter: CheckFilter + 'static
|
|
||||||
{
|
|
||||||
fn add_update(
|
|
||||||
&mut self,
|
|
||||||
name: &str,
|
|
||||||
priority: u32,
|
|
||||||
func: Func,
|
|
||||||
) -> Result<()> {
|
|
||||||
paste::item! {
|
|
||||||
self.add(name, priority, Update::Single(Archetype::create(func)))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<Func, Filter, $s, $( $res, )+> AddUpdates<$s, ( $( $res, )+ ), Func, Filter> for WorldBuilder
|
|
||||||
where
|
|
||||||
$s: EntityComponent + ComponentDebug,
|
|
||||||
$(
|
|
||||||
$res: ResourceTrait,
|
|
||||||
)+
|
|
||||||
Func: Fn(& mut Commands, Query<&mut $s, Filter>, $(&mut $res,)+) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
Filter: CheckFilter + 'static
|
|
||||||
{
|
|
||||||
fn add_update(
|
|
||||||
&mut self,
|
|
||||||
name: &str,
|
|
||||||
priority: u32,
|
|
||||||
func: Func,
|
|
||||||
) -> Result<()> {
|
|
||||||
self.updates.add_update(name, priority, func)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
// without resources
|
|
||||||
( $s:ident, $($var:ident $(,)?)+ ) => {
|
|
||||||
impl<Func, Filter, $s, $( $var, )+> CreateArchetype<( $s, $( $var, )+ ), (), Func, Filter> for Archetype
|
|
||||||
where
|
|
||||||
Func: Fn(&mut Commands, Query<( &mut $s, $( &mut $var, )+ ), Filter>) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
Filter: CheckFilter + 'static,
|
|
||||||
$s: EntityComponent + ComponentDebug,
|
|
||||||
$(
|
|
||||||
$var: EntityComponent + ComponentDebug,
|
|
||||||
)+
|
|
||||||
{
|
|
||||||
paste::item! {
|
|
||||||
fn create(f: Func) -> Self {
|
|
||||||
Filter::verify_dedup::<$s>();
|
|
||||||
$(
|
|
||||||
Filter::verify_dedup::<$var>();
|
|
||||||
)+
|
|
||||||
|
|
||||||
Self {
|
|
||||||
check_entity: Box::new({
|
|
||||||
move |entity| {
|
|
||||||
if !entity.components.contains::<$s>() {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
$(
|
|
||||||
if !entity.components.contains::<$var>() {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
)+
|
|
||||||
|
|
||||||
if !Filter::check(entity) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
true
|
|
||||||
}
|
|
||||||
}),
|
|
||||||
|
|
||||||
create_callback: Box::new(move |entity| {
|
|
||||||
let [< $s:lower >] = UnsafeComponentStore::from(
|
|
||||||
entity.get_component::<$s>()?
|
|
||||||
);
|
|
||||||
|
|
||||||
$(
|
|
||||||
let [< $var:lower >] = UnsafeComponentStore::from(
|
|
||||||
entity.get_component::<$var>()?
|
|
||||||
);
|
|
||||||
)+
|
|
||||||
|
|
||||||
let e = entity.as_entity();
|
|
||||||
let f = f.clone();
|
|
||||||
|
|
||||||
Ok(Box::new(move |commands, _world| {
|
|
||||||
let query = Query {
|
|
||||||
entity: e,
|
|
||||||
c: unsafe { ( [< $s:lower >].as_mut(), $([< $var:lower >].as_mut(),)+) },
|
|
||||||
filter: PhantomData,
|
|
||||||
};
|
|
||||||
|
|
||||||
f(commands, query)
|
|
||||||
}))
|
|
||||||
}),
|
|
||||||
|
|
||||||
entities: IndexMap::new(),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<Func, Filter, $s, $( $var, )+> AddUpdates<( $s, $( $var, )+ ), (), Func, Filter> for Updates
|
|
||||||
where
|
|
||||||
$s: EntityComponent + ComponentDebug,
|
|
||||||
$(
|
|
||||||
$var: EntityComponent + ComponentDebug,
|
|
||||||
)+
|
|
||||||
Func: Fn(&mut Commands, Query<( &mut $s, $( &mut $var, )+ ), Filter>) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
Filter: CheckFilter + 'static
|
|
||||||
{
|
|
||||||
fn add_update(
|
|
||||||
&mut self,
|
|
||||||
name: &str,
|
|
||||||
priority: u32,
|
|
||||||
func: Func,
|
|
||||||
) -> Result<()> {
|
|
||||||
paste::item! {
|
|
||||||
self.add(name, priority, Update::Single(Archetype::create(func)))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<Func, Filter, $s, $( $var, )+> AddUpdates<( $s, $( $var, )+ ), (), Func, Filter> for WorldBuilder
|
|
||||||
where
|
|
||||||
$s: EntityComponent + ComponentDebug,
|
|
||||||
$(
|
|
||||||
$var: EntityComponent + ComponentDebug,
|
|
||||||
)+
|
|
||||||
Func: Fn(&mut Commands, Query<( &mut $s, $( &mut $var, )+ ), Filter>) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
Filter: CheckFilter + 'static
|
|
||||||
{
|
|
||||||
fn add_update(
|
|
||||||
&mut self,
|
|
||||||
name: &str,
|
|
||||||
priority: u32,
|
|
||||||
func: Func,
|
|
||||||
) -> Result<()> {
|
|
||||||
self.updates.add_update(name, priority, func)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
// with resources
|
|
||||||
( $s:ident, $($var:ident $(,)?)+ [$($res:ident $(,)?)+] ) => {
|
|
||||||
impl<Func, Filter, $s, $( $var, )+ $( $res, )+> CreateArchetype<( $s, $( $var, )+ ), ( $( $res, )+ ), Func, Filter> for Archetype
|
|
||||||
where
|
|
||||||
Func: Fn(&mut Commands, Query<( &mut $s, $( &mut $var, )+ ), Filter>, $(&mut $res,)+) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
Filter: CheckFilter + 'static,
|
|
||||||
$s: EntityComponent + ComponentDebug,
|
|
||||||
$(
|
|
||||||
$var: EntityComponent + ComponentDebug,
|
|
||||||
)+
|
|
||||||
$(
|
|
||||||
$res: ResourceTrait,
|
|
||||||
)+
|
|
||||||
{
|
|
||||||
paste::item! {
|
|
||||||
fn create(f: Func) -> Self {
|
|
||||||
Filter::verify_dedup::<$s>();
|
|
||||||
$(
|
|
||||||
Filter::verify_dedup::<$var>();
|
|
||||||
)+
|
|
||||||
|
|
||||||
Self {
|
|
||||||
check_entity: Box::new({
|
|
||||||
move |entity| {
|
|
||||||
if !entity.components.contains::<$s>() {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
$(
|
|
||||||
if !entity.components.contains::<$var>() {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
)+
|
|
||||||
|
|
||||||
if !Filter::check(entity) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
true
|
|
||||||
}
|
|
||||||
}),
|
|
||||||
|
|
||||||
create_callback: Box::new(move |entity| {
|
|
||||||
let [< $s:lower >] = UnsafeComponentStore::from(
|
|
||||||
entity.get_component::<$s>()?
|
|
||||||
);
|
|
||||||
|
|
||||||
$(
|
|
||||||
let [< $var:lower >] = UnsafeComponentStore::from(
|
|
||||||
entity.get_component::<$var>()?
|
|
||||||
);
|
|
||||||
)+
|
|
||||||
|
|
||||||
let e = entity.as_entity();
|
|
||||||
let f = f.clone();
|
|
||||||
|
|
||||||
Ok(Box::new(move |commands, world| {
|
|
||||||
let (
|
|
||||||
$(
|
|
||||||
[< $res:lower _var >],
|
|
||||||
)+
|
|
||||||
): (
|
|
||||||
$(
|
|
||||||
&mut $res,
|
|
||||||
)+
|
|
||||||
) = world.resources.get_mut()?;
|
|
||||||
|
|
||||||
let query = Query {
|
|
||||||
entity: e,
|
|
||||||
c: unsafe { ( [< $s:lower >].as_mut(), $([< $var:lower >].as_mut(),)+ ) },
|
|
||||||
filter: PhantomData,
|
|
||||||
};
|
|
||||||
|
|
||||||
f(commands, query, $([< $res:lower _var >],)+)
|
|
||||||
}))
|
|
||||||
}),
|
|
||||||
|
|
||||||
entities: IndexMap::new(),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<Func, Filter, $s, $( $var, )+ $( $res, )+> AddUpdates<( $s, $( $var, )+ ), ( $( $res, )+ ), Func, Filter> for Updates
|
|
||||||
where
|
|
||||||
$s: EntityComponent + ComponentDebug,
|
|
||||||
$(
|
|
||||||
$var: EntityComponent + ComponentDebug,
|
|
||||||
)+
|
|
||||||
$(
|
|
||||||
$res: ResourceTrait,
|
|
||||||
)+
|
|
||||||
Func: Fn(&mut Commands, Query<( &mut $s, $( &mut $var, )+ ), Filter>, $(&mut $res,)+) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
Filter: CheckFilter + 'static
|
|
||||||
{
|
|
||||||
fn add_update(
|
|
||||||
&mut self,
|
|
||||||
name: &str,
|
|
||||||
priority: u32,
|
|
||||||
func: Func,
|
|
||||||
) -> Result<()> {
|
|
||||||
paste::item! {
|
|
||||||
self.add(name, priority, Update::Single(Archetype::create(func)))
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<Func, Filter, $s, $( $var, )+ $( $res, )+> AddUpdates<( $s, $( $var, )+ ), ( $( $res, )+ ), Func, Filter> for WorldBuilder
|
|
||||||
where
|
|
||||||
$s: EntityComponent + ComponentDebug,
|
|
||||||
$(
|
|
||||||
$var: EntityComponent + ComponentDebug,
|
|
||||||
)+
|
|
||||||
$(
|
|
||||||
$res: ResourceTrait,
|
|
||||||
)+
|
|
||||||
Func: Fn(&mut Commands, Query<( &mut $s, $( &mut $var, )+ ), Filter>, $(&mut $res,)+) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
Filter: CheckFilter + 'static
|
|
||||||
{
|
|
||||||
fn add_update(
|
|
||||||
&mut self,
|
|
||||||
name: &str,
|
|
||||||
priority: u32,
|
|
||||||
func: Func,
|
|
||||||
) -> Result<()> {
|
|
||||||
self.updates.add_update(name, priority, func)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
macro_rules! impl_pair_update {
|
|
||||||
// lhs single
|
|
||||||
(
|
|
||||||
$lhs_id: expr,
|
|
||||||
( [$lhs_little: ident: $lhs_big: ident]$(,)? ),
|
|
||||||
$rhs_id: expr,
|
|
||||||
( $([$rhs_little: ident: $rhs_big: ident]$(,)?)+ )
|
|
||||||
) => {
|
|
||||||
impl ArchetypePair {
|
|
||||||
paste::item! {
|
|
||||||
pub fn [<create_lhs_ $lhs_id _rhs_ $rhs_id>] <F, LeftFilter, RightFilter, $lhs_big, $($rhs_big,)+>
|
|
||||||
(f: F) -> Self
|
|
||||||
where
|
|
||||||
F: Fn(&mut Commands, Query<&mut $lhs_big, LeftFilter>, Query<( $( &mut $rhs_big, )+ ), RightFilter>) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
LeftFilter: CheckFilter + 'static,
|
|
||||||
RightFilter: CheckFilter + 'static,
|
|
||||||
$(
|
|
||||||
$rhs_big: EntityComponent + ComponentDebug,
|
|
||||||
)+
|
|
||||||
$lhs_big: EntityComponent + ComponentDebug,
|
|
||||||
{
|
|
||||||
LeftFilter::verify_dedup::<$lhs_big>();
|
|
||||||
|
|
||||||
$(
|
|
||||||
RightFilter::verify_dedup::<$rhs_big>();
|
|
||||||
)+
|
|
||||||
|
|
||||||
Self {
|
|
||||||
check_left_entity: Box::new({
|
|
||||||
move |entity| {
|
|
||||||
if !entity.components.contains::<$lhs_big>() {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if !LeftFilter::check(entity) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
true
|
|
||||||
}
|
|
||||||
}),
|
|
||||||
check_right_entity: Box::new({
|
|
||||||
move |entity| {
|
|
||||||
$(
|
|
||||||
if !entity.components.contains::<$rhs_big>() {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
)+
|
|
||||||
|
|
||||||
if !RightFilter::check(entity) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
true
|
|
||||||
}
|
|
||||||
}),
|
|
||||||
|
|
||||||
create_callback: Box::new(move |lhs_entity, rhs_entity| {
|
|
||||||
let $lhs_little = UnsafeComponentStore::from(
|
|
||||||
lhs_entity.get_component::<$lhs_big>()?
|
|
||||||
);
|
|
||||||
|
|
||||||
$(
|
|
||||||
let $rhs_little = UnsafeComponentStore::from(
|
|
||||||
rhs_entity.get_component::<$rhs_big>()?
|
|
||||||
);
|
|
||||||
)+
|
|
||||||
|
|
||||||
let lhs_e = lhs_entity.as_entity();
|
|
||||||
let rhs_e = rhs_entity.as_entity();
|
|
||||||
let f = f.clone();
|
|
||||||
|
|
||||||
Ok(Box::new(move |commands| {
|
|
||||||
let lhs_query = Query {
|
|
||||||
entity: lhs_e,
|
|
||||||
c: unsafe { $lhs_little.as_mut() },
|
|
||||||
filter: PhantomData,
|
|
||||||
};
|
|
||||||
|
|
||||||
let rhs_query = Query {
|
|
||||||
entity: rhs_e,
|
|
||||||
c: unsafe { ($($rhs_little.as_mut(),)+) },
|
|
||||||
filter: PhantomData,
|
|
||||||
};
|
|
||||||
|
|
||||||
f(commands, lhs_query, rhs_query )
|
|
||||||
}))
|
|
||||||
}),
|
|
||||||
|
|
||||||
entities: IndexMap::new(),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<Func, LhsFilter, RhsFilter, $lhs_big, $($rhs_big,)+> AddUpdates<( $lhs_big, ($($rhs_big,)+) ), (), Func, (LhsFilter, RhsFilter)> for Updates
|
|
||||||
where
|
|
||||||
$(
|
|
||||||
$rhs_big: EntityComponent + ComponentDebug,
|
|
||||||
)+
|
|
||||||
$lhs_big: EntityComponent + ComponentDebug,
|
|
||||||
Func: Fn(&mut Commands, Query<&mut $lhs_big, LhsFilter>, Query<( $( &mut $rhs_big, )+ ), RhsFilter>) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
LhsFilter: CheckFilter + 'static,
|
|
||||||
RhsFilter: CheckFilter + 'static
|
|
||||||
{
|
|
||||||
fn add_update(
|
|
||||||
&mut self,
|
|
||||||
name: &str,
|
|
||||||
priority: u32,
|
|
||||||
func: Func,
|
|
||||||
) -> Result<()> {
|
|
||||||
paste::item! {
|
|
||||||
self.add(name, priority, Update::Pair(ArchetypePair::[<create_lhs_ $lhs_id _rhs_ $rhs_id>](func)))?;
|
|
||||||
}
|
|
||||||
|
|
||||||
Ok(())
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<Func, LhsFilter, RhsFilter, $lhs_big, $($rhs_big,)+> AddUpdates<( $lhs_big, ($($rhs_big,)+) ), (), Func, (LhsFilter, RhsFilter)> for WorldBuilder
|
|
||||||
where
|
|
||||||
$(
|
|
||||||
$rhs_big: EntityComponent + ComponentDebug,
|
|
||||||
)+
|
|
||||||
$lhs_big: EntityComponent + ComponentDebug,
|
|
||||||
Func: Fn(&mut Commands, Query<&mut $lhs_big, LhsFilter>, Query<( $( &mut $rhs_big, )+ ), RhsFilter>) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
LhsFilter: CheckFilter + 'static,
|
|
||||||
RhsFilter: CheckFilter + 'static
|
|
||||||
{
|
|
||||||
fn add_update(
|
|
||||||
&mut self,
|
|
||||||
name: &str,
|
|
||||||
priority: u32,
|
|
||||||
func: Func,
|
|
||||||
) -> Result<()> {
|
|
||||||
self.updates.add_update(name, priority, func)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
// rhs_single
|
|
||||||
(
|
|
||||||
$lhs_id: expr,
|
|
||||||
( $([$lhs_little: ident: $lhs_big: ident]$(,)?)+ ),
|
|
||||||
$rhs_id: expr,
|
|
||||||
( [$rhs_little: ident: $rhs_big: ident]$(,)? )
|
|
||||||
) => {
|
|
||||||
impl ArchetypePair {
|
|
||||||
paste::item! {
|
|
||||||
pub fn [<create_lhs_ $lhs_id _rhs_ $rhs_id>] <F, LeftFilter, RightFilter, $($lhs_big,)+ $rhs_big>
|
|
||||||
(f: F) -> Self
|
|
||||||
where
|
|
||||||
F: Fn(&mut Commands, Query<( $( &mut $lhs_big, )+ ), LeftFilter>, Query<&mut $rhs_big, RightFilter>) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
LeftFilter: CheckFilter + 'static,
|
|
||||||
RightFilter: CheckFilter + 'static,
|
|
||||||
$rhs_big: EntityComponent + ComponentDebug,
|
|
||||||
$(
|
|
||||||
$lhs_big: EntityComponent + ComponentDebug,
|
|
||||||
)+
|
|
||||||
{
|
|
||||||
$(
|
|
||||||
LeftFilter::verify_dedup::<$lhs_big>();
|
|
||||||
)+
|
|
||||||
|
|
||||||
RightFilter::verify_dedup::<$rhs_big>();
|
|
||||||
|
|
||||||
Self {
|
|
||||||
check_left_entity: Box::new({
|
|
||||||
move |entity| {
|
|
||||||
$(
|
|
||||||
if !entity.components.contains::<$lhs_big>() {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
)+
|
|
||||||
|
|
||||||
if !LeftFilter::check(entity) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
true
|
|
||||||
}
|
|
||||||
}),
|
|
||||||
check_right_entity: Box::new({
|
|
||||||
move |entity| {
|
|
||||||
if !entity.components.contains::<$rhs_big>() {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if !RightFilter::check(entity) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
true
|
|
||||||
}
|
|
||||||
}),
|
|
||||||
|
|
||||||
create_callback: Box::new(move |lhs_entity, rhs_entity| {
|
|
||||||
$(
|
|
||||||
let $lhs_little = UnsafeComponentStore::from(
|
|
||||||
lhs_entity.get_component::<$lhs_big>()?
|
|
||||||
);
|
|
||||||
)+
|
|
||||||
|
|
||||||
let $rhs_little = UnsafeComponentStore::from(
|
|
||||||
rhs_entity.get_component::<$rhs_big>()?
|
|
||||||
);
|
|
||||||
|
|
||||||
let lhs_e = lhs_entity.as_entity();
|
|
||||||
let rhs_e = rhs_entity.as_entity();
|
|
||||||
let f = f.clone();
|
|
||||||
|
|
||||||
Ok(Box::new(move |commands| {
|
|
||||||
let lhs_query = Query {
|
|
||||||
entity: lhs_e,
|
|
||||||
c: unsafe { ($($lhs_little.as_mut(),)+) },
|
|
||||||
filter: PhantomData,
|
|
||||||
};
|
|
||||||
|
|
||||||
let rhs_query = Query {
|
|
||||||
entity: rhs_e,
|
|
||||||
c: unsafe { $rhs_little.as_mut() },
|
|
||||||
filter: PhantomData,
|
|
||||||
};
|
|
||||||
|
|
||||||
f(commands, lhs_query, rhs_query )
|
|
||||||
}))
|
|
||||||
}),
|
|
||||||
|
|
||||||
entities: IndexMap::new(),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<Func, LhsFilter, RhsFilter, $( $lhs_big, )+ $rhs_big> AddUpdates<( ($( $lhs_big, )+), $rhs_big ), (), Func, (LhsFilter, RhsFilter)> for Updates
|
|
||||||
where
|
|
||||||
$rhs_big: EntityComponent + ComponentDebug,
|
|
||||||
$(
|
|
||||||
$lhs_big: EntityComponent + ComponentDebug,
|
|
||||||
)+
|
|
||||||
Func: Fn(&mut Commands, Query<( $( &mut $lhs_big, )+ ), LhsFilter>, Query<&mut $rhs_big, RhsFilter>) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
LhsFilter: CheckFilter + 'static,
|
|
||||||
RhsFilter: CheckFilter + 'static
|
|
||||||
{
|
|
||||||
fn add_update(
|
|
||||||
&mut self,
|
|
||||||
name: &str,
|
|
||||||
priority: u32,
|
|
||||||
func: Func,
|
|
||||||
) -> Result<()> {
|
|
||||||
paste::item! {
|
|
||||||
self.add(name, priority, Update::Pair(ArchetypePair::[<create_lhs_ $lhs_id _rhs_ $rhs_id>](func)))?;
|
|
||||||
}
|
|
||||||
|
|
||||||
Ok(())
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<Func, LhsFilter, RhsFilter, $( $lhs_big, )+ $rhs_big> AddUpdates<( ($( $lhs_big, )+), $rhs_big ), (), Func, (LhsFilter, RhsFilter)> for WorldBuilder
|
|
||||||
where
|
|
||||||
$rhs_big: EntityComponent + ComponentDebug,
|
|
||||||
$(
|
|
||||||
$lhs_big: EntityComponent + ComponentDebug,
|
|
||||||
)+
|
|
||||||
Func: Fn(&mut Commands, Query<( $( &mut $lhs_big, )+ ), LhsFilter>, Query<&mut $rhs_big, RhsFilter>) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
LhsFilter: CheckFilter + 'static,
|
|
||||||
RhsFilter: CheckFilter + 'static
|
|
||||||
{
|
|
||||||
fn add_update(
|
|
||||||
&mut self,
|
|
||||||
name: &str,
|
|
||||||
priority: u32,
|
|
||||||
func: Func,
|
|
||||||
) -> Result<()> {
|
|
||||||
self.updates.add_update(name, priority, func)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
(
|
|
||||||
$lhs_id: expr,
|
|
||||||
( $([$lhs_little: ident: $lhs_big: ident]$(,)?)+ ),
|
|
||||||
$rhs_id: expr,
|
|
||||||
( $([$rhs_little: ident: $rhs_big: ident]$(,)?)+ )
|
|
||||||
) => {
|
|
||||||
impl ArchetypePair {
|
|
||||||
paste::item! {
|
|
||||||
pub fn [<create_lhs_ $lhs_id _rhs_ $rhs_id>] <F, LeftFilter, RightFilter, $($lhs_big,)+ $($rhs_big,)+>
|
|
||||||
(f: F) -> Self
|
|
||||||
where
|
|
||||||
F: Fn(&mut Commands, Query<( $( &mut $lhs_big, )+ ), LeftFilter>, Query<( $( &mut $rhs_big, )+ ), RightFilter>) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
LeftFilter: CheckFilter + 'static,
|
|
||||||
RightFilter: CheckFilter + 'static,
|
|
||||||
$(
|
|
||||||
$rhs_big: EntityComponent + ComponentDebug,
|
|
||||||
)+
|
|
||||||
$(
|
|
||||||
$lhs_big: EntityComponent + ComponentDebug,
|
|
||||||
)+
|
|
||||||
{
|
|
||||||
$(
|
|
||||||
LeftFilter::verify_dedup::<$lhs_big>();
|
|
||||||
)+
|
|
||||||
|
|
||||||
$(
|
|
||||||
RightFilter::verify_dedup::<$rhs_big>();
|
|
||||||
)+
|
|
||||||
|
|
||||||
Self {
|
|
||||||
check_left_entity: Box::new({
|
|
||||||
move |entity| {
|
|
||||||
$(
|
|
||||||
if !entity.components.contains::<$lhs_big>() {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
)+
|
|
||||||
|
|
||||||
if !LeftFilter::check(entity) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
true
|
|
||||||
}
|
|
||||||
}),
|
|
||||||
check_right_entity: Box::new({
|
|
||||||
move |entity| {
|
|
||||||
$(
|
|
||||||
if !entity.components.contains::<$rhs_big>() {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
)+
|
|
||||||
|
|
||||||
if !RightFilter::check(entity) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
true
|
|
||||||
}
|
|
||||||
}),
|
|
||||||
|
|
||||||
create_callback: Box::new(move |lhs_entity, rhs_entity| {
|
|
||||||
$(
|
|
||||||
let $lhs_little = UnsafeComponentStore::from(
|
|
||||||
lhs_entity.get_component::<$lhs_big>()?
|
|
||||||
);
|
|
||||||
)+
|
|
||||||
|
|
||||||
$(
|
|
||||||
let $rhs_little = UnsafeComponentStore::from(
|
|
||||||
rhs_entity.get_component::<$rhs_big>()?
|
|
||||||
);
|
|
||||||
)+
|
|
||||||
|
|
||||||
let lhs_e = lhs_entity.as_entity();
|
|
||||||
let rhs_e = rhs_entity.as_entity();
|
|
||||||
let f = f.clone();
|
|
||||||
|
|
||||||
Ok(Box::new(move |commands| {
|
|
||||||
let lhs_query = Query {
|
|
||||||
entity: lhs_e,
|
|
||||||
c: unsafe { ($($lhs_little.as_mut(),)+) },
|
|
||||||
filter: PhantomData,
|
|
||||||
};
|
|
||||||
|
|
||||||
let rhs_query = Query {
|
|
||||||
entity: rhs_e,
|
|
||||||
c: unsafe { ($($rhs_little.as_mut(),)+) },
|
|
||||||
filter: PhantomData,
|
|
||||||
};
|
|
||||||
|
|
||||||
f(commands, lhs_query, rhs_query )
|
|
||||||
}))
|
|
||||||
}),
|
|
||||||
|
|
||||||
entities: IndexMap::new(),
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<Func, LhsFilter, RhsFilter, $( $lhs_big, )+ $($rhs_big,)+> AddUpdates<( ($( $lhs_big, )+), ($($rhs_big,)+) ), (), Func, (LhsFilter, RhsFilter)> for Updates
|
|
||||||
where
|
|
||||||
$(
|
|
||||||
$rhs_big: EntityComponent + ComponentDebug,
|
|
||||||
)+
|
|
||||||
$(
|
|
||||||
$lhs_big: EntityComponent + ComponentDebug,
|
|
||||||
)+
|
|
||||||
Func: Fn(&mut Commands, Query<( $( &mut $lhs_big, )+ ), LhsFilter>, Query<( $( &mut $rhs_big, )+ ), RhsFilter>) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
LhsFilter: CheckFilter + 'static,
|
|
||||||
RhsFilter: CheckFilter + 'static
|
|
||||||
{
|
|
||||||
fn add_update(
|
|
||||||
&mut self,
|
|
||||||
name: &str,
|
|
||||||
priority: u32,
|
|
||||||
func: Func,
|
|
||||||
) -> Result<()> {
|
|
||||||
paste::item! {
|
|
||||||
self.add(name, priority, Update::Pair(ArchetypePair::[<create_lhs_ $lhs_id _rhs_ $rhs_id>](func)))?;
|
|
||||||
}
|
|
||||||
|
|
||||||
Ok(())
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
impl<Func, LhsFilter, RhsFilter, $( $lhs_big, )+ $($rhs_big,)+> AddUpdates<( ($( $lhs_big, )+), ($($rhs_big,)+) ), (), Func, (LhsFilter, RhsFilter)> for WorldBuilder
|
|
||||||
where
|
|
||||||
$(
|
|
||||||
$rhs_big: EntityComponent + ComponentDebug,
|
|
||||||
)+
|
|
||||||
$(
|
|
||||||
$lhs_big: EntityComponent + ComponentDebug,
|
|
||||||
)+
|
|
||||||
Func: Fn(&mut Commands, Query<( $( &mut $lhs_big, )+ ), LhsFilter>, Query<( $( &mut $rhs_big, )+ ), RhsFilter>) -> Result<()> + Send + Sync + Clone + 'static,
|
|
||||||
LhsFilter: CheckFilter + 'static,
|
|
||||||
RhsFilter: CheckFilter + 'static
|
|
||||||
{
|
|
||||||
fn add_update(
|
|
||||||
&mut self,
|
|
||||||
name: &str,
|
|
||||||
priority: u32,
|
|
||||||
func: Func,
|
|
||||||
) -> Result<()> {
|
|
||||||
self.updates.add_update(name, priority, func)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
macro_rules! impl_update_filter {
|
macro_rules! impl_update_filter {
|
||||||
( $name: ident, $([$big: ident, $little: ident]$(,)?)+ ) => {
|
( $name: ident, $([$big: ident, $little: ident]$(,)?)+ ) => {
|
||||||
|
@ -999,17 +138,18 @@ impl ArchetypeInfo {
|
||||||
}
|
}
|
||||||
|
|
||||||
pub struct Archetype {
|
pub struct Archetype {
|
||||||
check_entity: Box<dyn Fn(&EntityObject) -> bool + Send + Sync>,
|
check_entity: Box<dyn Fn(&[&EntityObject]) -> bool + Send + Sync>,
|
||||||
create_callback: Box<
|
create_callback: Box<
|
||||||
dyn Fn(
|
dyn Fn(
|
||||||
&EntityObject,
|
&[&EntityObject],
|
||||||
)
|
)
|
||||||
-> Result<Box<dyn Fn(&mut Commands, &mut World) -> Result<()> + Send + Sync>>
|
-> Result<Box<dyn Fn(&mut Commands, &mut World) -> Result<()> + Send + Sync>>
|
||||||
+ Send
|
+ Send
|
||||||
+ Sync,
|
+ Sync,
|
||||||
>,
|
>,
|
||||||
|
|
||||||
entities: IndexMap<Entity, Box<dyn Fn(&mut Commands, &mut World) -> Result<()> + Send + Sync>>,
|
entities:
|
||||||
|
IndexMap<Vec<Entity>, Box<dyn Fn(&mut Commands, &mut World) -> Result<()> + Send + Sync>>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Archetype {
|
impl Archetype {
|
||||||
|
@ -1259,26 +399,25 @@ impl Archetypes {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
implement_pair_update!(impl_pair_update, 1, 10);
|
implement_updates!(10, 4);
|
||||||
implement_single_update!(impl_singleton_update, 1, 10);
|
|
||||||
|
|
||||||
#[rustfmt::skip]
|
// #[rustfmt::skip]
|
||||||
impl_update_filter!(Monuple, [R, r]);
|
// impl_update_filter!(Monuple, [R, r]);
|
||||||
#[rustfmt::skip]
|
// #[rustfmt::skip]
|
||||||
impl_update_filter!(Couple, [R, r], [S, s]);
|
// impl_update_filter!(Couple, [R, r], [S, s]);
|
||||||
#[rustfmt::skip]
|
// #[rustfmt::skip]
|
||||||
impl_update_filter!(Triple, [R, r], [S, s], [T, t]);
|
// impl_update_filter!(Triple, [R, r], [S, s], [T, t]);
|
||||||
#[rustfmt::skip]
|
// #[rustfmt::skip]
|
||||||
impl_update_filter!(Quadruple, [R, r], [S, s], [T, t], [U, u]);
|
// impl_update_filter!(Quadruple, [R, r], [S, s], [T, t], [U, u]);
|
||||||
#[rustfmt::skip]
|
// #[rustfmt::skip]
|
||||||
impl_update_filter!(Quintuple, [R, r], [S, s], [T, t], [U, u], [V, v]);
|
// impl_update_filter!(Quintuple, [R, r], [S, s], [T, t], [U, u], [V, v]);
|
||||||
#[rustfmt::skip]
|
// #[rustfmt::skip]
|
||||||
impl_update_filter!(Sextuple, [R, r], [S, s], [T, t], [U, u], [V, v], [W, w]);
|
// impl_update_filter!(Sextuple, [R, r], [S, s], [T, t], [U, u], [V, v], [W, w]);
|
||||||
#[rustfmt::skip]
|
// #[rustfmt::skip]
|
||||||
impl_update_filter!(Septuple, [R, r], [S, s], [T, t], [U, u], [V, v], [W, w], [X, x]);
|
// impl_update_filter!(Septuple, [R, r], [S, s], [T, t], [U, u], [V, v], [W, w], [X, x]);
|
||||||
#[rustfmt::skip]
|
// #[rustfmt::skip]
|
||||||
impl_update_filter!(Octuple, [R, r], [S, s], [T, t], [U, u], [V, v], [W, w], [X, x], [Y, y]);
|
// impl_update_filter!(Octuple, [R, r], [S, s], [T, t], [U, u], [V, v], [W, w], [X, x], [Y, y]);
|
||||||
#[rustfmt::skip]
|
// #[rustfmt::skip]
|
||||||
impl_update_filter!(Nonuple, [R, r], [S, s], [T, t], [U, u], [V, v], [W, w], [X, x], [Y, y], [Z, z]);
|
// impl_update_filter!(Nonuple, [R, r], [S, s], [T, t], [U, u], [V, v], [W, w], [X, x], [Y, y], [Z, z]);
|
||||||
#[rustfmt::skip]
|
// #[rustfmt::skip]
|
||||||
impl_update_filter!(Decuple, [R, r], [S, s], [T, t], [U, u], [V, v], [W, w], [X, x], [Y, y], [Z, z], [A, a]);
|
// impl_update_filter!(Decuple, [R, r], [S, s], [T, t], [U, u], [V, v], [W, w], [X, x], [Y, y], [Z, z], [A, a]);
|
||||||
|
|
|
@ -47,8 +47,8 @@ impl Query {
|
||||||
let filter = &self.filter;
|
let filter = &self.filter;
|
||||||
|
|
||||||
quote! {
|
quote! {
|
||||||
(
|
{
|
||||||
let entity = &entites[#index];
|
let entity = &entities[#index];
|
||||||
|
|
||||||
#(
|
#(
|
||||||
if !entity.components.contains::<#components>() {
|
if !entity.components.contains::<#components>() {
|
||||||
|
@ -59,7 +59,7 @@ impl Query {
|
||||||
if !#filter::check(entity) {
|
if !#filter::check(entity) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
)
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -72,16 +72,16 @@ impl Query {
|
||||||
.map(|component| format_ident!("q_{index}_{component}"))
|
.map(|component| format_ident!("q_{index}_{component}"))
|
||||||
.collect::<Vec<_>>();
|
.collect::<Vec<_>>();
|
||||||
let query_ident = format_ident!("query_{index}");
|
let query_ident = format_ident!("query_{index}");
|
||||||
let entity_ident = format_ident!("entity_{index}");
|
let entity_ident = format_ident!("e_{index}");
|
||||||
|
|
||||||
(
|
(
|
||||||
quote! {
|
quote! {
|
||||||
let #entity_name = &entities[#index];
|
let #entity_name = &entities[#index];
|
||||||
let #entity_ident = entity_name.as_entity();
|
let #entity_ident = #entity_name.as_entity();
|
||||||
|
|
||||||
#(
|
#(
|
||||||
let #component_name = UnsafeComponentStore::from(
|
let #component_name = UnsafeComponentStore::from(
|
||||||
entity.get_component::<#components>()?
|
#entity_name.get_component::<#components>()?
|
||||||
);
|
);
|
||||||
)*
|
)*
|
||||||
},
|
},
|
||||||
|
@ -136,6 +136,7 @@ struct Update {
|
||||||
|
|
||||||
impl Update {
|
impl Update {
|
||||||
const MIN_RESOURCE: usize = 0;
|
const MIN_RESOURCE: usize = 0;
|
||||||
|
const MAX_RESOURCE: usize = 10;
|
||||||
const MIN_COMPONENTS: usize = 1;
|
const MIN_COMPONENTS: usize = 1;
|
||||||
const MIN_QUERIES: usize = 1;
|
const MIN_QUERIES: usize = 1;
|
||||||
|
|
||||||
|
@ -145,7 +146,7 @@ impl Update {
|
||||||
.enumerate()
|
.enumerate()
|
||||||
.map(|(query, component_count)| {
|
.map(|(query, component_count)| {
|
||||||
Query::new(
|
Query::new(
|
||||||
(1..component_count).map(|component| format_ident!("C{component}Q{query}")),
|
(0..component_count).map(|component| format_ident!("C{component}Q{query}")),
|
||||||
query,
|
query,
|
||||||
)
|
)
|
||||||
})
|
})
|
||||||
|
@ -176,6 +177,18 @@ impl Update {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn filter_type_impls(&self) -> TokenStream2 {
|
||||||
|
let filter_types = self
|
||||||
|
.queries
|
||||||
|
.iter()
|
||||||
|
.map(|query| query.filter())
|
||||||
|
.collect::<Vec<_>>();
|
||||||
|
|
||||||
|
quote! {
|
||||||
|
#( #filter_types, )*
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
pub fn filter_requirements(&self) -> TokenStream2 {
|
pub fn filter_requirements(&self) -> TokenStream2 {
|
||||||
let filter_requirements = self
|
let filter_requirements = self
|
||||||
.queries
|
.queries
|
||||||
|
@ -200,6 +213,19 @@ impl Update {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn query_type_impls(&self) -> TokenStream2 {
|
||||||
|
let query_types = self
|
||||||
|
.queries
|
||||||
|
.iter()
|
||||||
|
.map(|query| query.components())
|
||||||
|
.flatten()
|
||||||
|
.collect::<Vec<_>>();
|
||||||
|
|
||||||
|
quote! {
|
||||||
|
#( #query_types, )*
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
pub fn component_requirements(&self) -> TokenStream2 {
|
pub fn component_requirements(&self) -> TokenStream2 {
|
||||||
let component_requirements = self
|
let component_requirements = self
|
||||||
.queries
|
.queries
|
||||||
|
@ -215,10 +241,30 @@ impl Update {
|
||||||
.collect::<Vec<_>>();
|
.collect::<Vec<_>>();
|
||||||
|
|
||||||
quote! {
|
quote! {
|
||||||
#( #component_requirements, )*
|
#( #component_requirements )*
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn resource_store(&self) -> (TokenStream2, Vec<Ident>) {
|
||||||
|
let resource_types = &self.resources;
|
||||||
|
let resource_idents = self
|
||||||
|
.resources
|
||||||
|
.iter()
|
||||||
|
.map(|resource| format_ident!("res_{resource}"))
|
||||||
|
.collect::<Vec<_>>();
|
||||||
|
|
||||||
|
(
|
||||||
|
quote! {
|
||||||
|
let (
|
||||||
|
#( #resource_idents, )*
|
||||||
|
): (
|
||||||
|
#( &mut #resource_types, )*
|
||||||
|
) = world.resources.get_mut()?;
|
||||||
|
},
|
||||||
|
resource_idents,
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
pub fn resource_types(&self) -> TokenStream2 {
|
pub fn resource_types(&self) -> TokenStream2 {
|
||||||
let resource_types = &self.resources;
|
let resource_types = &self.resources;
|
||||||
|
|
||||||
|
@ -227,6 +273,14 @@ impl Update {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn resource_type_impls(&self) -> TokenStream2 {
|
||||||
|
let resource_types = &self.resources;
|
||||||
|
|
||||||
|
quote! {
|
||||||
|
#( #resource_types, )*
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
pub fn reource_requirement(&self) -> TokenStream2 {
|
pub fn reource_requirement(&self) -> TokenStream2 {
|
||||||
let resource_types = &self.resources;
|
let resource_types = &self.resources;
|
||||||
|
|
||||||
|
@ -240,8 +294,13 @@ impl ToTokens for Update {
|
||||||
fn to_tokens(&self, tokens: &mut TokenStream2) {
|
fn to_tokens(&self, tokens: &mut TokenStream2) {
|
||||||
// generics to specify trait implementations
|
// generics to specify trait implementations
|
||||||
let filter_types = self.filter_types();
|
let filter_types = self.filter_types();
|
||||||
|
let filter_type_impls = self.filter_type_impls();
|
||||||
let query_types = self.query_types();
|
let query_types = self.query_types();
|
||||||
|
let query_type_impls = self.query_type_impls();
|
||||||
let resource_types = self.resource_types();
|
let resource_types = self.resource_types();
|
||||||
|
let resource_type_impls = self.resource_type_impls();
|
||||||
|
|
||||||
|
// panic!("{resource_type_impls}");
|
||||||
|
|
||||||
// function parameter
|
// function parameter
|
||||||
let queries = &self.queries;
|
let queries = &self.queries;
|
||||||
|
@ -273,15 +332,27 @@ impl ToTokens for Update {
|
||||||
.map(|(index, query)| query.check_entity(index))
|
.map(|(index, query)| query.check_entity(index))
|
||||||
.collect::<Vec<_>>();
|
.collect::<Vec<_>>();
|
||||||
|
|
||||||
let component_stores = self
|
let component_stores_and_queries = self
|
||||||
.queries
|
.queries
|
||||||
.iter()
|
.iter()
|
||||||
.enumerate()
|
.enumerate()
|
||||||
.map(|(index, query)| query.component_store_and_query(index))
|
.map(|(index, query)| query.component_store_and_query(index))
|
||||||
.collect::<Vec<_>>();
|
.collect::<Vec<_>>();
|
||||||
|
|
||||||
|
let mut component_stores = Vec::new();
|
||||||
|
let mut query_structs = Vec::new();
|
||||||
|
let mut query_idents = Vec::new();
|
||||||
|
|
||||||
|
for (component_store, query_struct, query_ident) in component_stores_and_queries {
|
||||||
|
component_stores.push(component_store);
|
||||||
|
query_structs.push(query_struct);
|
||||||
|
query_idents.push(query_ident);
|
||||||
|
}
|
||||||
|
|
||||||
|
let (resource_store, resource_idents) = self.resource_store();
|
||||||
|
|
||||||
TokenStream2::from(quote! {
|
TokenStream2::from(quote! {
|
||||||
impl<Func, #filter_types, #query_types, #resource_types> CreateArchetype<#query_types, #resource_types, Func, #filter_types> for Archetype
|
impl<Func, #filter_type_impls #query_type_impls #resource_type_impls> CreateArchetype<#query_types, #resource_types, Func, #filter_types> for Archetype
|
||||||
where
|
where
|
||||||
Func: Fn(&mut Commands, #( #queries, )* #resources ) -> Result<()> + Send + Sync + Clone + 'static,
|
Func: Fn(&mut Commands, #( #queries, )* #resources ) -> Result<()> + Send + Sync + Clone + 'static,
|
||||||
#filter_requirements
|
#filter_requirements
|
||||||
|
@ -299,13 +370,15 @@ impl ToTokens for Update {
|
||||||
}),
|
}),
|
||||||
|
|
||||||
create_callback: Box::new(move |entities| {
|
create_callback: Box::new(move |entities| {
|
||||||
let e = entity.as_entity();
|
#( #component_stores )*
|
||||||
|
|
||||||
let f = f.clone();
|
let f = f.clone();
|
||||||
|
|
||||||
Ok(Box::new(move |commands, world| {
|
Ok(Box::new(move |commands, world| {
|
||||||
|
#( #query_structs )*
|
||||||
|
#resource_store
|
||||||
|
|
||||||
|
f(commands, #( #query_idents, )* #( #resource_idents, )*)
|
||||||
f(commands )
|
|
||||||
}))
|
}))
|
||||||
}),
|
}),
|
||||||
|
|
||||||
|
@ -314,7 +387,7 @@ impl ToTokens for Update {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<Func, #filter_types, #query_types, #resource_types> AddUpdates<#query_types, #resource_types, Func, #filter_types> for Updates
|
impl<Func, #filter_type_impls #query_type_impls #resource_type_impls> AddUpdates<#query_types, #resource_types, Func, #filter_types> for Updates
|
||||||
where
|
where
|
||||||
Func: Fn(&mut Commands, #( #queries, )* #resources ) -> Result<()> + Send + Sync + Clone + 'static,
|
Func: Fn(&mut Commands, #( #queries, )* #resources ) -> Result<()> + Send + Sync + Clone + 'static,
|
||||||
#filter_requirements
|
#filter_requirements
|
||||||
|
@ -330,7 +403,7 @@ impl ToTokens for Update {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<Func, #filter_types, #query_types, #resource_types> AddUpdates<#query_types, #resource_types, Func, #filter_types> for WorldBuilder
|
impl<Func, #filter_type_impls #query_type_impls #resource_type_impls> AddUpdates<#query_types, #resource_types, Func, #filter_types> for WorldBuilder
|
||||||
where
|
where
|
||||||
Func: Fn(&mut Commands, #( #queries, )* #resources ) -> Result<()> + Send + Sync + Clone + 'static,
|
Func: Fn(&mut Commands, #( #queries, )* #resources ) -> Result<()> + Send + Sync + Clone + 'static,
|
||||||
#filter_requirements
|
#filter_requirements
|
||||||
|
@ -351,13 +424,29 @@ impl ToTokens for Update {
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn update(max_components: usize, max_queries: usize) -> TokenStream {
|
pub fn update(max_components: usize, max_queries: usize) -> TokenStream {
|
||||||
let updates = (Update::MIN_QUERIES..max_queries)
|
// let updates = (Update::MIN_QUERIES..max_queries)
|
||||||
.map(|query_count| {
|
// .map(|query_count| {
|
||||||
//
|
// let queries = (1..query_count).map(|q| {
|
||||||
})
|
|
||||||
.collect::<Vec<_>>();
|
// })
|
||||||
|
// })
|
||||||
|
// .collect::<Vec<_>>();
|
||||||
|
|
||||||
|
let mut query_counts = Vec::new();
|
||||||
|
|
||||||
|
for components in Update::MIN_COMPONENTS..=max_components {
|
||||||
|
query_counts.push(components);
|
||||||
|
}
|
||||||
|
|
||||||
|
let mut resources = Vec::new();
|
||||||
|
|
||||||
|
for resource in Update::MIN_RESOURCE..Update::MAX_RESOURCE {
|
||||||
|
resources.push(resource);
|
||||||
|
}
|
||||||
|
|
||||||
|
let updates = vec![Update::new(vec![2, 2].into_iter(), 1)];
|
||||||
|
|
||||||
TokenStream::from(quote! {
|
TokenStream::from(quote! {
|
||||||
#( #updates )
|
#( #updates )*
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue