#[derive(Component, Debug)]
struct Value(u32);
trait Mutable {
fn update() -> Box<dyn System<In = Mut<'static, Self>, Out = ()>>;
}
#[derive(Component)]
struct CloneValues {
values: Vec<u32>,
}
impl Mutable for CloneValues {
fn update() -> Box<dyn System<In = Mut<'static, Self>, Out = ()>> {
Box::new(bevy::ecs::system::IntoSystem::into_system(
|this: In<Mut<Self>>, values: Query<(Entity, &Value)>| {
let mut this = this.0;
this.values.clear();
for (entity, value) in &values {
info!("{:?}: Adding Value {:?}", entity, value);
this.values.push(value.0);
}
},
))
}
}
fn run_clone_values(world: &mut World) {
let id = world.component_id::<CloneValues>().unwrap();
let access = {
let mut a = Access::new();
a.add_write(id);
a
};
let mut system = CloneValues::update();
// SAFETY: we must make sure the system's access does not include CloneValues
assert!(access.is_compatible(system.component_access()));
let cell = world.as_unsafe_world_cell();
// SAFETY: this will only be used to query for CloneValues
let query_world = unsafe { cell.world_mut() };
// SAFETY: this will only be used by the system
let system_world = unsafe { cell.world_mut() };
// At this point we have multiple exclusive references to world
let mut query = query_world.query::<&mut CloneValues>();
system.initialize(system_world);
for comp in query.iter_mut(query_world) {
// SAFETY: system does not outlive world
let input: Mut<'static, CloneValues> = unsafe { std::mem::transmute(comp) };
system.run(input, system_world);
}
}
Is there a better way to do this?