Solid reload working for entities

attempt/001
Elijah Voigt 1 year ago
parent d8f67c2cef
commit d619d87f1b

@ -27,7 +27,7 @@ fn main() {
exit_condition: bevy::window::ExitCondition::OnPrimaryClosed,
..default()
}))
// .add_plugins(camera::CameraPlugin)
.add_plugins(camera::CameraPlugin)
// .add_plugins(editor::EditorPlugin)
// .add_plugins(menu::MenuPlugin)
// .add_plugins(window::WindowPlugin)

@ -13,8 +13,23 @@ impl Plugin for SavePlugin {
.init_asset::<SaveScene>()
.init_asset_loader::<SaveSceneLoader>()
.add_systems(Startup, load_scenes)
.add_systems(Update, spawn_scenes.run_if(on_event::<AssetEvent<SaveEntity>>()))
.add_systems(Update, spawn_entities.run_if(any_component_added::<Handle<SaveEntity>>));
.add_systems(
Update,
spawn_scenes.run_if(on_event::<AssetEvent<SaveScene>>()),
)
.add_systems(
Update,
sync_entities
.run_if(on_event::<AssetEvent<SaveEntity>>())
.after(spawn_scenes),
)
.add_systems(
Update,
spawn_entities
.run_if(any_component_added::<Handle<SaveEntity>>)
.after(sync_entities),
)
.add_systems(Update, debug_entities);
}
}
@ -148,7 +163,6 @@ impl AssetLoader for SaveSceneLoader {
.map(|line| parent_dir.join(line))
.map(|path| load_context.load(path))
.collect();
info!("Entities: {:?}", entities);
Ok(SaveScene { entities })
}
@ -170,22 +184,26 @@ fn spawn_scenes(
query: Query<(Entity, &Handle<SaveScene>)>,
mut events: EventReader<AssetEvent<SaveScene>>,
save_scenes: Res<Assets<SaveScene>>,
server: Res<AssetServer>,
mut commands: Commands,
) {
events.read().for_each(|event| {
if let AssetEvent::LoadedWithDependencies { id } = event {
debug!("Spawning scene {:?}", server.get_id_handle(*id).unwrap());
query
.iter()
.filter(|(_, handle)| handle.id() == *id)
.for_each(|(entity, handle)| {
debug!("Spawning scene {:?} on {:?}", handle, entity);
let scene = save_scenes.get(handle).unwrap();
// Get entity with SaveEntity handle
let mut e = commands.entity(entity);
// Clear the entity of descendants
debug!("Despawning scene descendants");
e.despawn_descendants();
debug!("Populating children in scene");
// Populate with entities
e.with_children(|parent| {
scene.entities.iter().for_each(|this| {
@ -199,22 +217,74 @@ fn spawn_scenes(
/// Spawns entities with the Handle<SaveEntity> component
fn spawn_entities(
events: Query<(Entity, &Handle<SaveEntity>), Added<Handle<SaveEntity>>>,
events: Query<
(Entity, &Handle<SaveEntity>),
Or<(Added<Handle<SaveEntity>>, Changed<Handle<SaveEntity>>)>,
>,
save_entities: Res<Assets<SaveEntity>>,
mut commands: Commands,
) {
events.iter().for_each(|(entity, handle)| {
debug!("Spawning entity {:?} {:?}", entity, handle);
// Get a handle on the
let mut e = commands.entity(entity);
debug!("Despawning entity descendants {:?}", entity);
e.despawn_descendants();
debug!("Clearing components on entity {:?}", entity);
// Clear any existing components on the entity;
e.retain::<Handle<SaveEntity>>();
// Get the entity asset containing reflected component
let save_entity = save_entities.get(handle).unwrap();
// Add each component to the entity
debug!("Populating entity with components {:?}", entity);
save_entity.components.iter().for_each(|component| {
e.insert_reflect(component.clone_value());
});
});
}
/// When an entity asset is updated, re-spawn it
/// NOTE: This should only be enabled in development mode(?)
fn sync_entities(
query: Query<(Entity, &Handle<SaveEntity>)>,
server: Res<AssetServer>,
mut events: EventReader<AssetEvent<SaveEntity>>,
mut commands: Commands,
) {
// Any time a SaveEntity asset is updated
events.read().for_each(|event| {
match event {
AssetEvent::LoadedWithDependencies { id } => {
debug!(
"SaveEnity loaded {:?}",
server.get_id_handle(*id).unwrap().path().unwrap()
);
// Find any entities with this Handle<SaveEntity>
for (entity, handle) in query.iter() {
if handle.id() == *id {
debug!("Found entity with same ID, updating");
// Get this entity with SaveEntity handle
let mut e = commands.entity(entity);
// Re-Insert the SaveEntity handle
e.remove::<Handle<SaveEntity>>().insert(handle.clone());
}
}
}
_ => debug!("Skipping SaveEntity event {:?}", event),
}
})
}
fn debug_entities(
events: Query<Entity, Or<(Changed<Handle<SaveEntity>>, Added<Handle<SaveEntity>>)>>,
mut commands: Commands,
) {
events.iter().for_each(|e| {
commands.entity(e).log_components();
});
}

Loading…
Cancel
Save