12 #include "plugins/InputPlugin.h"
13 #include "controllers/InputDevice.h"
14 #include "OpenXrContext.h"
20 #define MAX_TRACKER_COUNT 64
22 class OpenXrInputPlugin :
public InputPlugin {
25 OpenXrInputPlugin(std::shared_ptr<OpenXrContext> c);
26 bool isSupported()
const override;
27 const QString getName()
const override {
return "OpenXR"; }
29 bool isHandController()
const override {
return true; }
30 bool configurable()
override {
return true; }
32 QString configurationLayout()
override;
33 void setConfigurationSettings(
const QJsonObject configurationSettings)
override;
34 QJsonObject configurationSettings()
override;
35 void calibrate()
override;
36 bool uncalibrate()
override;
37 bool isHeadController()
const override {
return true; }
39 bool activate()
override;
40 void deactivate()
override;
42 QString getDeviceName()
override {
return _context.get()->_systemName; }
44 void pluginFocusOutEvent()
override { _inputDevice->focusOutEvent(); }
46 void pluginUpdate(
float deltaTime,
const controller::InputCalibrationData& inputCalibrationData)
override;
48 virtual void saveSettings()
const override;
49 virtual void loadSettings()
override;
54 Action(std::shared_ptr<OpenXrContext> c,
const std::string&
id,
const std::string &friendlyName, XrActionType type) {
57 _friendlyName = friendlyName;
61 bool init(XrActionSet actionSet);
62 std::vector<XrActionSuggestedBinding> getBindings();
63 XrActionStateFloat getFloat();
64 XrActionStateVector2f getVector2f();
65 XrActionStateBoolean getBool();
66 XrSpaceLocation getPose();
68 bool applyHaptic(XrDuration duration,
float frequency,
float amplitude);
70 XrAction _action = XR_NULL_HANDLE;
72 bool createPoseSpaces();
73 std::shared_ptr<OpenXrContext> _context;
74 std::string _id, _friendlyName;
76 XrSpace _poseSpace = XR_NULL_HANDLE;
82 std::optional<controller::StandardPoseChannel> pose_channel;
83 XrXDevPropertiesMNDX properties;
85 void guessXDevRoles(std::unordered_map<XrXDevIdMNDX, XDevTracker>& trackers);
87 class InputDevice :
public controller::InputDevice {
89 InputDevice(std::shared_ptr<OpenXrContext> c);
92 controller::Input::NamedVector getAvailableInputs()
const override;
93 QString getDefaultMappingConfig()
const override;
94 void update(
float deltaTime,
const controller::InputCalibrationData& inputCalibrationData)
override;
95 void focusOutEvent()
override;
96 bool triggerHapticPulse(
float strength,
float duration, uint16_t index)
override;
98 void setupControllerFlags();
99 void getHandTrackingInputs(
int index,
const mat4& sensorToAvatar);
101 void updateBodyFromViveTrackers(
const mat4& sensorToAvatar);
102 void updateBodyFromXDevSpaces(
const mat4& sensorToAvatar);
103 void calibratePucks(
const controller::InputCalibrationData& inputCalibrationData);
105 mutable std::recursive_mutex _lock;
106 template <
typename F>
107 void withLock(F&& f) {
108 std::unique_lock<std::recursive_mutex> locker(_lock);
112 friend class OpenXrInputPlugin;
114 uint32_t _trackedControllers = 0;
115 XrActionSet _actionSet;
116 std::map<std::string, std::shared_ptr<Action>> _actions;
117 std::shared_ptr<OpenXrContext> _context;
118 bool _actionsInitialized =
false;
120 std::unordered_map<XrXDevIdMNDX, XDevTracker> _xdev;
121 std::unordered_map<controller::StandardPoseChannel, controller::Pose> _trackerCalibrations;
122 bool _wantsCalibrate =
false;
124 XrHandTrackerEXT _handTracker[2] = {XR_NULL_HANDLE, XR_NULL_HANDLE};
126 bool _hapticsEnabled =
true;
129 bool initBindings(
const std::string& profileName,
const std::map<std::string, std::string>& actionsToBind);
132 bool _registeredWithInputMapper =
false;
133 std::shared_ptr<OpenXrContext> _context;
134 std::shared_ptr<InputDevice> _inputDevice;