summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/core/hid/emulated_controller.cpp12
-rw-r--r--src/core/hid/motion_input.cpp14
-rw-r--r--src/core/hid/motion_input.h6
-rw-r--r--src/input_common/drivers/mouse.cpp94
-rw-r--r--src/input_common/drivers/mouse.h5
-rw-r--r--src/input_common/input_mapping.cpp10
6 files changed, 115 insertions, 26 deletions
diff --git a/src/core/hid/emulated_controller.cpp b/src/core/hid/emulated_controller.cpp
index 6d5a3dead..a29c9a6f8 100644
--- a/src/core/hid/emulated_controller.cpp
+++ b/src/core/hid/emulated_controller.cpp
@@ -363,7 +363,17 @@ void EmulatedController::ReloadInput() {
363 SetMotion(callback, index); 363 SetMotion(callback, index);
364 }, 364 },
365 }); 365 });
366 motion_devices[index]->ForceUpdate(); 366
367 // Restore motion state
368 auto& emulated_motion = controller.motion_values[index].emulated;
369 auto& motion = controller.motion_state[index];
370 emulated_motion.ResetRotations();
371 emulated_motion.ResetQuaternion();
372 motion.accel = emulated_motion.GetAcceleration();
373 motion.gyro = emulated_motion.GetGyroscope();
374 motion.rotation = emulated_motion.GetRotations();
375 motion.orientation = emulated_motion.GetOrientation();
376 motion.is_at_rest = !emulated_motion.IsMoving(motion_sensitivity);
367 } 377 }
368 378
369 for (std::size_t index = 0; index < camera_devices.size(); ++index) { 379 for (std::size_t index = 0; index < camera_devices.size(); ++index) {
diff --git a/src/core/hid/motion_input.cpp b/src/core/hid/motion_input.cpp
index eef6edf4b..0dd66c1cc 100644
--- a/src/core/hid/motion_input.cpp
+++ b/src/core/hid/motion_input.cpp
@@ -10,6 +10,8 @@ MotionInput::MotionInput() {
10 // Initialize PID constants with default values 10 // Initialize PID constants with default values
11 SetPID(0.3f, 0.005f, 0.0f); 11 SetPID(0.3f, 0.005f, 0.0f);
12 SetGyroThreshold(ThresholdStandard); 12 SetGyroThreshold(ThresholdStandard);
13 ResetQuaternion();
14 ResetRotations();
13} 15}
14 16
15void MotionInput::SetPID(f32 new_kp, f32 new_ki, f32 new_kd) { 17void MotionInput::SetPID(f32 new_kp, f32 new_ki, f32 new_kd) {
@@ -20,11 +22,19 @@ void MotionInput::SetPID(f32 new_kp, f32 new_ki, f32 new_kd) {
20 22
21void MotionInput::SetAcceleration(const Common::Vec3f& acceleration) { 23void MotionInput::SetAcceleration(const Common::Vec3f& acceleration) {
22 accel = acceleration; 24 accel = acceleration;
25
26 accel.x = std::clamp(accel.x, -AccelMaxValue, AccelMaxValue);
27 accel.y = std::clamp(accel.y, -AccelMaxValue, AccelMaxValue);
28 accel.z = std::clamp(accel.z, -AccelMaxValue, AccelMaxValue);
23} 29}
24 30
25void MotionInput::SetGyroscope(const Common::Vec3f& gyroscope) { 31void MotionInput::SetGyroscope(const Common::Vec3f& gyroscope) {
26 gyro = gyroscope - gyro_bias; 32 gyro = gyroscope - gyro_bias;
27 33
34 gyro.x = std::clamp(gyro.x, -GyroMaxValue, GyroMaxValue);
35 gyro.y = std::clamp(gyro.y, -GyroMaxValue, GyroMaxValue);
36 gyro.z = std::clamp(gyro.z, -GyroMaxValue, GyroMaxValue);
37
28 // Auto adjust drift to minimize drift 38 // Auto adjust drift to minimize drift
29 if (!IsMoving(IsAtRestRelaxed)) { 39 if (!IsMoving(IsAtRestRelaxed)) {
30 gyro_bias = (gyro_bias * 0.9999f) + (gyroscope * 0.0001f); 40 gyro_bias = (gyro_bias * 0.9999f) + (gyroscope * 0.0001f);
@@ -61,6 +71,10 @@ void MotionInput::ResetRotations() {
61 rotations = {}; 71 rotations = {};
62} 72}
63 73
74void MotionInput::ResetQuaternion() {
75 quat = {{0.0f, 0.0f, -1.0f}, 0.0f};
76}
77
64bool MotionInput::IsMoving(f32 sensitivity) const { 78bool MotionInput::IsMoving(f32 sensitivity) const {
65 return gyro.Length() >= sensitivity || accel.Length() <= 0.9f || accel.Length() >= 1.1f; 79 return gyro.Length() >= sensitivity || accel.Length() <= 0.9f || accel.Length() >= 1.1f;
66} 80}
diff --git a/src/core/hid/motion_input.h b/src/core/hid/motion_input.h
index 9180bb9aa..e2c1bbf95 100644
--- a/src/core/hid/motion_input.h
+++ b/src/core/hid/motion_input.h
@@ -20,6 +20,9 @@ public:
20 static constexpr float IsAtRestStandard = 0.01f; 20 static constexpr float IsAtRestStandard = 0.01f;
21 static constexpr float IsAtRestThight = 0.005f; 21 static constexpr float IsAtRestThight = 0.005f;
22 22
23 static constexpr float GyroMaxValue = 5.0f;
24 static constexpr float AccelMaxValue = 7.0f;
25
23 explicit MotionInput(); 26 explicit MotionInput();
24 27
25 MotionInput(const MotionInput&) = default; 28 MotionInput(const MotionInput&) = default;
@@ -40,6 +43,7 @@ public:
40 43
41 void EnableReset(bool reset); 44 void EnableReset(bool reset);
42 void ResetRotations(); 45 void ResetRotations();
46 void ResetQuaternion();
43 47
44 void UpdateRotation(u64 elapsed_time); 48 void UpdateRotation(u64 elapsed_time);
45 void UpdateOrientation(u64 elapsed_time); 49 void UpdateOrientation(u64 elapsed_time);
@@ -69,7 +73,7 @@ private:
69 Common::Vec3f derivative_error; 73 Common::Vec3f derivative_error;
70 74
71 // Quaternion containing the device orientation 75 // Quaternion containing the device orientation
72 Common::Quaternion<f32> quat{{0.0f, 0.0f, -1.0f}, 0.0f}; 76 Common::Quaternion<f32> quat;
73 77
74 // Number of full rotations in each axis 78 // Number of full rotations in each axis
75 Common::Vec3f rotations; 79 Common::Vec3f rotations;
diff --git a/src/input_common/drivers/mouse.cpp b/src/input_common/drivers/mouse.cpp
index da50e0a24..8b7f9aee9 100644
--- a/src/input_common/drivers/mouse.cpp
+++ b/src/input_common/drivers/mouse.cpp
@@ -10,17 +10,25 @@
10#include "input_common/drivers/mouse.h" 10#include "input_common/drivers/mouse.h"
11 11
12namespace InputCommon { 12namespace InputCommon {
13constexpr int update_time = 10;
14constexpr float default_stick_sensitivity = 0.022f;
15constexpr float default_motion_sensitivity = 0.008f;
13constexpr int mouse_axis_x = 0; 16constexpr int mouse_axis_x = 0;
14constexpr int mouse_axis_y = 1; 17constexpr int mouse_axis_y = 1;
15constexpr int wheel_axis_x = 2; 18constexpr int wheel_axis_x = 2;
16constexpr int wheel_axis_y = 3; 19constexpr int wheel_axis_y = 3;
17constexpr int motion_wheel_y = 4;
18constexpr PadIdentifier identifier = { 20constexpr PadIdentifier identifier = {
19 .guid = Common::UUID{}, 21 .guid = Common::UUID{},
20 .port = 0, 22 .port = 0,
21 .pad = 0, 23 .pad = 0,
22}; 24};
23 25
26constexpr PadIdentifier motion_identifier = {
27 .guid = Common::UUID{},
28 .port = 0,
29 .pad = 1,
30};
31
24constexpr PadIdentifier real_mouse_identifier = { 32constexpr PadIdentifier real_mouse_identifier = {
25 .guid = Common::UUID{}, 33 .guid = Common::UUID{},
26 .port = 1, 34 .port = 1,
@@ -37,47 +45,87 @@ Mouse::Mouse(std::string input_engine_) : InputEngine(std::move(input_engine_))
37 PreSetController(identifier); 45 PreSetController(identifier);
38 PreSetController(real_mouse_identifier); 46 PreSetController(real_mouse_identifier);
39 PreSetController(touch_identifier); 47 PreSetController(touch_identifier);
48 PreSetController(motion_identifier);
40 49
41 // Initialize all mouse axis 50 // Initialize all mouse axis
42 PreSetAxis(identifier, mouse_axis_x); 51 PreSetAxis(identifier, mouse_axis_x);
43 PreSetAxis(identifier, mouse_axis_y); 52 PreSetAxis(identifier, mouse_axis_y);
44 PreSetAxis(identifier, wheel_axis_x); 53 PreSetAxis(identifier, wheel_axis_x);
45 PreSetAxis(identifier, wheel_axis_y); 54 PreSetAxis(identifier, wheel_axis_y);
46 PreSetAxis(identifier, motion_wheel_y);
47 PreSetAxis(real_mouse_identifier, mouse_axis_x); 55 PreSetAxis(real_mouse_identifier, mouse_axis_x);
48 PreSetAxis(real_mouse_identifier, mouse_axis_y); 56 PreSetAxis(real_mouse_identifier, mouse_axis_y);
49 PreSetAxis(touch_identifier, mouse_axis_x); 57 PreSetAxis(touch_identifier, mouse_axis_x);
50 PreSetAxis(touch_identifier, mouse_axis_y); 58 PreSetAxis(touch_identifier, mouse_axis_y);
59
60 // Initialize variables
61 mouse_origin = {};
62 last_mouse_position = {};
63 wheel_position = {};
64 last_mouse_change = {};
65 last_motion_change = {};
66
51 update_thread = std::jthread([this](std::stop_token stop_token) { UpdateThread(stop_token); }); 67 update_thread = std::jthread([this](std::stop_token stop_token) { UpdateThread(stop_token); });
52} 68}
53 69
54void Mouse::UpdateThread(std::stop_token stop_token) { 70void Mouse::UpdateThread(std::stop_token stop_token) {
55 Common::SetCurrentThreadName("Mouse"); 71 Common::SetCurrentThreadName("Mouse");
56 constexpr int update_time = 10;
57 while (!stop_token.stop_requested()) {
58 if (Settings::values.mouse_panning) {
59 // Slow movement by 4%
60 last_mouse_change *= 0.96f;
61 const float sensitivity =
62 Settings::values.mouse_panning_sensitivity.GetValue() * 0.022f;
63 SetAxis(identifier, mouse_axis_x, last_mouse_change.x * sensitivity);
64 SetAxis(identifier, mouse_axis_y, -last_mouse_change.y * sensitivity);
65 }
66 72
67 SetAxis(identifier, motion_wheel_y, 0.0f); 73 while (!stop_token.stop_requested()) {
74 UpdateStickInput();
75 UpdateMotionInput();
68 76
69 if (mouse_panning_timout++ > 20) { 77 if (mouse_panning_timeout++ > 20) {
70 StopPanning(); 78 StopPanning();
71 } 79 }
72 std::this_thread::sleep_for(std::chrono::milliseconds(update_time)); 80 std::this_thread::sleep_for(std::chrono::milliseconds(update_time));
73 } 81 }
74} 82}
75 83
84void Mouse::UpdateStickInput() {
85 if (!Settings::values.mouse_panning) {
86 return;
87 }
88
89 const float sensitivity =
90 Settings::values.mouse_panning_sensitivity.GetValue() * default_stick_sensitivity;
91
92 // Slow movement by 4%
93 last_mouse_change *= 0.96f;
94 SetAxis(identifier, mouse_axis_x, last_mouse_change.x * sensitivity);
95 SetAxis(identifier, mouse_axis_y, -last_mouse_change.y * sensitivity);
96}
97
98void Mouse::UpdateMotionInput() {
99 const float sensitivity =
100 Settings::values.mouse_panning_sensitivity.GetValue() * default_motion_sensitivity;
101
102 // Slow movement by 7%
103 if (Settings::values.mouse_panning) {
104 last_motion_change *= 0.93f;
105 } else {
106 last_motion_change.z *= 0.93f;
107 }
108
109 const BasicMotion motion_data{
110 .gyro_x = last_motion_change.x * sensitivity,
111 .gyro_y = last_motion_change.y * sensitivity,
112 .gyro_z = last_motion_change.z * sensitivity,
113 .accel_x = 0,
114 .accel_y = 0,
115 .accel_z = 0,
116 .delta_timestamp = update_time * 1000,
117 };
118
119 SetMotion(motion_identifier, 0, motion_data);
120}
121
76void Mouse::Move(int x, int y, int center_x, int center_y) { 122void Mouse::Move(int x, int y, int center_x, int center_y) {
77 if (Settings::values.mouse_panning) { 123 if (Settings::values.mouse_panning) {
124 mouse_panning_timeout = 0;
125
78 auto mouse_change = 126 auto mouse_change =
79 (Common::MakeVec(x, y) - Common::MakeVec(center_x, center_y)).Cast<float>(); 127 (Common::MakeVec(x, y) - Common::MakeVec(center_x, center_y)).Cast<float>();
80 mouse_panning_timout = 0; 128 Common::Vec3<float> motion_change{-mouse_change.y, -mouse_change.x, last_motion_change.z};
81 129
82 const auto move_distance = mouse_change.Length(); 130 const auto move_distance = mouse_change.Length();
83 if (move_distance == 0) { 131 if (move_distance == 0) {
@@ -93,6 +141,7 @@ void Mouse::Move(int x, int y, int center_x, int center_y) {
93 141
94 // Average mouse movements 142 // Average mouse movements
95 last_mouse_change = (last_mouse_change * 0.91f) + (mouse_change * 0.09f); 143 last_mouse_change = (last_mouse_change * 0.91f) + (mouse_change * 0.09f);
144 last_motion_change = (last_motion_change * 0.69f) + (motion_change * 0.31f);
96 145
97 const auto last_move_distance = last_mouse_change.Length(); 146 const auto last_move_distance = last_mouse_change.Length();
98 147
@@ -116,6 +165,12 @@ void Mouse::Move(int x, int y, int center_x, int center_y) {
116 const float sensitivity = Settings::values.mouse_panning_sensitivity.GetValue() * 0.0012f; 165 const float sensitivity = Settings::values.mouse_panning_sensitivity.GetValue() * 0.0012f;
117 SetAxis(identifier, mouse_axis_x, static_cast<float>(mouse_move.x) * sensitivity); 166 SetAxis(identifier, mouse_axis_x, static_cast<float>(mouse_move.x) * sensitivity);
118 SetAxis(identifier, mouse_axis_y, static_cast<float>(-mouse_move.y) * sensitivity); 167 SetAxis(identifier, mouse_axis_y, static_cast<float>(-mouse_move.y) * sensitivity);
168
169 last_motion_change = {
170 static_cast<float>(-mouse_move.y) / 50.0f,
171 static_cast<float>(-mouse_move.x) / 50.0f,
172 last_motion_change.z,
173 };
119 } 174 }
120} 175}
121 176
@@ -157,15 +212,19 @@ void Mouse::ReleaseButton(MouseButton button) {
157 SetAxis(identifier, mouse_axis_x, 0); 212 SetAxis(identifier, mouse_axis_x, 0);
158 SetAxis(identifier, mouse_axis_y, 0); 213 SetAxis(identifier, mouse_axis_y, 0);
159 } 214 }
215
216 last_motion_change.x = 0;
217 last_motion_change.y = 0;
218
160 button_pressed = false; 219 button_pressed = false;
161} 220}
162 221
163void Mouse::MouseWheelChange(int x, int y) { 222void Mouse::MouseWheelChange(int x, int y) {
164 wheel_position.x += x; 223 wheel_position.x += x;
165 wheel_position.y += y; 224 wheel_position.y += y;
225 last_motion_change.z += static_cast<f32>(y) / 100.0f;
166 SetAxis(identifier, wheel_axis_x, static_cast<f32>(wheel_position.x)); 226 SetAxis(identifier, wheel_axis_x, static_cast<f32>(wheel_position.x));
167 SetAxis(identifier, wheel_axis_y, static_cast<f32>(wheel_position.y)); 227 SetAxis(identifier, wheel_axis_y, static_cast<f32>(wheel_position.y));
168 SetAxis(identifier, motion_wheel_y, static_cast<f32>(y) / 100.0f);
169} 228}
170 229
171void Mouse::ReleaseAllButtons() { 230void Mouse::ReleaseAllButtons() {
@@ -234,6 +293,9 @@ Common::Input::ButtonNames Mouse::GetUIName(const Common::ParamPackage& params)
234 if (params.Has("axis_x") && params.Has("axis_y") && params.Has("axis_z")) { 293 if (params.Has("axis_x") && params.Has("axis_y") && params.Has("axis_z")) {
235 return Common::Input::ButtonNames::Engine; 294 return Common::Input::ButtonNames::Engine;
236 } 295 }
296 if (params.Has("motion")) {
297 return Common::Input::ButtonNames::Engine;
298 }
237 299
238 return Common::Input::ButtonNames::Invalid; 300 return Common::Input::ButtonNames::Invalid;
239} 301}
diff --git a/src/input_common/drivers/mouse.h b/src/input_common/drivers/mouse.h
index f3b65bdd1..b872c7a0f 100644
--- a/src/input_common/drivers/mouse.h
+++ b/src/input_common/drivers/mouse.h
@@ -96,6 +96,8 @@ public:
96 96
97private: 97private:
98 void UpdateThread(std::stop_token stop_token); 98 void UpdateThread(std::stop_token stop_token);
99 void UpdateStickInput();
100 void UpdateMotionInput();
99 void StopPanning(); 101 void StopPanning();
100 102
101 Common::Input::ButtonNames GetUIButtonName(const Common::ParamPackage& params) const; 103 Common::Input::ButtonNames GetUIButtonName(const Common::ParamPackage& params) const;
@@ -103,9 +105,10 @@ private:
103 Common::Vec2<int> mouse_origin; 105 Common::Vec2<int> mouse_origin;
104 Common::Vec2<int> last_mouse_position; 106 Common::Vec2<int> last_mouse_position;
105 Common::Vec2<float> last_mouse_change; 107 Common::Vec2<float> last_mouse_change;
108 Common::Vec3<float> last_motion_change;
106 Common::Vec2<int> wheel_position; 109 Common::Vec2<int> wheel_position;
107 bool button_pressed; 110 bool button_pressed;
108 int mouse_panning_timout{}; 111 int mouse_panning_timeout{};
109 std::jthread update_thread; 112 std::jthread update_thread;
110}; 113};
111 114
diff --git a/src/input_common/input_mapping.cpp b/src/input_common/input_mapping.cpp
index 6990a86b9..2ff480ff9 100644
--- a/src/input_common/input_mapping.cpp
+++ b/src/input_common/input_mapping.cpp
@@ -142,14 +142,10 @@ void MappingFactory::RegisterMotion(const MappingData& data) {
142 new_input.Set("port", static_cast<int>(data.pad.port)); 142 new_input.Set("port", static_cast<int>(data.pad.port));
143 new_input.Set("pad", static_cast<int>(data.pad.pad)); 143 new_input.Set("pad", static_cast<int>(data.pad.pad));
144 144
145 // If engine is mouse map the mouse position as 3 axis motion 145 // If engine is mouse map it automatically to mouse motion
146 if (data.engine == "mouse") { 146 if (data.engine == "mouse") {
147 new_input.Set("axis_x", 1); 147 new_input.Set("motion", 0);
148 new_input.Set("invert_x", "-"); 148 new_input.Set("pad", 1);
149 new_input.Set("axis_y", 0);
150 new_input.Set("axis_z", 4);
151 new_input.Set("range", 1.0f);
152 new_input.Set("deadzone", 0.0f);
153 input_queue.Push(new_input); 149 input_queue.Push(new_input);
154 return; 150 return;
155 } 151 }