Monado OpenXR Runtime
device.hpp
Go to the documentation of this file.
1// Copyright 2023, Shawn Wallace
2// SPDX-License-Identifier: BSL-1.0
3/*!
4 * @file
5 * @brief SteamVR driver device header - inherits xrt_device.
6 * @author Shawn Wallace <yungwallace@live.com>
7 * @ingroup drv_steamvr_lh
8 */
9
10#include <string>
11#include <vector>
12#include <memory>
13#include <unordered_map>
14
15#include <condition_variable>
16#include <mutex>
17
20#include "xrt/xrt_device.h"
21#include "openvr_driver.h"
22
23class Context;
24struct InputClass;
25
27{
28 std::shared_ptr<Context> ctx;
29 vr::ITrackedDeviceServerDriver *driver;
30 const char *serial;
31 const std::string &steam_install;
32
33 // no copies!
34 DeviceBuilder(const DeviceBuilder &) = delete;
36 operator=(const DeviceBuilder &) = delete;
37};
38
39class Device : public xrt_device
40{
41
42public:
43 m_relation_history *relation_hist;
44
45 virtual ~Device();
46
47 xrt_input *
48 get_input_from_name(std::string_view name);
49
50 void
52
53 void
54 update_pose(const vr::DriverPose_t &newPose) const;
55
56 //! Helper to use the @ref m_relation_history member.
57 void
58 get_pose(uint64_t at_timestamp_ns, xrt_space_relation *out_relation);
59
60 void
61 handle_properties(const vr::PropertyWrite_t *batch, uint32_t count);
62
63 //! Maps to @ref xrt_device::get_tracked_pose.
64 virtual void
65 get_tracked_pose(xrt_input_name name, uint64_t at_timestamp_ns, xrt_space_relation *out_relation) = 0;
66
67protected:
68 Device(const DeviceBuilder &builder);
69 std::shared_ptr<Context> ctx;
70 vr::PropertyContainerHandle_t container_handle{0};
71 std::unordered_map<std::string_view, xrt_input *> inputs_map;
72 std::vector<xrt_input> inputs_vec;
73 inline static xrt_pose chaperone = XRT_POSE_IDENTITY;
74 const InputClass *input_class;
75
76 float vsync_to_photon_ns{0.f};
77
78 virtual void
79 handle_property_write(const vr::PropertyWrite_t &prop) = 0;
80
81 void
82 set_input_class(const InputClass *input_class);
83
84private:
85 vr::ITrackedDeviceServerDriver *driver;
86 uint64_t current_frame{0};
87
88 std::mutex frame_mutex;
89
90 void
91 init_chaperone(const std::string &steam_install);
92};
93
94class HmdDevice : public Device
95{
96public:
97 xrt_pose eye[2];
98 float ipd{0.063}; // meters
99 struct Parts
100 {
101 xrt_hmd_parts base;
102 vr::IVRDisplayComponent *display;
103 };
104
105 HmdDevice(const DeviceBuilder &builder);
106
107 void
108 get_tracked_pose(xrt_input_name name, uint64_t at_timestamp_ns, xrt_space_relation *out_relation) override;
109
110 void
111 SetDisplayEyeToHead(uint32_t unWhichDevice,
112 const vr::HmdMatrix34_t &eyeToHeadLeft,
113 const vr::HmdMatrix34_t &eyeToHeadRight);
114
115 void
116 get_view_poses(const xrt_vec3 *default_eye_relation,
117 uint64_t at_timestamp_ns,
118 uint32_t view_count,
119 xrt_space_relation *out_head_relation,
120 xrt_fov *out_fovs,
121 xrt_pose *out_poses);
122
123 bool
124 compute_distortion(uint32_t view, float u, float v, xrt_uv_triplet *out_result);
125
126 void
127 set_hmd_parts(std::unique_ptr<Parts> parts);
128
129 inline float
130 get_ipd() const
131 {
132 return ipd;
133 }
134
135private:
136 std::unique_ptr<Parts> hmd_parts{nullptr};
137
138 void
139 handle_property_write(const vr::PropertyWrite_t &prop) override;
140
141 void
142 set_nominal_frame_interval(uint64_t interval_ns);
143
144 std::condition_variable hmd_parts_cv;
145 std::mutex hmd_parts_mut;
146};
147
149{
150protected:
151 void
152 set_input_class(const InputClass *input_class);
153
154public:
155 ControllerDevice(vr::PropertyContainerHandle_t container_handle, const DeviceBuilder &builder);
156
157 void
159
160 void
161 set_haptic_handle(vr::VRInputComponentHandle_t handle);
162
163 void
164 get_tracked_pose(xrt_input_name name, uint64_t at_timestamp_ns, xrt_space_relation *out_relation) override;
165
167 get_finger_from_name(std::string_view name);
168
169 void
171 uint64_t desired_timestamp_ns,
172 struct xrt_hand_joint_set *out_value,
173 uint64_t *out_timestamp_ns);
174
176 get_xrt_hand();
177
178 void
179 update_hand_tracking(struct xrt_hand_joint_set *out);
180
181private:
182 vr::VRInputComponentHandle_t haptic_handle{0};
183 std::unique_ptr<xrt_output> output{nullptr};
184 bool has_index_hand_tracking{false};
185 std::vector<IndexFingerInput> finger_inputs_vec;
186 std::unordered_map<std::string_view, IndexFingerInput *> finger_inputs_map;
187 uint64_t hand_tracking_timestamp;
188
189 void
190 set_hand_tracking_hand(xrt_input_name name);
191
192 void
193 handle_property_write(const vr::PropertyWrite_t &prop) override;
194};
Definition: context.hpp:57
Definition: device.hpp:149
Definition: device.hpp:40
void get_pose(uint64_t at_timestamp_ns, xrt_space_relation *out_relation)
Helper to use the m_relation_history member.
Definition: device.cpp:429
void update_inputs()
Update any attached inputs.
Definition: device.cpp:397
virtual void get_tracked_pose(xrt_input_name name, uint64_t at_timestamp_ns, xrt_space_relation *out_relation)=0
Maps to xrt_device::get_tracked_pose.
Definition: device.hpp:95
SteamVR driver context - implements xrt_tracking_origin and IVRDriverContext.
xrt_hand
Enumeration for left and right hand.
Definition: xrt_defines.h:1190
xrt_input_name
Every internal input source known to monado with a baked in type.
Definition: xrt_defines.h:1134
xrt_output_name
Name of a output with a baked in type.
Definition: xrt_defines.h:1388
Small utility for keeping track of the history of an xrt_space_relation, ie.
Definition: device.hpp:27
Definition: device.hpp:100
Definition: context.hpp:41
Definition: device.cpp:44
Definition: m_relation_history.cpp:46
A single HMD or input device.
Definition: xrt_device.h:230
void(* set_output)(struct xrt_device *xdev, enum xrt_output_name name, const union xrt_output_value *value)
Set a output value.
Definition: xrt_device.h:365
void(* get_view_poses)(struct xrt_device *xdev, const struct xrt_vec3 *default_eye_relation, uint64_t at_timestamp_ns, uint32_t view_count, struct xrt_space_relation *out_head_relation, struct xrt_fov *out_fovs, struct xrt_pose *out_poses)
Get the per-view pose in relation to the view space.
Definition: xrt_device.h:404
void(* get_tracked_pose)(struct xrt_device *xdev, enum xrt_input_name name, uint64_t at_timestamp_ns, struct xrt_space_relation *out_relation)
Get relationship of a tracked device to the tracking origin space as the base space.
Definition: xrt_device.h:309
enum xrt_device_name name
Enum identifier of the device.
Definition: xrt_device.h:232
bool(* compute_distortion)(struct xrt_device *xdev, uint32_t view, float u, float v, struct xrt_uv_triplet *out_result)
Compute the distortion at a single point.
Definition: xrt_device.h:426
void(* get_hand_tracking)(struct xrt_device *xdev, enum xrt_input_name name, uint64_t desired_timestamp_ns, struct xrt_hand_joint_set *out_value, uint64_t *out_timestamp_ns)
Get relationship of hand joints to the tracking origin space as the base space.
Definition: xrt_device.h:337
Describes a projection matrix fov.
Definition: xrt_defines.h:486
Joint set type used for hand tracking.
Definition: xrt_defines.h:1233
All of the device components that deals with interfacing to a users head.
Definition: xrt_device.h:90
A single named input, that sits on a xrt_device.
Definition: xrt_device.h:161
A pose composed of a position and orientation.
Definition: xrt_defines.h:465
A relation with two spaces, includes velocity and acceleration.
Definition: xrt_defines.h:657
Represents a uv triplet for distortion, basically just three xrt_vec2.
Definition: xrt_defines.h:261
A 3 element vector with single floats.
Definition: xrt_defines.h:271
A union of all output types.
Definition: xrt_defines.h:1463
Header defining an xrt display or controller device.