diff --git a/gfx/vr/VRManager.cpp b/gfx/vr/VRManager.cpp index 701bd31c8656..7eba9d1e8402 100644 --- a/gfx/vr/VRManager.cpp +++ b/gfx/vr/VRManager.cpp @@ -26,7 +26,6 @@ #endif #if defined(XP_WIN) || defined(XP_MACOSX) || (defined(XP_LINUX) && !defined(MOZ_WIDGET_ANDROID)) #include "gfxVROpenVR.h" -#include "gfxVROSVR.h" #endif #include "gfxVRPuppet.h" @@ -142,12 +141,6 @@ VRManager::VRManager() if (mgr) { mManagers.AppendElement(mgr); } - - // OSVR is cross platform compatible - mgr = VRSystemManagerOSVR::Create(); - if (mgr) { - mManagers.AppendElement(mgr); - } } // !mVRService #endif diff --git a/gfx/vr/gfxVROSVR.h b/gfx/vr/gfxVROSVR.h deleted file mode 100644 index 41e5e7b89c95..000000000000 --- a/gfx/vr/gfxVROSVR.h +++ /dev/null @@ -1,131 +0,0 @@ -/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ -/* vim: set ts=8 sts=2 et sw=2 tw=80: */ -/* 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 http://mozilla.org/MPL/2.0/. */ - -#ifndef GFX_VR_OSVR_H -#define GFX_VR_OSVR_H - -#include "nsTArray.h" -#include "mozilla/RefPtr.h" -#include "nsThreadUtils.h" - -#include "mozilla/gfx/2D.h" -#include "mozilla/EnumeratedArray.h" - -#include "VRDisplayLocal.h" - -#include -#include - -#if defined(XP_MACOSX) -class MacIOSurface; -#endif -namespace mozilla { -namespace gfx { -namespace impl { - -class VRDisplayOSVR : public VRDisplayLocal -{ -public: - void ZeroSensor() override; - -protected: - VRHMDSensorState GetSensorState() override; - virtual void StartPresentation() override; - virtual void StopPresentation() override; - -#if defined(XP_WIN) - virtual bool SubmitFrame(ID3D11Texture2D* aSource, - const IntSize& aSize, - const gfx::Rect& aLeftEyeRect, - const gfx::Rect& aRightEyeRect) override; -#elif defined(XP_MACOSX) - virtual bool SubmitFrame(MacIOSurface* aMacIOSurface, - const IntSize& aSize, - const gfx::Rect& aLeftEyeRect, - const gfx::Rect& aRightEyeRect) override; -#endif - -public: - explicit VRDisplayOSVR(OSVR_ClientContext* context, - OSVR_ClientInterface* iface, - OSVR_DisplayConfig* display); - -protected: - virtual ~VRDisplayOSVR() - { - Destroy(); - MOZ_COUNT_DTOR_INHERITED(VRDisplayOSVR, VRDisplayLocal); - } - void Destroy(); - - OSVR_ClientContext* m_ctx; - OSVR_ClientInterface* m_iface; - OSVR_DisplayConfig* m_display; - - gfx::Matrix4x4 mHeadToEye[2]; -}; - -} // namespace impl - -class VRSystemManagerOSVR : public VRSystemManager -{ -public: - static already_AddRefed Create(); - virtual void Destroy() override; - virtual void Shutdown() override; - virtual void NotifyVSync() override; - virtual void Enumerate() override; - virtual bool ShouldInhibitEnumeration() override; - virtual void GetHMDs(nsTArray>& aHMDResult) override; - virtual bool GetIsPresenting() override; - virtual void HandleInput() override; - virtual void GetControllers(nsTArray>& - aControllerResult) override; - virtual void ScanForControllers() override; - virtual void RemoveControllers() override; - virtual void VibrateHaptic(uint32_t aControllerIdx, uint32_t aHapticIndex, - double aIntensity, double aDuration, - const VRManagerPromise& aPromise) override; - virtual void StopVibrateHaptic(uint32_t aControllerIdx) override; - -protected: - VRSystemManagerOSVR() - : mOSVRInitialized(false) - , mClientContextInitialized(false) - , mDisplayConfigInitialized(false) - , mInterfaceInitialized(false) - , m_ctx(nullptr) - , m_iface(nullptr) - , m_display(nullptr) - { - } - - bool Init(); - - RefPtr mHMDInfo; - bool mOSVRInitialized; - bool mClientContextInitialized; - bool mDisplayConfigInitialized; - bool mInterfaceInitialized; - RefPtr mOSVRThread; - - OSVR_ClientContext m_ctx; - OSVR_ClientInterface m_iface; - OSVR_DisplayConfig m_display; - -private: - // check if all components are initialized - // and if not, it will try to initialize them - void CheckOSVRStatus(); - void InitializeClientContext(); - void InitializeDisplay(); - void InitializeInterface(); -}; - -} // namespace gfx -} // namespace mozilla - -#endif /* GFX_VR_OSVR_H */ diff --git a/gfx/vr/moz.build b/gfx/vr/moz.build index b697fcf2d3bc..e64e6e2f52cc 100644 --- a/gfx/vr/moz.build +++ b/gfx/vr/moz.build @@ -51,11 +51,6 @@ UNIFIED_SOURCES += [ 'VRThread.cpp', ] -if CONFIG['OS_TARGET'] != 'Android': - UNIFIED_SOURCES += [ - 'gfxVROSVR.cpp', - ] - # VRDisplayHost includes MacIOSurface.h which includes Mac headers # which define Size and Points types in the root namespace that # often conflict with our own types. diff --git a/gfx/vr/gfxVROSVR.cpp b/gfx/vr/service/OSVRSession.cpp similarity index 72% rename from gfx/vr/gfxVROSVR.cpp rename to gfx/vr/service/OSVRSession.cpp index 6af82362dd25..9fb70f8f23c0 100644 --- a/gfx/vr/gfxVROSVR.cpp +++ b/gfx/vr/service/OSVRSession.cpp @@ -4,34 +4,25 @@ * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ -#include - +#include "OSVRSession.h" #include "prenv.h" #include "gfxPrefs.h" #include "nsString.h" #include "mozilla/Preferences.h" #include "mozilla/SharedLibrary.h" - #include "mozilla/gfx/Quaternion.h" -#ifdef XP_WIN -#include "../layers/d3d11/CompositorD3D11.h" -#include "../layers/d3d11/TextureD3D11.h" -#endif - -#include "gfxVROSVR.h" - -#include "mozilla/dom/GamepadEventTypes.h" -#include "mozilla/dom/GamepadBinding.h" +#if defined(XP_WIN) +#include +#include "mozilla/gfx/DeviceManagerDx.h" +#endif // defined(XP_WIN) #ifndef M_PI #define M_PI 3.14159265358979323846 #endif -using namespace mozilla::layers; +using namespace mozilla; using namespace mozilla::gfx; -using namespace mozilla::gfx::impl; -using namespace mozilla::dom; namespace { // need to typedef functions that will be used in the code below @@ -208,194 +199,59 @@ SetFromTanRadians(double left, double right, double bottom, double top) return fovInfo; } -VRDisplayOSVR::VRDisplayOSVR(OSVR_ClientContext* context, - OSVR_ClientInterface* iface, - OSVR_DisplayConfig* display) - : VRDisplayLocal(VRDeviceType::OSVR) - , m_ctx(context) - , m_iface(iface) - , m_display(display) +OSVRSession::OSVRSession() + : VRSession() + , mRuntimeLoaded(false) + , mOSVRInitialized(false) + , mClientContextInitialized(false) + , mDisplayConfigInitialized(false) + , mInterfaceInitialized(false) + , m_ctx(nullptr) + , m_iface(nullptr) + , m_display(nullptr) { - MOZ_COUNT_CTOR_INHERITED(VRDisplayOSVR, VRDisplayLocal); - - VRDisplayState& state = mDisplayInfo.mDisplayState; - state.mIsConnected = true; - strncpy(state.mDisplayName, "OSVR HMD", kVRDisplayNameMaxLen); - state.mCapabilityFlags = VRDisplayCapabilityFlags::Cap_None; - state.mCapabilityFlags = - VRDisplayCapabilityFlags::Cap_Orientation | VRDisplayCapabilityFlags::Cap_Position; - - state.mCapabilityFlags |= VRDisplayCapabilityFlags::Cap_External; - state.mCapabilityFlags |= VRDisplayCapabilityFlags::Cap_Present; - - // XXX OSVR display topology allows for more than one viewer - // will assume only one viewer for now (most likely stay that way) - - OSVR_EyeCount numEyes; - osvr_ClientGetNumEyesForViewer(*m_display, 0, &numEyes); - - for (uint8_t eye = 0; eye < numEyes; eye++) { - double left, right, bottom, top; - // XXX for now there is only one surface per eye - osvr_ClientGetViewerEyeSurfaceProjectionClippingPlanes( - *m_display, 0, eye, 0, &left, &right, &bottom, &top); - state.mEyeFOV[eye] = - SetFromTanRadians(-left, right, -bottom, top); - } - - // XXX Assuming there is only one display input for now - // however, it's possible to have more than one (dSight with 2 HDMI inputs) - OSVR_DisplayDimension width, height; - osvr_ClientGetDisplayDimensions(*m_display, 0, &width, &height); - - - for (uint8_t eye = 0; eye < numEyes; eye++) { - - OSVR_ViewportDimension l, b, w, h; - osvr_ClientGetRelativeViewportForViewerEyeSurface(*m_display, 0, eye, 0, &l, - &b, &w, &h); - state.mEyeResolution.width = w; - state.mEyeResolution.height = h; - OSVR_Pose3 eyePose; - // Viewer eye pose may not be immediately available, update client context until we get it - OSVR_ReturnCode ret = - osvr_ClientGetViewerEyePose(*m_display, 0, eye, &eyePose); - while (ret != OSVR_RETURN_SUCCESS) { - osvr_ClientUpdate(*m_ctx); - ret = osvr_ClientGetViewerEyePose(*m_display, 0, eye, &eyePose); - } - state.mEyeTranslation[eye].x = eyePose.translation.data[0]; - state.mEyeTranslation[eye].y = eyePose.translation.data[1]; - state.mEyeTranslation[eye].z = eyePose.translation.data[2]; - - Matrix4x4 pose; - pose.SetRotationFromQuaternion(gfx::Quaternion(osvrQuatGetX(&eyePose.rotation), - osvrQuatGetY(&eyePose.rotation), - osvrQuatGetZ(&eyePose.rotation), - osvrQuatGetW(&eyePose.rotation))); - pose.PreTranslate(eyePose.translation.data[0], eyePose.translation.data[1], eyePose.translation.data[2]); - pose.Invert(); - mHeadToEye[eye] = pose; - } } - -void -VRDisplayOSVR::Destroy() +OSVRSession::~OSVRSession() { - // destroy non-owning pointers - m_ctx = nullptr; - m_iface = nullptr; - m_display = nullptr; + Shutdown(); } -void -VRDisplayOSVR::ZeroSensor() -{ - // recenter pose aka reset yaw - osvr_ClientSetRoomRotationUsingHead(*m_ctx); -} - -VRHMDSensorState -VRDisplayOSVR::GetSensorState() -{ - - //update client context before anything - //this usually goes into app's mainloop - osvr_ClientUpdate(*m_ctx); - - VRHMDSensorState result{}; - OSVR_TimeValue timestamp; - - OSVR_OrientationState orientation; - - OSVR_ReturnCode ret = - osvr_GetOrientationState(*m_iface, ×tamp, &orientation); - - result.timestamp = timestamp.seconds; - result.inputFrameID = mDisplayInfo.mFrameId; - - if (ret == OSVR_RETURN_SUCCESS) { - result.flags |= VRDisplayCapabilityFlags::Cap_Orientation; - result.pose.orientation[0] = orientation.data[1]; - result.pose.orientation[1] = orientation.data[2]; - result.pose.orientation[2] = orientation.data[3]; - result.pose.orientation[3] = orientation.data[0]; - } else { - // default to an identity quaternion - result.pose.orientation[3] = 1.0f; - } - - OSVR_PositionState position; - ret = osvr_GetPositionState(*m_iface, ×tamp, &position); - if (ret == OSVR_RETURN_SUCCESS) { - result.flags |= VRDisplayCapabilityFlags::Cap_Position; - result.pose.position[0] = position.data[0]; - result.pose.position[1] = position.data[1]; - result.pose.position[2] = position.data[2]; - } - - result.CalcViewMatrices(mHeadToEye); - - return result; -} - -#if defined(XP_WIN) - bool -VRDisplayOSVR::SubmitFrame(ID3D11Texture2D* aSource, - const IntSize& aSize, - const gfx::Rect& aLeftEyeRect, - const gfx::Rect& aRightEyeRect) +OSVRSession::Initialize(mozilla::gfx::VRSystemState& aSystemState) { - // XXX Add code to submit frame - return false; -} - -#elif defined(XP_MACOSX) - -bool -VRDisplayOSVR::SubmitFrame(MacIOSurface* aMacIOSurface, - const IntSize& aSize, - const gfx::Rect& aLeftEyeRect, - const gfx::Rect& aRightEyeRect) -{ - // XXX Add code to submit frame - MOZ_ASSERT(mSubmitThread->GetThread() == NS_GetCurrentThread()); - return false; -} - -#endif - -void -VRDisplayOSVR::StartPresentation() -{ - // XXX Add code to start VR Presentation -} - -void -VRDisplayOSVR::StopPresentation() -{ - // XXX Add code to end VR Presentation -} - -already_AddRefed -VRSystemManagerOSVR::Create() -{ - MOZ_ASSERT(NS_IsMainThread()); - if (!gfxPrefs::VREnabled() || !gfxPrefs::VROSVREnabled()) { - return nullptr; + return false; + } + if (mOSVRInitialized) { + return true; } if (!LoadOSVRRuntime()) { - return nullptr; + return false; } - RefPtr manager = new VRSystemManagerOSVR(); - return manager.forget(); + mRuntimeLoaded = true; + // initialize client context + InitializeClientContext(); + // try to initialize interface + InitializeInterface(); + // try to initialize display object + InitializeDisplay(); + // verify all components are initialized + CheckOSVRStatus(); + + if (!mOSVRInitialized) { + return false; + } + + if (!InitState(aSystemState)) { + return false; + } + + return true; } void -VRSystemManagerOSVR::CheckOSVRStatus() +OSVRSession::CheckOSVRStatus() { if (mOSVRInitialized) { return; @@ -419,7 +275,7 @@ VRSystemManagerOSVR::CheckOSVRStatus() } void -VRSystemManagerOSVR::InitializeClientContext() +OSVRSession::InitializeClientContext() { // already initialized if (mClientContextInitialized) { @@ -448,7 +304,7 @@ VRSystemManagerOSVR::InitializeClientContext() } void -VRSystemManagerOSVR::InitializeInterface() +OSVRSession::InitializeInterface() { // already initialized if (mInterfaceInitialized) { @@ -465,7 +321,7 @@ VRSystemManagerOSVR::InitializeInterface() } void -VRSystemManagerOSVR::InitializeDisplay() +OSVRSession::InitializeDisplay() { // display is fully configured if (mDisplayConfigInitialized) { @@ -500,44 +356,86 @@ VRSystemManagerOSVR::InitializeDisplay() } bool -VRSystemManagerOSVR::Init() +OSVRSession::InitState(mozilla::gfx::VRSystemState& aSystemState) { + VRDisplayState& state = aSystemState.displayState; + strncpy(state.mDisplayName, "OSVR HMD", kVRDisplayNameMaxLen); + state.mEightCC = GFX_VR_EIGHTCC('O', 'S', 'V', 'R', ' ', ' ', ' ', ' '); + state.mIsConnected = true; + state.mIsMounted = false; + state.mCapabilityFlags = (VRDisplayCapabilityFlags)((int)VRDisplayCapabilityFlags::Cap_None | + (int)VRDisplayCapabilityFlags::Cap_Orientation | + (int)VRDisplayCapabilityFlags::Cap_Position | + (int)VRDisplayCapabilityFlags::Cap_External | + (int)VRDisplayCapabilityFlags::Cap_Present); + state.mReportsDroppedFrames = false; - // OSVR server should be running in the background - // It would load plugins and take care of detecting HMDs - if (!mOSVRInitialized) { - nsIThread* thread = nullptr; - NS_GetCurrentThread(&thread); - mOSVRThread = already_AddRefed(thread); + // XXX OSVR display topology allows for more than one viewer + // will assume only one viewer for now (most likely stay that way) - // initialize client context - InitializeClientContext(); - // try to initialize interface - InitializeInterface(); - // try to initialize display object - InitializeDisplay(); - // verify all components are initialized - CheckOSVRStatus(); + OSVR_EyeCount numEyes; + osvr_ClientGetNumEyesForViewer(m_display, 0, &numEyes); + + for (uint8_t eye = 0; eye < numEyes; eye++) { + double left, right, bottom, top; + // XXX for now there is only one surface per eye + osvr_ClientGetViewerEyeSurfaceProjectionClippingPlanes( + m_display, 0, eye, 0, &left, &right, &bottom, &top); + state.mEyeFOV[eye] = + SetFromTanRadians(-left, right, -bottom, top); } - return mOSVRInitialized; + // XXX Assuming there is only one display input for now + // however, it's possible to have more than one (dSight with 2 HDMI inputs) + OSVR_DisplayDimension width, height; + osvr_ClientGetDisplayDimensions(m_display, 0, &width, &height); + + for (uint8_t eye = 0; eye < numEyes; eye++) { + + OSVR_ViewportDimension l, b, w, h; + osvr_ClientGetRelativeViewportForViewerEyeSurface(m_display, 0, eye, 0, &l, + &b, &w, &h); + state.mEyeResolution.width = w; + state.mEyeResolution.height = h; + OSVR_Pose3 eyePose; + // Viewer eye pose may not be immediately available, update client context until we get it + OSVR_ReturnCode ret = + osvr_ClientGetViewerEyePose(m_display, 0, eye, &eyePose); + while (ret != OSVR_RETURN_SUCCESS) { + osvr_ClientUpdate(m_ctx); + ret = osvr_ClientGetViewerEyePose(m_display, 0, eye, &eyePose); + } + state.mEyeTranslation[eye].x = eyePose.translation.data[0]; + state.mEyeTranslation[eye].y = eyePose.translation.data[1]; + state.mEyeTranslation[eye].z = eyePose.translation.data[2]; + + Matrix4x4 pose; + pose.SetRotationFromQuaternion(gfx::Quaternion(osvrQuatGetX(&eyePose.rotation), + osvrQuatGetY(&eyePose.rotation), + osvrQuatGetZ(&eyePose.rotation), + osvrQuatGetW(&eyePose.rotation))); + pose.PreTranslate(eyePose.translation.data[0], eyePose.translation.data[1], eyePose.translation.data[2]); + pose.Invert(); + mHeadToEye[eye] = pose; + } + + // default to an identity quaternion + VRHMDSensorState& sensorState = aSystemState.sensorState; + sensorState.flags = (VRDisplayCapabilityFlags)( + (int)VRDisplayCapabilityFlags::Cap_Orientation | + (int)VRDisplayCapabilityFlags::Cap_Position); + sensorState.pose.orientation[3] = 1.0f; // Default to an identity quaternion + + return true; } void -VRSystemManagerOSVR::Destroy() +OSVRSession::Shutdown() { - Shutdown(); -} - -void -VRSystemManagerOSVR::Shutdown() -{ - if (mOSVRInitialized) { - MOZ_ASSERT(NS_GetCurrentThread() == mOSVRThread); - mOSVRThread = nullptr; - mHMDInfo = nullptr; - mOSVRInitialized = false; + if (!mRuntimeLoaded) { + return; } + mOSVRInitialized = false; // client context may not have been initialized if (m_ctx) { osvr_ClientFreeDisplay(m_display); @@ -548,91 +446,98 @@ VRSystemManagerOSVR::Shutdown() } void -VRSystemManagerOSVR::NotifyVSync() +OSVRSession::ProcessEvents(mozilla::gfx::VRSystemState& aSystemState) { - VRSystemManager::NotifyVSync(); - // TODO - Check for device disconnection or other OSVR events } void -VRSystemManagerOSVR::Enumerate() +OSVRSession::StartFrame(mozilla::gfx::VRSystemState& aSystemState) { - // make sure context, interface and display are initialized - CheckOSVRStatus(); + UpdateHeadsetPose(aSystemState); +} - if (!Init()) { - return; +void +OSVRSession::UpdateHeadsetPose(mozilla::gfx::VRSystemState& aState) +{ + // Update client context before anything + // this usually goes into app's mainloop + osvr_ClientUpdate(m_ctx); + + VRHMDSensorState result{}; + OSVR_TimeValue timestamp; + + OSVR_OrientationState orientation; + + OSVR_ReturnCode ret = + osvr_GetOrientationState(m_iface, ×tamp, &orientation); + + aState.sensorState.timestamp = timestamp.seconds; + + if (ret == OSVR_RETURN_SUCCESS) { + result.flags |= VRDisplayCapabilityFlags::Cap_Orientation; + result.pose.orientation[0] = orientation.data[1]; + result.pose.orientation[1] = orientation.data[2]; + result.pose.orientation[2] = orientation.data[3]; + result.pose.orientation[3] = orientation.data[0]; + } else { + // default to an identity quaternion + result.pose.orientation[3] = 1.0f; } - mHMDInfo = new VRDisplayOSVR(&m_ctx, &m_iface, &m_display); + OSVR_PositionState position; + ret = osvr_GetPositionState(m_iface, ×tamp, &position); + if (ret == OSVR_RETURN_SUCCESS) { + result.flags |= VRDisplayCapabilityFlags::Cap_Position; + result.pose.position[0] = position.data[0]; + result.pose.position[1] = position.data[1]; + result.pose.position[2] = position.data[2]; + } + + result.CalcViewMatrices(mHeadToEye); } bool -VRSystemManagerOSVR::ShouldInhibitEnumeration() +OSVRSession::ShouldQuit() const { - if (VRSystemManager::ShouldInhibitEnumeration()) { - return true; - } - if (mHMDInfo) { - // When we find an a VR device, don't - // allow any further enumeration as it - // may get picked up redundantly by other - // API's. - return true; - } return false; } -void -VRSystemManagerOSVR::GetHMDs(nsTArray>& aHMDResult) -{ - if (mHMDInfo) { - aHMDResult.AppendElement(mHMDInfo); - } -} - bool -VRSystemManagerOSVR::GetIsPresenting() +OSVRSession::StartPresentation() { - if (mHMDInfo) { - VRDisplayInfo displayInfo(mHMDInfo->GetDisplayInfo()); - return displayInfo.GetPresentingGroups() != kVRGroupNone; - } - return false; + // TODO Implement } void -VRSystemManagerOSVR::HandleInput() +OSVRSession::StopPresentation() { + // TODO Implement +} + +bool +OSVRSession::SubmitFrame(const mozilla::gfx::VRLayer_Stereo_Immersive& aLayer) +{ + return false; + // TODO Implement } void -VRSystemManagerOSVR::VibrateHaptic(uint32_t aControllerIdx, - uint32_t aHapticIndex, - double aIntensity, - double aDuration, - const VRManagerPromise& aPromise) +OSVRSession::VibrateHaptic(uint32_t aControllerIdx, uint32_t aHapticIndex, + float aIntensity, float aDuration) { + } void -VRSystemManagerOSVR::StopVibrateHaptic(uint32_t aControllerIdx) +OSVRSession::StopVibrateHaptic(uint32_t aControllerIdx) { + } void -VRSystemManagerOSVR::GetControllers(nsTArray>& aControllerResult) +OSVRSession::StopAllHaptics() { -} -void -VRSystemManagerOSVR::ScanForControllers() -{ -} - -void -VRSystemManagerOSVR::RemoveControllers() -{ -} +} \ No newline at end of file diff --git a/gfx/vr/service/OSVRSession.h b/gfx/vr/service/OSVRSession.h new file mode 100644 index 000000000000..990e1877265e --- /dev/null +++ b/gfx/vr/service/OSVRSession.h @@ -0,0 +1,71 @@ +/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ +/* vim: set ts=8 sts=2 et sw=2 tw=80: */ +/* 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 http://mozilla.org/MPL/2.0/. */ + +#ifndef GFX_VR_SERVICE_OSVRSESSION_H +#define GFX_VR_SERVICE_OSVRSESSION_H + +#include "VRSession.h" + +#include "mozilla/gfx/2D.h" +#include "mozilla/TimeStamp.h" +#include "moz_external_vr.h" + +#include +#include + +#if defined(XP_WIN) +#include +#elif defined(XP_MACOSX) +class MacIOSurface; +#endif + +namespace mozilla { +namespace gfx { + +class OSVRSession : public VRSession +{ +public: + OSVRSession(); + virtual ~OSVRSession(); + + bool Initialize(mozilla::gfx::VRSystemState& aSystemState) override; + void Shutdown() override; + void ProcessEvents(mozilla::gfx::VRSystemState& aSystemState) override; + void StartFrame(mozilla::gfx::VRSystemState& aSystemState) override; + bool ShouldQuit() const override; + bool StartPresentation() override; + void StopPresentation() override; + bool SubmitFrame(const mozilla::gfx::VRLayer_Stereo_Immersive& aLayer) override; + void VibrateHaptic(uint32_t aControllerIdx, uint32_t aHapticIndex, + float aIntensity, float aDuration) override; + void StopVibrateHaptic(uint32_t aControllerIdx) override; + void StopAllHaptics() override; + +private: + bool InitState(mozilla::gfx::VRSystemState& aSystemState); + void UpdateHeadsetPose(mozilla::gfx::VRSystemState& aState); + bool mRuntimeLoaded; + bool mOSVRInitialized; + bool mClientContextInitialized; + bool mDisplayConfigInitialized; + bool mInterfaceInitialized; + OSVR_ClientContext m_ctx; + OSVR_ClientInterface m_iface; + OSVR_DisplayConfig m_display; + gfx::Matrix4x4 mHeadToEye[2]; + + // check if all components are initialized + // and if not, it will try to initialize them + void CheckOSVRStatus(); + void InitializeClientContext(); + void InitializeDisplay(); + void InitializeInterface(); +}; + +} // namespace mozilla +} // namespace gfx + +#endif // GFX_VR_SERVICE_OSVRSESSION_H diff --git a/gfx/vr/service/OpenVRSession.cpp b/gfx/vr/service/OpenVRSession.cpp index 45fd0226b422..779af1d0cf8b 100644 --- a/gfx/vr/service/OpenVRSession.cpp +++ b/gfx/vr/service/OpenVRSession.cpp @@ -121,6 +121,9 @@ OpenVRSession::~OpenVRSession() bool OpenVRSession::Initialize(mozilla::gfx::VRSystemState& aSystemState) { + if (!gfxPrefs::VREnabled() || !gfxPrefs::VROpenVREnabled()) { + return false; + } if (mVRSystem != nullptr) { // Already initialized return true; diff --git a/gfx/vr/service/VRService.cpp b/gfx/vr/service/VRService.cpp index 64bf5318650b..cf2e08658ef1 100644 --- a/gfx/vr/service/VRService.cpp +++ b/gfx/vr/service/VRService.cpp @@ -5,11 +5,15 @@ * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ #include "VRService.h" -#include "OpenVRSession.h" #include "gfxPrefs.h" #include "base/thread.h" // for Thread #include // for memcmp +#if defined(XP_WIN) || defined(XP_MACOSX) || (defined(XP_LINUX) && !defined(MOZ_WIDGET_ANDROID)) +#include "OpenVRSession.h" +#include "OSVRSession.h" +#endif + using namespace mozilla; using namespace mozilla::gfx; using namespace std; @@ -208,11 +212,23 @@ VRService::ServiceInitialize() // Try to start a VRSession UniquePtr session; +#if defined(XP_WIN) || defined(XP_MACOSX) || (defined(XP_LINUX) && !defined(MOZ_WIDGET_ANDROID)) // Try OpenVR - session = MakeUnique(); - if (!session->Initialize(mSystemState)) { - session = nullptr; + if (!session) { + session = MakeUnique(); + if (!session->Initialize(mSystemState)) { + session = nullptr; + } } + // Try OSVR + if (!session) { + session = MakeUnique(); + if (!session->Initialize(mSystemState)) { + session = nullptr; + } + } +#endif + if (session) { mSession = std::move(session); // Setting enumerationCompleted to true indicates to the browser diff --git a/gfx/vr/service/moz.build b/gfx/vr/service/moz.build index 04c904ed7cb1..21fc866c7ac9 100644 --- a/gfx/vr/service/moz.build +++ b/gfx/vr/service/moz.build @@ -4,6 +4,12 @@ # License, v. 2.0. If a copy of the MPL was not distributed with this # file, You can obtain one at http://mozilla.org/MPL/2.0/. +# Build OSVR on all platforms except Android +if CONFIG['OS_TARGET'] != 'Android': + UNIFIED_SOURCES += [ + 'OSVRSession.cpp', + ] + # Build OpenVR on Windows, Linux, and macOS desktop targets if CONFIG['OS_TARGET'] in ('WINNT', 'Linux', 'Darwin'): UNIFIED_SOURCES += [ diff --git a/gfx/vr/osvr/ClientKit/ClientKitC.h b/gfx/vr/service/osvr/ClientKit/ClientKitC.h similarity index 100% rename from gfx/vr/osvr/ClientKit/ClientKitC.h rename to gfx/vr/service/osvr/ClientKit/ClientKitC.h diff --git a/gfx/vr/osvr/ClientKit/ContextC.h b/gfx/vr/service/osvr/ClientKit/ContextC.h similarity index 100% rename from gfx/vr/osvr/ClientKit/ContextC.h rename to gfx/vr/service/osvr/ClientKit/ContextC.h diff --git a/gfx/vr/osvr/ClientKit/DisplayC.h b/gfx/vr/service/osvr/ClientKit/DisplayC.h similarity index 100% rename from gfx/vr/osvr/ClientKit/DisplayC.h rename to gfx/vr/service/osvr/ClientKit/DisplayC.h diff --git a/gfx/vr/osvr/ClientKit/Export.h b/gfx/vr/service/osvr/ClientKit/Export.h similarity index 100% rename from gfx/vr/osvr/ClientKit/Export.h rename to gfx/vr/service/osvr/ClientKit/Export.h diff --git a/gfx/vr/osvr/ClientKit/InterfaceC.h b/gfx/vr/service/osvr/ClientKit/InterfaceC.h similarity index 100% rename from gfx/vr/osvr/ClientKit/InterfaceC.h rename to gfx/vr/service/osvr/ClientKit/InterfaceC.h diff --git a/gfx/vr/osvr/ClientKit/InterfaceCallbackC.h b/gfx/vr/service/osvr/ClientKit/InterfaceCallbackC.h similarity index 100% rename from gfx/vr/osvr/ClientKit/InterfaceCallbackC.h rename to gfx/vr/service/osvr/ClientKit/InterfaceCallbackC.h diff --git a/gfx/vr/osvr/ClientKit/InterfaceStateC.h b/gfx/vr/service/osvr/ClientKit/InterfaceStateC.h similarity index 100% rename from gfx/vr/osvr/ClientKit/InterfaceStateC.h rename to gfx/vr/service/osvr/ClientKit/InterfaceStateC.h diff --git a/gfx/vr/osvr/ClientKit/SystemCallbackC.h b/gfx/vr/service/osvr/ClientKit/SystemCallbackC.h similarity index 100% rename from gfx/vr/osvr/ClientKit/SystemCallbackC.h rename to gfx/vr/service/osvr/ClientKit/SystemCallbackC.h diff --git a/gfx/vr/osvr/ClientKit/TransformsC.h b/gfx/vr/service/osvr/ClientKit/TransformsC.h similarity index 100% rename from gfx/vr/osvr/ClientKit/TransformsC.h rename to gfx/vr/service/osvr/ClientKit/TransformsC.h diff --git a/gfx/vr/osvr/Util/APIBaseC.h b/gfx/vr/service/osvr/Util/APIBaseC.h similarity index 100% rename from gfx/vr/osvr/Util/APIBaseC.h rename to gfx/vr/service/osvr/Util/APIBaseC.h diff --git a/gfx/vr/osvr/Util/AnnotationMacrosC.h b/gfx/vr/service/osvr/Util/AnnotationMacrosC.h similarity index 100% rename from gfx/vr/osvr/Util/AnnotationMacrosC.h rename to gfx/vr/service/osvr/Util/AnnotationMacrosC.h diff --git a/gfx/vr/osvr/Util/BoolC.h b/gfx/vr/service/osvr/Util/BoolC.h similarity index 100% rename from gfx/vr/osvr/Util/BoolC.h rename to gfx/vr/service/osvr/Util/BoolC.h diff --git a/gfx/vr/osvr/Util/ChannelCountC.h b/gfx/vr/service/osvr/Util/ChannelCountC.h similarity index 100% rename from gfx/vr/osvr/Util/ChannelCountC.h rename to gfx/vr/service/osvr/Util/ChannelCountC.h diff --git a/gfx/vr/osvr/Util/ClientCallbackTypesC.h b/gfx/vr/service/osvr/Util/ClientCallbackTypesC.h similarity index 100% rename from gfx/vr/osvr/Util/ClientCallbackTypesC.h rename to gfx/vr/service/osvr/Util/ClientCallbackTypesC.h diff --git a/gfx/vr/osvr/Util/ClientOpaqueTypesC.h b/gfx/vr/service/osvr/Util/ClientOpaqueTypesC.h similarity index 100% rename from gfx/vr/osvr/Util/ClientOpaqueTypesC.h rename to gfx/vr/service/osvr/Util/ClientOpaqueTypesC.h diff --git a/gfx/vr/osvr/Util/ClientReportTypesC.h b/gfx/vr/service/osvr/Util/ClientReportTypesC.h similarity index 100% rename from gfx/vr/osvr/Util/ClientReportTypesC.h rename to gfx/vr/service/osvr/Util/ClientReportTypesC.h diff --git a/gfx/vr/osvr/Util/Export.h b/gfx/vr/service/osvr/Util/Export.h similarity index 100% rename from gfx/vr/osvr/Util/Export.h rename to gfx/vr/service/osvr/Util/Export.h diff --git a/gfx/vr/osvr/Util/ImagingReportTypesC.h b/gfx/vr/service/osvr/Util/ImagingReportTypesC.h similarity index 100% rename from gfx/vr/osvr/Util/ImagingReportTypesC.h rename to gfx/vr/service/osvr/Util/ImagingReportTypesC.h diff --git a/gfx/vr/osvr/Util/MatrixConventionsC.h b/gfx/vr/service/osvr/Util/MatrixConventionsC.h similarity index 100% rename from gfx/vr/osvr/Util/MatrixConventionsC.h rename to gfx/vr/service/osvr/Util/MatrixConventionsC.h diff --git a/gfx/vr/osvr/Util/PlatformConfig.h b/gfx/vr/service/osvr/Util/PlatformConfig.h similarity index 100% rename from gfx/vr/osvr/Util/PlatformConfig.h rename to gfx/vr/service/osvr/Util/PlatformConfig.h diff --git a/gfx/vr/osvr/Util/Pose3C.h b/gfx/vr/service/osvr/Util/Pose3C.h similarity index 100% rename from gfx/vr/osvr/Util/Pose3C.h rename to gfx/vr/service/osvr/Util/Pose3C.h diff --git a/gfx/vr/osvr/Util/QuaternionC.h b/gfx/vr/service/osvr/Util/QuaternionC.h similarity index 100% rename from gfx/vr/osvr/Util/QuaternionC.h rename to gfx/vr/service/osvr/Util/QuaternionC.h diff --git a/gfx/vr/osvr/Util/QuatlibInteropC.h b/gfx/vr/service/osvr/Util/QuatlibInteropC.h similarity index 100% rename from gfx/vr/osvr/Util/QuatlibInteropC.h rename to gfx/vr/service/osvr/Util/QuatlibInteropC.h diff --git a/gfx/vr/osvr/Util/RadialDistortionParametersC.h b/gfx/vr/service/osvr/Util/RadialDistortionParametersC.h similarity index 100% rename from gfx/vr/osvr/Util/RadialDistortionParametersC.h rename to gfx/vr/service/osvr/Util/RadialDistortionParametersC.h diff --git a/gfx/vr/osvr/Util/RenderingTypesC.h b/gfx/vr/service/osvr/Util/RenderingTypesC.h similarity index 100% rename from gfx/vr/osvr/Util/RenderingTypesC.h rename to gfx/vr/service/osvr/Util/RenderingTypesC.h diff --git a/gfx/vr/osvr/Util/ReturnCodesC.h b/gfx/vr/service/osvr/Util/ReturnCodesC.h similarity index 100% rename from gfx/vr/osvr/Util/ReturnCodesC.h rename to gfx/vr/service/osvr/Util/ReturnCodesC.h diff --git a/gfx/vr/osvr/Util/StdInt.h b/gfx/vr/service/osvr/Util/StdInt.h similarity index 100% rename from gfx/vr/osvr/Util/StdInt.h rename to gfx/vr/service/osvr/Util/StdInt.h diff --git a/gfx/vr/osvr/Util/TimeValueC.h b/gfx/vr/service/osvr/Util/TimeValueC.h similarity index 100% rename from gfx/vr/osvr/Util/TimeValueC.h rename to gfx/vr/service/osvr/Util/TimeValueC.h diff --git a/gfx/vr/osvr/Util/Vec2C.h b/gfx/vr/service/osvr/Util/Vec2C.h similarity index 100% rename from gfx/vr/osvr/Util/Vec2C.h rename to gfx/vr/service/osvr/Util/Vec2C.h diff --git a/gfx/vr/osvr/Util/Vec3C.h b/gfx/vr/service/osvr/Util/Vec3C.h similarity index 100% rename from gfx/vr/osvr/Util/Vec3C.h rename to gfx/vr/service/osvr/Util/Vec3C.h