diff --git a/Cargo.toml b/Cargo.toml index e91b065..59fc2ba 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -1,7 +1,7 @@ [package] edition = "2018" name = "stardust-xr-server" -version = "0.9.1" +version = "0.10.0" authors = ["Nova King "] description = "Stardust XR reference display server" license = "GPLv2" @@ -32,7 +32,7 @@ prisma = "0.1.1" slog = "2.7.0" slog-stdlog = "4.1.1" xkbcommon = { version = "0.5.0", default-features = false } -stardust-xr = "0.2.0" +stardust-xr = "0.3.0" stardust-xr-schemas = "0.1.0" stereokit = {default-features = false, features = ["linux-egl"], version = "0.2.0"} wayland-backend = "=0.1.0-beta.9" diff --git a/src/nodes/data.rs b/src/nodes/data.rs index f02d764..5594c4a 100644 --- a/src/nodes/data.rs +++ b/src/nodes/data.rs @@ -1,14 +1,13 @@ use super::fields::Field; -use super::spatial::{get_spatial_parent_flex, parse_pose, Spatial}; +use super::spatial::{get_spatial_parent_flex, parse_transform, Spatial}; use super::{Alias, Node}; use crate::core::client::Client; use crate::core::nodelist::LifeLinkedNodeList; use crate::core::registry::Registry; use anyhow::{anyhow, ensure, Result}; -use glam::{vec3a, Mat4}; +use glam::vec3a; use parking_lot::Mutex; use stardust_xr::flex::flexbuffer_from_vector_arguments; -use stardust_xr::{flex_to_quat, flex_to_vec3}; use std::sync::{Arc, Weak}; static PULSE_SENDER_REGISTRY: Registry = Registry::new(); @@ -249,14 +248,7 @@ pub fn create_pulse_sender_flex( true, ); let parent = get_spatial_parent_flex(&calling_client, flex_vec.idx(1).get_str()?)?; - let transform = Mat4::from_rotation_translation( - flex_to_quat!(flex_vec.idx(3)) - .ok_or_else(|| anyhow!("Rotation not found"))? - .into(), - flex_to_vec3!(flex_vec.idx(2)) - .ok_or_else(|| anyhow!("Position not found"))? - .into(), - ); + let transform = parse_transform(flex_vec.index(2)?, true, true, false)?; let node = node.add_to_scenegraph(); Spatial::add_to(&node, Some(parent), transform)?; PulseSender::add_to(&node)?; @@ -287,7 +279,7 @@ pub fn create_pulse_receiver_flex( true, ); let parent = get_spatial_parent_flex(&calling_client, flex_vec.idx(1).get_str()?)?; - let transform = parse_pose(flex_vec.idx(2), flex_vec.idx(3))?; + let transform = parse_transform(flex_vec.index(2)?, true, true, false)?; let field = calling_client .scenegraph .get_node(flex_vec.idx(4).as_str()) diff --git a/src/nodes/drawable/model.rs b/src/nodes/drawable/model.rs index 2812496..6e4ec40 100644 --- a/src/nodes/drawable/model.rs +++ b/src/nodes/drawable/model.rs @@ -172,8 +172,8 @@ pub fn create(_node: &Node, calling_client: Arc, data: &[u8]) -> Result< true, ); let parent = get_spatial_parent_flex(&calling_client, flex_vec.idx(1).get_str()?)?; - let resource_id = parse_resource_id(flex_vec.idx(2))?; - let transform = parse_transform(flex_vec.index(3)?, flex_vec.index(4)?, flex_vec.index(5)?)?; + let transform = parse_transform(flex_vec.index(2)?, true, true, true)?; + let resource_id = parse_resource_id(flex_vec.idx(3))?; let node = node.add_to_scenegraph(); Spatial::add_to(&node, Some(parent), transform)?; Model::add_to(&node, resource_id)?; diff --git a/src/nodes/fields/box.rs b/src/nodes/fields/box.rs index 6bc9b4c..80ed84e 100644 --- a/src/nodes/fields/box.rs +++ b/src/nodes/fields/box.rs @@ -1,10 +1,10 @@ use super::{Field, FieldTrait, Node}; use crate::core::client::Client; -use crate::nodes::spatial::{get_spatial_parent_flex, Spatial}; +use crate::nodes::spatial::{get_spatial_parent_flex, parse_transform, Spatial}; use anyhow::{anyhow, ensure, Result}; -use glam::{vec3, vec3a, Mat4, Vec3, Vec3A}; +use glam::{vec3, vec3a, Vec3, Vec3A}; use parking_lot::Mutex; -use stardust_xr::{flex_to_quat, flex_to_vec3}; +use stardust_xr::values::parse_vec3; use std::sync::Arc; pub struct BoxField { @@ -38,7 +38,7 @@ impl BoxField { pub fn set_size_flex(node: &Node, _calling_client: Arc, data: &[u8]) -> Result<()> { let root = flexbuffers::Reader::get_root(data)?; - let size = flex_to_vec3!(root).ok_or_else(|| anyhow!("Size is invalid"))?; + let size = parse_vec3(root).ok_or_else(|| anyhow!("Size is invalid"))?; if let Field::Box(box_field) = node.field.get().unwrap().as_ref() { box_field.set_size(size.into()); } @@ -64,17 +64,15 @@ impl FieldTrait for BoxField { pub fn create_box_field_flex(_node: &Node, calling_client: Arc, data: &[u8]) -> Result<()> { let flex_vec = flexbuffers::Reader::get_root(data)?.get_vector()?; - let node = Node::create(&calling_client, "/field", flex_vec.idx(0).get_str()?, true); - let parent = get_spatial_parent_flex(&calling_client, flex_vec.idx(1).get_str()?)?; - let transform = Mat4::from_rotation_translation( - flex_to_quat!(flex_vec.idx(3)) - .ok_or_else(|| anyhow!("Rotation not found"))? - .into(), - flex_to_vec3!(flex_vec.idx(2)) - .ok_or_else(|| anyhow!("Position not found"))? - .into(), + let node = Node::create( + &calling_client, + "/field", + flex_vec.index(0)?.get_str()?, + true, ); - let size = flex_to_vec3!(flex_vec.idx(4)).ok_or_else(|| anyhow!("Size invalid"))?; + let parent = get_spatial_parent_flex(&calling_client, flex_vec.index(1)?.get_str()?)?; + let transform = parse_transform(flex_vec.index(2)?, true, true, false)?; + let size = parse_vec3(flex_vec.idx(4)).ok_or_else(|| anyhow!("Size invalid"))?; let node = node.add_to_scenegraph(); Spatial::add_to(&node, Some(parent), transform)?; BoxField::add_to(&node, size.into())?; diff --git a/src/nodes/fields/cylinder.rs b/src/nodes/fields/cylinder.rs index 0959754..e484cd2 100644 --- a/src/nodes/fields/cylinder.rs +++ b/src/nodes/fields/cylinder.rs @@ -1,10 +1,11 @@ use super::{Field, FieldTrait, Node}; use crate::core::client::Client; -use crate::nodes::spatial::{get_spatial_parent_flex, Spatial}; -use anyhow::{anyhow, ensure, Result}; -use glam::{swizzles::*, vec2, Mat4, Vec3A}; +use crate::nodes::spatial::{get_spatial_parent_flex, parse_transform, Spatial}; +use anyhow::{ensure, Result}; +use glam::{swizzles::*, vec2, Vec3A}; use portable_atomic::AtomicF32; -use stardust_xr::{flex_to_quat, flex_to_vec3}; +use stardust_xr::values::parse_f32; + use std::sync::atomic::Ordering; use std::sync::Arc; @@ -72,20 +73,18 @@ pub fn create_cylinder_field_flex( data: &[u8], ) -> Result<()> { let flex_vec = flexbuffers::Reader::get_root(data)?.get_vector()?; - let node = Node::create(&calling_client, "/field", flex_vec.idx(0).get_str()?, true); - let parent = get_spatial_parent_flex(&calling_client, flex_vec.idx(1).get_str()?)?; - let transform = Mat4::from_rotation_translation( - flex_to_quat!(flex_vec.idx(3)) - .ok_or_else(|| anyhow!("Rotation not found"))? - .into(), - flex_to_vec3!(flex_vec.idx(2)) - .ok_or_else(|| anyhow!("Position not found"))? - .into(), + let node = Node::create( + &calling_client, + "/field", + flex_vec.index(0)?.get_str()?, + true, ); - let length = flex_vec.idx(0).as_f32(); - let radius = flex_vec.idx(1).as_f32(); + let parent = get_spatial_parent_flex(&calling_client, flex_vec.idx(1).get_str()?)?; + let transform = parse_transform(flex_vec.index(2)?, true, true, false)?; + let length = parse_f32(flex_vec.index(3)?).ok_or_else(|| anyhow::anyhow!("Invalid length"))?; + let radius = parse_f32(flex_vec.index(4)?).ok_or_else(|| anyhow::anyhow!("Invalid radius"))?; let node = node.add_to_scenegraph(); Spatial::add_to(&node, Some(parent), transform)?; - CylinderField::add_to(&node, length, radius)?; + CylinderField::add_to(&node, dbg!(length), dbg!(radius))?; Ok(()) } diff --git a/src/nodes/fields/mod.rs b/src/nodes/fields/mod.rs index c4e0e89..ca1eb24 100644 --- a/src/nodes/fields/mod.rs +++ b/src/nodes/fields/mod.rs @@ -12,7 +12,7 @@ use crate::core::client::Client; use anyhow::{anyhow, Result}; use glam::{vec2, vec3a, Vec3, Vec3A}; use stardust_xr::flex::FlexBuffable; -use stardust_xr::flex_to_vec3; +use stardust_xr::values::parse_vec3; use std::ops::Deref; use std::sync::Arc; @@ -78,7 +78,7 @@ fn field_distance_flex(node: &Node, calling_client: Arc, data: &[u8]) -> .get() .ok_or_else(|| anyhow!("Reference space node does not have a spatial"))? .clone(); - let point = flex_to_vec3!(flex_vec.idx(1)).ok_or_else(|| anyhow!("Point is invalid"))?; + let point = parse_vec3(flex_vec.idx(1)).ok_or_else(|| anyhow!("Point is invalid"))?; let distance = node .field @@ -97,7 +97,7 @@ fn field_normal_flex(node: &Node, calling_client: Arc, data: &[u8]) -> R .get() .ok_or_else(|| anyhow!("Reference space node does not have a spatial"))? .clone(); - let point = flex_to_vec3!(flex_vec.idx(1)).ok_or_else(|| anyhow!("Point is invalid"))?; + let point = parse_vec3(flex_vec.idx(1)).ok_or_else(|| anyhow!("Point is invalid"))?; let normal = node.field.get().as_ref().unwrap().normal( reference_space.as_ref(), @@ -120,7 +120,7 @@ fn field_closest_point_flex( .get() .ok_or_else(|| anyhow!("Reference space node does not have a spatial"))? .clone(); - let point = flex_to_vec3!(flex_vec.idx(1)).ok_or_else(|| anyhow!("Point is invalid"))?; + let point = parse_vec3(flex_vec.idx(1)).ok_or_else(|| anyhow!("Point is invalid"))?; let closest_point = node.field diff --git a/src/nodes/fields/sphere.rs b/src/nodes/fields/sphere.rs index 15791e2..48c0d95 100644 --- a/src/nodes/fields/sphere.rs +++ b/src/nodes/fields/sphere.rs @@ -4,7 +4,7 @@ use crate::nodes::spatial::{get_spatial_parent_flex, Spatial}; use anyhow::{anyhow, ensure, Result}; use glam::{Mat4, Vec3A}; use portable_atomic::AtomicF32; -use stardust_xr::flex_to_vec3; +use stardust_xr::values::parse_vec3; use std::sync::atomic::Ordering; use std::sync::Arc; @@ -70,7 +70,7 @@ pub fn create_sphere_field_flex( let node = Node::create(&calling_client, "/field", flex_vec.idx(0).get_str()?, true); let parent = get_spatial_parent_flex(&calling_client, flex_vec.idx(1).get_str()?)?; let transform = Mat4::from_translation( - flex_to_vec3!(flex_vec.idx(2)) + parse_vec3(flex_vec.idx(2)) .ok_or_else(|| anyhow!("Position not found"))? .into(), ); diff --git a/src/nodes/input/mod.rs b/src/nodes/input/mod.rs index f949e00..96c1fcc 100644 --- a/src/nodes/input/mod.rs +++ b/src/nodes/input/mod.rs @@ -5,7 +5,7 @@ use self::hand::Hand; use self::pointer::Pointer; use super::fields::Field; -use super::spatial::{get_spatial_parent_flex, parse_pose, Spatial}; +use super::spatial::{get_spatial_parent_flex, parse_transform, Spatial}; use super::Node; use crate::core::client::Client; use crate::core::eventloop::FRAME; @@ -218,10 +218,10 @@ pub fn create_input_handler_flex( true, ); let parent = get_spatial_parent_flex(&calling_client, flex_vec.idx(1).get_str()?)?; - let transform = parse_pose(flex_vec.idx(2), flex_vec.idx(3))?; + let transform = parse_transform(flex_vec.idx(2), true, true, false)?; let field = calling_client .scenegraph - .get_node(flex_vec.idx(4).as_str()) + .get_node(flex_vec.idx(3).as_str()) .ok_or_else(|| anyhow!("Field not found"))? .field .get() diff --git a/src/nodes/items/mod.rs b/src/nodes/items/mod.rs index 743c739..235781a 100644 --- a/src/nodes/items/mod.rs +++ b/src/nodes/items/mod.rs @@ -3,7 +3,7 @@ mod environment; use self::environment::EnvironmentItem; use super::fields::Field; -use super::spatial::{get_spatial_parent_flex, parse_pose, Spatial}; +use super::spatial::{get_spatial_parent_flex, parse_transform, Spatial}; use super::{Alias, Node}; use crate::core::client::{Client, INTERNAL_CLIENT}; use crate::core::nodelist::LifeLinkedNodeList; @@ -352,10 +352,10 @@ pub fn create_environment_item_flex( true, ); let space = get_spatial_parent_flex(&calling_client, flex_vec.idx(1).get_str()?)?; - let transform = parse_pose(flex_vec.idx(2), flex_vec.idx(3))?; + let transform = parse_transform(flex_vec.idx(2), true, true, false)?; let node = node.add_to_scenegraph(); Spatial::add_to(&node, None, transform * space.global_transform())?; - EnvironmentItem::add_to(&node, flex_vec.idx(4).get_str()?.to_string()); + EnvironmentItem::add_to(&node, flex_vec.idx(3).get_str()?.to_string()); node.item .get() .unwrap() @@ -372,10 +372,10 @@ pub fn create_item_acceptor_flex( let flex_vec = root.get_vector()?; let parent_name = format!("/item/{}/acceptor/", ITEM_TYPE_INFO_ENVIRONMENT.type_name); let space = get_spatial_parent_flex(&calling_client, flex_vec.idx(1).get_str()?)?; - let transform = parse_pose(flex_vec.idx(2), flex_vec.idx(3))?; + let transform = parse_transform(flex_vec.idx(2), true, true, false)?; let field = calling_client .scenegraph - .get_node(flex_vec.idx(4).get_str()?) + .get_node(flex_vec.idx(3).get_str()?) .ok_or_else(|| anyhow!("Field node not found"))?; let field = field .field diff --git a/src/nodes/spatial.rs b/src/nodes/spatial.rs index 43830f8..e9ff467 100644 --- a/src/nodes/spatial.rs +++ b/src/nodes/spatial.rs @@ -2,10 +2,11 @@ use super::Node; use crate::core::client::Client; use anyhow::{anyhow, ensure, Result}; use glam::{Mat4, Quat, Vec3}; +use mint::Vector3; use parking_lot::Mutex; use stardust_xr::flex::flexbuffer_from_vector_arguments; use stardust_xr::push_to_vec; -use stardust_xr::{flex_to_quat, flex_to_vec3}; +use stardust_xr::values::{parse_quat, parse_vec3}; use std::ptr; use std::sync::{Arc, Weak}; @@ -205,9 +206,9 @@ impl Spatial { }; node.spatial.get().unwrap().set_local_transform_components( reference_space_transform.as_deref(), - flex_to_vec3!(flex_vec.idx(1)).map(|v| v.into()), - flex_to_quat!(flex_vec.idx(2)).map(|v| v.into()), - flex_to_vec3!(flex_vec.idx(3)).map(|v| v.into()), + parse_vec3(flex_vec.idx(1)).map(|v| v.into()), + parse_quat(flex_vec.idx(2)).map(|v| v.into()), + parse_vec3(flex_vec.idx(3)).map(|v| v.into()), ); Ok(()) } @@ -266,34 +267,30 @@ pub fn get_spatial_parent_flex( .ok_or_else(|| anyhow!("Spatial parent node is not a spatial"))? .clone()) } -pub fn parse_pose( - translation: flexbuffers::Reader, - rotation: flexbuffers::Reader, -) -> Result { - Ok(Mat4::from_rotation_translation( - flex_to_quat!(rotation) - .ok_or_else(|| anyhow!("Rotation not found"))? - .into(), - flex_to_vec3!(translation) - .ok_or_else(|| anyhow!("Position not found"))? - .into(), - )) -} pub fn parse_transform( - translation: flexbuffers::Reader, - rotation: flexbuffers::Reader, - scale: flexbuffers::Reader, + reader: flexbuffers::Reader, + translation: bool, + rotation: bool, + scale: bool, ) -> Result { + let transform_vec = reader.get_vector()?; + let translation = translation + .then(|| parse_vec3(transform_vec.idx(0))) + .flatten() + .unwrap_or(Vector3::from([0.0; 3])); + let rotation = rotation + .then(|| parse_quat(transform_vec.idx(1))) + .flatten() + .unwrap_or(Quat::IDENTITY.into()); + let scale = scale + .then(|| parse_vec3(transform_vec.idx(2))) + .flatten() + .unwrap_or(Vector3::from([1.0; 3])); + Ok(Mat4::from_scale_rotation_translation( - flex_to_vec3!(scale) - .ok_or_else(|| anyhow!("Scale not found"))? - .into(), - flex_to_quat!(rotation) - .ok_or_else(|| anyhow!("Rotation not found"))? - .into(), - flex_to_vec3!(translation) - .ok_or_else(|| anyhow!("Position not found"))? - .into(), + scale.into(), + rotation.into(), + translation.into(), )) } @@ -312,7 +309,7 @@ pub fn create_spatial_flex(_node: &Node, calling_client: Arc, data: &[u8 true, ); let parent = get_spatial_parent_flex(&calling_client, flex_vec.index(1)?.get_str()?)?; - let transform = parse_transform(flex_vec.index(2)?, flex_vec.index(3)?, flex_vec.index(4)?)?; + let transform = parse_transform(flex_vec.index(2)?, true, true, true)?; let node = node.add_to_scenegraph(); Spatial::add_to(&node, Some(parent), transform)?; Ok(()) diff --git a/src/wayland/panel_item.rs b/src/wayland/panel_item.rs index c68964b..b0b54dd 100644 --- a/src/wayland/panel_item.rs +++ b/src/wayland/panel_item.rs @@ -24,7 +24,7 @@ use smithay::{ }; use stardust_xr::{ flex::{flexbuffer_from_arguments, flexbuffer_from_vector_arguments}, - flex_to_vec2, + values::parse_vec2, }; use std::sync::{Arc, Weak}; use xkbcommon::xkb::{self, ffi::XKB_KEYMAP_FORMAT_TEXT_V1, Keymap}; @@ -328,11 +328,11 @@ impl PanelItem { pointer.axis_stop(0, Axis::VerticalScroll); } else { let flex_vec = flex.get_vector()?; - let axis_continuous_vec = flex_to_vec2!(flex_vec.idx(0)) + let axis_continuous_vec = parse_vec2(flex_vec.idx(0)) .ok_or_else(|| anyhow!("No continuous axis vector!"))?; pointer.axis(0, Axis::HorizontalScroll, axis_continuous_vec.x as f64); pointer.axis(0, Axis::VerticalScroll, axis_continuous_vec.y as f64); - if let Some(axis_discrete_vec) = flex_to_vec2!(flex_vec.idx(0)) { + if let Some(axis_discrete_vec) = parse_vec2(flex_vec.idx(0)) { pointer.axis_discrete( Axis::HorizontalScroll, axis_discrete_vec.x as i32,