diff --git a/libraries/input-plugins/src/input-plugins/TouchscreenVirtualPadDevice.cpp b/libraries/input-plugins/src/input-plugins/TouchscreenVirtualPadDevice.cpp index 7f9caf193a..f9a712a70d 100644 --- a/libraries/input-plugins/src/input-plugins/TouchscreenVirtualPadDevice.cpp +++ b/libraries/input-plugins/src/input-plugins/TouchscreenVirtualPadDevice.cpp @@ -224,6 +224,7 @@ void TouchscreenVirtualPadDevice::touchEndEvent(const QTouchEvent* event) { } // touch end here is a big reset -> resets both pads _touchPointCount = 0; + _unusedTouches.clear(); KeyboardMouseDevice::enableTouch(true); debugPoints(event, " END ----------------"); moveTouchEnd(); @@ -231,6 +232,25 @@ void TouchscreenVirtualPadDevice::touchEndEvent(const QTouchEvent* event) { _inputDevice->_axisStateMap.clear(); } +void TouchscreenVirtualPadDevice::processUnusedTouches(std::map unusedTouchesInEvent) { + std::vector touchesToDelete; + for (auto const& touchEntry : _unusedTouches) { + if (!unusedTouchesInEvent.count(touchEntry.first)) { + touchesToDelete.push_back(touchEntry.first); + } + } + for (int touchToDelete : touchesToDelete) { + _unusedTouches.erase(touchToDelete); + } + + for (auto const& touchEntry : unusedTouchesInEvent) { + if (!_unusedTouches.count(touchEntry.first)) { + _unusedTouches[touchEntry.first] = touchEntry.second; + } + } + +} + void TouchscreenVirtualPadDevice::touchUpdateEvent(const QTouchEvent* event) { auto& virtualPadManager = VirtualPad::Manager::instance(); if (!virtualPadManager.isEnabled() && !virtualPadManager.isHidden()) { @@ -249,12 +269,16 @@ void TouchscreenVirtualPadDevice::touchUpdateEvent(const QTouchEvent* event) { bool thisPointConsumed = false; glm::vec2 thisPoint; + int thisPointId; + std::map unusedTouchesInEvent; + for (int i = 0; i < _touchPointCount; ++i) { thisPoint.x = tPoints[i].pos().x(); thisPoint.y = tPoints[i].pos().y(); + thisPointId = tPoints[i].id(); thisPointConsumed = false; - if (!moveTouchFound && _moveHasValidTouch && _moveCurrentTouchId == tPoints[i].id()) { + if (!moveTouchFound && _moveHasValidTouch && _moveCurrentTouchId == thisPointId) { // valid if it's an ongoing touch moveTouchFound = true; moveTouchUpdate(thisPoint); @@ -263,7 +287,7 @@ void TouchscreenVirtualPadDevice::touchUpdateEvent(const QTouchEvent* event) { if (thisPointConsumed) continue; - if (!viewTouchFound && _viewHasValidTouch && _viewCurrentTouchId == tPoints[i].id()) { + if (!viewTouchFound && _viewHasValidTouch && _viewCurrentTouchId == thisPointId) { // valid if it's an ongoing touch viewTouchFound = true; viewTouchUpdate(thisPoint); @@ -272,23 +296,36 @@ void TouchscreenVirtualPadDevice::touchUpdateEvent(const QTouchEvent* event) { if (thisPointConsumed) continue; - if (!moveTouchFound && idxMoveStartingPointCandidate==-1 && moveTouchBeginIsValid(thisPoint)) { + if (!moveTouchFound && idxMoveStartingPointCandidate==-1 && moveTouchBeginIsValid(thisPoint) && + (!_unusedTouches.count(thisPointId) || _unusedTouches[thisPointId] == MOVE )) { idxMoveStartingPointCandidate = i; thisPointConsumed = true; } if (thisPointConsumed) continue; - if (!viewTouchFound && idxViewStartingPointCandidate==-1 && viewTouchBeginIsValid(thisPoint)) { + if (!viewTouchFound && idxViewStartingPointCandidate==-1 && viewTouchBeginIsValid(thisPoint) && + (!_unusedTouches.count(thisPointId) || _unusedTouches[thisPointId] == VIEW )) { idxViewStartingPointCandidate = i; thisPointConsumed = true; } + if (thisPointConsumed) continue; + + if (moveTouchBeginIsValid(thisPoint)) { + unusedTouchesInEvent[thisPointId] = MOVE; + } else if (viewTouchBeginIsValid(thisPoint)) { + unusedTouchesInEvent[thisPointId] = VIEW; + } + } + processUnusedTouches(unusedTouchesInEvent); + if (!moveTouchFound) { if (idxMoveStartingPointCandidate!=-1) { _moveCurrentTouchId = tPoints[idxMoveStartingPointCandidate].id(); + _unusedTouches.erase(_moveCurrentTouchId); moveTouchBegin(thisPoint); } else { moveTouchEnd(); @@ -297,11 +334,13 @@ void TouchscreenVirtualPadDevice::touchUpdateEvent(const QTouchEvent* event) { if (!viewTouchFound) { if (idxViewStartingPointCandidate!=-1) { _viewCurrentTouchId = tPoints[idxViewStartingPointCandidate].id(); + _unusedTouches.erase(_viewCurrentTouchId); viewTouchBegin(thisPoint); } else { viewTouchEnd(); } } + } bool TouchscreenVirtualPadDevice::viewTouchBeginIsValid(glm::vec2 touchPoint) { diff --git a/libraries/input-plugins/src/input-plugins/TouchscreenVirtualPadDevice.h b/libraries/input-plugins/src/input-plugins/TouchscreenVirtualPadDevice.h index 3f94dfef07..c0f37e2e51 100644 --- a/libraries/input-plugins/src/input-plugins/TouchscreenVirtualPadDevice.h +++ b/libraries/input-plugins/src/input-plugins/TouchscreenVirtualPadDevice.h @@ -62,6 +62,12 @@ public: const std::shared_ptr& getInputDevice() const { return _inputDevice; } protected: + + enum TouchType { + MOVE = 1, + VIEW + }; + float _lastPinchScale; float _pinchScale; float _screenDPI; @@ -78,6 +84,8 @@ protected: glm::vec2 _viewCurrentTouchPoint; int _viewCurrentTouchId; + std::map _unusedTouches; + int _touchPointCount; int _screenWidthCenter; std::shared_ptr _inputDevice { std::make_shared() }; @@ -103,6 +111,8 @@ protected: void processInputDeviceForMove(VirtualPad::Manager& virtualPadManager); glm::vec2 clippedPointInCircle(float radius, glm::vec2 origin, glm::vec2 touchPoint); + void processUnusedTouches(std::map unusedTouchesInEvent); + void processInputDeviceForView(); // just for debug private: