Android joystick - Enforce validity of touches to the ones that start in their area of activation (Movement only from joystick area, View only from outside joystick area).

This commit is contained in:
Cristian Luis Duarte 2018-03-13 12:52:26 -03:00
parent 9e429e9f03
commit b8c0f4d686
2 changed files with 53 additions and 4 deletions

View file

@ -224,6 +224,7 @@ void TouchscreenVirtualPadDevice::touchEndEvent(const QTouchEvent* event) {
} }
// touch end here is a big reset -> resets both pads // touch end here is a big reset -> resets both pads
_touchPointCount = 0; _touchPointCount = 0;
_unusedTouches.clear();
KeyboardMouseDevice::enableTouch(true); KeyboardMouseDevice::enableTouch(true);
debugPoints(event, " END ----------------"); debugPoints(event, " END ----------------");
moveTouchEnd(); moveTouchEnd();
@ -231,6 +232,25 @@ void TouchscreenVirtualPadDevice::touchEndEvent(const QTouchEvent* event) {
_inputDevice->_axisStateMap.clear(); _inputDevice->_axisStateMap.clear();
} }
void TouchscreenVirtualPadDevice::processUnusedTouches(std::map<int, TouchType> unusedTouchesInEvent) {
std::vector<int> 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) { void TouchscreenVirtualPadDevice::touchUpdateEvent(const QTouchEvent* event) {
auto& virtualPadManager = VirtualPad::Manager::instance(); auto& virtualPadManager = VirtualPad::Manager::instance();
if (!virtualPadManager.isEnabled() && !virtualPadManager.isHidden()) { if (!virtualPadManager.isEnabled() && !virtualPadManager.isHidden()) {
@ -249,12 +269,16 @@ void TouchscreenVirtualPadDevice::touchUpdateEvent(const QTouchEvent* event) {
bool thisPointConsumed = false; bool thisPointConsumed = false;
glm::vec2 thisPoint; glm::vec2 thisPoint;
int thisPointId;
std::map<int, TouchType> unusedTouchesInEvent;
for (int i = 0; i < _touchPointCount; ++i) { for (int i = 0; i < _touchPointCount; ++i) {
thisPoint.x = tPoints[i].pos().x(); thisPoint.x = tPoints[i].pos().x();
thisPoint.y = tPoints[i].pos().y(); thisPoint.y = tPoints[i].pos().y();
thisPointId = tPoints[i].id();
thisPointConsumed = false; thisPointConsumed = false;
if (!moveTouchFound && _moveHasValidTouch && _moveCurrentTouchId == tPoints[i].id()) { if (!moveTouchFound && _moveHasValidTouch && _moveCurrentTouchId == thisPointId) {
// valid if it's an ongoing touch // valid if it's an ongoing touch
moveTouchFound = true; moveTouchFound = true;
moveTouchUpdate(thisPoint); moveTouchUpdate(thisPoint);
@ -263,7 +287,7 @@ void TouchscreenVirtualPadDevice::touchUpdateEvent(const QTouchEvent* event) {
if (thisPointConsumed) continue; if (thisPointConsumed) continue;
if (!viewTouchFound && _viewHasValidTouch && _viewCurrentTouchId == tPoints[i].id()) { if (!viewTouchFound && _viewHasValidTouch && _viewCurrentTouchId == thisPointId) {
// valid if it's an ongoing touch // valid if it's an ongoing touch
viewTouchFound = true; viewTouchFound = true;
viewTouchUpdate(thisPoint); viewTouchUpdate(thisPoint);
@ -272,23 +296,36 @@ void TouchscreenVirtualPadDevice::touchUpdateEvent(const QTouchEvent* event) {
if (thisPointConsumed) continue; if (thisPointConsumed) continue;
if (!moveTouchFound && idxMoveStartingPointCandidate==-1 && moveTouchBeginIsValid(thisPoint)) { if (!moveTouchFound && idxMoveStartingPointCandidate==-1 && moveTouchBeginIsValid(thisPoint) &&
(!_unusedTouches.count(thisPointId) || _unusedTouches[thisPointId] == MOVE )) {
idxMoveStartingPointCandidate = i; idxMoveStartingPointCandidate = i;
thisPointConsumed = true; thisPointConsumed = true;
} }
if (thisPointConsumed) continue; if (thisPointConsumed) continue;
if (!viewTouchFound && idxViewStartingPointCandidate==-1 && viewTouchBeginIsValid(thisPoint)) { if (!viewTouchFound && idxViewStartingPointCandidate==-1 && viewTouchBeginIsValid(thisPoint) &&
(!_unusedTouches.count(thisPointId) || _unusedTouches[thisPointId] == VIEW )) {
idxViewStartingPointCandidate = i; idxViewStartingPointCandidate = i;
thisPointConsumed = true; thisPointConsumed = true;
} }
if (thisPointConsumed) continue;
if (moveTouchBeginIsValid(thisPoint)) {
unusedTouchesInEvent[thisPointId] = MOVE;
} else if (viewTouchBeginIsValid(thisPoint)) {
unusedTouchesInEvent[thisPointId] = VIEW;
}
} }
processUnusedTouches(unusedTouchesInEvent);
if (!moveTouchFound) { if (!moveTouchFound) {
if (idxMoveStartingPointCandidate!=-1) { if (idxMoveStartingPointCandidate!=-1) {
_moveCurrentTouchId = tPoints[idxMoveStartingPointCandidate].id(); _moveCurrentTouchId = tPoints[idxMoveStartingPointCandidate].id();
_unusedTouches.erase(_moveCurrentTouchId);
moveTouchBegin(thisPoint); moveTouchBegin(thisPoint);
} else { } else {
moveTouchEnd(); moveTouchEnd();
@ -297,11 +334,13 @@ void TouchscreenVirtualPadDevice::touchUpdateEvent(const QTouchEvent* event) {
if (!viewTouchFound) { if (!viewTouchFound) {
if (idxViewStartingPointCandidate!=-1) { if (idxViewStartingPointCandidate!=-1) {
_viewCurrentTouchId = tPoints[idxViewStartingPointCandidate].id(); _viewCurrentTouchId = tPoints[idxViewStartingPointCandidate].id();
_unusedTouches.erase(_viewCurrentTouchId);
viewTouchBegin(thisPoint); viewTouchBegin(thisPoint);
} else { } else {
viewTouchEnd(); viewTouchEnd();
} }
} }
} }
bool TouchscreenVirtualPadDevice::viewTouchBeginIsValid(glm::vec2 touchPoint) { bool TouchscreenVirtualPadDevice::viewTouchBeginIsValid(glm::vec2 touchPoint) {

View file

@ -62,6 +62,12 @@ public:
const std::shared_ptr<InputDevice>& getInputDevice() const { return _inputDevice; } const std::shared_ptr<InputDevice>& getInputDevice() const { return _inputDevice; }
protected: protected:
enum TouchType {
MOVE = 1,
VIEW
};
float _lastPinchScale; float _lastPinchScale;
float _pinchScale; float _pinchScale;
float _screenDPI; float _screenDPI;
@ -78,6 +84,8 @@ protected:
glm::vec2 _viewCurrentTouchPoint; glm::vec2 _viewCurrentTouchPoint;
int _viewCurrentTouchId; int _viewCurrentTouchId;
std::map<int, TouchType> _unusedTouches;
int _touchPointCount; int _touchPointCount;
int _screenWidthCenter; int _screenWidthCenter;
std::shared_ptr<InputDevice> _inputDevice { std::make_shared<InputDevice>() }; std::shared_ptr<InputDevice> _inputDevice { std::make_shared<InputDevice>() };
@ -103,6 +111,8 @@ protected:
void processInputDeviceForMove(VirtualPad::Manager& virtualPadManager); void processInputDeviceForMove(VirtualPad::Manager& virtualPadManager);
glm::vec2 clippedPointInCircle(float radius, glm::vec2 origin, glm::vec2 touchPoint); glm::vec2 clippedPointInCircle(float radius, glm::vec2 origin, glm::vec2 touchPoint);
void processUnusedTouches(std::map<int, TouchType> unusedTouchesInEvent);
void processInputDeviceForView(); void processInputDeviceForView();
// just for debug // just for debug
private: private: