mirror of
https://github.com/storytold/storyteller-bevy.git
synced 2026-10-28 08:58:07 +00:00
Refactor Studio entry-points (#54)
This PR heavily refactors the entry-point functions in `studio/src/lib.rs` to simplify and consolidate. Additionally, the frontend application should now be configurable as expected with any valid combination of the following URL parameters: * `objectId` : A pre-bundled library object to load (e.g., "couch.gltf") * `bvh` : Any resolvable path to a BVH animation with a MocapNET skeleton (e.g., "mocap/shuffle.bvh") * `mixamo` : Any resolvable path to a glTF animation with the Mixamo skeleton (e.g., "mocap/hip-hop-dancing.gltf") * `sceneImport` : Any resolvable path to an arbitrary glTF scene (untested, but should theoretically work) * `scene` : Any resolvable path to a previously saved Storyteller Studio scene in `*.scn.ron` format * `skybox` : The ID of a pre-bundled skybox asset. Valid options are: - "gum_trees_4k" - "kloofenfal_28d_misty_4k" - "meadow_4k" - "promenade_de_vidy_4k" - "scythian_tombs_4k" - "test_scene" (this is the default if not specified) * `mode` : One of "studio" or "viewer" (the default if not specified) "Validity" rules are as follows: * `objectId`, `bvh`, `mixamo`, `sceneImport` and `scene` are mutually exclusive * `skybox` is not supported for `scene` (the skybox should be saved and loaded as part of the scene description, though this is not currently working) * Both `mode` options are valid for all other parameters
This commit is contained in:
@@ -0,0 +1,164 @@
|
||||
use bevy::prelude::*;
|
||||
use serde::{Deserialize, Serialize};
|
||||
use wasm_bindgen::prelude::*;
|
||||
|
||||
use crate::{InitAsset, InitParams, StudioMode, ViewportSize};
|
||||
|
||||
#[wasm_bindgen(typescript_custom_section)]
|
||||
const WASM_ENTRY_POINTS: &str = r#"
|
||||
export type SkyboxId
|
||||
= "gum_trees_4k"
|
||||
| "kloofenfal_28d_misty_4k"
|
||||
| "meadow_4k"
|
||||
| "promenade_de_vidy_4k"
|
||||
| "scythian_tombs_4k"
|
||||
| "test_scene"
|
||||
;
|
||||
|
||||
export interface InitOptions {
|
||||
mode: StudioMode;
|
||||
/** Required for all entry-points except `initFromStorytellerScene()` */
|
||||
skyboxId?: SkyboxId;
|
||||
canvasSelector: string;
|
||||
canvasAlt: string;
|
||||
viewportSize: ViewportSize;
|
||||
}
|
||||
|
||||
export function initFromLibrary(objectId: string, options: InitOptions): void;
|
||||
export function initFromBvh(animPath: string, options: InitOptions): void;
|
||||
export function initFromMixamo(animPath: string, options: InitOptions): void;
|
||||
export function initFromSceneImport(scenePath: string, options: InitOptions): void;
|
||||
export function initFromStorytellerScene(scenePath: string, options: InitOptions): void;
|
||||
"#;
|
||||
|
||||
#[derive(Serialize, Deserialize)]
|
||||
struct WasmInitOptions {
|
||||
#[serde(rename = "skyboxId")]
|
||||
skybox_id: Option<String>,
|
||||
mode: StudioMode,
|
||||
#[serde(rename = "canvasSelector")]
|
||||
canvas_selector: String,
|
||||
#[serde(rename = "canvasAlt")]
|
||||
canvas_alt: String,
|
||||
#[serde(rename = "viewportSize")]
|
||||
viewport_size: ViewportSize,
|
||||
}
|
||||
|
||||
#[wasm_bindgen(skip_typescript, js_name = initFromLibrary)]
|
||||
pub fn init_from_library(object_id: String, options: JsValue) -> Result<(), JsValue> {
|
||||
let options = serde_wasm_bindgen::from_value::<WasmInitOptions>(options)?;
|
||||
let skybox_id = options
|
||||
.skybox_id
|
||||
.expect("`skyboxId` is required for `initFromLibrary`");
|
||||
|
||||
crate::start(
|
||||
InitParams::FromAsset {
|
||||
asset: InitAsset::LibraryObject(object_id),
|
||||
skybox_id,
|
||||
},
|
||||
options.mode,
|
||||
Some(Window {
|
||||
resolution: options.viewport_size.into(),
|
||||
title: options.canvas_alt,
|
||||
canvas: Some(options.canvas_selector),
|
||||
..default()
|
||||
}),
|
||||
)
|
||||
.run();
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[wasm_bindgen(skip_typescript, js_name = initFromBvh)]
|
||||
pub fn init_from_bvh(anim_path: String, options: JsValue) -> Result<(), JsValue> {
|
||||
let options = serde_wasm_bindgen::from_value::<WasmInitOptions>(options)?;
|
||||
let skybox_id = options
|
||||
.skybox_id
|
||||
.expect("`skyboxId` is required for `initFromBvh`");
|
||||
|
||||
crate::start(
|
||||
InitParams::FromAsset {
|
||||
asset: InitAsset::BvhAnim(anim_path),
|
||||
skybox_id,
|
||||
},
|
||||
options.mode,
|
||||
Some(Window {
|
||||
resolution: options.viewport_size.into(),
|
||||
title: options.canvas_alt,
|
||||
canvas: Some(options.canvas_selector),
|
||||
..default()
|
||||
}),
|
||||
)
|
||||
.run();
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[wasm_bindgen(skip_typescript, js_name = initFromMixamo)]
|
||||
pub fn init_from_mixamo(anim_path: String, options: JsValue) -> Result<(), JsValue> {
|
||||
let options = serde_wasm_bindgen::from_value::<WasmInitOptions>(options)?;
|
||||
let skybox_id = options
|
||||
.skybox_id
|
||||
.expect("`skyboxId` is required for `initFromMixamo`");
|
||||
|
||||
crate::start(
|
||||
InitParams::FromAsset {
|
||||
asset: InitAsset::MixamoAnim(anim_path),
|
||||
skybox_id,
|
||||
},
|
||||
options.mode,
|
||||
Some(Window {
|
||||
resolution: options.viewport_size.into(),
|
||||
title: options.canvas_alt,
|
||||
canvas: Some(options.canvas_selector),
|
||||
..default()
|
||||
}),
|
||||
)
|
||||
.run();
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[wasm_bindgen(skip_typescript, js_name = initFromSceneImport)]
|
||||
pub fn init_from_scene_import(scene_path: String, options: JsValue) -> Result<(), JsValue> {
|
||||
let options = serde_wasm_bindgen::from_value::<WasmInitOptions>(options)?;
|
||||
let skybox_id = options
|
||||
.skybox_id
|
||||
.expect("`skyboxId` is required for `initFromSceneImport`");
|
||||
|
||||
crate::start(
|
||||
InitParams::FromAsset {
|
||||
asset: InitAsset::ImportedScene(scene_path),
|
||||
skybox_id,
|
||||
},
|
||||
options.mode,
|
||||
Some(Window {
|
||||
resolution: options.viewport_size.into(),
|
||||
title: options.canvas_alt,
|
||||
canvas: Some(options.canvas_selector),
|
||||
..default()
|
||||
}),
|
||||
)
|
||||
.run();
|
||||
|
||||
Ok(())
|
||||
}
|
||||
|
||||
#[wasm_bindgen(skip_typescript, js_name = initFromStorytellerScene)]
|
||||
pub fn init_from_storyteller_scene(scene_path: String, options: JsValue) -> Result<(), JsValue> {
|
||||
let options = serde_wasm_bindgen::from_value::<WasmInitOptions>(options)?;
|
||||
|
||||
crate::start(
|
||||
InitParams::FromScene(scene_path),
|
||||
options.mode,
|
||||
Some(Window {
|
||||
resolution: options.viewport_size.into(),
|
||||
title: options.canvas_alt,
|
||||
canvas: Some(options.canvas_selector),
|
||||
..default()
|
||||
}),
|
||||
)
|
||||
.run();
|
||||
|
||||
Ok(())
|
||||
}
|
||||
Reference in New Issue
Block a user