File indexing completed on 2024-04-28 07:44:50
0001 /* 0002 * SPDX-FileCopyrightText: 2020 Carson Black <uhhadd@gmail.com> 0003 * 0004 * SPDX-License-Identifier: LGPL-2.0-or-later 0005 */ 0006 0007 #include <QQmlProperty> 0008 0009 #include "sizegroup.h" 0010 0011 #define pThis (static_cast<SizeGroup *>(prop->object)) 0012 0013 void SizeGroup::appendItem(QQmlListProperty<QQuickItem> *prop, QQuickItem *value) 0014 { 0015 pThis->m_items << value; 0016 pThis->connectItem(value); 0017 } 0018 0019 qsizetype SizeGroup::itemCount(QQmlListProperty<QQuickItem> *prop) 0020 { 0021 return pThis->m_items.count(); 0022 } 0023 0024 QQuickItem *SizeGroup::itemAt(QQmlListProperty<QQuickItem> *prop, qsizetype index) 0025 { 0026 return pThis->m_items[index]; 0027 } 0028 0029 void SizeGroup::clearItems(QQmlListProperty<QQuickItem> *prop) 0030 { 0031 for (const auto &item : std::as_const(pThis->m_items)) { 0032 QObject::disconnect(pThis->m_connections[item].first); 0033 QObject::disconnect(pThis->m_connections[item].second); 0034 } 0035 pThis->m_items.clear(); 0036 } 0037 0038 void SizeGroup::connectItem(QQuickItem *item) 0039 { 0040 auto conn1 = connect(item, &QQuickItem::implicitWidthChanged, this, [this]() { 0041 adjustItems(Mode::Width); 0042 }); 0043 auto conn2 = connect(item, &QQuickItem::implicitHeightChanged, this, [this]() { 0044 adjustItems(Mode::Height); 0045 }); 0046 m_connections[item] = qMakePair(conn1, conn2); 0047 adjustItems(m_mode); 0048 } 0049 0050 QQmlListProperty<QQuickItem> SizeGroup::items() 0051 { 0052 return QQmlListProperty<QQuickItem>(this, // 0053 nullptr, 0054 appendItem, 0055 itemCount, 0056 itemAt, 0057 clearItems); 0058 } 0059 0060 void SizeGroup::relayout() 0061 { 0062 adjustItems(Mode::Both); 0063 } 0064 0065 void SizeGroup::componentComplete() 0066 { 0067 adjustItems(Mode::Both); 0068 } 0069 0070 void SizeGroup::adjustItems(Mode whatChanged) 0071 { 0072 if (m_mode == Mode::Width && whatChanged == Mode::Height) { 0073 return; 0074 } 0075 if (m_mode == Mode::Height && whatChanged == Mode::Width) { 0076 return; 0077 } 0078 0079 qreal maxHeight = 0.0; 0080 qreal maxWidth = 0.0; 0081 0082 for (const auto &item : std::as_const(m_items)) { 0083 if (item == nullptr) { 0084 continue; 0085 } 0086 0087 switch (m_mode) { 0088 case Mode::Width: 0089 maxWidth = qMax(maxWidth, item->implicitWidth()); 0090 break; 0091 case Mode::Height: 0092 maxHeight = qMax(maxHeight, item->implicitHeight()); 0093 break; 0094 case Mode::Both: 0095 maxWidth = qMax(maxWidth, item->implicitWidth()); 0096 maxHeight = qMax(maxHeight, item->implicitHeight()); 0097 break; 0098 case Mode::None: 0099 break; 0100 } 0101 } 0102 0103 for (const auto &item : std::as_const(m_items)) { 0104 if (item == nullptr) { 0105 continue; 0106 } 0107 0108 if (!qmlEngine(item) || !qmlContext(item)) { 0109 continue; 0110 } 0111 0112 switch (m_mode) { 0113 case Mode::Width: 0114 QQmlProperty(item, QStringLiteral("Layout.preferredWidth"), qmlContext(item)).write(maxWidth); 0115 break; 0116 case Mode::Height: 0117 QQmlProperty(item, QStringLiteral("Layout.preferredHeight"), qmlContext(item)).write(maxHeight); 0118 break; 0119 case Mode::Both: 0120 QQmlProperty(item, QStringLiteral("Layout.preferredWidth"), qmlContext(item)).write(maxWidth); 0121 QQmlProperty(item, QStringLiteral("Layout.preferredHeight"), qmlContext(item)).write(maxHeight); 0122 break; 0123 case Mode::None: 0124 break; 0125 } 0126 } 0127 } 0128 0129 #include "moc_sizegroup.cpp"