diff options
Diffstat (limited to 'src/quicktemplates2')
23 files changed, 239 insertions, 141 deletions
diff --git a/src/quicktemplates2/qquickcontrol.cpp b/src/quicktemplates2/qquickcontrol.cpp index 84f7a6cf..20de449e 100644 --- a/src/quicktemplates2/qquickcontrol.cpp +++ b/src/quicktemplates2/qquickcontrol.cpp @@ -766,10 +766,13 @@ qreal QQuickControl::spacing() const void QQuickControl::setSpacing(qreal spacing) { Q_D(QQuickControl); - if (!qFuzzyCompare(d->spacing, spacing)) { - d->spacing = spacing; - emit spacingChanged(); - } + if (qFuzzyCompare(d->spacing, spacing)) + return; + + qreal oldSpacing = d->spacing; + d->spacing = spacing; + emit spacingChanged(); + spacingChange(spacing, oldSpacing); } void QQuickControl::resetSpacing() @@ -1012,6 +1015,10 @@ void QQuickControl::setHovered(bool hovered) Setting this property propagates the value to all child controls that do not have \c hoverEnabled explicitly set. + You can also enable or disable hover effects for all Qt Quick Controls 2 applications + by setting the \c QT_QUICK_CONTROLS_HOVER_ENABLED \l {Supported Environment Variables + in Qt Quick Controls 2}{environment variable}. + \sa hovered */ bool QQuickControl::isHoverEnabled() const @@ -1287,6 +1294,12 @@ void QQuickControl::mirrorChange() emit mirroredChanged(); } +void QQuickControl::spacingChange(qreal newSpacing, qreal oldSpacing) +{ + Q_UNUSED(newSpacing); + Q_UNUSED(oldSpacing); +} + void QQuickControl::paddingChange(const QMarginsF &newPadding, const QMarginsF &oldPadding) { Q_D(QQuickControl); diff --git a/src/quicktemplates2/qquickcontrol_p.h b/src/quicktemplates2/qquickcontrol_p.h index 7187344a..3bc21684 100644 --- a/src/quicktemplates2/qquickcontrol_p.h +++ b/src/quicktemplates2/qquickcontrol_p.h @@ -189,6 +189,7 @@ protected: virtual void fontChange(const QFont &newFont, const QFont &oldFont); virtual void hoverChange(); virtual void mirrorChange(); + virtual void spacingChange(qreal newSpacing, qreal oldSpacing); virtual void paddingChange(const QMarginsF &newPadding, const QMarginsF &oldPadding); virtual void contentItemChange(QQuickItem *newItem, QQuickItem *oldItem); virtual void localeChange(const QLocale &newLocale, const QLocale &oldLocale); diff --git a/src/quicktemplates2/qquickdialog.cpp b/src/quicktemplates2/qquickdialog.cpp index e747b251..94378a15 100644 --- a/src/quicktemplates2/qquickdialog.cpp +++ b/src/quicktemplates2/qquickdialog.cpp @@ -39,10 +39,6 @@ #include "qquickdialogbuttonbox_p.h" #include "qquickpopupitem_p_p.h" -#include <QtQml/qqmlinfo.h> -#include <QtQml/qqmlcontext.h> -#include <QtQml/qqmlcomponent.h> - QT_BEGIN_NAMESPACE /*! @@ -61,22 +57,19 @@ QT_BEGIN_NAMESPACE \image qtquickcontrols2-page-wireframe.png - \section1 Dialog Buttons + \section1 Dialog Title and Buttons + + Dialog's \l title is displayed by a style-specific title bar that is assigned + as a dialog \l header by default. - Dialog's standard buttons are managed by \l DialogButtonBox. When a button box - is assigned as a dialog \l footer or \l header, the dialog's \l standardButtons - property is forwarded to the respective property of the button box. Furthermore, - the \l {DialogButtonBox::}{accepted()} and \l {DialogButtonBox::}{rejected()} + Dialog's standard buttons are managed by a \l DialogButtonBox that is assigned + as a dialog \l footer by default. The dialog's \l standardButtons property is + forwarded to the respective property of the button box. Furthermore, the + \l {DialogButtonBox::}{accepted()} and \l {DialogButtonBox::}{rejected()} signals of the button box are connected to the respective signals in Dialog. \snippet qtquickcontrols2-dialog.qml 1 - \note If any standard buttons are specified for the dialog but no button box has - been assigned as a footer or header, Dialog automatically creates an instance of - \l buttonBox, and assigns it as a footer or header of the dialog depending on the - value of the \l {DialogButtonBox::}{position} property. All built-in Dialog styles - assign the button box as a footer. - \section1 Modal Dialogs A \l {Popup::}{modal} dialog blocks input to other content beneath @@ -122,45 +115,44 @@ QT_BEGIN_NAMESPACE \sa accepted() */ -void QQuickDialogPrivate::createButtonBox() +QQuickDialog::QQuickDialog(QObject *parent) : + QQuickPopup(*(new QQuickDialogPrivate), parent) { - Q_Q(QQuickDialog); - QQmlContext *context = qmlContext(q); - if (!context || !buttonBoxComponent) - return; + Q_D(QQuickDialog); + d->layout.reset(new QQuickPageLayout(d->popupItem)); +} - QObject *object = buttonBoxComponent->create(context); - QQuickDialogButtonBox *buttonBox = qobject_cast<QQuickDialogButtonBox *>(object); - if (!buttonBox) { - if (object) { - qmlInfo(q) << "buttonBox must be an instance of DialogButtonBox"; - delete object; - } - return; - } +/*! + \qmlproperty string QtQuick.Controls::Dialog::title - if (buttonBox->position() == QQuickDialogButtonBox::Header) { - if (layout->header()) { - qmlInfo(q) << "Custom header detected. Cannot assign buttonBox as a header. No standard buttons will appear in the header."; - delete buttonBox; - } else { - q->setHeader(buttonBox); - } - } else { - if (layout->footer()) { - qmlInfo(q) << "Custom footer detected. Cannot assign buttonBox as a footer. No standard buttons will appear in the footer."; - delete buttonBox; - } else { - q->setFooter(buttonBox); + This property holds the dialog title. + + The title is displayed in the dialog header. + + \code + Dialog { + title: qsTr("About") + + Label { + text: "Lorem ipsum..." } } + \endcode +*/ +QString QQuickDialog::title() const +{ + Q_D(const QQuickDialog); + return d->title; } -QQuickDialog::QQuickDialog(QObject *parent) : - QQuickPopup(*(new QQuickDialogPrivate), parent) +void QQuickDialog::setTitle(const QString &title) { Q_D(QQuickDialog); - d->layout.reset(new QQuickPageLayout(d->popupItem)); + if (d->title == title) + return; + + d->title = title; + emit titleChanged(); } /*! @@ -177,7 +169,7 @@ QQuickDialog::QQuickDialog(QObject *parent) : header automatically sets the respective \l DialogButtonBox::position, \l ToolBar::position, or \l TabBar::position property to \c Header. - \sa footer, buttonBox + \sa footer */ QQuickItem *QQuickDialog::header() const { @@ -224,7 +216,7 @@ void QQuickDialog::setHeader(QQuickItem *header) footer automatically sets the respective \l DialogButtonBox::position, \l ToolBar::position, or \l TabBar::position property to \c Footer. - \sa header, buttonBox + \sa header */ QQuickItem *QQuickDialog::footer() const { @@ -258,33 +250,6 @@ void QQuickDialog::setFooter(QQuickItem *footer) } /*! - \qmlproperty Component QtQuick.Controls::Dialog::buttonBox - - This property holds a delegate for creating a button box. - - A button box is only created if any standard buttons are set. - The \l {DialogButtonBox::}{position} property determines whether - the button box is assigned as a \l header or \l footer. - - \sa standardButtons, header, footer, DialogButtonBox -*/ -QQmlComponent *QQuickDialog::buttonBox() const -{ - Q_D(const QQuickDialog); - return d->buttonBoxComponent; -} - -void QQuickDialog::setButtonBox(QQmlComponent *box) -{ - Q_D(QQuickDialog); - if (d->buttonBoxComponent == box) - return; - - d->buttonBoxComponent = box; - emit buttonBoxChanged(); -} - -/*! \qmlproperty enumeration QtQuick.Controls::Dialog::standardButtons This property holds a combination of standard buttons that are used by the dialog. @@ -312,7 +277,7 @@ void QQuickDialog::setButtonBox(QQmlComponent *box) \value Dialog.Ignore An "Ignore" button defined with the \c AcceptRole. \value Dialog.NoButton An invalid button. - \sa buttonBox, DialogButtonBox + \sa DialogButtonBox */ QPlatformDialogHelper::StandardButtons QQuickDialog::standardButtons() const { @@ -327,12 +292,8 @@ void QQuickDialog::setStandardButtons(QPlatformDialogHelper::StandardButtons but return; d->standardButtons = buttons; - if (isComponentComplete()) { - if (d->buttonBox) - d->buttonBox->setStandardButtons(buttons); - else if (buttons) - d->createButtonBox(); - } + if (d->buttonBox) + d->buttonBox->setStandardButtons(buttons); emit standardButtonsChanged(); } @@ -362,14 +323,6 @@ void QQuickDialog::reject() emit rejected(); } -void QQuickDialog::componentComplete() -{ - Q_D(QQuickDialog); - QQuickPopup::componentComplete(); - if (!d->buttonBox && d->standardButtons) - d->createButtonBox(); -} - void QQuickDialog::geometryChanged(const QRectF &newGeometry, const QRectF &oldGeometry) { Q_D(QQuickDialog); @@ -384,4 +337,11 @@ void QQuickDialog::paddingChange(const QMarginsF &newPadding, const QMarginsF &o d->layout->update(); } +void QQuickDialog::spacingChange(qreal newSpacing, qreal oldSpacing) +{ + Q_D(QQuickDialog); + QQuickPopup::spacingChange(newSpacing, oldSpacing); + d->layout->update(); +} + QT_END_NAMESPACE diff --git a/src/quicktemplates2/qquickdialog_p.h b/src/quicktemplates2/qquickdialog_p.h index 2c7eee95..ea03dddf 100644 --- a/src/quicktemplates2/qquickdialog_p.h +++ b/src/quicktemplates2/qquickdialog_p.h @@ -53,30 +53,29 @@ QT_BEGIN_NAMESPACE -class QQmlComponent; class QQuickDialogPrivate; class Q_QUICKTEMPLATES2_PRIVATE_EXPORT QQuickDialog : public QQuickPopup { Q_OBJECT + Q_PROPERTY(QString title READ title WRITE setTitle NOTIFY titleChanged FINAL) Q_PROPERTY(QQuickItem *header READ header WRITE setHeader NOTIFY headerChanged FINAL) Q_PROPERTY(QQuickItem *footer READ footer WRITE setFooter NOTIFY footerChanged FINAL) - Q_PROPERTY(QQmlComponent *buttonBox READ buttonBox WRITE setButtonBox NOTIFY buttonBoxChanged FINAL) Q_PROPERTY(QPlatformDialogHelper::StandardButtons standardButtons READ standardButtons WRITE setStandardButtons NOTIFY standardButtonsChanged FINAL) Q_FLAGS(QPlatformDialogHelper::StandardButtons) public: explicit QQuickDialog(QObject *parent = nullptr); + QString title() const; + void setTitle(const QString &title); + QQuickItem *header() const; void setHeader(QQuickItem *header); QQuickItem *footer() const; void setFooter(QQuickItem *footer); - QQmlComponent *buttonBox() const; - void setButtonBox(QQmlComponent *box); - QPlatformDialogHelper::StandardButtons standardButtons() const; void setStandardButtons(QPlatformDialogHelper::StandardButtons buttons); @@ -88,15 +87,15 @@ Q_SIGNALS: void accepted(); void rejected(); + void titleChanged(); void headerChanged(); void footerChanged(); - void buttonBoxChanged(); void standardButtonsChanged(); protected: - void componentComplete() override; void geometryChanged(const QRectF &newGeometry, const QRectF &oldGeometry) override; void paddingChange(const QMarginsF &newPadding, const QMarginsF &oldPadding) override; + void spacingChange(qreal newSpacing, qreal oldSpacing) override; private: Q_DISABLE_COPY(QQuickDialog) diff --git a/src/quicktemplates2/qquickdialog_p_p.h b/src/quicktemplates2/qquickdialog_p_p.h index a893690d..5ea84cc8 100644 --- a/src/quicktemplates2/qquickdialog_p_p.h +++ b/src/quicktemplates2/qquickdialog_p_p.h @@ -53,7 +53,6 @@ QT_BEGIN_NAMESPACE -class QQmlComponent; class QQuickDialogButtonBox; class QQuickDialogPrivate : public QQuickPopupPrivate @@ -61,17 +60,15 @@ class QQuickDialogPrivate : public QQuickPopupPrivate Q_DECLARE_PUBLIC(QQuickDialog) public: - QQuickDialogPrivate() : buttonBox(nullptr), buttonBoxComponent(nullptr) { } + QQuickDialogPrivate() : buttonBox(nullptr) { } static QQuickDialogPrivate *get(QQuickDialog *dialog) { return dialog->d_func(); } - void createButtonBox(); - + QString title; QQuickDialogButtonBox *buttonBox; - QQmlComponent *buttonBoxComponent; QScopedPointer<QQuickPageLayout> layout; QPlatformDialogHelper::StandardButtons standardButtons; }; diff --git a/src/quicktemplates2/qquickdrawer.cpp b/src/quicktemplates2/qquickdrawer.cpp index a996b343..839fb1c9 100644 --- a/src/quicktemplates2/qquickdrawer.cpp +++ b/src/quicktemplates2/qquickdrawer.cpp @@ -157,7 +157,9 @@ QT_BEGIN_NAMESPACE the drawer is opened, don't apply a translation. \note On some platforms, certain edges may be reserved for system - gestures and therefore cannot be used with Drawer. + gestures and therefore cannot be used with Drawer. For example, the + top and bottom edges may be reserved for system notifications and + control centers on Android and iOS. \sa SwipeView, {Customizing Drawer}, {Navigation Controls}, {Popup Controls} */ @@ -482,13 +484,13 @@ QQuickDrawer::QQuickDrawer(QObject *parent) : /*! \qmlproperty enumeration QtQuick.Controls::Drawer::edge - This property holds the edge of the content item at which the drawer will + This property holds the edge of the window at which the drawer will open from. The acceptable values are: - \value Qt.TopEdge The top edge of the content item. - \value Qt.LeftEdge The left edge of the content item (default). - \value Qt.RightEdge The right edge of the content item. - \value Qt.BottomEdge The bottom edge of the content item. + \value Qt.TopEdge The top edge of the window. + \value Qt.LeftEdge The left edge of the window (default). + \value Qt.RightEdge The right edge of the window. + \value Qt.BottomEdge The bottom edge of the window. */ Qt::Edge QQuickDrawer::edge() const { @@ -512,8 +514,8 @@ void QQuickDrawer::setEdge(Qt::Edge edge) \qmlproperty real QtQuick.Controls::Drawer::position This property holds the position of the drawer relative to its final - destination. That is, the position will be \c 0 when the drawer - is fully closed, and \c 1 when fully open. + destination. That is, the position will be \c 0.0 when the drawer + is fully closed, and \c 1.0 when fully open. */ qreal QQuickDrawer::position() const { diff --git a/src/quicktemplates2/qquickgroupbox.cpp b/src/quicktemplates2/qquickgroupbox.cpp index 27c325ef..5a5a8005 100644 --- a/src/quicktemplates2/qquickgroupbox.cpp +++ b/src/quicktemplates2/qquickgroupbox.cpp @@ -56,8 +56,8 @@ QT_BEGIN_NAMESPACE or a \l ColumnLayout. Items declared as children of a GroupBox are automatically parented to the - GroupBox's contentItem. Items created dynamically need to be explicitly - parented to the contentItem. + GroupBox's \l {Control::}{contentItem}. Items created dynamically need to be + explicitly parented to the contentItem. If only a single item is used within a GroupBox, it will resize to fit the implicit size of its contained item. This makes it particularly suitable diff --git a/src/quicktemplates2/qquicklabel.cpp b/src/quicktemplates2/qquicklabel.cpp index 03bed16f..b3596022 100644 --- a/src/quicktemplates2/qquicklabel.cpp +++ b/src/quicktemplates2/qquicklabel.cpp @@ -66,7 +66,7 @@ QT_BEGIN_NAMESPACE \snippet qtquickcontrols2-label.qml 1 - You can use the properties of Text to change the appearance of the text as desired: + You can use the properties of \l Text to change the appearance of the text as desired: \qml Label { diff --git a/src/quicktemplates2/qquickpage.cpp b/src/quicktemplates2/qquickpage.cpp index 0098cb93..432c8c63 100644 --- a/src/quicktemplates2/qquickpage.cpp +++ b/src/quicktemplates2/qquickpage.cpp @@ -349,6 +349,13 @@ void QQuickPage::paddingChange(const QMarginsF &newPadding, const QMarginsF &old d->layout->update(); } +void QQuickPage::spacingChange(qreal newSpacing, qreal oldSpacing) +{ + Q_D(QQuickPage); + QQuickControl::spacingChange(newSpacing, oldSpacing); + d->layout->update(); +} + #ifndef QT_NO_ACCESSIBILITY QAccessible::Role QQuickPage::accessibleRole() const { diff --git a/src/quicktemplates2/qquickpage_p.h b/src/quicktemplates2/qquickpage_p.h index c63b11d7..36ba9fff 100644 --- a/src/quicktemplates2/qquickpage_p.h +++ b/src/quicktemplates2/qquickpage_p.h @@ -100,6 +100,7 @@ protected: void contentItemChange(QQuickItem *newItem, QQuickItem *oldItem) override; void geometryChanged(const QRectF &newGeometry, const QRectF &oldGeometry) override; void paddingChange(const QMarginsF &newPadding, const QMarginsF &oldPadding) override; + void spacingChange(qreal newSpacing, qreal oldSpacing) override; #ifndef QT_NO_ACCESSIBILITY QAccessible::Role accessibleRole() const override; diff --git a/src/quicktemplates2/qquickpagelayout.cpp b/src/quicktemplates2/qquickpagelayout.cpp index a1747b47..b787dd08 100644 --- a/src/quicktemplates2/qquickpagelayout.cpp +++ b/src/quicktemplates2/qquickpagelayout.cpp @@ -142,17 +142,19 @@ void QQuickPageLayout::update() const qreal hh = m_header && m_header->isVisible() ? m_header->height() : 0; const qreal fh = m_footer && m_footer->isVisible() ? m_footer->height() : 0; + const qreal hsp = hh > 0 ? m_control->spacing() : 0; + const qreal fsp = fh > 0 ? m_control->spacing() : 0; - content->setY(hh + m_control->topPadding()); + content->setY(m_control->topPadding() + hh + hsp); content->setX(m_control->leftPadding()); content->setWidth(m_control->availableWidth()); - content->setHeight(m_control->availableHeight() - hh - fh); + content->setHeight(m_control->availableHeight() - hh - fh - hsp - fsp); if (m_header) m_header->setWidth(m_control->width()); if (m_footer) { - m_footer->setY(m_control->height() - fh); + m_footer->setY(m_control->height() - m_footer->height()); m_footer->setWidth(m_control->width()); } } diff --git a/src/quicktemplates2/qquickpopup.cpp b/src/quicktemplates2/qquickpopup.cpp index 13dd1a4d..a7927d19 100644 --- a/src/quicktemplates2/qquickpopup.cpp +++ b/src/quicktemplates2/qquickpopup.cpp @@ -123,6 +123,7 @@ QQuickPopupPrivate::QQuickPopupPrivate() , hasDim(false) , visible(false) , complete(false) + , positioning(false) , hasWidth(false) , hasHeight(false) , hasTopMargin(false) @@ -717,6 +718,35 @@ qreal QQuickPopup::availableHeight() const } /*! + \since QtQuick.Controls 2.1 + \qmlproperty real QtQuick.Controls::Popup::spacing + + This property holds the spacing. + + Spacing is useful for popups that have multiple or repetitive building + blocks. For example, some styles use spacing to determine the distance + between the header, content, and footer of \l Dialog. Spacing is not + enforced by Popup, so each style may interpret it differently, and some + may ignore it altogether. +*/ +qreal QQuickPopup::spacing() const +{ + Q_D(const QQuickPopup); + return d->popupItem->spacing(); +} + +void QQuickPopup::setSpacing(qreal spacing) +{ + Q_D(QQuickPopup); + d->popupItem->setSpacing(spacing); +} + +void QQuickPopup::resetSpacing() +{ + setSpacing(0); +} + +/*! \qmlproperty real QtQuick.Controls::Popup::margins This property holds the default margins around the popup. @@ -1740,6 +1770,13 @@ void QQuickPopup::paddingChange(const QMarginsF &newPadding, const QMarginsF &ol emit availableHeightChanged(); } +void QQuickPopup::spacingChange(qreal newSpacing, qreal oldSpacing) +{ + Q_UNUSED(newSpacing); + Q_UNUSED(oldSpacing); + emit spacingChanged(); +} + QFont QQuickPopup::defaultFont() const { return QQuickControlPrivate::themeFont(QPlatformTheme::SystemFont); diff --git a/src/quicktemplates2/qquickpopup_p.h b/src/quicktemplates2/qquickpopup_p.h index a024c68f..de42b793 100644 --- a/src/quicktemplates2/qquickpopup_p.h +++ b/src/quicktemplates2/qquickpopup_p.h @@ -84,6 +84,7 @@ class Q_QUICKTEMPLATES2_PRIVATE_EXPORT QQuickPopup : public QObject, public QQml Q_PROPERTY(qreal contentHeight READ contentHeight WRITE setContentHeight NOTIFY contentHeightChanged FINAL) Q_PROPERTY(qreal availableWidth READ availableWidth NOTIFY availableWidthChanged FINAL) Q_PROPERTY(qreal availableHeight READ availableHeight NOTIFY availableHeightChanged FINAL) + Q_PROPERTY(qreal spacing READ spacing WRITE setSpacing RESET resetSpacing NOTIFY spacingChanged FINAL REVISION 1) Q_PROPERTY(qreal margins READ margins WRITE setMargins RESET resetMargins NOTIFY marginsChanged FINAL) Q_PROPERTY(qreal topMargin READ topMargin WRITE setTopMargin RESET resetTopMargin NOTIFY topMarginChanged FINAL) Q_PROPERTY(qreal leftMargin READ leftMargin WRITE setLeftMargin RESET resetLeftMargin NOTIFY leftMarginChanged FINAL) @@ -154,6 +155,10 @@ public: qreal availableWidth() const; qreal availableHeight() const; + qreal spacing() const; + void setSpacing(qreal spacing); + void resetSpacing(); + qreal margins() const; void setMargins(qreal margins); void resetMargins(); @@ -293,6 +298,7 @@ Q_SIGNALS: void contentHeightChanged(); void availableWidthChanged(); void availableHeightChanged(); + Q_REVISION(1) void spacingChanged(); void marginsChanged(); void topMarginChanged(); void leftMarginChanged(); @@ -354,6 +360,7 @@ protected: virtual void itemChange(QQuickItem::ItemChange change, const QQuickItem::ItemChangeData &data); virtual void marginsChange(const QMarginsF &newMargins, const QMarginsF &oldMargins); virtual void paddingChange(const QMarginsF &newPadding, const QMarginsF &oldPadding); + virtual void spacingChange(qreal newSpacing, qreal oldSpacing); virtual QFont defaultFont() const; diff --git a/src/quicktemplates2/qquickpopup_p_p.h b/src/quicktemplates2/qquickpopup_p_p.h index 56baaa36..1d25f922 100644 --- a/src/quicktemplates2/qquickpopup_p_p.h +++ b/src/quicktemplates2/qquickpopup_p_p.h @@ -123,6 +123,7 @@ public: bool hasDim; bool visible; bool complete; + bool positioning; bool hasWidth; bool hasHeight; bool hasTopMargin; diff --git a/src/quicktemplates2/qquickpopupitem.cpp b/src/quicktemplates2/qquickpopupitem.cpp index b599b145..b939d57c 100644 --- a/src/quicktemplates2/qquickpopupitem.cpp +++ b/src/quicktemplates2/qquickpopupitem.cpp @@ -103,6 +103,12 @@ QQuickPopupItem::QQuickPopupItem(QQuickPopup *popup) : // connect(QGuiApplication::styleHints(), &QStyleHints::useHoverEffectsChanged, this, &QQuickItem::setAcceptHoverEvents); } +void QQuickPopupItem::updatePolish() +{ + Q_D(QQuickPopupItem); + return QQuickPopupPrivate::get(d->popup)->reposition(); +} + bool QQuickPopupItem::childMouseEventFilter(QQuickItem *child, QEvent *event) { Q_D(QQuickPopupItem); diff --git a/src/quicktemplates2/qquickpopupitem_p_p.h b/src/quicktemplates2/qquickpopupitem_p_p.h index a72f5646..4b675010 100644 --- a/src/quicktemplates2/qquickpopupitem_p_p.h +++ b/src/quicktemplates2/qquickpopupitem_p_p.h @@ -63,6 +63,8 @@ public: explicit QQuickPopupItem(QQuickPopup *popup); protected: + void updatePolish() override; + bool childMouseEventFilter(QQuickItem *child, QEvent *event) override; void focusInEvent(QFocusEvent *event) override; void focusOutEvent(QFocusEvent *event) override; diff --git a/src/quicktemplates2/qquickpopuppositioner.cpp b/src/quicktemplates2/qquickpopuppositioner.cpp index cdd9332f..762b6d30 100644 --- a/src/quicktemplates2/qquickpopuppositioner.cpp +++ b/src/quicktemplates2/qquickpopuppositioner.cpp @@ -50,6 +50,7 @@ static const QQuickItemPrivate::ChangeTypes ItemChangeTypes = QQuickItemPrivate: | QQuickItemPrivate::Parent; QQuickPopupPositioner::QQuickPopupPositioner(QQuickPopup *popup) : + m_positioning(false), m_parentItem(nullptr), m_popup(popup) { @@ -96,6 +97,11 @@ void QQuickPopupPositioner::reposition() if (!popupItem->isVisible()) return; + if (m_positioning) { + popupItem->polish(); + return; + } + const qreal w = popupItem->width(); const qreal h = popupItem->height(); const qreal iw = popupItem->implicitWidth(); @@ -205,6 +211,8 @@ void QQuickPopupPositioner::reposition() } } + m_positioning = true; + popupItem->setPosition(rect.topLeft()); const QPointF effectivePos = m_parentItem ? m_parentItem->mapFromScene(rect.topLeft()) : rect.topLeft(); @@ -221,6 +229,8 @@ void QQuickPopupPositioner::reposition() popupItem->setWidth(rect.width()); if (!p->hasHeight && heightAdjusted && rect.height() > 0) popupItem->setHeight(rect.height()); + + m_positioning = false; } void QQuickPopupPositioner::itemGeometryChanged(QQuickItem *, QQuickGeometryChange, const QRectF &) diff --git a/src/quicktemplates2/qquickpopuppositioner_p_p.h b/src/quicktemplates2/qquickpopuppositioner_p_p.h index 10f5465a..8d3c6386 100644 --- a/src/quicktemplates2/qquickpopuppositioner_p_p.h +++ b/src/quicktemplates2/qquickpopuppositioner_p_p.h @@ -75,6 +75,7 @@ private: void removeAncestorListeners(QQuickItem *item); void addAncestorListeners(QQuickItem *item); + bool m_positioning; QQuickItem *m_parentItem; QQuickPopup *m_popup; }; diff --git a/src/quicktemplates2/qquickscrollbar.cpp b/src/quicktemplates2/qquickscrollbar.cpp index ebccbcba..06cc8832 100644 --- a/src/quicktemplates2/qquickscrollbar.cpp +++ b/src/quicktemplates2/qquickscrollbar.cpp @@ -65,9 +65,9 @@ QT_BEGIN_NAMESPACE } \endcode - \note When ScrollBar is attached \l {ScrollBar::vertical}{vertically} or - \l {ScrollBar::horizontal}{horizontally} to a Flickable, its geometry and - the following properties are automatically set and updated as appropriate: + When ScrollBar is attached \l {ScrollBar::vertical}{vertically} or + \l {ScrollBar::horizontal}{horizontally} to a Flickable, the following + properties are automatically set and updated as appropriate: \list \li \l orientation \li \l position @@ -75,6 +75,29 @@ QT_BEGIN_NAMESPACE \li \l active \endlist + An attached ScrollBar re-parents itself to the target Flickable. A vertically + attached ScrollBar resizes itself to the height of the Flickable, and positions + itself to either side of it based on the \l {Control::mirrored}{layout direction}. + A horizontally attached ScrollBar resizes itself to the width of the Flickable, + and positions itself to the bottom. The automatic geometry management can be disabled + by specifying another parent for the attached ScrollBar. This can be useful, for + example, if the ScrollBar should be placed outside a clipping Flickable. This is + demonstrated by the following example: + + \code + Flickable { + id: flickable + clip: true + // ... + ScrollBar.vertical: ScrollBar { + parent: flickable.parent + anchors.top: flickable.top + anchors.left: flickable.right + anchors.bottom: flickable.bottom + } + } + \endcode + Notice that ScrollBar does not filter key events of the Flickable it is attached to. The following example illustrates how to implement scrolling with up and down keys: @@ -477,6 +500,8 @@ void QQuickScrollBarAttachedPrivate::mirrorVertical() void QQuickScrollBarAttachedPrivate::layoutHorizontal(bool move) { Q_ASSERT(horizontal && flickable); + if (horizontal->parentItem() != flickable) + return; horizontal->setWidth(flickable->width()); if (move) horizontal->setY(flickable->height() - horizontal->height()); @@ -485,6 +510,8 @@ void QQuickScrollBarAttachedPrivate::layoutHorizontal(bool move) void QQuickScrollBarAttachedPrivate::layoutVertical(bool move) { Q_ASSERT(vertical && flickable); + if (vertical->parentItem() != flickable) + return; vertical->setHeight(flickable->height()); if (move) vertical->setX(vertical->isMirrored() ? 0 : flickable->width() - vertical->width()); diff --git a/src/quicktemplates2/qquickscrollindicator.cpp b/src/quicktemplates2/qquickscrollindicator.cpp index b1a3e4ec..6145a5b3 100644 --- a/src/quicktemplates2/qquickscrollindicator.cpp +++ b/src/quicktemplates2/qquickscrollindicator.cpp @@ -65,9 +65,9 @@ QT_BEGIN_NAMESPACE } \endcode - \note When ScrollIndicator is attached \l {ScrollIndicator::vertical}{vertically} - or \l {ScrollIndicator::horizontal}{horizontally} to a Flickable, its geometry and - the following properties are automatically set and updated as appropriate: + When ScrollIndicator is attached \l {ScrollIndicator::vertical}{vertically} or + \l {ScrollIndicator::horizontal}{horizontally} to a Flickable, the following + properties are automatically set and updated as appropriate: \list \li \l orientation \li \l position @@ -75,6 +75,29 @@ QT_BEGIN_NAMESPACE \li \l active \endlist + An attached ScrollIndicator re-parents itself to the target Flickable. A vertically + attached ScrollIndicator resizes itself to the height of the Flickable, and positions + itself to either side of it based on the \l {Control::mirrored}{layout direction}. + A horizontally attached ScrollIndicator resizes itself to the width of the Flickable, + and positions itself to the bottom. The automatic geometry management can be disabled + by specifying another parent for the attached ScrollIndicator. This can be useful, for + example, if the ScrollIndicator should be placed outside a clipping Flickable. This is + demonstrated by the following example: + + \code + Flickable { + id: flickable + clip: true + // ... + ScrollIndicator.vertical: ScrollIndicator { + parent: flickable.parent + anchors.top: flickable.top + anchors.left: flickable.right + anchors.bottom: flickable.bottom + } + } + \endcode + Horizontal and vertical scroll indicators do not share the \l active state with each other by default. In order to keep both indicators visible whilst scrolling to either direction, establish a two-way binding between the active states as @@ -268,6 +291,8 @@ void QQuickScrollIndicatorAttachedPrivate::activateVertical() void QQuickScrollIndicatorAttachedPrivate::layoutHorizontal(bool move) { Q_ASSERT(horizontal && flickable); + if (horizontal->parentItem() != flickable) + return; horizontal->setWidth(flickable->width()); if (move) horizontal->setY(flickable->height() - horizontal->height()); @@ -276,6 +301,8 @@ void QQuickScrollIndicatorAttachedPrivate::layoutHorizontal(bool move) void QQuickScrollIndicatorAttachedPrivate::layoutVertical(bool move) { Q_ASSERT(vertical && flickable); + if (vertical->parentItem() != flickable) + return; vertical->setHeight(flickable->height()); if (move && !QQuickItemPrivate::get(vertical)->isMirrored()) vertical->setX(flickable->width() - vertical->width()); diff --git a/src/quicktemplates2/qquickswitch.cpp b/src/quicktemplates2/qquickswitch.cpp index a7d17e86..8c3d9f0b 100644 --- a/src/quicktemplates2/qquickswitch.cpp +++ b/src/quicktemplates2/qquickswitch.cpp @@ -57,17 +57,11 @@ QT_BEGIN_NAMESPACE Switch is an option button that can be dragged or toggled on (checked) or off (unchecked). Switches are typically used to select between two states. + For larger sets of options, such as those in a list, consider using + \l SwitchDelegate instead. - \table - \row \li \image qtquickcontrols2-switch-normal.png - \li A switch in its normal state. - \row \li \image qtquickcontrols2-switch-checked.png - \li A switch that is checked. - \row \li \image qtquickcontrols2-switch-focused.png - \li A switch that has active focus. - \row \li \image qtquickcontrols2-switch-disabled.png - \li A switch that is disabled. - \endtable + Switch inherits its API from \l AbstractButton. For instance, the state + of the switch can be set with the \l {AbstractButton::}{checked} property. \code ColumnLayout { diff --git a/src/quicktemplates2/qquickswitchdelegate.cpp b/src/quicktemplates2/qquickswitchdelegate.cpp index 62b677e5..edfb15d5 100644 --- a/src/quicktemplates2/qquickswitchdelegate.cpp +++ b/src/quicktemplates2/qquickswitchdelegate.cpp @@ -53,9 +53,13 @@ QT_BEGIN_NAMESPACE SwitchDelegate presents an item delegate that can be toggled on (checked) or off (unchecked). Switch delegates are typically used to select one or more - options from a set of options. + options from a set of options. For smaller sets of options, or for options + that need to be uniquely identifiable, consider using \l Switch instead. - The state of the check delegate can be set with the + SwitchDelegate inherits its API from \l ItemDelegate, which is inherited + from \l AbstractButton. For instance, you can set \l {AbstractButton::text}{text}, + and react to \l {AbstractButton::clicked}{clicks} using the \l AbstractButton + API. The state of the switch delegate can be set with the \l {AbstractButton::}{checked} property. \code diff --git a/src/quicktemplates2/qquicktextarea.cpp b/src/quicktemplates2/qquicktextarea.cpp index 9a5590a5..7d15a428 100644 --- a/src/quicktemplates2/qquicktextarea.cpp +++ b/src/quicktemplates2/qquicktextarea.cpp @@ -79,6 +79,8 @@ QT_BEGIN_NAMESPACE decoration of the TextArea scrolls together with the rest of the scrollable content. + \section2 Scrollable TextArea + If you want to make a TextArea scrollable, for example, when it covers an entire application page, attach it to a \l Flickable and combine with a \l ScrollBar or \l ScrollIndicator. @@ -87,7 +89,7 @@ QT_BEGIN_NAMESPACE \snippet qtquickcontrols2-textarea-flickable.qml 1 - A TextArea that is attached to a Flickable does the following: + A TextArea that is attached to a \l Flickable does the following: \list \li Sets the content size automatically @@ -755,9 +757,7 @@ QQuickTextAreaAttached::~QQuickTextAreaAttached() This property attaches a text area to a \l Flickable. - \snippet qtquickcontrols2-textarea-flickable.qml 1 - - \sa ScrollBar, ScrollIndicator + \sa ScrollBar, ScrollIndicator, {Scrollable TextArea} */ QQuickTextArea *QQuickTextAreaAttached::flickable() const { |