Add new gestures and improve naming clarity in gesture.h
I've added VerticalAxis, HorizontalAxis, DirectionlessSwipe and BiDirectionalPinch gestures directions. These are all combinations of other gesture directions that semantically work well together. I've implemented these gestures as well as changed some labels and improved documentation, Also, Add vector signal to SwipeGesture
This commit is contained in:
parent
634182d489
commit
bc15b72e3d
7 changed files with 225 additions and 75 deletions
|
@ -343,11 +343,11 @@ void GestureTest::testNotEmitCallbacksBeforeDirectionDecided()
|
|||
recognizer.registerPinchGesture(&expand);
|
||||
recognizer.registerPinchGesture(&contract);
|
||||
|
||||
QSignalSpy upSpy(&up, &SwipeGesture::progress);
|
||||
QSignalSpy downSpy(&down, &SwipeGesture::progress);
|
||||
QSignalSpy rightSpy(&right, &SwipeGesture::progress);
|
||||
QSignalSpy expandSpy(&expand, &PinchGesture::progress);
|
||||
QSignalSpy contractSpy(&contract, &PinchGesture::progress);
|
||||
QSignalSpy upSpy(&up, &SwipeGesture::triggerProgress);
|
||||
QSignalSpy downSpy(&down, &SwipeGesture::triggerProgress);
|
||||
QSignalSpy rightSpy(&right, &SwipeGesture::triggerProgress);
|
||||
QSignalSpy expandSpy(&expand, &PinchGesture::triggerProgress);
|
||||
QSignalSpy contractSpy(&contract, &PinchGesture::triggerProgress);
|
||||
|
||||
// don't release callback until we know the direction of swipe gesture
|
||||
recognizer.startSwipeGesture(4);
|
||||
|
|
143
src/gestures.cpp
143
src/gestures.cpp
|
@ -41,24 +41,28 @@ void SwipeGesture::setStartGeometry(const QRect &geometry)
|
|||
Q_ASSERT(m_maximumY >= m_minimumY);
|
||||
}
|
||||
|
||||
qreal SwipeGesture::deltaToProgress(const QSizeF &delta) const
|
||||
qreal SwipeGesture::getTriggerProgress(const QSizeF &delta) const
|
||||
{
|
||||
if (!m_minimumDeltaRelevant || m_minimumDelta.isNull()) {
|
||||
if (!m_triggerDeltaRelevant || m_triggerDelta.isNull()) {
|
||||
return 1.0;
|
||||
}
|
||||
|
||||
if (m_direction & (GestureDirection::Up | GestureDirection::Down)) {
|
||||
return std::min(std::abs(delta.height()) / std::abs(m_minimumDelta.height()), 1.0);
|
||||
} else if (m_direction & (GestureDirection::Left | GestureDirection::Right)) {
|
||||
return std::min(std::abs(delta.width()) / std::abs(m_minimumDelta.width()), 1.0);
|
||||
if (m_direction.testFlag(GestureDirection::DirectionlessSwipe)) {
|
||||
return std::min(std::hypot(delta.width(), delta.height()) / m_triggerDelta.width(), 1.0);
|
||||
}
|
||||
|
||||
if (m_direction & GestureDirection::VerticalAxis) {
|
||||
return std::min(std::abs(delta.height()) / std::abs(m_triggerDelta.height()), 1.0);
|
||||
} else if (m_direction & GestureDirection::HorizontalAxis) {
|
||||
return std::min(std::abs(delta.width()) / std::abs(m_triggerDelta.width()), 1.0);
|
||||
}
|
||||
|
||||
return 1.0;
|
||||
}
|
||||
|
||||
bool SwipeGesture::minimumDeltaReached(const QSizeF &delta) const
|
||||
bool SwipeGesture::triggerDeltaReached(const QSizeF &delta) const
|
||||
{
|
||||
return deltaToProgress(delta) >= 1.0;
|
||||
return getTriggerProgress(delta) >= 1.0;
|
||||
}
|
||||
|
||||
PinchGesture::PinchGesture(QObject *parent)
|
||||
|
@ -68,14 +72,14 @@ PinchGesture::PinchGesture(QObject *parent)
|
|||
|
||||
PinchGesture::~PinchGesture() = default;
|
||||
|
||||
qreal PinchGesture::scaleDeltaToProgress(const qreal &scaleDelta) const
|
||||
qreal PinchGesture::getTriggerProgress(const qreal &scaleDelta) const
|
||||
{
|
||||
return std::clamp(std::abs(scaleDelta - 1) / minimumScaleDelta(), 0.0, 1.0);
|
||||
return std::clamp(std::abs(scaleDelta - 1) / triggerScaleDelta(), 0.0, 1.0);
|
||||
}
|
||||
|
||||
bool PinchGesture::minimumScaleDeltaReached(const qreal &scaleDelta) const
|
||||
bool PinchGesture::triggerScaleDeltaReached(const qreal &scaleDelta) const
|
||||
{
|
||||
return scaleDeltaToProgress(scaleDelta) >= 1.0;
|
||||
return getTriggerProgress(scaleDelta) >= 1.0;
|
||||
}
|
||||
|
||||
GestureRecognizer::GestureRecognizer(QObject *parent)
|
||||
|
@ -163,11 +167,12 @@ int GestureRecognizer::startSwipeGesture(uint fingerCount, const QPointF &startP
|
|||
}
|
||||
|
||||
// Only add gestures who's direction aligns with current swipe axis
|
||||
if (gesture->direction() & (GestureDirection::Up | GestureDirection::Down)) {
|
||||
if (gesture->direction().testFlag(GestureDirection::DirectionlessSwipe)) {
|
||||
} else if (gesture->direction() & GestureDirection::VerticalAxis) {
|
||||
if (m_currentSwipeAxis == Axis::Horizontal) {
|
||||
continue;
|
||||
}
|
||||
} else if (gesture->direction() & (GestureDirection::Left | GestureDirection::Right)) {
|
||||
} else if (gesture->direction() & GestureDirection::HorizontalAxis) {
|
||||
if (m_currentSwipeAxis == Axis::Vertical) {
|
||||
continue;
|
||||
}
|
||||
|
@ -242,11 +247,39 @@ void GestureRecognizer::updateSwipeGesture(const QSizeF &delta)
|
|||
|
||||
// Send progress update
|
||||
for (SwipeGesture *g : std::as_const(m_activeSwipeGestures)) {
|
||||
Q_EMIT g->progress(g->deltaToProgress(m_currentDelta));
|
||||
Q_EMIT g->deltaProgress(m_currentDelta);
|
||||
Q_EMIT g->triggerProgress(g->getTriggerProgress(m_currentDelta));
|
||||
Q_EMIT g->semanticProgress(g->getSemanticProgress(m_currentDelta), g->direction());
|
||||
Q_EMIT g->pixelDelta(m_currentDelta, g->direction());
|
||||
Q_EMIT g->semanticDelta(g->getSemanticDelta(m_currentDelta), g->direction());
|
||||
if (!g->direction().testFlag(GestureDirection::DirectionlessSwipe)) {
|
||||
Q_EMIT g->semanticProgressAxis(g->getSemanticAxisProgress(m_currentDelta), g->direction());
|
||||
}
|
||||
Q_EMIT g->swipePixelVector(QVector2D(m_currentDelta.width(), m_currentDelta.height()));
|
||||
}
|
||||
}
|
||||
|
||||
bool GestureRecognizer::mutuallyExclusive(GestureDirections currentDir, GestureDirections gestureDir)
|
||||
{
|
||||
if (currentDir == gestureDir) {
|
||||
return false;
|
||||
}
|
||||
if (gestureDir.testFlag(GestureDirection::DirectionlessSwipe)) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (currentDir & GestureDirection::VerticalAxis) {
|
||||
if (gestureDir.testFlag(GestureDirection::VerticalAxis)) {
|
||||
return false;
|
||||
}
|
||||
} else if (currentDir & GestureDirection::HorizontalAxis) {
|
||||
if (gestureDir.testFlag(GestureDirection::HorizontalAxis)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void GestureRecognizer::cancelActiveGestures()
|
||||
{
|
||||
for (auto g : qAsConst(m_activeSwipeGestures)) {
|
||||
|
@ -274,7 +307,7 @@ void GestureRecognizer::endSwipeGesture()
|
|||
{
|
||||
const QSizeF delta = m_currentDelta;
|
||||
for (auto g : qAsConst(m_activeSwipeGestures)) {
|
||||
if (static_cast<SwipeGesture *>(g)->minimumDeltaReached(delta)) {
|
||||
if (static_cast<SwipeGesture *>(g)->triggerDeltaReached(delta)) {
|
||||
Q_EMIT g->triggered();
|
||||
} else {
|
||||
Q_EMIT g->cancelled();
|
||||
|
@ -339,7 +372,9 @@ void GestureRecognizer::updatePinchGesture(qreal scale, qreal angleDelta, const
|
|||
}
|
||||
|
||||
for (PinchGesture *g : std::as_const(m_activePinchGestures)) {
|
||||
Q_EMIT g->progress(g->scaleDeltaToProgress(scale));
|
||||
Q_EMIT g->triggerProgress(g->getTriggerProgress(scale));
|
||||
Q_EMIT g->semanticProgress(g->getSemanticProgress(scale), g->direction());
|
||||
Q_EMIT g->semanticProgressAxis(g->getSemanticAxisProgress(scale), g->direction());
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -354,7 +389,7 @@ void GestureRecognizer::cancelPinchGesture()
|
|||
void GestureRecognizer::endPinchGesture() // because fingers up
|
||||
{
|
||||
for (auto g : qAsConst(m_activePinchGestures)) {
|
||||
if (g->minimumScaleDeltaReached(m_currentScale)) {
|
||||
if (g->triggerScaleDeltaReached(m_currentScale)) {
|
||||
Q_EMIT g->triggered();
|
||||
} else {
|
||||
Q_EMIT g->cancelled();
|
||||
|
@ -431,36 +466,36 @@ bool SwipeGesture::maximumYIsRelevant() const
|
|||
return m_maximumYRelevant;
|
||||
}
|
||||
|
||||
QSizeF SwipeGesture::minimumDelta() const
|
||||
QSizeF SwipeGesture::triggerDelta() const
|
||||
{
|
||||
return m_minimumDelta;
|
||||
return m_triggerDelta;
|
||||
}
|
||||
|
||||
void SwipeGesture::setMinimumDelta(const QSizeF &delta)
|
||||
void SwipeGesture::setTriggerDelta(const QSizeF &delta)
|
||||
{
|
||||
m_minimumDelta = delta;
|
||||
m_minimumDeltaRelevant = true;
|
||||
m_triggerDelta = delta;
|
||||
m_triggerDeltaRelevant = true;
|
||||
}
|
||||
|
||||
bool SwipeGesture::isMinimumDeltaRelevant() const
|
||||
bool SwipeGesture::isTriggerDeltaRelevant() const
|
||||
{
|
||||
return m_minimumDeltaRelevant;
|
||||
return m_triggerDeltaRelevant;
|
||||
}
|
||||
|
||||
qreal PinchGesture::minimumScaleDelta() const
|
||||
qreal PinchGesture::triggerScaleDelta() const
|
||||
{
|
||||
return m_minimumScaleDelta;
|
||||
return m_triggerScaleDelta;
|
||||
}
|
||||
|
||||
void PinchGesture::setMinimumScaleDelta(const qreal &scaleDelta)
|
||||
void PinchGesture::setTriggerScaleDelta(const qreal &scaleDelta)
|
||||
{
|
||||
m_minimumScaleDelta = scaleDelta;
|
||||
m_minimumScaleDeltaRelevant = true;
|
||||
m_triggerScaleDelta = scaleDelta;
|
||||
m_triggerScaleDeltaRelevant = true;
|
||||
}
|
||||
|
||||
bool PinchGesture::isMinimumScaleDeltaRelevant() const
|
||||
bool PinchGesture::isTriggerScaleDeltaRelevant() const
|
||||
{
|
||||
return m_minimumScaleDeltaRelevant;
|
||||
return m_triggerScaleDeltaRelevant;
|
||||
}
|
||||
|
||||
int GestureRecognizer::startSwipeGesture(uint fingerCount)
|
||||
|
@ -468,6 +503,48 @@ int GestureRecognizer::startSwipeGesture(uint fingerCount)
|
|||
return startSwipeGesture(fingerCount, QPointF(), StartPositionBehavior::Irrelevant);
|
||||
}
|
||||
|
||||
QSizeF SwipeGesture::getSemanticDelta(const QSizeF &delta) const
|
||||
{
|
||||
QSizeF d = QSizeF();
|
||||
d.setWidth(delta.width() / m_unitDelta);
|
||||
d.setHeight(delta.height() / m_unitDelta);
|
||||
return d;
|
||||
}
|
||||
|
||||
qreal SwipeGesture::getSemanticProgress(const QSizeF &delta) const
|
||||
{
|
||||
if (m_direction.testFlag(GestureDirection::DirectionlessSwipe)) {
|
||||
return std::hypot(delta.width(), delta.height()) / m_unitDelta;
|
||||
} else if (m_direction & GestureDirection::VerticalAxis) {
|
||||
return std::abs(delta.height()) / m_unitDelta;
|
||||
} else if (m_direction & GestureDirection::HorizontalAxis) {
|
||||
return std::abs(delta.width()) / m_unitDelta;
|
||||
}
|
||||
|
||||
return 1.0;
|
||||
}
|
||||
|
||||
qreal PinchGesture::getSemanticProgress(const qreal scale) const
|
||||
{
|
||||
return std::max(std::abs(1 - scale) / m_unitScaleDelta, 0.0);
|
||||
}
|
||||
|
||||
qreal SwipeGesture::getSemanticAxisProgress(const QSizeF &delta) const
|
||||
{
|
||||
if (m_direction & GestureDirection::VerticalAxis) {
|
||||
return delta.height() / m_unitDelta;
|
||||
} else if (m_direction & GestureDirection::HorizontalAxis) {
|
||||
return delta.width() / m_unitDelta;
|
||||
}
|
||||
|
||||
return 1.0;
|
||||
}
|
||||
|
||||
qreal PinchGesture::getSemanticAxisProgress(const qreal scale) const
|
||||
{
|
||||
return (scale - 1) / m_unitScaleDelta;
|
||||
}
|
||||
|
||||
int GestureRecognizer::startSwipeGesture(const QPointF &startPos)
|
||||
{
|
||||
return startSwipeGesture(1, startPos, StartPositionBehavior::Relevant);
|
||||
|
|
114
src/gestures.h
114
src/gestures.h
|
@ -17,16 +17,17 @@
|
|||
#include <QPointF>
|
||||
#include <QSet>
|
||||
#include <QSizeF>
|
||||
#include <QVector2D>
|
||||
#include <QVector>
|
||||
|
||||
namespace KWin
|
||||
{
|
||||
static const QSet<uint> DEFAULT_VALID_FINGER_COUNTS = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10};
|
||||
|
||||
/*
|
||||
* Everytime the scale of the gesture changes by this much, the callback changes by 1.
|
||||
/**
|
||||
* This is the amount of change for 1 unit of change, like switch by 1 desktop.
|
||||
* */
|
||||
*/
|
||||
static const qreal DEFAULT_UNIT_DELTA = 400; // Pixels
|
||||
static const qreal DEFAULT_UNIT_SCALE_DELTA = .2; // 20%
|
||||
|
||||
class Gesture : public QObject
|
||||
|
@ -72,6 +73,24 @@ Q_SIGNALS:
|
|||
* This Gesture no longer matches.
|
||||
*/
|
||||
void cancelled();
|
||||
/**
|
||||
* Progress towards the minimum threshold to trigger
|
||||
*/
|
||||
void triggerProgress(qreal);
|
||||
/**
|
||||
* The progress of the gesture if a minimumDelta is set.
|
||||
* The progress is reported in [0.0,1.0+]
|
||||
* Progress is always positive
|
||||
* It can be more than 1, indicating an action should happen more than once.
|
||||
*/
|
||||
void semanticProgress(qreal, GestureDirections);
|
||||
/**
|
||||
* Like semantic progress except [-1, 1] and
|
||||
* it captures both of something
|
||||
* example: Up and Down (VerticalAxis), Contracting and Expanding (BiDirectionalPinch)
|
||||
* Positive values are Up, Right and Expanding
|
||||
*/
|
||||
void semanticProgressAxis(qreal, GestureDirections);
|
||||
|
||||
private:
|
||||
QSet<uint> m_validFingerCounts = DEFAULT_VALID_FINGER_COUNTS;
|
||||
|
@ -99,24 +118,51 @@ public:
|
|||
bool maximumYIsRelevant() const;
|
||||
void setStartGeometry(const QRect &geometry);
|
||||
|
||||
QSizeF minimumDelta() const;
|
||||
void setMinimumDelta(const QSizeF &delta);
|
||||
bool isMinimumDeltaRelevant() const;
|
||||
QSizeF triggerDelta() const;
|
||||
void setTriggerDelta(const QSizeF &delta);
|
||||
bool isTriggerDeltaRelevant() const;
|
||||
|
||||
qreal deltaToProgress(const QSizeF &delta) const;
|
||||
bool minimumDeltaReached(const QSizeF &delta) const;
|
||||
qreal getTriggerProgress(const QSizeF &delta) const;
|
||||
bool triggerDeltaReached(const QSizeF &delta) const;
|
||||
|
||||
/**
|
||||
* Take the given pixel delta and
|
||||
* map it to a simple [0, 1+] semantic scale.
|
||||
* 0 = no progress
|
||||
* 1 = complete something once
|
||||
* The value can be greater than 1, indicating
|
||||
* that the action should be done more times.
|
||||
*/
|
||||
qreal getSemanticProgress(const QSizeF &delta) const;
|
||||
/**
|
||||
* Like the last one, except [-1, 1]
|
||||
* Positive values are Up and Right
|
||||
*/
|
||||
qreal getSemanticAxisProgress(const QSizeF &delta) const;
|
||||
/**
|
||||
* A two dimensional semantic delta.
|
||||
* [-1, 1] on each axis.
|
||||
* Positive is Up and Right
|
||||
*/
|
||||
QSizeF getSemanticDelta(const QSizeF &delta) const;
|
||||
|
||||
Q_SIGNALS:
|
||||
/**
|
||||
* The progress of the gesture if a minimumDelta is set.
|
||||
* The progress is reported in [0.0,1.0]
|
||||
* Summative pixel delta from where the gesture
|
||||
* started to where it is now.
|
||||
*/
|
||||
void progress(qreal);
|
||||
|
||||
void pixelDelta(const QSizeF &delta, GestureDirections);
|
||||
/**
|
||||
* The progress in actual pixel distance traveled by the fingers
|
||||
* A 2d coordinate giving the semantic axis delta
|
||||
* [-1, 1] on both horizontal and vertical axes.
|
||||
*/
|
||||
void deltaProgress(const QSizeF &delta);
|
||||
void semanticDelta(const QSizeF &delta, GestureDirections);
|
||||
/**
|
||||
* GIves a 2d vector of pointing from
|
||||
* where the gesture started to where
|
||||
* it is now.
|
||||
*/
|
||||
void swipePixelVector(const QVector2D &vector);
|
||||
|
||||
private:
|
||||
bool m_minimumXRelevant = false;
|
||||
|
@ -127,8 +173,9 @@ private:
|
|||
int m_maximumX = 0;
|
||||
bool m_maximumYRelevant = false;
|
||||
int m_maximumY = 0;
|
||||
bool m_minimumDeltaRelevant = false;
|
||||
QSizeF m_minimumDelta;
|
||||
bool m_triggerDeltaRelevant = false;
|
||||
QSizeF m_triggerDelta;
|
||||
qreal m_unitDelta = DEFAULT_UNIT_DELTA;
|
||||
};
|
||||
|
||||
class PinchGesture : public Gesture
|
||||
|
@ -138,28 +185,44 @@ public:
|
|||
explicit PinchGesture(QObject *parent = nullptr);
|
||||
~PinchGesture() override;
|
||||
|
||||
qreal minimumScaleDelta() const;
|
||||
qreal triggerScaleDelta() const;
|
||||
|
||||
/**
|
||||
* scaleDelta is the % scale difference needed to trigger
|
||||
* 0.25 will trigger when scale reaches 0.75 or 1.25
|
||||
*/
|
||||
void setMinimumScaleDelta(const qreal &scaleDelta);
|
||||
bool isMinimumScaleDeltaRelevant() const;
|
||||
void setTriggerScaleDelta(const qreal &scaleDelta);
|
||||
bool isTriggerScaleDeltaRelevant() const;
|
||||
|
||||
qreal scaleDeltaToProgress(const qreal &scaleDelta) const;
|
||||
bool minimumScaleDeltaReached(const qreal &scaleDelta) const;
|
||||
qreal getTriggerProgress(const qreal &scaleDelta) const;
|
||||
bool triggerScaleDeltaReached(const qreal &scaleDelta) const;
|
||||
|
||||
/**
|
||||
* Take the given pixel delta and
|
||||
* map it to a simple [0, 1+] semantic scale.
|
||||
* 0 = no progress
|
||||
* 1 = complete something once
|
||||
* The value can be greater than 1, indicating
|
||||
* that the action should be done more times.
|
||||
*/
|
||||
qreal getSemanticProgress(const qreal scale) const;
|
||||
/**
|
||||
* Like the last one, except [-1, 1]
|
||||
* Positive is expanding.
|
||||
* Positive values are Expanding
|
||||
*/
|
||||
qreal getSemanticAxisProgress(const qreal scale) const;
|
||||
|
||||
Q_SIGNALS:
|
||||
/**
|
||||
* The progress of the gesture if a minimumDelta is set.
|
||||
* The progress is reported in [0.0,1.0]
|
||||
*/
|
||||
void progress(qreal);
|
||||
void triggerProgress(qreal);
|
||||
|
||||
private:
|
||||
bool m_minimumScaleDeltaRelevant = false;
|
||||
qreal m_minimumScaleDelta = DEFAULT_UNIT_SCALE_DELTA;
|
||||
bool m_triggerScaleDeltaRelevant = false;
|
||||
qreal m_triggerScaleDelta = .2;
|
||||
qreal m_unitScaleDelta = DEFAULT_UNIT_SCALE_DELTA;
|
||||
};
|
||||
|
||||
class KWIN_EXPORT GestureRecognizer : public QObject
|
||||
|
@ -188,6 +251,7 @@ public:
|
|||
|
||||
private:
|
||||
void cancelActiveGestures();
|
||||
bool mutuallyExclusive(GestureDirections d, GestureDirections gestureDir);
|
||||
enum class StartPositionBehavior {
|
||||
Relevant,
|
||||
Irrelevant,
|
||||
|
|
|
@ -24,6 +24,8 @@
|
|||
#include <signal.h>
|
||||
#include <variant>
|
||||
|
||||
#include <iostream>
|
||||
|
||||
namespace KWin
|
||||
{
|
||||
GlobalShortcut::GlobalShortcut(Shortcut &&sc, QAction *action)
|
||||
|
@ -121,22 +123,22 @@ void GlobalShortcutsManager::registerAxisShortcut(QAction *action, Qt::KeyboardM
|
|||
addIfNotExists(GlobalShortcut(PointerAxisShortcut{modifiers, axis}, action));
|
||||
}
|
||||
|
||||
void GlobalShortcutsManager::registerGesture(GestureDeviceType device, GestureDirection direction, uint fingerCount, QAction *onUp, std::function<void(qreal)> progressCallback)
|
||||
void GlobalShortcutsManager::registerGesture(GestureDeviceType device, GestureDirections direction, uint fingerCount, QAction *onUp, std::function<void(qreal)> progressCallback)
|
||||
{
|
||||
// Create and setup the GestureShortcut
|
||||
GestureShortcut shortcut{device, direction};
|
||||
if (isSwipeDirection(direction)) {
|
||||
std::unique_ptr<SwipeGesture> gesture = std::make_unique<SwipeGesture>();
|
||||
gesture->addFingerCount(fingerCount);
|
||||
gesture->setMinimumDelta(QSizeF(200, 200));
|
||||
connect(gesture.get(), &SwipeGesture::progress, progressCallback);
|
||||
gesture->setTriggerDelta(QSizeF(200, 200));
|
||||
connect(gesture.get(), &SwipeGesture::triggerProgress, progressCallback);
|
||||
connect(gesture.get(), &Gesture::triggered, onUp, &QAction::trigger, Qt::QueuedConnection);
|
||||
connect(gesture.get(), &Gesture::cancelled, onUp, &QAction::trigger, Qt::QueuedConnection);
|
||||
shortcut.swipeGesture = std::move(gesture);
|
||||
} else if (isPinchDirection(direction)) {
|
||||
std::unique_ptr<PinchGesture> gesture = std::make_unique<PinchGesture>();
|
||||
gesture->addFingerCount(fingerCount);
|
||||
connect(gesture.get(), &PinchGesture::progress, progressCallback);
|
||||
connect(gesture.get(), &PinchGesture::triggerProgress, progressCallback);
|
||||
connect(gesture.get(), &Gesture::triggered, onUp, &QAction::trigger, Qt::QueuedConnection);
|
||||
connect(gesture.get(), &Gesture::cancelled, onUp, &QAction::trigger, Qt::QueuedConnection);
|
||||
shortcut.pinchGesture = std::move(gesture);
|
||||
|
@ -151,19 +153,21 @@ void GlobalShortcutsManager::forceRegisterTouchscreenSwipe(QAction *onUp, std::f
|
|||
std::unique_ptr<SwipeGesture> gesture = std::make_unique<SwipeGesture>();
|
||||
gesture->addFingerCount(fingerCount);
|
||||
gesture->setDirection(direction);
|
||||
gesture->setMinimumDelta(QSizeF(200, 200));
|
||||
connect(gesture.get(), &SwipeGesture::progress, progressCallback);
|
||||
gesture->setTriggerDelta(QSizeF(200, 200));
|
||||
connect(gesture.get(), &SwipeGesture::triggerProgress, progressCallback);
|
||||
connect(gesture.get(), &Gesture::triggered, onUp, &QAction::trigger, Qt::QueuedConnection);
|
||||
connect(gesture.get(), &Gesture::cancelled, onUp, &QAction::trigger, Qt::QueuedConnection);
|
||||
GestureShortcut gestureShortcut{GestureDeviceType::Touchscreen, direction};
|
||||
gestureShortcut.swipeGesture = std::move(gesture);
|
||||
m_touchscreenGestureRecognizer->registerSwipeGesture(gestureShortcut.swipeGesture.get());
|
||||
|
||||
GlobalShortcut shortcut{GestureShortcut{GestureDeviceType::Touchscreen, direction, std::move(gesture)}, onUp};
|
||||
GlobalShortcut shortcut{std::move(gestureShortcut), onUp};
|
||||
const auto it = std::find_if(m_shortcuts.begin(), m_shortcuts.end(), [&shortcut](const auto &s) {
|
||||
return shortcut.shortcut() == s.shortcut();
|
||||
});
|
||||
if (it != m_shortcuts.end()) {
|
||||
m_shortcuts.erase(it);
|
||||
}
|
||||
m_touchscreenGestureRecognizer->registerSwipeGesture(gesture.get());
|
||||
connect(shortcut.action(), &QAction::destroyed, this, &GlobalShortcutsManager::objectDeleted);
|
||||
m_shortcuts.push_back(std::move(shortcut));
|
||||
}
|
||||
|
|
|
@ -15,6 +15,7 @@
|
|||
#include <QKeySequence>
|
||||
|
||||
#include <memory>
|
||||
#include <vector>
|
||||
|
||||
class QAction;
|
||||
class KGlobalAccelD;
|
||||
|
@ -58,7 +59,7 @@ public:
|
|||
*/
|
||||
void registerAxisShortcut(QAction *action, Qt::KeyboardModifiers modifiers, PointerAxisDirection axis);
|
||||
|
||||
void registerGesture(GestureDeviceType device, GestureDirection direction, uint fingerCount, QAction *onUp, std::function<void(qreal)> progressCallback = nullptr);
|
||||
void registerGesture(GestureDeviceType device, GestureDirections direction, uint fingerCount, QAction *onUp, std::function<void(qreal)> progressCallback = nullptr);
|
||||
|
||||
void forceRegisterTouchscreenSwipe(QAction *action, std::function<void(qreal)> progressCallback, GestureDirection direction, uint fingerCount);
|
||||
|
||||
|
|
|
@ -232,6 +232,10 @@ enum class GestureDirection {
|
|||
Right = 1 << 4,
|
||||
Expanding = 1 << 5,
|
||||
Contracting = 1 << 6,
|
||||
VerticalAxis = Up | Down, // Up is positive values
|
||||
HorizontalAxis = Left | Right, // Right is positive
|
||||
DirectionlessSwipe = Left | Right | Up | Down, // Positive is Up/Right
|
||||
BiDirectionalPinch = Expanding | Contracting, // Positive is Expanding
|
||||
};
|
||||
|
||||
Q_DECLARE_FLAGS(GestureDirections, GestureDirection)
|
||||
|
|
|
@ -121,14 +121,14 @@ Edge::Edge(ScreenEdges *parent)
|
|||
handleTouchCallback();
|
||||
}
|
||||
});
|
||||
connect(m_gesture, &SwipeGesture::progress, this, [this](qreal progress) {
|
||||
connect(m_gesture, &SwipeGesture::triggerProgress, this, [this](qreal progress) {
|
||||
int factor = progress * 256.0f;
|
||||
if (m_lastApproachingFactor != factor) {
|
||||
m_lastApproachingFactor = factor;
|
||||
Q_EMIT approaching(border(), m_lastApproachingFactor / 256.0f, m_approachGeometry);
|
||||
}
|
||||
});
|
||||
connect(m_gesture, &SwipeGesture::deltaProgress, this, [this](const QSizeF &progressDelta) {
|
||||
connect(m_gesture, &SwipeGesture::pixelDelta, this, [this](const QSizeF &progressDelta) {
|
||||
if (!m_touchCallbacks.isEmpty()) {
|
||||
m_touchCallbacks.constFirst().progressCallback(border(), progressDelta, m_output);
|
||||
}
|
||||
|
@ -569,7 +569,7 @@ void Edge::setGeometry(const QRect &geometry)
|
|||
if (isScreenEdge()) {
|
||||
const Output *output = workspace()->outputAt(m_geometry.center());
|
||||
m_gesture->setStartGeometry(m_geometry);
|
||||
m_gesture->setMinimumDelta(QSizeF(MINIMUM_DELTA, MINIMUM_DELTA) / output->scale());
|
||||
m_gesture->setTriggerDelta(QSizeF(MINIMUM_DELTA, MINIMUM_DELTA) / output->scale());
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in a new issue