diff options
author | bors-servo <lbergstrom+bors@mozilla.com> | 2019-05-30 22:04:22 -0400 |
---|---|---|
committer | GitHub <noreply@github.com> | 2019-05-30 22:04:22 -0400 |
commit | 7c8a4ecead45d576bec3aaba02a13d8f21434eb4 (patch) | |
tree | 30371c01567eadc86858796c438ab3304e3987bc /components/script/dom/fakexrdevicecontroller.rs | |
parent | a5506365d6f1e8a75db7e7fa2f9e0b1ef73972ee (diff) | |
parent | c2d4900c1616cb7acfd21a7ae7a5d1d134c085f9 (diff) | |
download | servo-7c8a4ecead45d576bec3aaba02a13d8f21434eb4.tar.gz servo-7c8a4ecead45d576bec3aaba02a13d8f21434eb4.zip |
Auto merge of #23485 - Manishearth:xrtest, r=asajeffrey
Basic XR Testing support
This adds support for the XRTest and FakeXRDeviceController APIs from https://github.com/immersive-web/webxr-test-api, and plugs them into the `mock` backend of rust-webvr.
Tested with [a modified webxr test page](https://github.com/immersive-web/webxr-test-api)
r? @jdm @asajeffrey
<!-- Reviewable:start -->
---
This change is [<img src="https://reviewable.io/review_button.svg" height="34" align="absmiddle" alt="Reviewable"/>](https://reviewable.io/reviews/servo/servo/23485)
<!-- Reviewable:end -->
Diffstat (limited to 'components/script/dom/fakexrdevicecontroller.rs')
-rw-r--r-- | components/script/dom/fakexrdevicecontroller.rs | 104 |
1 files changed, 104 insertions, 0 deletions
diff --git a/components/script/dom/fakexrdevicecontroller.rs b/components/script/dom/fakexrdevicecontroller.rs new file mode 100644 index 00000000000..3d051283155 --- /dev/null +++ b/components/script/dom/fakexrdevicecontroller.rs @@ -0,0 +1,104 @@ +/* This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at https://mozilla.org/MPL/2.0/. */ + +/* This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at https://mozilla.org/MPL/2.0/. */ + +use crate::dom::bindings::codegen::Bindings::FakeXRDeviceControllerBinding::{ + self, FakeXRDeviceControllerMethods, FakeXRRigidTransform, FakeXRViewInit, +}; +use crate::dom::bindings::codegen::Bindings::XRViewBinding::XREye; +use crate::dom::bindings::error::{Error, Fallible}; +use crate::dom::bindings::reflector::{reflect_dom_object, DomObject, Reflector}; +use crate::dom::bindings::root::DomRoot; +use crate::dom::globalscope::GlobalScope; +use dom_struct::dom_struct; +use webvr_traits::{MockVRControlMsg, WebVREyeParameters, WebVRMsg}; + +#[dom_struct] +pub struct FakeXRDeviceController { + reflector: Reflector, +} + +impl FakeXRDeviceController { + pub fn new_inherited() -> FakeXRDeviceController { + FakeXRDeviceController { + reflector: Reflector::new(), + } + } + + pub fn new(global: &GlobalScope) -> DomRoot<FakeXRDeviceController> { + reflect_dom_object( + Box::new(FakeXRDeviceController::new_inherited()), + global, + FakeXRDeviceControllerBinding::Wrap, + ) + } + + pub fn send_msg(&self, msg: MockVRControlMsg) { + self.global() + .as_window() + .webvr_thread() + .unwrap() + .send(WebVRMsg::MessageMockDisplay(msg)) + .unwrap(); + } +} + +impl FakeXRDeviceControllerMethods for FakeXRDeviceController { + /// https://github.com/immersive-web/webxr-test-api/blob/master/explainer.md + fn SetViews(&self, views: Vec<FakeXRViewInit>) -> Fallible<()> { + if views.len() != 2 { + return Err(Error::NotSupported); + } + + let (left, right) = match (views[0].eye, views[1].eye) { + (XREye::Left, XREye::Right) => (&views[0], &views[1]), + (XREye::Right, XREye::Left) => (&views[1], &views[0]), + _ => return Err(Error::NotSupported), + }; + + if left.projectionMatrix.len() != 16 || + right.projectionMatrix.len() != 16 || + left.viewOffset.position.len() != 4 || + right.viewOffset.position.len() != 4 + { + return Err(Error::Type("Incorrectly sized array".into())); + } + + let mut proj_l = [0.; 16]; + let mut proj_r = [0.; 16]; + let v: Vec<_> = left.projectionMatrix.iter().map(|x| **x).collect(); + proj_l.copy_from_slice(&v); + let v: Vec<_> = right.projectionMatrix.iter().map(|x| **x).collect(); + proj_r.copy_from_slice(&v); + + let mut params_l = WebVREyeParameters::default(); + let mut params_r = WebVREyeParameters::default(); + let v: Vec<_> = left.viewOffset.position.iter().map(|x| **x).collect(); + params_l.offset.copy_from_slice(&v); + let v: Vec<_> = right.viewOffset.position.iter().map(|x| **x).collect(); + params_r.offset.copy_from_slice(&v); + + self.send_msg(MockVRControlMsg::SetProjectionMatrices(proj_l, proj_r)); + self.send_msg(MockVRControlMsg::SetEyeParameters(params_l, params_r)); + Ok(()) + } + + /// https://github.com/immersive-web/webxr-test-api/blob/master/explainer.md + fn SetViewerOrigin(&self, origin: &FakeXRRigidTransform) -> Fallible<()> { + if origin.position.len() != 4 || origin.orientation.len() != 4 { + return Err(Error::Type("Incorrectly sized array".into())); + } + let mut position = [0.; 3]; + let mut orientation = [0.; 4]; + let v: Vec<_> = origin.position.iter().map(|x| **x).collect(); + position.copy_from_slice(&v[0..3]); + let v: Vec<_> = origin.orientation.iter().map(|x| **x).collect(); + orientation.copy_from_slice(&v); + self.send_msg(MockVRControlMsg::SetViewerPose(position, orientation)); + Ok(()) + } +} |