VTK  9.2.6
vtkOpenXRManager.h
Go to the documentation of this file.
1 /*=========================================================================
2 
3  Program: Visualization Toolkit
4  Module: vtkOpenXRManager.h
5 
6  Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen
7  All rights reserved.
8  See Copyright.txt or http://www.kitware.com/Copyright.htm for details.
9 
10  This software is distributed WITHOUT ANY WARRANTY; without even
11  the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
12  PURPOSE. See the above copyright notice for more information.
13 
14 =========================================================================*/
25 #ifndef vtkOpenXRManager_h
26 #define vtkOpenXRManager_h
27 
28 #include "vtkRenderingOpenXRModule.h" // needed for exports
29 
30 #include "vtkOpenXR.h"
31 #include "vtkSystemIncludes.h"
32 
33 #include <array>
34 #include <memory>
35 #include <string>
36 #include <vector>
37 
39 
40 class VTKRENDERINGOPENXR_EXPORT vtkOpenXRManager
41 {
42 public:
44 
48  {
49  static vtkOpenXRManager UniqueInstance;
50  return UniqueInstance;
51  }
53 
55 
59  bool XrCheckError(const XrResult&, const std::string& message);
61 
63 
67  bool XrCheckWarn(const XrResult&, const std::string& message);
69 
71 
74  void PrintInstanceProperties();
75  void PrintSystemProperties(XrSystemProperties* system_properties);
76  void PrintSupportedViewConfigs();
77  void PrintViewConfigViewInfo(const std::vector<XrViewConfigurationView>&);
78  bool PrintReferenceSpaces();
80 
82 
87  bool Initialize(vtkOpenGLRenderWindow*);
89 
91 
94  void Finalize();
96 
98 
101  std::tuple<uint32_t, uint32_t> GetRecommendedImageRectSize();
103 
107  uint32_t GetViewCount()
108  {
109  return static_cast<uint32_t>(this->RenderResources->ConfigViews.size());
110  }
111 
113 
117  std::string GetOpenXRPropertiesAsString();
119 
121 
127  const XrPosef* GetViewPose(uint32_t eye)
128  {
129  if (eye >= this->GetViewCount())
130  {
131  return nullptr;
132  }
133  return &(this->RenderResources->Views[eye].pose);
134  }
136 
138 
143  const XrFovf* GetProjectionFov(uint32_t eye)
144  {
145  if (eye >= this->GetViewCount())
146  {
147  return nullptr;
148  }
149  return &(this->RenderResources->Views[eye].fov);
150  }
152 
154 
157  bool IsDepthExtensionSupported() { return this->OptionalExtensions.DepthExtensionSupported; }
159 
161 
166  bool GetShouldRenderCurrentFrame() { return this->ShouldRenderCurrentFrame; }
168 
170 
174  bool BeginSession();
176 
178 
181  const XrSession& GetSession() { return this->Session; }
183 
185 
188  const XrInstance& GetXrRuntimeInstance() { return this->Instance; }
190 
192 
196  bool IsSessionRunning() { return this->SessionRunning; }
198 
200 
205  bool WaitAndBeginFrame();
207 
209 
215  bool PrepareRendering(uint32_t eye, GLuint& colorTextureId, GLuint& depthTextureId);
217 
219 
223  void ReleaseSwapchainImage(uint32_t eye);
225 
227 
231  bool EndFrame();
233 
235 
238  bool PollEvent(XrEventDataBuffer& eventData);
240 
242 
245  XrPath GetXrPath(const std::string& path);
247 
248  const std::array<XrPath, 2>& GetSubactionPaths() { return this->SubactionPaths; }
249 
251 
254  bool CreateActionSet(const std::string& actionSetName, const std::string& localizedActionSetName);
256 
258 
262  bool SelectActiveActionSet(unsigned int index);
264 
266 
269  bool AttachSessionActionSets();
271 
273 
277  void DestroyActionSets();
278 
279  struct Action_t;
280 
282 
287  bool CreateOneAction(
288  Action_t& actionT, const std::string& name, const std::string& localizedName);
290 
292 
295  bool SuggestActions(
296  const std::string& profile, std::vector<XrActionSuggestedBinding>& actionSuggestedBindings);
298 
300 
304  bool SyncActions();
306 
308 
315  bool UpdateActionData(Action_t& action_t, const int hand);
317 
323  bool ApplyVibration(const Action_t& actionT, const int hand, const float amplitude = 0.5f,
324  const float duration = 25000000.0f, const float frequency = XR_FREQUENCY_UNSPECIFIED);
325 
327  {
328  Inactive = -1,
329  Left = 0,
330  Right = 1,
331  Head = 2,
332  Generic = 3,
333  NumberOfControllers = 4
334  };
335 
336  struct Action_t
337  {
338  XrAction Action;
339  XrActionType ActionType;
340 
341  union {
342  XrActionStateFloat _float;
343  XrActionStateBoolean _boolean;
344  XrActionStatePose _pose;
345  XrActionStateVector2f _vec2f;
346  } States[ControllerIndex::NumberOfControllers];
347 
348  XrSpace PoseSpaces[ControllerIndex::NumberOfControllers];
349  XrSpaceLocation PoseLocations[ControllerIndex::NumberOfControllers];
350  XrSpaceVelocity PoseVelocities[ControllerIndex::NumberOfControllers];
351  };
352 
353 protected:
354  vtkOpenXRManager() = default;
355  ~vtkOpenXRManager() = default;
356 
358 
363  bool CreateInstance();
364  std::vector<const char*> SelectExtensions();
366 
368 
371  void PrintOptionalExtensions();
373 
375 
378  bool CreateSystem();
380 
382 
386  bool CheckGraphicsRequirements();
388 
390 
396  bool CreateGraphicsBinding(vtkOpenGLRenderWindow* helperWindow);
398 
400 
405  bool CreateSession();
407 
409 
413  bool CreateSwapchains();
415 
417 
421  bool CreateConfigViews();
423 
425 
432  std::tuple<int64_t, int64_t> SelectSwapchainPixelFormats();
433  const std::vector<int64_t>& GetSupportedColorFormats();
434  const std::vector<int64_t>& GetSupportedDepthFormats();
436 
437  struct SwapchainOpenGL_t;
438 
440 
444  SwapchainOpenGL_t CreateSwapchainOpenGL(int64_t format, uint32_t width, uint32_t height,
445  uint32_t sampleCount, XrSwapchainCreateFlags createFlags, XrSwapchainUsageFlags usageFlags);
447 
449 
452  bool CreateReferenceSpace();
454 
455  bool LoadControllerModels();
456 
458 
461  bool CreateOneActionSpace(const XrAction& action, const XrPath& subactionPath,
462  const XrPosef& poseInActionSpace, XrSpace& space);
464 
466 
469  bool CreateSubactionPaths();
471 
473 
477  uint32_t WaitAndAcquireSwapchainImage(const XrSwapchain& swapchainHandle);
479 
480  // Currently VTK only supports HeadMountedDisplay (HMD)
481  constexpr static XrFormFactor FormFactor = XR_FORM_FACTOR_HEAD_MOUNTED_DISPLAY;
482 
483  // Pick the view type to be stereo rather than mono or anything else
484  constexpr static XrViewConfigurationType ViewType = XR_VIEW_CONFIGURATION_TYPE_PRIMARY_STEREO;
485 
486  // PRIMARY_STEREO view configuration always has 2 views
487  constexpr static uint32_t StereoViewCount = 2;
488 
489  // Three available types: VIEW, LOCAL and STAGE. We use LOCAL space which
490  // establishes a world-locked origin, rather than VIEW space, which tracks the
491  // view origin.
492  constexpr static XrReferenceSpaceType ReferenceSpaceType = XR_REFERENCE_SPACE_TYPE_STAGE;
493 
494  // Communication with the runtime happens through this instance
495  XrInstance Instance;
496 
497  // A system is defined by an id and is used to create a session
498  XrSystemId SystemId;
499 
500  XrSession Session;
501  XrSessionState SessionState;
502  XrSpace ReferenceSpace;
503 
504  // At the end of a frame, we must select en environment blend mode
505  // to tell the runtime how we want to blend the image with the user's
506  // view of the physical world. For example, in VR, we will generally
507  // choose XR_ENVIRONMENT_BLEND_MODE_OPAQUE while AR will generally
508  // choose XR_ENVIRONMENT_BLEND_MODE_ADDITIVE or XR_ENVIRONMENT_BLEND_MODE_ALPHA_BLEND
509  XrEnvironmentBlendMode EnvironmentBlendMode;
510 
511  // See vtkXrExtensions.h
513 
514  // Non optional extension
515  bool HasOpenGLExtension = false;
516 
518 
522  struct
523  {
524  bool DepthExtensionSupported{ false };
525  bool ControllerModelExtensionSupported{ false };
526  bool UnboundedRefSpaceSupported{ false };
527  bool SpatialAnchorSupported{ false };
528  bool HandTrackingSupported{ false };
529  } OptionalExtensions;
531 
532  std::shared_ptr<void> GraphicsBinding;
533 
538  {
539  XrSwapchain Swapchain;
540  int64_t Format{ GL_NONE };
541  uint32_t Width{ 0 };
542  uint32_t Height{ 0 };
543  std::vector<XrSwapchainImageOpenGLKHR> Images;
544  };
545 
547 
554  {
555  XrViewState ViewState{ XR_TYPE_VIEW_STATE };
556  // Each physical Display/Eye is described by a view
557  std::vector<XrView> Views;
558  // One configuration view per view : this store
559  std::vector<XrViewConfigurationView> ConfigViews;
560 
561  std::vector<SwapchainOpenGL_t> ColorSwapchains;
562  std::vector<SwapchainOpenGL_t> DepthSwapchains;
563 
564  std::vector<XrCompositionLayerProjectionView> ProjectionLayerViews;
565  std::vector<XrCompositionLayerDepthInfoKHR> DepthInfoViews;
566  };
567  std::unique_ptr<RenderResources_t> RenderResources{};
569 
570  // There is one subaction path for each hand.
571  std::array<XrPath, 2> SubactionPaths;
572 
573  std::vector<XrActionSet> ActionSets;
574  XrActionSet* ActiveActionSet = nullptr;
575 
581 
582  bool SessionRunning = false;
583  // After each WaitAndBeginFrame, the OpenXR runtime may inform us that
584  // the current frame should not be rendered. Store it to avoid a render
585  bool ShouldRenderCurrentFrame = false;
586  // If true, the function UpdateActionData will store
587  // pose velocities for pose actions
588  bool StorePoseVelocities = false;
589 
590 private:
591  vtkOpenXRManager(const vtkOpenXRManager&) = delete;
592  void operator=(const vtkOpenXRManager&) = delete;
593 };
594 
595 #endif
596 // VTK-HeaderTest-Exclude: vtkOpenXRManager.h
OpenGL rendering window.
std::shared_ptr< void > GraphicsBinding
This struct stores all needed information to render the images and send it to the user We can't make ...
XrActionStateVector2f _vec2f
static vtkOpenXRManager & GetInstance()
Return the singleton instance.
Singleton class that holds a collection of utility functions and member variables to communicate with...
XrSessionState SessionState
uint32_t GetViewCount()
Return the number of OpenXR views (typically one per physical display / eye)
const XrInstance & GetXrRuntimeInstance()
Return the instance used to communicate with the runtime.
bool IsDepthExtensionSupported()
Return true if the runtime supports the depth extension.
const XrPosef * GetViewPose(uint32_t eye)
Returns a pointer to the view pose that contains the view orientation and position for the specified ...
bool GetShouldRenderCurrentFrame()
Return true if the current frame should be rendered.
Swapchain structure for OpenGL backend.
XrEnvironmentBlendMode EnvironmentBlendMode
std::vector< SwapchainOpenGL_t > DepthSwapchains
const std::array< XrPath, 2 > & GetSubactionPaths()
bool IsSessionRunning()
Return true if the OpenXR session is currently running, ie.
std::vector< XrSwapchainImageOpenGLKHR > Images
XrTime PredictedDisplayTime
Store the frame predicted display time in WaitAndBeginFrame To get the action data at this time and t...
std::vector< XrActionSet > ActionSets
XrActionStateBoolean _boolean
std::array< XrPath, 2 > SubactionPaths
const XrSession & GetSession()
Return the OpenXR Session.
std::vector< SwapchainOpenGL_t > ColorSwapchains
std::vector< XrViewConfigurationView > ConfigViews
std::vector< XrCompositionLayerDepthInfoKHR > DepthInfoViews
const XrFovf * GetProjectionFov(uint32_t eye)
Returns a pointer to the projection field of view for the specified eye, or nullptr if eye exceeds or...
xr::ExtensionDispatchTable Extensions
std::vector< XrCompositionLayerProjectionView > ProjectionLayerViews