Getting warmer...

This commit is contained in:
Danny McGee
2023-11-16 02:14:00 -05:00
parent c50a6246a9
commit 0a639429be
2 changed files with 37 additions and 49 deletions
+14 -5
View File
@@ -44,9 +44,9 @@ impl Plugin for ScenePlugin {
PostUpdate,
(
wasm::notify_entity_spawn_changes.pipe(error),
wasm::save_scene_system
.pipe(error)
.run_if(wasm::scene_download_requested),
wasm::save_scene_system.pipe(error).run_if(
resource_exists::<ActiveScene>().and_then(wasm::scene_download_requested),
),
),
);
}
@@ -62,6 +62,9 @@ struct NewScene {
pub gltf: Option<Handle<Gltf>>,
}
#[derive(Resource, Deref, DerefMut)]
pub struct ActiveScene(pub Handle<Scene>);
#[derive(Component)]
struct Inspectable;
@@ -161,7 +164,8 @@ fn scene_inst_ready(r_scene_mgr: Res<SceneSpawner>, q_scene_inst: Query<&SceneIn
fn mark_scene_objects(
mut cmd: Commands,
r_scene: Res<NewScene>,
r_new_scene: Res<NewScene>,
mut r_active_scene: Option<ResMut<ActiveScene>>,
r_assets: Res<AssetServer>,
ra_gltfs: Res<Assets<Gltf>>,
ra_gltf_nodes: Res<Assets<GltfNode>>,
@@ -212,7 +216,7 @@ fn mark_scene_objects(
));
});
if let Some(gltf) = r_scene
if let Some(gltf) = r_new_scene
.gltf
.as_ref()
.and_then(|handle| ra_gltfs.get(handle))
@@ -273,6 +277,11 @@ fn mark_scene_objects(
}
}
// Set the new scene as the active scene
match r_active_scene.as_mut() {
Some(active_scene) => ***active_scene = r_new_scene.clone(),
None => cmd.insert_resource(ActiveScene(r_new_scene.clone())),
};
cmd.remove_resource::<NewScene>();
}
+23 -44
View File
@@ -1,8 +1,6 @@
use std::collections::VecDeque;
use bevy::{
prelude::*, reflect::serde::TypedReflectSerializer, utils::HashSet, window::PrimaryWindow,
};
use bevy::{prelude::*, scene::SceneInstance, utils::HashSet, window::PrimaryWindow};
use serde::Serialize;
use wasm_bindgen::prelude::*;
@@ -22,53 +20,34 @@ pub(super) fn scene_download_requested() -> bool {
}
pub(super) fn save_scene_system(world: &mut World) -> Result<(), String> {
let mut scene = DynamicScene::from_world(world);
let scene_inst = world
.query::<&SceneInstance>()
.get_single(world)
.map_err(|err| format!("{err}"))?;
let scene_mgr = world.resource::<SceneSpawner>();
let mut builder = DynamicSceneBuilder::from_world(world);
builder
.allow_all()
.allow_all_resources()
.deny::<ComputedVisibility>()
.deny_resource::<Time>()
.extract_entities(scene_mgr.iter_instance_entities(**scene_inst))
.remove_empty_entities()
.extract_resources();
let scene = builder.build();
let type_registry = world.resource::<AppTypeRegistry>();
#[allow(clippy::borrowed_box)]
let is_serializable = |reflect: &Box<dyn Reflect>| -> bool {
TypedReflectSerializer::new(&**reflect, &type_registry.read())
.serialize(&wasm::SERIALIZER)
.is_ok()
};
// FIXME: This includes some stuff we don't want, including (most
// importantly) the _window_. We probably want to grab just the
// main camera, the skybox, the glTF scene instance and its
// children.
scene.resources = scene
.resources
.into_iter()
.filter(is_serializable)
.collect();
scene.entities = scene
.entities
.into_iter()
.filter_map(|mut ent| {
ent.components = ent.components.into_iter().filter(is_serializable).collect();
if ent.components.is_empty() {
None
} else {
Some(ent)
}
})
.collect();
let serialized = scene
.serialize_ron(type_registry)
.map_err(|err| format!("{err}"))?;
let window = world
.iter_entities()
.find_map(|ent| {
if ent.contains::<PrimaryWindow>() {
ent.get::<Window>()
} else {
None
}
})
.ok_or_else(|| "Failed to get Window from &mut World".to_string())?;
.query_filtered::<&Window, With<PrimaryWindow>>()
.get_single(world)
.map_err(|err| format!("{err}"))?;
wasm::dispatch_to_js(window, "scene-download-ready", &serialized)
}