feat(Blenvy:Bevy): slowly adding back save/load (wip)
* moved out old code * added very basics of saving (HEAVY WIP)
This commit is contained in:
parent
ae9f07f549
commit
171ec7490a
|
@ -10,6 +10,9 @@ pub use registry::*;
|
|||
pub mod blueprints;
|
||||
pub use blueprints::*;
|
||||
|
||||
pub mod save_load;
|
||||
pub use save_load::*;
|
||||
|
||||
#[derive(Clone, Resource)]
|
||||
pub struct BlenvyConfig {
|
||||
// registry
|
||||
|
@ -26,6 +29,8 @@ pub struct BlenvyConfig {
|
|||
// save & load
|
||||
pub(crate) save_component_filter: SceneFilter,
|
||||
pub(crate) save_resource_filter: SceneFilter,
|
||||
//pub(crate) save_path: PathBuf,
|
||||
// save_path: PathBuf::from("saves"),
|
||||
}
|
||||
|
||||
#[derive(Debug, Clone)]
|
||||
|
@ -63,6 +68,7 @@ impl Plugin for BlenvyPlugin {
|
|||
#[cfg(not(target_arch = "wasm32"))]
|
||||
ExportRegistryPlugin::default(),
|
||||
BlueprintsPlugin::default(),
|
||||
SaveLoadPlugin::default()
|
||||
))
|
||||
.insert_resource(BlenvyConfig {
|
||||
export_registry: self.export_registry,
|
||||
|
|
|
@ -1,108 +1,59 @@
|
|||
pub mod saveable;
|
||||
use std::path::PathBuf;
|
||||
|
||||
pub use saveable::*;
|
||||
|
||||
pub mod saving;
|
||||
pub use saving::*;
|
||||
|
||||
pub mod loading;
|
||||
pub use loading::*;
|
||||
|
||||
use bevy::core_pipeline::core_3d::{Camera3dDepthTextureUsage, ScreenSpaceTransmissionQuality};
|
||||
use bevy::prelude::*;
|
||||
use bevy::prelude::{App, IntoSystemConfigs, Plugin};
|
||||
use blenvy::GltfBlueprintsSet;
|
||||
|
||||
#[derive(SystemSet, Debug, Hash, PartialEq, Eq, Clone)]
|
||||
pub enum SavingSet {
|
||||
Save,
|
||||
}
|
||||
#[derive(Component, Reflect, Debug, Default)]
|
||||
#[reflect(Component)]
|
||||
/// component used to mark any entity as Dynamic: aka add this to make sure your entity is going to be saved
|
||||
pub struct Dynamic;
|
||||
|
||||
#[derive(SystemSet, Debug, Hash, PartialEq, Eq, Clone)]
|
||||
pub enum LoadingSet {
|
||||
Load,
|
||||
}
|
||||
#[derive(Component, Reflect, Debug, Default)]
|
||||
#[reflect(Component)]
|
||||
/// marker component for entities that do not have parents, or whose parents should be ignored when serializing
|
||||
pub(crate) struct RootEntity;
|
||||
|
||||
// Plugin configuration
|
||||
#[derive(Component, Debug)]
|
||||
/// internal helper component to store parents before resetting them
|
||||
pub(crate) struct OriginalParent(pub(crate) Entity);
|
||||
|
||||
#[derive(Clone, Resource)]
|
||||
pub struct SaveLoadConfig {
|
||||
pub(crate) save_path: PathBuf,
|
||||
pub(crate) component_filter: SceneFilter,
|
||||
pub(crate) resource_filter: SceneFilter,
|
||||
}
|
||||
|
||||
// define the plugin
|
||||
|
||||
pub struct SaveLoadPlugin {
|
||||
pub component_filter: SceneFilter,
|
||||
pub resource_filter: SceneFilter,
|
||||
pub save_path: PathBuf,
|
||||
}
|
||||
|
||||
impl Default for SaveLoadPlugin {
|
||||
fn default() -> Self {
|
||||
Self {
|
||||
component_filter: SceneFilter::default(),
|
||||
resource_filter: SceneFilter::default(),
|
||||
save_path: PathBuf::from("scenes"),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// Marker component to Flag the root entity of all static entities (immutables)
|
||||
#[derive(Component, Reflect, Debug, Default)]
|
||||
#[reflect(Component)]
|
||||
pub struct StaticEntitiesRoot;
|
||||
|
||||
/// Marker component to Flag the root entity of all dynamic entities (mutables)
|
||||
#[derive(Component, Reflect, Debug, Default)]
|
||||
#[reflect(Component)]
|
||||
pub struct DynamicEntitiesRoot;
|
||||
|
||||
|
||||
#[derive(Resource, Clone, Debug, Default, Reflect)]
|
||||
#[reflect(Resource)]
|
||||
pub struct StaticEntitiesBlueprintInfo {
|
||||
//pub blueprint_info: BlueprintInfo,
|
||||
pub path: String,
|
||||
}
|
||||
|
||||
|
||||
pub mod saving;
|
||||
pub use saving::*;
|
||||
|
||||
#[derive(Debug, Clone, Default)]
|
||||
/// Plugin for saving & loading
|
||||
pub struct SaveLoadPlugin {}
|
||||
|
||||
impl Plugin for SaveLoadPlugin {
|
||||
fn build(&self, app: &mut App) {
|
||||
app.register_type::<Dynamic>()
|
||||
.register_type::<StaticEntitiesRoot>()
|
||||
// TODO: remove these in bevy 0.13, as these are now registered by default
|
||||
.register_type::<Camera3dDepthTextureUsage>()
|
||||
.register_type::<ScreenSpaceTransmissionQuality>()
|
||||
.register_type::<StaticEntitiesStorage>()
|
||||
.add_event::<SaveRequest>()
|
||||
.add_event::<LoadRequest>()
|
||||
.add_event::<LoadingFinished>()
|
||||
.add_event::<SavingFinished>()
|
||||
.insert_resource(SaveLoadConfig {
|
||||
save_path: self.save_path.clone(),
|
||||
|
||||
component_filter: self.component_filter.clone(),
|
||||
resource_filter: self.resource_filter.clone(),
|
||||
})
|
||||
.configure_sets(
|
||||
Update,
|
||||
(LoadingSet::Load).chain().before(GltfBlueprintsSet::Spawn), //.before(GltfComponentsSet::Injection)
|
||||
)
|
||||
.add_event::<SaveRequest>()
|
||||
.add_event::<SaveFinished>()
|
||||
.add_systems(
|
||||
PreUpdate,
|
||||
Update,
|
||||
(prepare_save_game, apply_deferred, save_game, cleanup_save)
|
||||
.chain()
|
||||
.run_if(should_save),
|
||||
)
|
||||
.add_systems(Update, mark_load_requested)
|
||||
.add_systems(
|
||||
Update,
|
||||
(unload_world, apply_deferred, load_game)
|
||||
.chain()
|
||||
.run_if(resource_exists::<LoadRequested>)
|
||||
.run_if(not(resource_exists::<LoadFirstStageDone>))
|
||||
.in_set(LoadingSet::Load),
|
||||
)
|
||||
.add_systems(
|
||||
Update,
|
||||
(load_static, apply_deferred, cleanup_loaded_scene)
|
||||
.chain()
|
||||
.run_if(resource_exists::<LoadFirstStageDone>)
|
||||
// .run_if(in_state(AppState::LoadingGame))
|
||||
.in_set(LoadingSet::Load),
|
||||
);
|
||||
;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,76 @@
|
|||
pub mod saveable;
|
||||
use std::path::PathBuf;
|
||||
|
||||
pub use saveable::*;
|
||||
|
||||
pub mod saving;
|
||||
pub use saving::*;
|
||||
|
||||
pub mod loading;
|
||||
pub use loading::*;
|
||||
|
||||
use bevy::core_pipeline::core_3d::{Camera3dDepthTextureUsage, ScreenSpaceTransmissionQuality};
|
||||
use bevy::prelude::*;
|
||||
use bevy::prelude::{App, IntoSystemConfigs, Plugin};
|
||||
use blenvy::GltfBlueprintsSet;
|
||||
|
||||
#[derive(SystemSet, Debug, Hash, PartialEq, Eq, Clone)]
|
||||
pub enum SavingSet {
|
||||
Save,
|
||||
}
|
||||
|
||||
#[derive(SystemSet, Debug, Hash, PartialEq, Eq, Clone)]
|
||||
pub enum LoadingSet {
|
||||
Load,
|
||||
}
|
||||
|
||||
|
||||
#[derive(Component, Reflect, Debug, Default)]
|
||||
#[reflect(Component)]
|
||||
pub struct StaticEntitiesRoot;
|
||||
|
||||
#[derive(Component, Reflect, Debug, Default)]
|
||||
#[reflect(Component)]
|
||||
pub struct DynamicEntitiesRoot;
|
||||
|
||||
impl Plugin for SaveLoadPlugin {
|
||||
fn build(&self, app: &mut App) {
|
||||
app.register_type::<Dynamic>()
|
||||
.register_type::<StaticEntitiesRoot>()
|
||||
// TODO: remove these in bevy 0.13, as these are now registered by default
|
||||
.register_type::<Camera3dDepthTextureUsage>()
|
||||
.register_type::<ScreenSpaceTransmissionQuality>()
|
||||
.register_type::<StaticEntitiesStorage>()
|
||||
.add_event::<SaveRequest>()
|
||||
.add_event::<LoadRequest>()
|
||||
.add_event::<LoadingFinished>()
|
||||
.add_event::<SavingFinished>()
|
||||
.configure_sets(
|
||||
Update,
|
||||
(LoadingSet::Load).chain().before(GltfBlueprintsSet::Spawn), //.before(GltfComponentsSet::Injection)
|
||||
)
|
||||
.add_systems(
|
||||
PreUpdate,
|
||||
(prepare_save_game, apply_deferred, save_game, cleanup_save)
|
||||
.chain()
|
||||
.run_if(should_save),
|
||||
)
|
||||
.add_systems(Update, mark_load_requested)
|
||||
.add_systems(
|
||||
Update,
|
||||
(unload_world, apply_deferred, load_game)
|
||||
.chain()
|
||||
.run_if(resource_exists::<LoadRequested>)
|
||||
.run_if(not(resource_exists::<LoadFirstStageDone>))
|
||||
.in_set(LoadingSet::Load),
|
||||
)
|
||||
.add_systems(
|
||||
Update,
|
||||
(load_static, apply_deferred, cleanup_loaded_scene)
|
||||
.chain()
|
||||
.run_if(resource_exists::<LoadFirstStageDone>)
|
||||
// .run_if(in_state(AppState::LoadingGame))
|
||||
.in_set(LoadingSet::Load),
|
||||
);
|
||||
}
|
||||
}
|
|
@ -0,0 +1,196 @@
|
|||
use bevy::prelude::*;
|
||||
use bevy::tasks::IoTaskPool;
|
||||
use blenvy::{BlueprintName, InBlueprint, Library, SpawnHere};
|
||||
|
||||
use std::fs::File;
|
||||
use std::io::Write;
|
||||
use std::path::Path;
|
||||
|
||||
use crate::{DynamicEntitiesRoot, SaveLoadConfig, StaticEntitiesRoot};
|
||||
|
||||
#[derive(Event, Debug)]
|
||||
pub struct SaveRequest {
|
||||
pub path: String,
|
||||
}
|
||||
|
||||
#[derive(Event)]
|
||||
pub struct SavingFinished;
|
||||
|
||||
pub fn should_save(save_requests: EventReader<SaveRequest>) -> bool {
|
||||
!save_requests.is_empty()
|
||||
}
|
||||
|
||||
#[derive(Resource, Clone, Debug, Default, Reflect)]
|
||||
#[reflect(Resource)]
|
||||
pub struct StaticEntitiesStorage {
|
||||
pub name: String,
|
||||
pub library_path: String,
|
||||
}
|
||||
|
||||
#[derive(Component, Reflect, Debug, Default)]
|
||||
#[reflect(Component)]
|
||||
/// marker component for entities that do not have parents, or whose parents should be ignored when serializing
|
||||
pub(crate) struct RootEntity;
|
||||
|
||||
#[derive(Component, Debug)]
|
||||
/// internal helper component to store parents before resetting them
|
||||
pub(crate) struct OriginalParent(pub(crate) Entity);
|
||||
|
||||
// any child of dynamic/ saveable entities that is not saveable itself should be removed from the list of children
|
||||
pub(crate) fn prepare_save_game(
|
||||
saveables: Query<Entity, (With<Dynamic>, With<BlueprintName>)>,
|
||||
root_entities: Query<Entity, Or<(With<DynamicEntitiesRoot>, Without<Parent>)>>, // With<DynamicEntitiesRoot>
|
||||
dynamic_entities: Query<(Entity, &Parent, Option<&Children>), With<Dynamic>>,
|
||||
static_entities: Query<(Entity, &BlueprintName, Option<&Library>), With<StaticEntitiesRoot>>,
|
||||
|
||||
mut commands: Commands,
|
||||
) {
|
||||
for entity in saveables.iter() {
|
||||
commands.entity(entity).insert(SpawnHere);
|
||||
}
|
||||
|
||||
for (entity, parent, children) in dynamic_entities.iter() {
|
||||
let parent = parent.get();
|
||||
if root_entities.contains(parent) {
|
||||
commands.entity(entity).insert(RootEntity);
|
||||
}
|
||||
|
||||
if let Some(children) = children {
|
||||
for sub_child in children.iter() {
|
||||
if !dynamic_entities.contains(*sub_child) {
|
||||
commands.entity(*sub_child).insert(OriginalParent(entity));
|
||||
commands.entity(entity).remove_children(&[*sub_child]);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
for (_, blueprint_name, library) in static_entities.iter() {
|
||||
let library_path: String = library.map_or_else(|| "", |l| l.0.to_str().unwrap()).into();
|
||||
commands.insert_resource(StaticEntitiesStorage {
|
||||
name: blueprint_name.0.clone(),
|
||||
library_path,
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
pub(crate) fn save_game(world: &mut World) {
|
||||
info!("saving");
|
||||
|
||||
let mut save_path: String = "".into();
|
||||
let mut events = world.resource_mut::<Events<SaveRequest>>();
|
||||
|
||||
for event in events.get_reader().read(&events) {
|
||||
info!("SAVE EVENT !! {:?}", event);
|
||||
save_path.clone_from(&event.path);
|
||||
}
|
||||
events.clear();
|
||||
|
||||
let saveable_entities: Vec<Entity> = world
|
||||
.query_filtered::<Entity, (With<Dynamic>, Without<InBlueprint>, Without<RootEntity>)>()
|
||||
.iter(world)
|
||||
.collect();
|
||||
|
||||
let saveable_root_entities: Vec<Entity> = world
|
||||
.query_filtered::<Entity, (With<Dynamic>, Without<InBlueprint>, With<RootEntity>)>()
|
||||
.iter(world)
|
||||
.collect();
|
||||
|
||||
info!("saveable entities {}", saveable_entities.len());
|
||||
info!("saveable root entities {}", saveable_root_entities.len());
|
||||
|
||||
let save_load_config = world
|
||||
.get_resource::<SaveLoadConfig>()
|
||||
.expect("SaveLoadConfig should exist at this stage");
|
||||
|
||||
// we hardcode some of the always allowed types
|
||||
let filter = save_load_config
|
||||
.component_filter
|
||||
.clone()
|
||||
.allow::<Parent>()
|
||||
.allow::<Children>()
|
||||
.allow::<BlueprintName>()
|
||||
.allow::<SpawnHere>()
|
||||
.allow::<Dynamic>()
|
||||
|
||||
|
||||
;
|
||||
|
||||
// for root entities, it is the same EXCEPT we make sure parents are not included
|
||||
let filter_root = filter.clone().deny::<Parent>();
|
||||
|
||||
let filter_resources = save_load_config
|
||||
.resource_filter
|
||||
.clone()
|
||||
.allow::<StaticEntitiesStorage>()
|
||||
;
|
||||
|
||||
// for default stuff
|
||||
let scene_builder = DynamicSceneBuilder::from_world(world)
|
||||
.with_filter(filter.clone())
|
||||
.with_resource_filter(filter_resources.clone());
|
||||
|
||||
let mut dyn_scene = scene_builder
|
||||
.extract_resources()
|
||||
.extract_entities(saveable_entities.clone().into_iter())
|
||||
.remove_empty_entities()
|
||||
.build();
|
||||
|
||||
// for root entities
|
||||
let scene_builder_root = DynamicSceneBuilder::from_world(world)
|
||||
.with_filter(filter_root.clone())
|
||||
.with_resource_filter(filter_resources.clone());
|
||||
|
||||
// FIXME : add back
|
||||
let mut dyn_scene_root = scene_builder_root
|
||||
.extract_resources()
|
||||
.extract_entities(
|
||||
saveable_root_entities.clone().into_iter(), // .chain(static_world_markers.into_iter()),
|
||||
)
|
||||
.remove_empty_entities()
|
||||
.build();
|
||||
|
||||
dyn_scene.entities.append(&mut dyn_scene_root.entities);
|
||||
// dyn_scene.resources.append(&mut dyn_scene_root.resources);
|
||||
|
||||
let serialized_scene = dyn_scene
|
||||
.serialize(&world.resource::<AppTypeRegistry>().read())
|
||||
.unwrap();
|
||||
|
||||
let save_path = Path::new("assets")
|
||||
.join(&save_load_config.save_path)
|
||||
.join(Path::new(save_path.as_str())); // Path::new(&save_load_config.save_path).join(Path::new(save_path.as_str()));
|
||||
info!("saving game to {:?}", save_path);
|
||||
|
||||
// world.send_event(SavingFinished);
|
||||
|
||||
#[cfg(not(target_arch = "wasm32"))]
|
||||
IoTaskPool::get()
|
||||
.spawn(async move {
|
||||
// Write the scene RON data to file
|
||||
File::create(save_path)
|
||||
.and_then(|mut file| file.write(serialized_scene.as_bytes()))
|
||||
.expect("Error while writing save to file");
|
||||
})
|
||||
.detach();
|
||||
}
|
||||
|
||||
pub(crate) fn cleanup_save(
|
||||
needs_parent_reset: Query<(Entity, &OriginalParent)>,
|
||||
mut saving_finished: EventWriter<SavingFinished>,
|
||||
mut commands: Commands,
|
||||
) {
|
||||
for (entity, original_parent) in needs_parent_reset.iter() {
|
||||
commands.entity(original_parent.0).add_child(entity);
|
||||
}
|
||||
commands.remove_resource::<StaticEntitiesStorage>();
|
||||
saving_finished.send(SavingFinished);
|
||||
}
|
||||
/*
|
||||
pub(crate) fn cleanup_save(mut world: &mut World) {
|
||||
|
||||
let mut query = world.query::<(Entity, &OriginalParent)>();
|
||||
for (mut entity, original_parent) in query.iter_mut(&mut world) {
|
||||
let e = world.entity_mut(original_parent.0);
|
||||
// .add_child(entity);
|
||||
}
|
||||
}*/
|
|
@ -1,7 +0,0 @@
|
|||
use bevy::prelude::*;
|
||||
|
||||
#[derive(Component, Reflect, Debug, Default)]
|
||||
#[reflect(Component)]
|
||||
/// component used to mark any entity as Dynamic: aka add this to make sure your entity is going to be saved
|
||||
pub struct Dynamic(pub bool);
|
||||
|
|
@ -1,55 +1,42 @@
|
|||
use bevy::prelude::*;
|
||||
use bevy::tasks::IoTaskPool;
|
||||
use blenvy::{BlueprintName, InBlueprint, Library, SpawnHere};
|
||||
|
||||
use std::fs::File;
|
||||
use std::io::Write;
|
||||
use std::path::Path;
|
||||
|
||||
use crate::{Dynamic, DynamicEntitiesRoot, SaveLoadConfig, StaticEntitiesRoot};
|
||||
use bevy::render::camera::{CameraMainTextureUsages, CameraRenderGraph};
|
||||
use bevy::{prelude::*, tasks::IoTaskPool};
|
||||
use bevy::prelude::World;
|
||||
|
||||
use crate::{BlenvyConfig, BlueprintInfo, Dynamic, FromBlueprint, RootEntity, SpawnBlueprint};
|
||||
|
||||
use super::{DynamicEntitiesRoot, OriginalParent, StaticEntitiesRoot};
|
||||
|
||||
#[derive(Event, Debug)]
|
||||
pub struct SaveRequest {
|
||||
pub path: String,
|
||||
}
|
||||
|
||||
#[derive(Event)]
|
||||
pub struct SavingFinished;
|
||||
pub struct SaveFinished; // TODO: merge the the events above
|
||||
|
||||
pub fn should_save(save_requests: EventReader<SaveRequest>) -> bool {
|
||||
!save_requests.is_empty()
|
||||
}
|
||||
|
||||
#[derive(Resource, Clone, Debug, Default, Reflect)]
|
||||
#[reflect(Resource)]
|
||||
pub struct StaticEntitiesStorage {
|
||||
pub name: String,
|
||||
pub library_path: String,
|
||||
}
|
||||
|
||||
#[derive(Component, Reflect, Debug, Default)]
|
||||
#[reflect(Component)]
|
||||
/// marker component for entities that do not have parents, or whose parents should be ignored when serializing
|
||||
pub(crate) struct RootEntity;
|
||||
|
||||
#[derive(Component, Debug)]
|
||||
/// internal helper component to store parents before resetting them
|
||||
pub(crate) struct OriginalParent(pub(crate) Entity);
|
||||
|
||||
// any child of dynamic/ saveable entities that is not saveable itself should be removed from the list of children
|
||||
pub(crate) fn prepare_save_game(
|
||||
saveables: Query<Entity, (With<Dynamic>, With<BlueprintName>)>,
|
||||
saveables: Query<Entity, (With<Dynamic>, With<BlueprintInfo>)>,
|
||||
root_entities: Query<Entity, Or<(With<DynamicEntitiesRoot>, Without<Parent>)>>, // With<DynamicEntitiesRoot>
|
||||
dynamic_entities: Query<(Entity, &Parent, Option<&Children>), With<Dynamic>>,
|
||||
static_entities: Query<(Entity, &BlueprintName, Option<&Library>), With<StaticEntitiesRoot>>,
|
||||
static_entities: Query<(Entity, &BlueprintInfo), With<StaticEntitiesRoot>>,
|
||||
|
||||
mut commands: Commands,
|
||||
) {
|
||||
for entity in saveables.iter() {
|
||||
commands.entity(entity).insert(SpawnHere);
|
||||
commands.entity(entity).insert(SpawnBlueprint);
|
||||
}
|
||||
|
||||
for (entity, parent, children) in dynamic_entities.iter() {
|
||||
println!("prepare save game");
|
||||
let parent = parent.get();
|
||||
if root_entities.contains(parent) {
|
||||
commands.entity(entity).insert(RootEntity);
|
||||
|
@ -64,14 +51,17 @@ pub(crate) fn prepare_save_game(
|
|||
}
|
||||
}
|
||||
}
|
||||
for (_, blueprint_name, library) in static_entities.iter() {
|
||||
/*for (_, blueprint_name) in static_entities.iter() {
|
||||
let library_path: String = library.map_or_else(|| "", |l| l.0.to_str().unwrap()).into();
|
||||
commands.insert_resource(StaticEntitiesStorage {
|
||||
name: blueprint_name.0.clone(),
|
||||
library_path,
|
||||
});
|
||||
}
|
||||
}*/
|
||||
}
|
||||
|
||||
|
||||
|
||||
pub(crate) fn save_game(world: &mut World) {
|
||||
info!("saving");
|
||||
|
||||
|
@ -85,39 +75,49 @@ pub(crate) fn save_game(world: &mut World) {
|
|||
events.clear();
|
||||
|
||||
let saveable_entities: Vec<Entity> = world
|
||||
.query_filtered::<Entity, (With<Dynamic>, Without<InBlueprint>, Without<RootEntity>)>()
|
||||
// .query_filtered::<Entity, (With<Dynamic>, Without<FromBlueprint>, Without<RootEntity>)>()
|
||||
.query_filtered::<Entity, (With<Dynamic>, Without<RootEntity>)>()
|
||||
.iter(world)
|
||||
.collect();
|
||||
|
||||
let saveable_root_entities: Vec<Entity> = world
|
||||
.query_filtered::<Entity, (With<Dynamic>, Without<InBlueprint>, With<RootEntity>)>()
|
||||
.query_filtered::<Entity, (With<Dynamic>, With<RootEntity>)>()
|
||||
//.query_filtered::<Entity, (With<Dynamic>, Without<FromBlueprint>, With<RootEntity>)>()
|
||||
.iter(world)
|
||||
.collect();
|
||||
|
||||
info!("saveable entities {}", saveable_entities.len());
|
||||
info!("saveable root entities {}", saveable_root_entities.len());
|
||||
|
||||
let save_load_config = world
|
||||
.get_resource::<SaveLoadConfig>()
|
||||
.expect("SaveLoadConfig should exist at this stage");
|
||||
let config = world
|
||||
.get_resource::<BlenvyConfig>()
|
||||
.expect("Blenvy configuration should exist at this stage");
|
||||
|
||||
// we hardcode some of the always allowed types
|
||||
let filter = save_load_config
|
||||
.component_filter
|
||||
let filter = config
|
||||
.save_component_filter
|
||||
.clone()
|
||||
.allow::<Parent>()
|
||||
.allow::<Children>()
|
||||
.allow::<BlueprintName>()
|
||||
.allow::<SpawnHere>()
|
||||
.allow::<Dynamic>();
|
||||
.allow::<BlueprintInfo>()
|
||||
.allow::<SpawnBlueprint>()
|
||||
.allow::<Dynamic>()
|
||||
|
||||
/*.deny::<CameraRenderGraph>()
|
||||
.deny::<CameraMainTextureUsages>()
|
||||
.deny::<Handle<Mesh>>()
|
||||
.deny::<Handle<StandardMaterial>>() */
|
||||
;
|
||||
|
||||
// for root entities, it is the same EXCEPT we make sure parents are not included
|
||||
let filter_root = filter.clone().deny::<Parent>();
|
||||
|
||||
let filter_resources = save_load_config
|
||||
.resource_filter
|
||||
.clone()
|
||||
.allow::<StaticEntitiesStorage>();
|
||||
let filter_resources = config.clone()
|
||||
.save_resource_filter
|
||||
.deny::<Time<Real>>()
|
||||
|
||||
.clone();
|
||||
//.allow::<StaticEntitiesStorage>();
|
||||
|
||||
// for default stuff
|
||||
let scene_builder = DynamicSceneBuilder::from_world(world)
|
||||
|
@ -143,15 +143,15 @@ pub(crate) fn save_game(world: &mut World) {
|
|||
.remove_empty_entities()
|
||||
.build();
|
||||
|
||||
dyn_scene.entities.append(&mut dyn_scene_root.entities);
|
||||
// dyn_scene.entities.append(&mut dyn_scene_root.entities);
|
||||
// dyn_scene.resources.append(&mut dyn_scene_root.resources);
|
||||
|
||||
let serialized_scene = dyn_scene
|
||||
.serialize(&world.resource::<AppTypeRegistry>().read())
|
||||
.unwrap();
|
||||
.expect("filtered scene should serialize correctly");
|
||||
|
||||
let save_path = Path::new("assets")
|
||||
.join(&save_load_config.save_path)
|
||||
//.join(&config.save_path)
|
||||
.join(Path::new(save_path.as_str())); // Path::new(&save_load_config.save_path).join(Path::new(save_path.as_str()));
|
||||
info!("saving game to {:?}", save_path);
|
||||
|
||||
|
@ -170,21 +170,12 @@ pub(crate) fn save_game(world: &mut World) {
|
|||
|
||||
pub(crate) fn cleanup_save(
|
||||
needs_parent_reset: Query<(Entity, &OriginalParent)>,
|
||||
mut saving_finished: EventWriter<SavingFinished>,
|
||||
mut saving_finished: EventWriter<SaveFinished>,
|
||||
mut commands: Commands,
|
||||
) {
|
||||
for (entity, original_parent) in needs_parent_reset.iter() {
|
||||
commands.entity(original_parent.0).add_child(entity);
|
||||
}
|
||||
commands.remove_resource::<StaticEntitiesStorage>();
|
||||
saving_finished.send(SavingFinished);
|
||||
// commands.remove_resource::<StaticEntitiesStorage>();
|
||||
saving_finished.send(SaveFinished);
|
||||
}
|
||||
/*
|
||||
pub(crate) fn cleanup_save(mut world: &mut World) {
|
||||
|
||||
let mut query = world.query::<(Entity, &OriginalParent)>();
|
||||
for (mut entity, original_parent) in query.iter_mut(&mut world) {
|
||||
let e = world.entity_mut(original_parent.0);
|
||||
// .add_child(entity);
|
||||
}
|
||||
}*/
|
||||
|
|
Loading…
Reference in New Issue