aboutsummaryrefslogtreecommitdiffstats
path: root/src/quicklayouts/qquicklayoutitemproxy_p.h
blob: 7d900bd2d6468201469f8bd6e0366265793c40f0 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
// Copyright (C) 2023 The Qt Company Ltd.
// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only

#ifndef QQUICKLAYOUTITEMPROXY_P_H
#define QQUICKLAYOUTITEMPROXY_P_H

//
//  W A R N I N G
//  -------------
//
// This file is not part of the Qt API.  It exists purely as an
// implementation detail.  This header file may change from version to
// version without notice, or even be removed.
//
// We mean it.
//

#include <private/qquickitem_p.h>
#include <private/qquickrectangle_p.h>

class QQuickLayoutItemProxyAttachedData;
class QQuickLayoutItemProxyPrivate;
class QQuickLayoutItemProxy : public QQuickItem
{
    Q_OBJECT

    Q_PROPERTY(QQuickItem *target READ target WRITE setTarget NOTIFY targetChanged)
    QML_NAMED_ELEMENT(LayoutItemProxy)
    QML_ADDED_IN_VERSION(6, 6)

public:
    QQuickLayoutItemProxy(QQuickItem *parent = nullptr);
    ~QQuickLayoutItemProxy() override;

    void geometryChange(const QRectF &newGeom, const QRectF &oldGeom) override;
    void itemChange(ItemChange c, const ItemChangeData &d) override;

    QQuickItem *target() const;
    void setTarget(QQuickItem *newTarget);
    Q_INVOKABLE QQuickItem *effectiveTarget() const;
    void clearTarget();

    void maybeTakeControl();
public slots:
    void updatePos();

private slots:
    // We define some slots to react to changes to the Layout attached properties.
    // They are all named following the same scheme, which allows us to use a macro.
#define propertyForwarding(Property) \
    void target##Property##Changed(); \
    void proxy##Property##Changed();

    propertyForwarding(MinimumWidth)
    propertyForwarding(MinimumHeight)
    propertyForwarding(PreferredWidth)
    propertyForwarding(PreferredHeight)
    propertyForwarding(MaximumWidth)
    propertyForwarding(MaximumHeight)
    propertyForwarding(FillWidth)
    propertyForwarding(FillHeight)
    propertyForwarding(Alignment)
    propertyForwarding(HorizontalStretchFactor)
    propertyForwarding(VerticalStretchFactor)
    propertyForwarding(Margins)
    propertyForwarding(LeftMargin)
    propertyForwarding(TopMargin)
    propertyForwarding(RightMargin)
    propertyForwarding(BottomMargin)
#undef propertyForwarding

signals:
    void targetChanged();

private:
    Q_DECLARE_PRIVATE(QQuickLayoutItemProxy)
};

class QQuickLayoutItemProxyPrivate : public QQuickItemPrivate
{
    Q_DECLARE_PUBLIC(QQuickLayoutItemProxy)

public:
    QQuickLayoutItemProxyPrivate();

    // the target of the LayoutItem
    QQuickItem *target = nullptr;

    // These values are required to know why the Layout property of the proxy changed
    // If it changed because the target changed we should keep the connection valid
    // If a Layout property change is not invoked by the target, it was set
    // explicitly by the application developer and we should disconnect the connection
    // between target and proxy for this property.
    unsigned m_expectProxyMinimumWidthChange : 1;
    unsigned m_expectProxyMinimumHeightChange : 1;
    unsigned m_expectProxyPreferredWidthChange : 1;
    unsigned m_expectProxyPreferredHeightChange : 1;
    unsigned m_expectProxyMaximumWidthChange : 1;
    unsigned m_expectProxyMaximumHeightChange : 1;
    unsigned m_expectProxyFillWidthChange : 1;
    unsigned m_expectProxyFillHeightChange : 1;
    unsigned m_expectProxyAlignmentChange : 1;
    unsigned m_expectProxyHorizontalStretchFactorChange : 1;
    unsigned m_expectProxyVerticalStretchFactorChange : 1;
    unsigned m_expectProxyMarginsChange : 1;
    unsigned m_expectProxyLeftMarginChange : 1;
    unsigned m_expectProxyTopMarginChange : 1;
    unsigned m_expectProxyRightMarginChange : 1;
    unsigned m_expectProxyBottomMarginChange : 1;

    friend class QQuickLayoutItemProxy;
};

class QQuickLayoutItemProxyAttachedData : public QObject
{
    Q_OBJECT

    QML_ANONYMOUS
    Q_PROPERTY(bool proxyHasControl READ proxyHasControl NOTIFY controllingProxyChanged)
    Q_PROPERTY(QQuickLayoutItemProxy* controllingProxy READ getControllingProxy NOTIFY controllingProxyChanged)
    Q_PROPERTY(QQmlListProperty<QQuickLayoutItemProxy> proxies READ getProxies NOTIFY proxiesChanged)

public:
    QQuickLayoutItemProxyAttachedData(QObject *parent);
    ~QQuickLayoutItemProxyAttachedData() override;
    void registerProxy(QQuickLayoutItemProxy *proxy);
    void releaseProxy(QQuickLayoutItemProxy *proxy);
    bool takeControl(QQuickLayoutItemProxy *proxy);
    void releaseControl(QQuickLayoutItemProxy *proxy);
    QQuickLayoutItemProxy *getControllingProxy() const;
    QQmlListProperty<QQuickLayoutItemProxy> getProxies();
    bool proxyHasControl() const;

signals:
    void controlTaken();
    void controlReleased();
    void controllingProxyChanged();
    void proxiesChanged();

private:
    QList<QQuickLayoutItemProxy*> proxies;
    QQuickLayoutItemProxy* controllingProxy;
};

Q_DECLARE_METATYPE(QQuickLayoutItemProxyAttachedData*);

#endif // QQUICKLAYOUTITEMPROXY_P_H