Lomiri
Loading...
Searching...
No Matches
ScrollCalculator.qml
1/*
2 * Copyright (C) 2014 Canonical Ltd.
3 *
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; version 3.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this program. If not, see <http://www.gnu.org/licenses/>.
15 */
16
17import QtQuick 2.12
18import Lomiri.Components 1.3
19
20Item {
21 id: scrollArea
22
23 readonly property bool areaActive: lateralPosition >= 0
24 property real stopScrollThreshold: units.gu(2)
25 property real progressThreshold: units.dp(4)
26 property int direction: Qt.LeftToRight
27 property real baseScrollAmount: units.dp(3)
28 property real maximumScrollAmount: units.dp(8)
29 property real lateralPosition: -1
30 property real forceScrollingPercentage: 0.4
31
32 signal scroll(real scrollAmount)
33
34 width: units.gu(5)
35 rotation: direction === Qt.LeftToRight ? 0 : 180
36
37 onAreaActiveChanged: areaActive ? handleEnter() : handleExit()
38
39 function handleEnter() {
40 d.thresholdAreaX = -scrollArea.stopScrollThreshold;
41 scrollTimer.restart();
42 d.init = true;
43 d.passedProgressThreshold = false;
44
45 d.progression = 0;
46 d.startingProgression = 0;
47 }
48
49 function handleExit() {
50 d.thresholdAreaX = -scrollArea.stopScrollThreshold;
51 scrollTimer.stop();
52 }
53
54 onLateralPositionChanged: {
55 if (scrollArea.areaActive) {
56 if (lateralPosition > width * (1 - forceScrollingPercentage)) {
57 d.thresholdAreaX = width * (1 - forceScrollingPercentage);
58 if (!scrollTimer.running) scrollTimer.restart();
59 } else if (lateralPosition > d.thresholdAreaX + scrollArea.stopScrollThreshold) {
60 d.thresholdAreaX = lateralPosition - scrollArea.stopScrollThreshold;
61 if (!scrollTimer.running) scrollTimer.restart();
62 } else if (lateralPosition < d.thresholdAreaX) {
63 d.thresholdAreaX = lateralPosition;
64 scrollTimer.stop();
65 }
66
67 d.progression = lateralPosition / width;
68 if (d.init) {
69 d.startingProgression = d.progression;
70 d.init = false;
71 }
72 }
73 }
74
75 Timer {
76 id: scrollTimer
77 interval: 16
78 repeat: true
79
80 onTriggered: {
81 if (d.passedProgressThreshold ||
82 Math.abs(d.progression - d.startingProgression) * scrollArea.width > scrollArea.progressThreshold) {
83 d.passedProgressThreshold = true;
84
85 var scrollAmount = scrollArea.baseScrollAmount + scrollArea.maximumScrollAmount * d.progression;
86 scrollArea.scroll(scrollAmount);
87 }
88 }
89 }
90
91 QtObject {
92 id: d
93 property real startingProgression: 0
94 property bool init: true
95
96 property real progression: 0
97 property real thresholdAreaX: -scrollArea.stopScrollThreshold
98 property bool passedProgressThreshold: false
99 }
100}