KWin
Loading...
Searching...
No Matches
timeline.cpp
Go to the documentation of this file.
1/*
2 SPDX-FileCopyrightText: 2018 Vlad Zahorodnii <vlad.zahorodnii@kde.org>
3
4 SPDX-License-Identifier: GPL-2.0-or-later
5*/
6
7#include "effect/timeline.h"
8
9namespace KWin
10{
11
12class Q_DECL_HIDDEN TimeLine::Data : public QSharedData
13{
14public:
15 std::chrono::milliseconds duration;
17 QEasingCurve easingCurve;
18
19 std::chrono::milliseconds elapsed = std::chrono::milliseconds::zero();
20 std::optional<std::chrono::milliseconds> lastTimestamp = std::nullopt;
21 bool done = false;
22 RedirectMode sourceRedirectMode = RedirectMode::Relaxed;
23 RedirectMode targetRedirectMode = RedirectMode::Strict;
24};
25
26TimeLine::TimeLine(std::chrono::milliseconds duration, Direction direction)
27 : d(new Data)
28{
29 Q_ASSERT(duration > std::chrono::milliseconds::zero());
30 d->duration = duration;
31 d->direction = direction;
32}
33
35 : d(other.d)
36{
37}
38
39TimeLine::~TimeLine() = default;
40
41qreal TimeLine::progress() const
42{
43 return static_cast<qreal>(d->elapsed.count()) / d->duration.count();
44}
45
46qreal TimeLine::value() const
47{
48 const qreal t = progress();
49 return d->easingCurve.valueForProgress(
50 d->direction == Backward ? 1.0 - t : t);
51}
52
53void TimeLine::advance(std::chrono::milliseconds timestamp)
54{
55 if (d->done) {
56 return;
57 }
58
59 std::chrono::milliseconds delta = std::chrono::milliseconds::zero();
60 if (d->lastTimestamp.has_value()) {
61 delta = timestamp - d->lastTimestamp.value();
62 }
63
64 Q_ASSERT(delta >= std::chrono::milliseconds::zero());
65 d->lastTimestamp = timestamp;
66
67 d->elapsed += delta;
68 if (d->elapsed >= d->duration) {
69 d->elapsed = d->duration;
70 d->done = true;
71 d->lastTimestamp = std::nullopt;
72 }
73}
74
75std::chrono::milliseconds TimeLine::elapsed() const
76{
77 return d->elapsed;
78}
79
80void TimeLine::setElapsed(std::chrono::milliseconds elapsed)
81{
82 Q_ASSERT(elapsed >= std::chrono::milliseconds::zero());
83 if (elapsed == d->elapsed) {
84 return;
85 }
86
87 reset();
88
89 d->elapsed = elapsed;
90
91 if (d->elapsed >= d->duration) {
92 d->elapsed = d->duration;
93 d->done = true;
94 d->lastTimestamp = std::nullopt;
95 }
96}
97
98std::chrono::milliseconds TimeLine::duration() const
99{
100 return d->duration;
101}
102
103void TimeLine::setDuration(std::chrono::milliseconds duration)
104{
105 Q_ASSERT(duration > std::chrono::milliseconds::zero());
106 if (duration == d->duration) {
107 return;
108 }
109 d->elapsed = std::chrono::milliseconds(qRound(progress() * duration.count()));
110 d->duration = duration;
111 if (d->elapsed == d->duration) {
112 d->done = true;
113 d->lastTimestamp = std::nullopt;
114 }
115}
116
118{
119 return d->direction;
120}
121
123{
124 if (d->direction == direction) {
125 return;
126 }
127
128 d->direction = direction;
129
130 if (d->elapsed > std::chrono::milliseconds::zero()
131 || d->sourceRedirectMode == RedirectMode::Strict) {
132 d->elapsed = d->duration - d->elapsed;
133 }
134
135 if (d->done && d->targetRedirectMode == RedirectMode::Relaxed) {
136 d->done = false;
137 }
138
139 if (d->elapsed >= d->duration) {
140 d->done = true;
141 d->lastTimestamp = std::nullopt;
142 }
143}
144
146{
147 setDirection(d->direction == Forward ? Backward : Forward);
148}
149
150QEasingCurve TimeLine::easingCurve() const
151{
152 return d->easingCurve;
153}
154
155void TimeLine::setEasingCurve(const QEasingCurve &easingCurve)
156{
157 d->easingCurve = easingCurve;
158}
159
160void TimeLine::setEasingCurve(QEasingCurve::Type type)
161{
162 d->easingCurve.setType(type);
163}
164
166{
167 return d->elapsed != std::chrono::milliseconds::zero()
168 && d->elapsed != d->duration;
169}
170
171bool TimeLine::done() const
172{
173 return d->done;
174}
175
177{
178 d->lastTimestamp = std::nullopt;
179 d->elapsed = std::chrono::milliseconds::zero();
180 d->done = false;
181}
182
184{
185 return d->sourceRedirectMode;
186}
187
189{
190 d->sourceRedirectMode = mode;
191}
192
194{
195 return d->targetRedirectMode;
196}
197
199{
200 d->targetRedirectMode = mode;
201}
202
204{
205 d = other.d;
206 return *this;
207}
208
209} // namespace KWin
RedirectMode sourceRedirectMode
Definition timeline.cpp:22
RedirectMode targetRedirectMode
Definition timeline.cpp:23
bool running() const
Definition timeline.cpp:165
TimeLine(std::chrono::milliseconds duration=std::chrono::milliseconds(1000), Direction direction=Forward)
Definition timeline.cpp:26
QEasingCurve easingCurve
Definition timeline.cpp:17
void setSourceRedirectMode(RedirectMode mode)
Definition timeline.cpp:188
qreal progress() const
Definition timeline.cpp:41
qreal value() const
Definition timeline.cpp:46
Direction direction
Definition timeline.cpp:16
TimeLine & operator=(const TimeLine &other)
Definition timeline.cpp:203
void advance(std::chrono::milliseconds timestamp)
Definition timeline.cpp:53
void setDuration(std::chrono::milliseconds duration)
Definition timeline.cpp:103
void setElapsed(std::chrono::milliseconds elapsed)
Definition timeline.cpp:80
void setTargetRedirectMode(RedirectMode mode)
Definition timeline.cpp:198
void setDirection(Direction direction)
Definition timeline.cpp:122
std::chrono::milliseconds duration
Definition timeline.cpp:15
std::chrono::milliseconds elapsed
Definition timeline.cpp:19
void setEasingCurve(const QEasingCurve &easingCurve)
Definition timeline.cpp:155
void toggleDirection()
Definition timeline.cpp:145
Session::Type type
Definition session.cpp:17