Make touchscreen gestures realtime

This commit is contained in:
Xaver Hugl 2022-05-10 17:31:10 +02:00
parent 946087ef37
commit 0b27ce4d34
11 changed files with 37 additions and 55 deletions

View file

@ -45,7 +45,7 @@ void InputRedirection::registerRealtimeTouchpadSwipeShortcut(SwipeDirection, uin
Q_UNUSED(fingerCount)
}
void InputRedirection::registerTouchscreenSwipeShortcut(SwipeDirection, uint fingerCount, QAction *)
void InputRedirection::registerTouchscreenSwipeShortcut(SwipeDirection, uint, QAction *, std::function<void(qreal)>)
{
}

View file

@ -786,9 +786,9 @@ void EffectsHandlerImpl::registerTouchpadPinchShortcut(PinchDirection direction,
input()->registerTouchpadPinchShortcut(direction, fingerCount, action);
}
void EffectsHandlerImpl::registerTouchscreenSwipeShortcut(SwipeDirection direction, uint fingerCount, QAction *action)
void EffectsHandlerImpl::registerTouchscreenSwipeShortcut(SwipeDirection direction, uint fingerCount, QAction *action, std::function<void(qreal)> progressCallback)
{
input()->registerTouchscreenSwipeShortcut(direction, fingerCount, action);
input()->registerTouchscreenSwipeShortcut(direction, fingerCount, action, progressCallback);
}
void *EffectsHandlerImpl::getProxy(QString name)

View file

@ -107,7 +107,7 @@ public:
void registerTouchpadSwipeShortcut(SwipeDirection direction, uint fingerCount, QAction *action) override;
void registerRealtimeTouchpadPinchShortcut(PinchDirection dir, uint fingerCount, QAction *onUp, std::function<void(qreal)> progressCallback) override;
void registerTouchpadPinchShortcut(PinchDirection direction, uint fingerCount, QAction *action) override;
void registerTouchscreenSwipeShortcut(SwipeDirection direction, uint fingerCount, QAction *action) override;
void registerTouchscreenSwipeShortcut(SwipeDirection direction, uint fingerCount, QAction *action, std::function<void(qreal)> progressCallback) override;
void *getProxy(QString name) override;
void startMousePolling() override;
void stopMousePolling() override;

View file

@ -45,8 +45,6 @@ OverviewEffect::OverviewEffect()
KGlobalAccel::self()->setShortcut(m_toggleAction, {defaultToggleShortcut});
m_toggleShortcut = KGlobalAccel::self()->shortcut(m_toggleAction);
effects->registerGlobalShortcut({defaultToggleShortcut}, m_toggleAction);
effects->registerTouchscreenSwipeShortcut(SwipeDirection::Up, 3, m_toggleAction);
effects->registerTouchscreenSwipeShortcut(SwipeDirection::Down, 3, m_toggleAction);
auto progressCallback = [this](qreal progress) {
if (m_status == Status::Active) {
@ -64,6 +62,7 @@ OverviewEffect::OverviewEffect()
};
effects->registerRealtimeTouchpadSwipeShortcut(SwipeDirection::Up, 4, m_realtimeToggleAction, progressCallback);
effects->registerTouchscreenSwipeShortcut(SwipeDirection::Up, 3, m_realtimeToggleAction, progressCallback);
connect(effects, &EffectsHandler::screenAboutToLock, this, &OverviewEffect::realDeactivate);

View file

@ -108,7 +108,7 @@ WindowViewEffect::WindowViewEffect()
}
});
effects->registerRealtimeTouchpadSwipeShortcut(SwipeDirection::Down, 4, m_realtimeToggleAction, [this](qreal progress) {
const auto gestureCallback = [this](qreal progress) {
if (m_status == Status::Active) {
return;
}
@ -121,7 +121,9 @@ WindowViewEffect::WindowViewEffect()
if (!isRunning()) {
partialActivate();
}
});
};
effects->registerRealtimeTouchpadSwipeShortcut(SwipeDirection::Down, 4, m_realtimeToggleAction, gestureCallback);
effects->registerTouchscreenSwipeShortcut(SwipeDirection::Down, 3, m_realtimeToggleAction, gestureCallback);
reconfigure(ReconfigureAll);
}

View file

