Fluid 1.3.0
Material Design for QtQuick and Qml
Loading...
Searching...
No Matches
inputregion.cpp
Go to the documentation of this file.
1// SPDX-FileCopyrightText: 2022 Pier Luigi Fiorini <pierluigi.fiorini@gmail.com>
2//
3// SPDX-License-Identifier: MPL-2.0
4
5#include <QLoggingCategory>
6
7#include "inputregion.h"
8
9Q_DECLARE_LOGGING_CATEGORY(gLcInputRegion)
10Q_LOGGING_CATEGORY(gLcInputRegion, "fluid.inputregion")
11
12/*
13 * InputArea
14 */
15
16InputArea::InputArea(QObject *parent)
17 : QObject(parent)
18{
19}
20
22{
23 if (m_region)
24 m_region->unregisterArea(this);
25}
26
28{
29 return m_region;
30}
31
33{
34 if (m_initialized) {
35 qCWarning(gLcInputRegion, "Unable to change InputArea::region after initialization");
36 return;
37 }
38
39 if (m_region == region)
40 return;
41
42 m_region = region;
43 Q_EMIT regionChanged(region);
44}
45
47{
48 return m_enabled;
49}
50
51void InputArea::setEnabled(bool enabled)
52{
53 if (m_enabled == enabled)
54 return;
55
56 m_enabled = enabled;
57 Q_EMIT enabledChanged(enabled);
58}
59
60qreal InputArea::x() const
61{
62 return m_x;
63}
64
65void InputArea::setX(qreal x)
66{
67 if (m_x == x)
68 return;
69
70 m_x = x;
71 emit xChanged(x);
72}
73
74qreal InputArea::y() const
75{
76 return m_y;
77}
78
79void InputArea::setY(qreal y)
80{
81 if (m_y == y)
82 return;
83
84 m_y = y;
85 emit yChanged(y);
86}
87
88qreal InputArea::width() const
89{
90 return m_width;
91}
92
93void InputArea::setWidth(qreal width)
94{
95 if (m_width == width)
96 return;
97
98 m_width = width;
99 emit widthChanged(width);
100}
101
102qreal InputArea::height() const
103{
104 return m_height;
105}
106
107void InputArea::setHeight(qreal height)
108{
109 if (m_height == height)
110 return;
111
112 m_height = height;
113 emit heightChanged(height);
114}
115
116QRectF InputArea::rect() const
117{
118 return QRectF(m_x, m_y, m_width, m_height);
119}
120
122{
123 if (m_initialized)
124 return;
125
126 m_initialized = true;
127
128 // Register this area
129 if (m_region)
130 m_region->registerArea(this);
131}
132
133/*
134 * InputRegion
135 */
136
138 : QObject(parent)
139{
140}
141
143{
144 return m_enabled;
145}
146
147void InputRegion::setEnabled(bool enabled)
148{
149 if (m_enabled == enabled)
150 return;
151
152 m_enabled = enabled;
153 Q_EMIT enabledChanged(enabled);
154
155 setInputRegion();
156}
157
158QWindow *InputRegion::window() const
159{
160 return m_window;
161}
162
163void InputRegion::setWindow(QWindow *window)
164{
165 if (m_initialized) {
166 qCWarning(gLcInputRegion, "Unable to change InputRegion::window after initialization");
167 return;
168 }
169
170 if (m_window == window)
171 return;
172
173 m_window = window;
174 Q_EMIT windowChanged(m_window);
175}
176
177QQmlListProperty<InputArea> InputRegion::areas()
178{
179 return QQmlListProperty<InputArea>(
180 this, nullptr,
181 &InputRegion::areasCount,
182 &InputRegion::areaAt
183 );
184}
185
187{
188 if (!m_areas.contains(area)) {
189 connect(area, &InputArea::enabledChanged, this, &InputRegion::setInputRegion);
190 connect(area, &InputArea::xChanged, this, &InputRegion::setInputRegion);
191 connect(area, &InputArea::yChanged, this, &InputRegion::setInputRegion);
192 connect(area, &InputArea::widthChanged, this, &InputRegion::setInputRegion);
193 connect(area, &InputArea::heightChanged, this, &InputRegion::setInputRegion);
194 m_areas.append(area);
195 }
196}
197
199{
200 if (m_areas.removeOne(area)) {
201 disconnect(area, &InputArea::enabledChanged, this, &InputRegion::setInputRegion);
202 disconnect(area, &InputArea::xChanged, this, &InputRegion::setInputRegion);
203 disconnect(area, &InputArea::yChanged, this, &InputRegion::setInputRegion);
204 disconnect(area, &InputArea::widthChanged, this, &InputRegion::setInputRegion);
205 disconnect(area, &InputArea::heightChanged, this, &InputRegion::setInputRegion);
206 }
207}
208
210{
211 if (m_initialized)
212 return;
213
214 // Find the window from the parent, if not specified
215 if (!m_window) {
216 for (auto *p = parent(); p != nullptr; p = p->parent()) {
217 if (auto *w = qobject_cast<QWindow *>(p)) {
218 setWindow(w);
219 break;
220 }
221 }
222 }
223
224 // Initialize
225 m_initialized = true;
226
227 // Set initial mask based on properties set when the component is complete
228 setInputRegion();
229}
230
231qsizetype InputRegion::areasCount(QQmlListProperty<InputArea> *list)
232{
233 return reinterpret_cast<InputRegion *>(list->data)->m_areas.count();
234}
235
236InputArea *InputRegion::areaAt(QQmlListProperty<InputArea> *list, qsizetype index)
237{
238 return reinterpret_cast<InputRegion *>(list->data)->m_areas.at(index);
239}
240
241void InputRegion::setInputRegion()
242{
243 if (!m_window)
244 return;
245
246 // Calculate input region
247 QRegion region;
248 if (m_enabled) {
249 for (auto *a : std::as_const(m_areas)) {
250 if (a->isEnabled()) {
251 //qCDebug(gLcInputRegion) << "Input area" << a << "for" << a->rect().toRect();
252 region += a->rect().toRect();
253 }
254 }
255 }
256
257 // Don't set the same mask twice
258 if (m_window->mask() != region) {
259 if (region.isNull())
260 qCDebug(gLcInputRegion) << "Unset input region from" << m_window;
261 else
262 qCDebug(gLcInputRegion) << "Set" << m_window << "input region to:" << region;
263 m_window->setMask(region);
264 }
265}
void setEnabled(bool enabled)
void yChanged(qreal y)
qreal width
Definition inputregion.h:21
void setY(qreal y)
InputRegion * region
Definition inputregion.h:17
bool isEnabled() const
qreal height
Definition inputregion.h:22
void regionChanged(InputRegion *region)
void componentComplete() override
void heightChanged(qreal height)
bool enabled
Definition inputregion.h:18
QRectF rect() const
void setX(qreal x)
void setHeight(qreal height)
void setRegion(InputRegion *region)
void xChanged(qreal x)
void setWidth(qreal width)
void enabledChanged(bool enabled)
void widthChanged(qreal width)
void registerArea(InputArea *area)
void unregisterArea(InputArea *area)
QWindow * window
Definition inputregion.h:73
void enabledChanged(bool enabled)
void setEnabled(bool enabled)
void componentComplete() override
void setWindow(QWindow *window)
bool isEnabled() const
void windowChanged(QWindow *window)
QQmlListProperty< InputArea > areas
Definition inputregion.h:74
InputRegion(QObject *parent=nullptr)