diff --git a/components/script/dom/xr.rs b/components/script/dom/xr.rs index a916d7a8267..4f5a90e89c4 100644 --- a/components/script/dom/xr.rs +++ b/components/script/dom/xr.rs @@ -42,6 +42,7 @@ pub struct XR { gamepads: DomRefCell>>, pending_immersive_session: Cell, active_immersive_session: MutNullableDom, + active_inline_sessions: DomRefCell>>, test: MutNullableDom, } @@ -53,6 +54,7 @@ impl XR { gamepads: DomRefCell::new(Vec::new()), pending_immersive_session: Cell::new(false), active_immersive_session: Default::default(), + active_inline_sessions: DomRefCell::new(Vec::new()), test: Default::default(), } } @@ -86,7 +88,9 @@ impl XR { self.active_immersive_session.set(None); } } - // XXXManishearth when we support inline sessions we should remove them too + self.active_inline_sessions + .borrow_mut() + .retain(|sess| Dom::from_ref(&**sess) != Dom::from_ref(session)); } } @@ -163,12 +167,14 @@ impl XRMethods for XR { return promise; } - if self.pending_or_active_session() { - promise.reject_error(Error::InvalidState); - return promise; - } + if mode != XRSessionMode::Inline { + if self.pending_or_active_session() { + promise.reject_error(Error::InvalidState); + return promise; + } - self.set_pending(); + self.set_pending(); + } let promise = Promise::new_in_current_compartment(&self.global(), comp); let mut trusted = Some(TrustedPromise::new(promise.clone())); @@ -193,7 +199,7 @@ impl XRMethods for XR { }; let _ = task_source.queue_with_canceller( task!(request_session: move || { - this.root().session_obtained(message, trusted.root()); + this.root().session_obtained(message, trusted.root(), mode); }), &canceller, ); @@ -211,7 +217,12 @@ impl XRMethods for XR { } impl XR { - fn session_obtained(&self, response: Result, promise: Rc) { + fn session_obtained( + &self, + response: Result, + promise: Rc, + mode: XRSessionMode, + ) { let session = match response { Ok(session) => session, Err(_) => { @@ -220,8 +231,14 @@ impl XR { }, }; - let session = XRSession::new(&self.global(), session); - self.set_active_immersive_session(&session); + let session = XRSession::new(&self.global(), session, mode); + if mode == XRSessionMode::Inline { + self.active_inline_sessions + .borrow_mut() + .push(Dom::from_ref(&*session)); + } else { + self.set_active_immersive_session(&session); + } promise.resolve_native(&session); } diff --git a/components/script/dom/xrsession.rs b/components/script/dom/xrsession.rs index 438705853f6..64f90d38118 100644 --- a/components/script/dom/xrsession.rs +++ b/components/script/dom/xrsession.rs @@ -8,6 +8,7 @@ use crate::dom::bindings::cell::DomRefCell; use crate::dom::bindings::codegen::Bindings::NavigatorBinding::NavigatorBinding::NavigatorMethods; use crate::dom::bindings::codegen::Bindings::WebGLRenderingContextBinding::WebGLRenderingContextMethods; use crate::dom::bindings::codegen::Bindings::WindowBinding::WindowBinding::WindowMethods; +use crate::dom::bindings::codegen::Bindings::XRBinding::XRSessionMode; use crate::dom::bindings::codegen::Bindings::XRReferenceSpaceBinding::XRReferenceSpaceType; use crate::dom::bindings::codegen::Bindings::XRRenderStateBinding::XRRenderStateInit; use crate::dom::bindings::codegen::Bindings::XRRenderStateBinding::XRRenderStateMethods; @@ -56,6 +57,7 @@ pub struct XRSession { eventtarget: EventTarget, base_layer: MutNullableDom, blend_mode: XREnvironmentBlendMode, + mode: XRSessionMode, visibility_state: Cell, viewer_space: MutNullableDom, #[ignore_malloc_size_of = "defined in webxr"] @@ -85,11 +87,13 @@ impl XRSession { session: Session, render_state: &XRRenderState, input_sources: &XRInputSourceArray, + mode: XRSessionMode, ) -> XRSession { XRSession { eventtarget: EventTarget::new_inherited(), base_layer: Default::default(), blend_mode: session.environment_blend_mode().into(), + mode, visibility_state: Cell::new(XRVisibilityState::Visible), viewer_space: Default::default(), session: DomRefCell::new(session), @@ -107,7 +111,7 @@ impl XRSession { } } - pub fn new(global: &GlobalScope, session: Session) -> DomRoot { + pub fn new(global: &GlobalScope, session: Session, mode: XRSessionMode) -> DomRoot { let render_state = XRRenderState::new(global, 0.1, 1000.0, None); let input_sources = XRInputSourceArray::new(global); let ret = reflect_dom_object( @@ -115,6 +119,7 @@ impl XRSession { session, &render_state, &input_sources, + mode, )), global, XRSessionBinding::Wrap,