@ -191,9 +191,9 @@ void GlobalShortcutsManager::registerRealtimeTouchpadPinch(QAction *onUp, std::f
addIfNotExists(GlobalShortcut(RealtimeFeedbackPinchShortcut{direction, progressCallback, fingerCount}, onUp), DeviceType::Touchpad);
}
void GlobalShortcutsManager::registerTouchscreenSwipe(QAction *action, SwipeDirection direction, uint fingerCount)
void GlobalShortcutsManager::registerTouchscreenSwipe(QAction *action, std::function<void(qreal)> progressCallback, SwipeDirection direction, uint fingerCount)
{
addIfNotExists(GlobalShortcut(SwipeShortcut{DeviceType::Touchscreen, direction, fingerCount}, action), DeviceType::Touchscreen);
addIfNotExists(GlobalShortcut(RealtimeFeedbackSwipeShortcut{DeviceType::Touchscreen, direction, progressCallback, fingerCount}, action), DeviceType::Touchscreen);
}
bool GlobalShortcutsManager::processKey(Qt::KeyboardModifiers mods, int keyQt)

View file

@ -72,7 +72,7 @@ public:
void registerRealtimeTouchpadPinch(QAction *onUp, std::function<void(qreal)> progressCallback, PinchDirection direction, uint fingerCount = 4);
void registerTouchscreenSwipe(QAction *action, SwipeDirection direction, uint fingerCount);
void registerTouchscreenSwipe(QAction *action, std::function<void(qreal)> progressCallback, SwipeDirection direction, uint fingerCount);
/**
* @brief Processes a key event to decide whether a shortcut needs to be triggered.

View file

@ -1065,7 +1065,7 @@ public:
m_gestureCancelled = true;
return true;
} else {
m_touchPoints.insert(id, {pos, QSize()});
m_touchPoints.insert(id, pos);
if (m_touchPoints.count() == 1) {
m_lastTouchDownTime = time;
} else {
@ -1078,7 +1078,7 @@ public:
float xfactor = output->physicalSize().width() / (float)output->geometry().width();
float yfactor = output->physicalSize().height() / (float)output->geometry().height();
bool distanceMatch = std::any_of(m_touchPoints.constBegin(), m_touchPoints.constEnd(), [pos, xfactor, yfactor](const auto &point) {
QPointF p = pos - point.pos;
QPointF p = pos - point;
return std::abs(xfactor * p.x()) + std::abs(yfactor * p.y()) < 50;
});
if (!distanceMatch) {
@ -1103,19 +1103,15 @@ public:
if (m_gestureCancelled) {
return true;
}
// only track one finger for simplicity
if (id != m_touchPoints.begin().key()) {
return true;
}
auto &point = m_touchPoints[id];
QPointF dist = pos - point.pos;
auto output = kwinApp()->platform()->outputAt(pos.toPoint());
float xfactor = output->physicalSize().width() / (float)output->geometry().width();
float yfactor = output->physicalSize().height() / (float)output->geometry().height();
QSize delta = QSize(xfactor * dist.x(), yfactor * dist.y()) * 10;
point.distance += delta;
point.pos = pos;
input()->shortcuts()->processSwipeUpdate(DeviceType::Touchscreen, delta);
const float xfactor = output->physicalSize().width() / (float)output->geometry().width();
const float yfactor = output->physicalSize().height() / (float)output->geometry().height();
auto &point = m_touchPoints[id];
const QPointF dist = pos - point;
const QSizeF delta = QSizeF(xfactor * dist.x(), yfactor * dist.y());
input()->shortcuts()->processSwipeUpdate(DeviceType::Touchscreen, 5 * delta / m_touchPoints.size());
point = pos;
return true;
}
return false;
@ -1144,17 +1140,12 @@ public:
}
private:
struct TouchPoint
{
QPointF pos;
QSize distance;
};
bool m_gestureTaken = false;
bool m_gestureCancelled = false;
bool m_touchGestureCancelSent = false;
uint32_t m_lastTouchDownTime = 0;
QPointF m_lastAverageDistance;
QMap<int32_t, TouchPoint> m_touchPoints;
QMap<int32_t, QPointF> m_touchPoints;
QTimer *m_powerDown = nullptr;
};
@ -3247,9 +3238,9 @@ void InputRedirection::registerGlobalAccel(KGlobalAccelInterface *interface)
m_shortcuts->setKGlobalAccelInterface(interface);
}
void InputRedirection::registerTouchscreenSwipeShortcut(SwipeDirection direction, uint fingerCount, QAction *action)
void InputRedirection::registerTouchscreenSwipeShortcut(SwipeDirection direction, uint fingerCount, QAction *action, std::function<void(qreal)> progressCallback)
{
m_shortcuts->registerTouchscreenSwipe(action, direction, fingerCount);
m_shortcuts->registerTouchscreenSwipe(action, progressCallback, direction, fingerCount);
}
void InputRedirection::warpPointer(const QPointF &pos)

View file

@ -139,7 +139,7 @@ public:
void registerRealtimeTouchpadSwipeShortcut(SwipeDirection direction, uint fingerCount, QAction *onUp, std::function<void(qreal)> progressCallback);
void registerTouchpadPinchShortcut(PinchDirection direction, uint fingerCount, QAction *action);
void registerRealtimeTouchpadPinchShortcut(PinchDirection direction, uint fingerCount, QAction *onUp, std::function<void(qreal)> progressCallback);
void registerTouchscreenSwipeShortcut(SwipeDirection direction, uint fingerCount, QAction *action);
void registerTouchscreenSwipeShortcut(SwipeDirection direction, uint fingerCount, QAction *action, std::function<void(qreal)> progressCallback);
void registerGlobalAccel(KGlobalAccelInterface *interface);
bool supportsPointerWarping() const;

View file

@ -941,7 +941,7 @@ public:
* @param action The action which gets triggered when the gesture triggers
* @since 5.25
*/
virtual void registerTouchscreenSwipeShortcut(SwipeDirection direction, uint fingerCount, QAction *action) = 0;
virtual void registerTouchscreenSwipeShortcut(SwipeDirection direction, uint fingerCount, QAction *action, std::function<void(qreal)> progressCallback) = 0;
/**
* Retrieve the proxy class for an effect if it has one. Will return NULL if

View file

@ -809,31 +809,22 @@ void VirtualDesktopManager::initShortcuts()
connect(m_swipeGestureReleasedX.get(), &QAction::triggered, this, &VirtualDesktopManager::gestureReleasedX);
connect(m_swipeGestureReleasedY.get(), &QAction::triggered, this, &VirtualDesktopManager::gestureReleasedY);
// These take the live feedback from a gesture
input()->registerRealtimeTouchpadSwipeShortcut(SwipeDirection::Left, 3, m_swipeGestureReleasedX.get(), [this](qreal cb) {
const auto left = [this](qreal cb) {
if (grid().width() > 1) {
m_currentDesktopOffset.setX(cb);
Q_EMIT currentChanging(current(), m_currentDesktopOffset);
}
});
input()->registerRealtimeTouchpadSwipeShortcut(SwipeDirection::Right, 3, m_swipeGestureReleasedX.get(), [this](qreal cb) {
};
const auto right = [this](qreal cb) {
if (grid().width() > 1) {
m_currentDesktopOffset.setX(-cb);
Q_EMIT currentChanging(current(), m_currentDesktopOffset);
}
});
input()->registerRealtimeTouchpadSwipeShortcut(SwipeDirection::Left, 4, m_swipeGestureReleasedX.get(), [this](qreal cb) {
if (grid().width() > 1) {
m_currentDesktopOffset.setX(cb);
Q_EMIT currentChanging(current(), m_currentDesktopOffset);
}
});
input()->registerRealtimeTouchpadSwipeShortcut(SwipeDirection::Right, 4, m_swipeGestureReleasedX.get(), [this](qreal cb) {
if (grid().width() > 1) {
m_currentDesktopOffset.setX(-cb);
Q_EMIT currentChanging(current(), m_currentDesktopOffset);
}
});
};
input()->registerRealtimeTouchpadSwipeShortcut(SwipeDirection::Left, 3, m_swipeGestureReleasedX.get(), left);
input()->registerRealtimeTouchpadSwipeShortcut(SwipeDirection::Right, 3, m_swipeGestureReleasedX.get(), right);
input()->registerRealtimeTouchpadSwipeShortcut(SwipeDirection::Left, 4, m_swipeGestureReleasedX.get(), left);
input()->registerRealtimeTouchpadSwipeShortcut(SwipeDirection::Right, 4, m_swipeGestureReleasedX.get(), right);
input()->registerRealtimeTouchpadSwipeShortcut(SwipeDirection::Down, 3, m_swipeGestureReleasedY.get(), [this](qreal cb) {
if (grid().height() > 1) {
m_currentDesktopOffset.setY(-cb);
@ -846,9 +837,8 @@ void VirtualDesktopManager::initShortcuts()
Q_EMIT currentChanging(current(), m_currentDesktopOffset);
}
});
input()->registerTouchscreenSwipeShortcut(SwipeDirection::Left, 3, slotRightAction);
input()->registerTouchscreenSwipeShortcut(SwipeDirection::Right, 3, slotLeftAction);
input()->registerTouchscreenSwipeShortcut(SwipeDirection::Left, 3, m_swipeGestureReleasedX.get(), left);
input()->registerTouchscreenSwipeShortcut(SwipeDirection::Right, 3, m_swipeGestureReleasedX.get(), right);
// axis events
input()->registerAxisShortcut(Qt::ControlModifier | Qt::AltModifier, PointerAxisDown,