summaryrefslogtreecommitdiffstats
path: root/src/input_common
diff options
context:
space:
mode:
Diffstat (limited to 'src/input_common')
-rw-r--r--src/input_common/drivers/touch_screen.cpp89
-rw-r--r--src/input_common/drivers/touch_screen.h52
2 files changed, 110 insertions, 31 deletions
diff --git a/src/input_common/drivers/touch_screen.cpp b/src/input_common/drivers/touch_screen.cpp
index 8acbe4584..1753e0893 100644
--- a/src/input_common/drivers/touch_screen.cpp
+++ b/src/input_common/drivers/touch_screen.cpp
@@ -14,38 +14,93 @@ constexpr PadIdentifier identifier = {
TouchScreen::TouchScreen(std::string input_engine_) : InputEngine(std::move(input_engine_)) {
PreSetController(identifier);
+ ReleaseAllTouch();
}
-void TouchScreen::TouchMoved(float x, float y, std::size_t finger) {
- if (finger >= 16) {
+void TouchScreen::TouchMoved(float x, float y, std::size_t finger_id) {
+ const auto index = GetIndexFromFingerId(finger_id);
+ if (!index) {
+ // Touch doesn't exist handle it as a new one
+ TouchPressed(x, y, finger_id);
return;
}
- TouchPressed(x, y, finger);
+ const auto i = index.value();
+ fingers[i].is_active = true;
+ SetButton(identifier, static_cast<int>(i), true);
+ SetAxis(identifier, static_cast<int>(i * 2), x);
+ SetAxis(identifier, static_cast<int>(i * 2 + 1), y);
}
-void TouchScreen::TouchPressed(float x, float y, std::size_t finger) {
- if (finger >= 16) {
+void TouchScreen::TouchPressed(float x, float y, std::size_t finger_id) {
+ if (GetIndexFromFingerId(finger_id)) {
+ // Touch already exist. Just update the data
+ TouchMoved(x, y, finger_id);
return;
}
- SetButton(identifier, static_cast<int>(finger), true);
- SetAxis(identifier, static_cast<int>(finger * 2), x);
- SetAxis(identifier, static_cast<int>(finger * 2 + 1), y);
+ const auto index = GetNextFreeIndex();
+ if (!index) {
+ // No free entries. Ignore input
+ return;
+ }
+ const auto i = index.value();
+ fingers[i].is_enabled = true;
+ fingers[i].finger_id = finger_id;
+ TouchMoved(x, y, finger_id);
}
-void TouchScreen::TouchReleased(std::size_t finger) {
- if (finger >= 16) {
+void TouchScreen::TouchReleased(std::size_t finger_id) {
+ const auto index = GetIndexFromFingerId(finger_id);
+ if (!index) {
return;
}
- SetButton(identifier, static_cast<int>(finger), false);
- SetAxis(identifier, static_cast<int>(finger * 2), 0.0f);
- SetAxis(identifier, static_cast<int>(finger * 2 + 1), 0.0f);
+ const auto i = index.value();
+ fingers[i].is_enabled = false;
+ SetButton(identifier, static_cast<int>(i), false);
+ SetAxis(identifier, static_cast<int>(i * 2), 0.0f);
+ SetAxis(identifier, static_cast<int>(i * 2 + 1), 0.0f);
+}
+
+std::optional<std::size_t> TouchScreen::GetIndexFromFingerId(std::size_t finger_id) const {
+ for (std::size_t index = 0; index < MAX_FINGER_COUNT; ++index) {
+ const auto& finger = fingers[index];
+ if (!finger.is_enabled) {
+ continue;
+ }
+ if (finger.finger_id == finger_id) {
+ return index;
+ }
+ }
+ return std::nullopt;
+}
+
+std::optional<std::size_t> TouchScreen::GetNextFreeIndex() const {
+ for (std::size_t index = 0; index < MAX_FINGER_COUNT; ++index) {
+ if (!fingers[index].is_enabled) {
+ return index;
+ }
+ }
+ return std::nullopt;
+}
+
+void TouchScreen::ClearActiveFlag() {
+ for (auto& finger : fingers) {
+ finger.is_active = false;
+ }
+}
+
+void TouchScreen::ReleaseInactiveTouch() {
+ for (const auto& finger : fingers) {
+ if (!finger.is_active) {
+ TouchReleased(finger.finger_id);
+ }
+ }
}
void TouchScreen::ReleaseAllTouch() {
- for (int index = 0; index < 16; ++index) {
- SetButton(identifier, index, false);
- SetAxis(identifier, index * 2, 0.0f);
- SetAxis(identifier, index * 2 + 1, 0.0f);
+ for (const auto& finger : fingers) {
+ if (finger.is_enabled) {
+ TouchReleased(finger.finger_id);
+ }
}
}
diff --git a/src/input_common/drivers/touch_screen.h b/src/input_common/drivers/touch_screen.h
index 193478ead..f46036ffd 100644
--- a/src/input_common/drivers/touch_screen.h
+++ b/src/input_common/drivers/touch_screen.h
@@ -3,41 +3,65 @@
#pragma once
+#include <optional>
+
#include "input_common/input_engine.h"
namespace InputCommon {
/**
- * A button device factory representing a keyboard. It receives keyboard events and forward them
- * to all button devices it created.
+ * A touch device factory representing a touch screen. It receives touch events and forward them
+ * to all touch devices it created.
*/
class TouchScreen final : public InputEngine {
public:
explicit TouchScreen(std::string input_engine_);
/**
- * Signals that mouse has moved.
- * @param x the x-coordinate of the cursor
- * @param y the y-coordinate of the cursor
- * @param center_x the x-coordinate of the middle of the screen
- * @param center_y the y-coordinate of the middle of the screen
+ * Signals that touch has moved and marks this touch point as active
+ * @param x new horizontal position
+ * @param y new vertical position
+ * @param finger_id of the touch point to be updated
*/
- void TouchMoved(float x, float y, std::size_t finger);
+ void TouchMoved(float x, float y, std::size_t finger_id);
/**
- * Sets the status of all buttons bound with the key to pressed
- * @param key_code the code of the key to press
+ * Signals and creates a new touch point with this finger id
+ * @param x starting horizontal position
+ * @param y starting vertical position
+ * @param finger_id to be assigned to the new touch point
*/
- void TouchPressed(float x, float y, std::size_t finger);
+ void TouchPressed(float x, float y, std::size_t finger_id);
/**
- * Sets the status of all buttons bound with the key to released
- * @param key_code the code of the key to release
+ * Signals and resets the touch point related to the this finger id
+ * @param finger_id to be released
*/
- void TouchReleased(std::size_t finger);
+ void TouchReleased(std::size_t finger_id);
+
+ /// Resets the active flag for each touch point
+ void ClearActiveFlag();
+
+ /// Releases all touch that haven't been marked as active
+ void ReleaseInactiveTouch();
/// Resets all inputs to their initial value
void ReleaseAllTouch();
+
+private:
+ static constexpr std::size_t MAX_FINGER_COUNT = 16;
+
+ struct TouchStatus {
+ std::size_t finger_id{};
+ bool is_enabled{};
+ bool is_active{};
+ };
+
+ std::optional<std::size_t> GetIndexFromFingerId(std::size_t finger_id) const;
+
+ std::optional<std::size_t> GetNextFreeIndex() const;
+
+ std::array<TouchStatus, MAX_FINGER_COUNT> fingers{};
};
} // namespace InputCommon