1// Copyright (C) 2019 The Qt Company Ltd.
2// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only
3
4#ifndef QQUICKFLICKABLE_P_P_H
5#define QQUICKFLICKABLE_P_P_H
6
7//
8// W A R N I N G
9// -------------
10//
11// This file is not part of the Qt API. It exists purely as an
12// implementation detail. This header file may change from version to
13// version without notice, or even be removed.
14//
15// We mean it.
16//
17
18#include "qquickflickable_p.h"
19#include "qquickitem_p.h"
20#include "qquickitemchangelistener_p.h"
21
22#include <QtQml/qqml.h>
23#include <QtCore/qdatetime.h>
24#include "qplatformdefs.h"
25
26#include <private/qquicktimeline_p_p.h>
27#include <private/qquickanimation_p_p.h>
28#include <private/qquicktransitionmanager_p_p.h>
29#include <private/qpodvector_p.h>
30
31QT_BEGIN_NAMESPACE
32
33class QQuickFlickableVisibleArea;
34class QQuickTransition;
35class QQuickFlickableReboundTransition;
36
37class Q_QUICK_EXPORT QQuickFlickablePrivate : public QQuickItemPrivate, public QQuickItemChangeListener
38{
39 Q_DECLARE_PUBLIC(QQuickFlickable)
40
41public:
42 static inline QQuickFlickablePrivate *get(QQuickFlickable *o) { return o->d_func(); }
43
44 QQuickFlickablePrivate();
45 void init();
46
47 struct Velocity : public QQuickTimeLineValue
48 {
49 Velocity(QQuickFlickablePrivate *p)
50 : parent(p) {}
51 void setValue(qreal v) override {
52 if (v != value()) {
53 QQuickTimeLineValue::setValue(v);
54 parent->updateVelocity();
55 }
56 }
57 QQuickFlickablePrivate *parent;
58 };
59
60 enum MovementReason { Other, SetIndex, Mouse };
61
62 struct AxisData {
63 AxisData(QQuickFlickablePrivate *fp, void (QQuickFlickablePrivate::*func)(qreal))
64 : move(fp, func)
65 , smoothVelocity(fp), atEnd(false), atBeginning(true)
66 , transitionToSet(false)
67 , fixingUp(false), inOvershoot(false), inRebound(false), moving(false), flicking(false)
68 , flickingWhenDragBegan(false), dragging(false), extentsChanged(false)
69 , explicitValue(false), contentPositionChangedExternallyDuringDrag(false)
70 , minExtentDirty(true), maxExtentDirty(true)
71 {}
72
73 ~AxisData();
74
75 void reset() {
76 velocityBuffer.clear();
77 dragStartOffset = 0;
78 fixingUp = false;
79 inOvershoot = false;
80 contentPositionChangedExternallyDuringDrag = false;
81 }
82
83 void markExtentsDirty() {
84 minExtentDirty = true;
85 maxExtentDirty = true;
86 extentsChanged = true;
87 }
88
89 void resetTransitionTo() {
90 transitionTo = 0;
91 transitionToSet = false;
92 }
93
94 void addVelocitySample(qreal v, qreal maxVelocity);
95 void updateVelocity();
96
97 QQuickTimeLineValueProxy<QQuickFlickablePrivate> move;
98 QQuickFlickableReboundTransition *transitionToBounds = nullptr;
99 qreal viewSize = -1;
100 qreal pressPos = 0;
101 qreal lastPos = 0;
102 qreal dragStartOffset = 0;
103 qreal dragMinBound = 0;
104 qreal dragMaxBound = 0;
105 qreal previousDragDelta = 0;
106 qreal velocity = 0;
107 qreal flickTarget = 0;
108 qreal startMargin = 0;
109 qreal endMargin = 0;
110 qreal origin = 0;
111 qreal overshoot = 0;
112 qreal transitionTo = 0;
113 qreal continuousFlickVelocity = 0;
114 QElapsedTimer velocityTime;
115 int vTime = 0;
116 QQuickFlickablePrivate::Velocity smoothVelocity;
117 QPODVector<qreal,10> velocityBuffer;
118 // bitfield
119 uint atEnd : 1;
120 uint atBeginning : 1;
121 uint transitionToSet : 1;
122 uint fixingUp : 1;
123 uint inOvershoot : 1;
124 uint inRebound : 1;
125 uint moving : 1;
126 uint flicking : 1;
127 uint flickingWhenDragBegan : 1;
128 uint dragging : 1;
129 uint extentsChanged : 1;
130 uint explicitValue : 1;
131 uint contentPositionChangedExternallyDuringDrag : 1;
132 // mutable portion of bitfield
133 mutable uint minExtentDirty : 1;
134 mutable uint maxExtentDirty : 1;
135 // end bitfield
136 };
137
138 bool flickX(QEvent::Type eventType, qreal velocity);
139 bool flickY(QEvent::Type eventType, qreal velocity);
140 virtual bool flick(AxisData &data, qreal minExtent, qreal maxExtent, qreal vSize,
141 QQuickTimeLineCallback::Callback fixupCallback,
142 QEvent::Type eventType, qreal velocity);
143 void flickingStarted(bool flickingH, bool flickingV);
144
145 void fixupX();
146 void fixupY();
147 virtual void fixup(AxisData &data, qreal minExtent, qreal maxExtent);
148 void adjustContentPos(AxisData &data, qreal toPos);
149 void resetTimeline(AxisData &data);
150 void clearTimeline();
151
152 void updateBeginningEnd();
153
154 bool isInnermostPressDelay(QQuickItem *item) const;
155 void captureDelayedPress(QQuickItem *item, QPointerEvent *event);
156 void clearDelayedPress();
157 void replayDelayedPress();
158
159 void setViewportX(qreal x);
160 void setViewportY(qreal y);
161
162 qreal overShootDistance(qreal velocity) const;
163
164 void itemGeometryChanged(QQuickItem *, QQuickGeometryChange, const QRectF &) override;
165
166 void draggingStarting();
167 void draggingEnding();
168
169 bool isViewMoving() const;
170
171 void cancelInteraction();
172
173 void addPointerHandler(QQuickPointerHandler *h) override;
174
175 virtual bool wantsPointerEvent(const QPointerEvent *) { return true; }
176
177public:
178 QQuickItem *contentItem;
179
180 AxisData hData;
181 AxisData vData;
182
183 MovementReason moveReason = Other;
184
185 QQuickTimeLine timeline;
186 bool hMoved : 1;
187 bool vMoved : 1;
188 bool stealMouse : 1;
189 bool pressed : 1;
190 bool scrollingPhase : 1;
191 bool interactive : 1;
192 bool calcVelocity : 1;
193 bool pixelAligned : 1;
194 bool syncDrag : 1;
195 QElapsedTimer timer;
196 qint64 lastPosTime;
197 qint64 lastPressTime;
198 QPointF lastPos;
199 QPointF pressPos;
200 QVector2D accumulatedWheelPixelDelta;
201 qreal deceleration;
202 qreal wheelDeceleration;
203 qreal maxVelocity;
204 QPointerEvent *delayedPressEvent;
205 QBasicTimer delayedPressTimer;
206 int pressDelay;
207 int fixupDuration;
208 qreal flickBoost;
209 qreal initialWheelFlickDistance;
210
211 enum FixupMode { Normal, Immediate, ExtentChanged };
212 FixupMode fixupMode;
213
214 static void fixupY_callback(void *);
215 static void fixupX_callback(void *);
216
217 void updateVelocity();
218 int vTime;
219 QQuickTimeLine velocityTimeline;
220 QQuickFlickableVisibleArea *visibleArea;
221 QQuickFlickable::FlickableDirection flickableDirection;
222 QQuickFlickable::BoundsBehavior boundsBehavior;
223 QQuickFlickable::BoundsMovement boundsMovement;
224 QQuickTransition *rebound;
225
226 void viewportAxisMoved(AxisData &data, qreal minExtent, qreal maxExtent,
227 QQuickTimeLineCallback::Callback fixupCallback);
228
229 void handlePressEvent(QPointerEvent *);
230 void handleMoveEvent(QPointerEvent *);
231 void handleReleaseEvent(QPointerEvent *);
232
233 void maybeBeginDrag(qint64 currentTimestamp, const QPointF &pressPosn,
234 Qt::MouseButtons buttons = Qt::NoButton);
235 void drag(qint64 currentTimestamp, QEvent::Type eventType, const QPointF &localPos,
236 const QVector2D &deltas, bool overThreshold, bool momentum,
237 bool velocitySensitiveOverBounds, const QVector2D &velocity);
238
239 QVector2D firstPointLocalVelocity(QPointerEvent *event);
240 qint64 computeCurrentTime(QInputEvent *event) const;
241 qreal devicePixelRatio() const;
242
243 // flickableData property
244 static void data_append(QQmlListProperty<QObject> *, QObject *);
245 static qsizetype data_count(QQmlListProperty<QObject> *);
246 static QObject *data_at(QQmlListProperty<QObject> *, qsizetype);
247 static void data_clear(QQmlListProperty<QObject> *);
248};
249
250class Q_QUICK_EXPORT QQuickFlickableVisibleArea : public QObject
251{
252 Q_OBJECT
253
254 Q_PROPERTY(qreal xPosition READ xPosition NOTIFY xPositionChanged FINAL)
255 Q_PROPERTY(qreal yPosition READ yPosition NOTIFY yPositionChanged FINAL)
256 Q_PROPERTY(qreal widthRatio READ widthRatio NOTIFY widthRatioChanged FINAL)
257 Q_PROPERTY(qreal heightRatio READ heightRatio NOTIFY heightRatioChanged FINAL)
258 QML_ANONYMOUS
259 QML_ADDED_IN_VERSION(2, 0)
260
261public:
262 QQuickFlickableVisibleArea(QQuickFlickable *parent=nullptr);
263
264 qreal xPosition() const;
265 qreal widthRatio() const;
266 qreal yPosition() const;
267 qreal heightRatio() const;
268
269 void updateVisible();
270
271Q_SIGNALS:
272 void xPositionChanged(qreal xPosition);
273 void yPositionChanged(qreal yPosition);
274 void widthRatioChanged(qreal widthRatio);
275 void heightRatioChanged(qreal heightRatio);
276
277private:
278 QQuickFlickable *flickable;
279 qreal m_xPosition;
280 qreal m_widthRatio;
281 qreal m_yPosition;
282 qreal m_heightRatio;
283};
284
285QT_END_NAMESPACE
286
287#endif // QQUICKFLICKABLE_P_P_H
288

Provided by KDAB

Privacy Policy
Learn Advanced QML with KDAB
Find out more

source code of qtdeclarative/src/quick/items/qquickflickable_p_p.h