// Copyright (c) 2020 OPEN CASCADE SAS // // This file is part of Open CASCADE Technology software library. // // This library is free software; you can redistribute it and/or modify it under // the terms of the GNU Lesser General Public License version 2.1 as published // by the Free Software Foundation, with special exception defined in the file // OCCT_LGPL_EXCEPTION.txt. Consult the file LICENSE_LGPL_21.txt included in OCCT // distribution for complete text of the license and disclaimer of any warranty. // // Alternatively, this file may be used under the terms of Open CASCADE // commercial license or contractual agreement. #ifndef _Aspect_XRSession_HeaderFile #define _Aspect_XRSession_HeaderFile #include "Aspect_ColorSpace.hxx" #include "Aspect_Eye.hxx" #include "Aspect_FrustumLRBT.hxx" #include "Aspect_GraphicsLibrary.hxx" #include "Aspect_XRActionSet.hxx" #include "Aspect_XRAnalogActionData.hxx" #include "Aspect_XRDigitalActionData.hxx" #include "Aspect_XRGenericAction.hxx" #include "Aspect_XRHapticActionData.hxx" #include "Aspect_XRPoseActionData.hxx" #include "Aspect_XRTrackedDeviceRole.hxx" #include "gp_Trsf.hxx" #include "NCollection_Array1.hxx" class Graphic3d_ArrayOfTriangles; class Image_Texture; //! Extended Reality (XR) Session interface. class Aspect_XRSession : public Standard_Transient { DEFINE_STANDARD_RTTIEXT(Aspect_XRSession, Standard_Transient) public: //! Identifies which style of tracking origin the application wants to use for the poses it is //! requesting. enum TrackingUniverseOrigin { TrackingUniverseOrigin_Seated, //! poses are provided relative to the seated zero pose TrackingUniverseOrigin_Standing, //! poses are provided relative to the safe bounds configured //! by the user }; public: //! Return TRUE if session is opened. virtual bool IsOpen() const = 0; //! Initialize session. virtual bool Open() = 0; //! Release session. virtual void Close() = 0; //! Fetch actual poses of tracked devices. virtual bool WaitPoses() = 0; //! Return recommended viewport Width x Height for rendering into VR. virtual NCollection_Vec2 RecommendedViewport() const = 0; //! Return transformation from eye to head. virtual NCollection_Mat4 EyeToHeadTransform(Aspect_Eye theEye) const = 0; //! Return transformation from head to eye. NCollection_Mat4 HeadToEyeTransform(Aspect_Eye theEye) const { NCollection_Mat4 aMat; EyeToHeadTransform(theEye).Inverted(aMat); return aMat; } //! Return projection matrix. virtual NCollection_Mat4 ProjectionMatrix(Aspect_Eye theEye, double theZNear, double theZFar) const = 0; //! Return FALSE if projection frustums are unsupported and general 4x4 projection matrix should //! be fetched instead virtual bool HasProjectionFrustums() const = 0; //! Receive XR events. virtual void ProcessEvents() = 0; //! Submit texture eye to XR Composer. //! @param[in] theTexture texture handle //! @param[in] theGraphicsLib graphics library in which texture handle is defined //! @param[in] theColorSpace texture color space; //! sRGB means no color conversion by composer; //! Linear means to sRGB color conversion by composer //! @param[in] theEye eye to display //! @return FALSE on error virtual bool SubmitEye(void* theTexture, Aspect_GraphicsLibrary theGraphicsLib, Aspect_ColorSpace theColorSpace, Aspect_Eye theEye) = 0; //! Return unit scale factor defined as scale factor for m (meters); 1.0 by default. double UnitFactor() const { return myUnitFactor; } //! Set unit scale factor. void SetUnitFactor(double theFactor) { myUnitFactor = theFactor; } //! Return aspect ratio. double Aspect() const { return myAspect; } //! Return field of view. double FieldOfView() const { return myFieldOfView; } //! Return Intra-ocular Distance (IOD); also known as Interpupillary Distance (IPD). //! Defined in meters by default (@sa UnitFactor()). double IOD() const { return myIod; } //! Return display frequency or 0 if unknown. float DisplayFrequency() const { return myDispFreq; } //! Return projection frustum. //! @sa HasProjectionFrustums(). const Aspect_FrustumLRBT& ProjectionFrustum(Aspect_Eye theEye) const { return theEye == Aspect_Eye_Right ? myFrustumR : myFrustumL; } //! Return head orientation in right-handed system: //! +y is up //! +x is to the right //! -z is forward //! Distance unit is meters by default (@sa UnitFactor()). const gp_Trsf& HeadPose() const { return myHeadPose; } //! Return left hand orientation. gp_Trsf LeftHandPose() const { const int aDevice = NamedTrackedDevice(Aspect_XRTrackedDeviceRole_LeftHand); return aDevice != -1 ? myTrackedPoses[aDevice].Orientation : gp_Trsf(); } //! Return right hand orientation. gp_Trsf RightHandPose() const { const int aDevice = NamedTrackedDevice(Aspect_XRTrackedDeviceRole_RightHand); return aDevice != -1 ? myTrackedPoses[aDevice].Orientation : gp_Trsf(); } //! Return number of tracked poses array. const NCollection_Array1& TrackedPoses() const { return myTrackedPoses; } //! Return TRUE if device orientation is defined. bool HasTrackedPose(int theDevice) const { return myTrackedPoses[theDevice].IsValidPose; } //! Return index of tracked device of known role, or -1 if undefined. virtual int NamedTrackedDevice(Aspect_XRTrackedDeviceRole theDevice) const = 0; //! Load model for displaying device. //! @param[in] theDevice device index //! @param[out] theTexture texture source //! @return model triangulation or NULL if not found occ::handle LoadRenderModel(int theDevice, occ::handle& theTexture) { return loadRenderModel(theDevice, true, theTexture); } //! Load model for displaying device. //! @param[in] theDevice device index //! @param[in] theToApplyUnitFactor flag to apply unit scale factor //! @param[out] theTexture texture source //! @return model triangulation or NULL if not found occ::handle LoadRenderModel(int theDevice, bool theToApplyUnitFactor, occ::handle& theTexture) { return loadRenderModel(theDevice, theToApplyUnitFactor, theTexture); } //! Fetch data for digital input action (like button). //! @param[in] theAction action of Aspect_XRActionType_InputDigital type virtual Aspect_XRDigitalActionData GetDigitalActionData( const occ::handle& theAction) const = 0; //! Fetch data for digital input action (like axis). //! @param[in] theAction action of Aspect_XRActionType_InputAnalog type virtual Aspect_XRAnalogActionData GetAnalogActionData( const occ::handle& theAction) const = 0; //! Fetch data for pose input action (like fingertip position). //! The returned values will match the values returned by the last call to WaitPoses(). //! @param[in] theAction action of Aspect_XRActionType_InputPose type virtual Aspect_XRPoseActionData GetPoseActionDataForNextFrame( const occ::handle& theAction) const = 0; //! Trigger vibration. Standard_EXPORT void TriggerHapticVibrationAction(const occ::handle& theAction, const Aspect_XRHapticActionData& theParams); //! Abort vibration. Standard_EXPORT void AbortHapticVibrationAction(const occ::handle& theAction); //! Return tracking origin. TrackingUniverseOrigin TrackingOrigin() const { return myTrackOrigin; } //! Set tracking origin. virtual void SetTrackingOrigin(TrackingUniverseOrigin theOrigin) { myTrackOrigin = theOrigin; } //! Return generic action for specific hand or NULL if undefined. const occ::handle& GenericAction(Aspect_XRTrackedDeviceRole theDevice, Aspect_XRGenericAction theAction) const { const NCollection_Array1>& anActions = myRoleActions[theDevice]; return anActions[theAction]; } public: //! Info string enumeration. enum InfoString { InfoString_Vendor, InfoString_Device, InfoString_Tracker, InfoString_SerialNumber, }; //! Query information. virtual TCollection_AsciiString GetString(InfoString theInfo) const = 0; protected: //! Empty constructor. Standard_EXPORT Aspect_XRSession(); //! Load model for displaying device. //! @param[in] theDevice device index //! @param[in] theToApplyUnitFactor flag to apply unit scale factor //! @param[out] theTexture texture source //! @return model triangulation or NULL if not found virtual occ::handle loadRenderModel( int theDevice, bool theToApplyUnitFactor, occ::handle& theTexture) = 0; //! Trigger vibration. virtual void triggerHapticVibrationAction(const occ::handle& theAction, const Aspect_XRHapticActionData& theParams) = 0; protected: NCollection_Array1> // clang-format off myRoleActions[Aspect_XRTrackedDeviceRole_NB]; //!< generic actions NCollection_IndexedDataMap> myActionSets; //!< actions sets TrackingUniverseOrigin myTrackOrigin; //!< tracking origin NCollection_Array1 myTrackedPoses; //!< array of tracked poses gp_Trsf myHeadPose; //!< head orientation NCollection_Vec2 myRendSize; //!< viewport Width x Height for rendering into VR Aspect_FrustumLRBT myFrustumL; //!< left eye projection frustum Aspect_FrustumLRBT myFrustumR; //!< right eye projection frustum double myUnitFactor; //!< unit scale factor defined as scale factor for m (meters) // clang-format on double myAspect; //!< aspect ratio double myFieldOfView; //!< field of view double myIod; //!< intra-ocular distance in meters float myDispFreq; //!< display frequency }; #endif // _Aspect_XRSession_HeaderFile