aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMorten Sørvig <morten.sorvig@qt.io>2026-09-01 16:10:47 +0200
committerMorten Sørvig <morten.sorvig@qt.io>2026-09-21 11:01:30 +0000
commitfbe7fa601343a50ef08f698db4a233687cadd681 (patch)
tree678367f4a2aa8087be34027a0a978cdb07e9cec2
parent87fe30c622af28b1fcf4a6de873b6504f7c85fe9 (diff)
QQuickMultiPointTouchArea: ignore sub-pixel noise at the drag threshold
updateTouchData() detects a grab gesture once a touch point has moved more than QStyleHints::startDragDistance(). tst_QQuickMultiPointTouchArea::mouseGestureStarted enforces this with a test which expects a move of +dragThreshold not to start a drag and a further +1 to do so However, at fractional scale factors the computed delta can end up having floating point rounding errors due to scaling round-trips between native and device independent coordinates. This would cause a mouseGestureStarted test failure when updateTouchData() decided that startDragDistance + (~1e-13) was larger than startDragDistance and start a drag. Fix this by replacing the operator > based comparison with one that checks for floating point rounding errors using qFuzzyCompare() as well. Task-number: QTBUG-146901 Change-Id: I8da3894cd2c922a59e0aec3a2a16f81b9d03e4bd Reviewed-by: Tor Arne Vestbø <tor.arne.vestbo@qt.io>
-rw-r--r--src/quick/items/qquickmultipointtoucharea.cpp13
1 files changed, 11 insertions, 2 deletions
diff --git a/src/quick/items/qquickmultipointtoucharea.cpp b/src/quick/items/qquickmultipointtoucharea.cpp
index 1865409de7..d36eebebda 100644
--- a/src/quick/items/qquickmultipointtoucharea.cpp
+++ b/src/quick/items/qquickmultipointtoucharea.cpp
@@ -659,14 +659,23 @@ void QQuickMultiPointTouchArea::updateTouchData(QEvent *event, RemapEventPoints
if (!_stealMouse /* !ignoring gesture*/) {
bool offerGrab = false;
const int dragThreshold = QGuiApplication::styleHints()->startDragDistance();
+
+ // overThreshold test predicate which does not consider deltas with floating
+ // point rounding residuals to be over the threshld. Required for test stability
+ // at fractional scale factors where scaling may introduce rounding errors.
+ const auto overThreshold = [dragThreshold](qreal delta) {
+ return qAbs(delta) > dragThreshold
+ && !qFuzzyCompare(qAbs(delta), qreal(dragThreshold));
+ };
+
for (const QEventPoint &p : std::as_const(touchPoints)) {
if (p.state() == QEventPoint::State::Released)
continue;
const QPointF currentPos = mapFromScene(p.scenePosition());
const QPointF startPos = mapFromScene(p.scenePressPosition());
- if (qAbs(currentPos.x() - startPos.x()) > dragThreshold)
+ if (overThreshold(currentPos.x() - startPos.x()))
offerGrab = true;
- else if (qAbs(currentPos.y() - startPos.y()) > dragThreshold)
+ else if (overThreshold(currentPos.y() - startPos.y()))
offerGrab = true;
if (offerGrab)
break;