1/*
2 * SPDX-FileCopyrightText: 2017 Marco Martin <mart@kde.org>
3 * SPDX-FileCopyrightText: 2023 ivan tkachenko <me@ratijas.tk>
4 *
5 * SPDX-License-Identifier: LGPL-2.0-or-later
6 */
7
8#include "alignedsizeattached.h"
9#include <QDebug>
10#include <QQuickItem>
11
12AlignedSizeAttached::AlignedSizeAttached(QObject *parent)
13 : QObject(parent)
14{
15 m_item = qobject_cast<QQuickItem *>(o: parent);
16
17 if (!m_item) {
18 qWarning() << "AlignedSizeAttached attached to" << parent << "Attaching to a non QQuickItem derived object won't work";
19 return;
20 }
21
22 connect(sender: m_item, signal: &QQuickItem::windowChanged, context: this, slot: [this](QQuickWindow *window) {
23 if (m_window) {
24 m_window->removeEventFilter(obj: this);
25 }
26 m_window = qobject_cast<QQuickWindow *>(object: m_item->window());
27 if (!m_window) {
28 return;
29 }
30 m_window->installEventFilter(filterObj: this);
31 dprChanged();
32 });
33 m_window = qobject_cast<QQuickWindow *>(object: m_item->window());
34 if (!m_window) {
35 return;
36 }
37 dprChanged();
38 m_window->installEventFilter(filterObj: this);
39}
40
41AlignedSizeAttached::~AlignedSizeAttached()
42{
43}
44
45qreal AlignedSizeAttached::width() const
46{
47 return m_width;
48}
49
50void AlignedSizeAttached::setWidth(qreal width)
51{
52 if (width == m_width) {
53 return;
54 }
55
56 m_width = width;
57
58 if (m_width >= 0) {
59 m_item->setWidth(alignedWidth());
60 }
61
62 Q_EMIT widthChanged();
63}
64
65void AlignedSizeAttached::resetWidth()
66{
67 m_width = -1.0;
68 Q_EMIT widthChanged();
69}
70
71qreal AlignedSizeAttached::height() const
72{
73 return m_height;
74}
75
76void AlignedSizeAttached::setHeight(qreal height)
77{
78 if (height == m_height) {
79 return;
80 }
81
82 m_height = height;
83
84 if (m_height >= 0) {
85 m_item->setHeight(alignedHeight());
86 }
87
88 Q_EMIT heightChanged();
89}
90
91void AlignedSizeAttached::resetHeight()
92{
93 m_height = -1.0;
94 Q_EMIT heightChanged();
95}
96
97qreal AlignedSizeAttached::alignedWidth() const
98{
99 return std::round(x: m_width * m_dpr) / m_dpr;
100}
101
102qreal AlignedSizeAttached::alignedHeight() const
103{
104 return std::round(x: m_height * m_dpr) / m_dpr;
105}
106
107void AlignedSizeAttached::dprChanged()
108{
109 m_dpr = m_window->effectiveDevicePixelRatio();
110 if (m_width >= 0) {
111 m_item->setWidth(alignedWidth());
112 }
113 if (m_height >= 0) {
114 m_item->setHeight(alignedHeight());
115 }
116}
117
118bool AlignedSizeAttached::eventFilter(QObject *watched, QEvent *event)
119{
120 if (event->type() == QEvent::DevicePixelRatioChange) {
121 dprChanged();
122 }
123 return QObject::eventFilter(watched, event);
124}
125
126AlignedSizeAttached *AlignedSizeAttached::qmlAttachedProperties(QObject *object)
127{
128 return new AlignedSizeAttached(object);
129}
130
131#include "moc_alignedsizeattached.cpp"
132

source code of kirigami/src/primitives/alignedsizeattached.cpp