aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--.qmake.conf2
-rw-r--r--src/imports/calendar/plugins.qmltypes23
-rw-r--r--src/imports/controls/SplitView.qml55
-rw-r--r--src/imports/controls/controls.pri1
-rw-r--r--src/imports/controls/controls.pro2
-rw-r--r--src/imports/controls/doc/images/qtquickcontrols2-splitview-custom.pngbin0 -> 383 bytes
-rw-r--r--src/imports/controls/doc/snippets/qtquickcontrols2-splitview-custom.qml57
-rw-r--r--src/imports/controls/doc/src/includes/qquickicon.qdocinc6
-rw-r--r--src/imports/controls/doc/src/qtquickcontrols2-customize.qdoc9
-rw-r--r--src/imports/controls/doc/src/qtquickcontrols2-differences.qdoc19
-rw-r--r--src/imports/controls/doc/src/qtquickcontrols2-index.qdoc2
-rw-r--r--src/imports/controls/fusion/SplitView.qml56
-rw-r--r--src/imports/controls/fusion/dependencies.json7
-rw-r--r--src/imports/controls/fusion/fusion.pri1
-rw-r--r--src/imports/controls/fusion/fusion.pro4
-rw-r--r--src/imports/controls/fusion/plugins.qmltypes72
-rw-r--r--src/imports/controls/fusion/qquickfusionstyle.cpp2
-rw-r--r--src/imports/controls/imagine/SplitView.qml63
-rw-r--r--src/imports/controls/imagine/dependencies.json7
-rw-r--r--src/imports/controls/imagine/design/imagine.sketchbin293192 -> 164993 bytes
-rw-r--r--src/imports/controls/imagine/images/splitview-handle-disabled.pngbin0 -> 93 bytes
-rw-r--r--src/imports/controls/imagine/images/splitview-handle-disabled@2x.pngbin0 -> 99 bytes
-rw-r--r--src/imports/controls/imagine/images/splitview-handle-disabled@3x.pngbin0 -> 112 bytes
-rw-r--r--src/imports/controls/imagine/images/splitview-handle-disabled@4x.pngbin0 -> 130 bytes
-rw-r--r--src/imports/controls/imagine/images/splitview-handle-hovered.pngbin0 -> 93 bytes
-rw-r--r--src/imports/controls/imagine/images/splitview-handle-hovered@2x.pngbin0 -> 99 bytes
-rw-r--r--src/imports/controls/imagine/images/splitview-handle-hovered@3x.pngbin0 -> 112 bytes
-rw-r--r--src/imports/controls/imagine/images/splitview-handle-hovered@4x.pngbin0 -> 130 bytes
-rw-r--r--src/imports/controls/imagine/images/splitview-handle-pressed.pngbin0 -> 93 bytes
-rw-r--r--src/imports/controls/imagine/images/splitview-handle-pressed@2x.pngbin0 -> 99 bytes
-rw-r--r--src/imports/controls/imagine/images/splitview-handle-pressed@3x.pngbin0 -> 112 bytes
-rw-r--r--src/imports/controls/imagine/images/splitview-handle-pressed@4x.pngbin0 -> 129 bytes
-rw-r--r--src/imports/controls/imagine/images/splitview-handle.pngbin0 -> 93 bytes
-rw-r--r--src/imports/controls/imagine/images/splitview-handle@2x.pngbin0 -> 99 bytes
-rw-r--r--src/imports/controls/imagine/images/splitview-handle@3x.pngbin0 -> 112 bytes
-rw-r--r--src/imports/controls/imagine/images/splitview-handle@4x.pngbin0 -> 130 bytes
-rw-r--r--src/imports/controls/imagine/imagine.pri1
-rw-r--r--src/imports/controls/imagine/imagine.pro4
-rw-r--r--src/imports/controls/imagine/plugins.qmltypes43
-rw-r--r--src/imports/controls/material/SplitView.qml74
-rw-r--r--src/imports/controls/material/dependencies.json7
-rw-r--r--src/imports/controls/material/material.pri1
-rw-r--r--src/imports/controls/material/material.pro4
-rw-r--r--src/imports/controls/material/plugins.qmltypes192
-rw-r--r--src/imports/controls/plugins.qmltypes1837
-rw-r--r--src/imports/controls/qtquickcontrols2plugin.cpp6
-rw-r--r--src/imports/controls/universal/SplitView.qml56
-rw-r--r--src/imports/controls/universal/dependencies.json7
-rw-r--r--src/imports/controls/universal/plugins.qmltypes82
-rw-r--r--src/imports/controls/universal/universal.pri1
-rw-r--r--src/imports/controls/universal/universal.pro4
-rw-r--r--src/imports/platform/plugins.qmltypes35
-rw-r--r--src/imports/templates/plugins.qmltypes43
-rw-r--r--src/imports/templates/qtquicktemplates2plugin.cpp8
-rw-r--r--src/imports/templates/templates.pro2
-rw-r--r--src/quickcontrols2/qquickiconlabel.cpp2
-rw-r--r--src/quickcontrols2/qquicktumblerview.cpp15
-rw-r--r--src/quicktemplates2/qquickicon.cpp28
-rw-r--r--src/quicktemplates2/qquickicon_p.h5
-rw-r--r--src/quicktemplates2/qquicksplitview.cpp2049
-rw-r--r--src/quicktemplates2/qquicksplitview_p.h218
-rw-r--r--src/quicktemplates2/qquicksplitview_p_p.h178
-rw-r--r--src/quicktemplates2/qquicktumbler.cpp37
-rw-r--r--src/quicktemplates2/qquicktumbler_p_p.h2
-rw-r--r--src/quicktemplates2/quicktemplates2.pri2
-rw-r--r--tests/auto/controls/data/splitview/fillItemInMiddle.qml77
-rw-r--r--tests/auto/controls/data/splitview/fillItemOnLeft.qml77
-rw-r--r--tests/auto/controls/data/splitview/fillItemOnTop.qml78
-rw-r--r--tests/auto/controls/data/tst_splitview.qml1953
-rw-r--r--tests/auto/controls/default/tst_default.cpp1
-rw-r--r--tests/auto/controls/fusion/tst_fusion.cpp1
-rw-r--r--tests/auto/controls/imagine/tst_imagine.cpp1
-rw-r--r--tests/auto/controls/material/tst_material.cpp1
-rw-r--r--tests/auto/controls/universal/tst_universal.cpp1
-rw-r--r--tests/auto/shared/qtest_quickcontrols.h4
-rw-r--r--tests/manual/gifs/gifrecorder.cpp78
-rw-r--r--tests/manual/gifs/tst_gifs.cpp4
-rw-r--r--tests/manual/testbench/controls/SplitView.qml79
-rw-r--r--tests/manual/testbench/qml.qrc1
79 files changed, 5793 insertions, 1894 deletions
diff --git a/.qmake.conf b/.qmake.conf
index 953a3db2..1a8da95c 100644
--- a/.qmake.conf
+++ b/.qmake.conf
@@ -4,4 +4,4 @@ DEFINES += QT_NO_FOREACH
QQC2_SOURCE_TREE = $$PWD
-MODULE_VERSION = 5.12.3
+MODULE_VERSION = 5.13.0
diff --git a/src/imports/calendar/plugins.qmltypes b/src/imports/calendar/plugins.qmltypes
index ef9a5d49..76902876 100644
--- a/src/imports/calendar/plugins.qmltypes
+++ b/src/imports/calendar/plugins.qmltypes
@@ -7,7 +7,7 @@ import QtQuick.tooling 1.2
// 'qmlplugindump -nonrelocatable Qt.labs.calendar 1.0'
Module {
- dependencies: ["QtQuick 2.6"]
+ dependencies: ["QtQuick 2.12"]
Component {
name: "QQuickCalendar"
prototype: "QObject"
@@ -86,8 +86,29 @@ Module {
Property { name: "wheelEnabled"; type: "bool" }
Property { name: "background"; type: "QQuickItem"; isPointer: true }
Property { name: "contentItem"; type: "QQuickItem"; isPointer: true }
+ Property { name: "baselineOffset"; type: "double" }
Property { name: "palette"; revision: 3; type: "QPalette" }
+ Property { name: "horizontalPadding"; revision: 5; type: "double" }
+ Property { name: "verticalPadding"; revision: 5; type: "double" }
+ Property { name: "implicitContentWidth"; revision: 5; type: "double"; isReadonly: true }
+ Property { name: "implicitContentHeight"; revision: 5; type: "double"; isReadonly: true }
+ Property { name: "implicitBackgroundWidth"; revision: 5; type: "double"; isReadonly: true }
+ Property { name: "implicitBackgroundHeight"; revision: 5; type: "double"; isReadonly: true }
+ Property { name: "topInset"; revision: 5; type: "double" }
+ Property { name: "leftInset"; revision: 5; type: "double" }
+ Property { name: "rightInset"; revision: 5; type: "double" }
+ Property { name: "bottomInset"; revision: 5; type: "double" }
Signal { name: "paletteChanged"; revision: 3 }
+ Signal { name: "horizontalPaddingChanged"; revision: 5 }
+ Signal { name: "verticalPaddingChanged"; revision: 5 }
+ Signal { name: "implicitContentWidthChanged"; revision: 5 }
+ Signal { name: "implicitContentHeightChanged"; revision: 5 }
+ Signal { name: "implicitBackgroundWidthChanged"; revision: 5 }
+ Signal { name: "implicitBackgroundHeightChanged"; revision: 5 }
+ Signal { name: "topInsetChanged"; revision: 5 }
+ Signal { name: "leftInsetChanged"; revision: 5 }
+ Signal { name: "rightInsetChanged"; revision: 5 }
+ Signal { name: "bottomInsetChanged"; revision: 5 }
}
Component {
name: "QQuickDayOfWeekRow"
diff --git a/src/imports/controls/SplitView.qml b/src/imports/controls/SplitView.qml
new file mode 100644
index 00000000..9d37a83e
--- /dev/null
+++ b/src/imports/controls/SplitView.qml
@@ -0,0 +1,55 @@
+/****************************************************************************
+**
+** Copyright (C) 2018 The Qt Company Ltd.
+** Contact: http://www.qt.io/licensing/
+**
+** This file is part of the Qt Quick Controls 2 module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL3$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see http://www.qt.io/terms-conditions. For further
+** information use the contact form at http://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPLv3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or later as published by the Free
+** Software Foundation and appearing in the file LICENSE.GPL included in
+** the packaging of this file. Please review the following information to
+** ensure the GNU General Public License version 2.0 requirements will be
+** met: http://www.gnu.org/licenses/gpl-2.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick 2.13
+import QtQuick.Templates 2.13 as T
+import QtQuick.Controls 2.13
+import QtQuick.Controls.impl 2.13
+
+T.SplitView {
+ id: control
+ implicitWidth: Math.max(implicitBackgroundWidth + leftInset + rightInset,
+ implicitContentWidth + leftPadding + rightPadding)
+ implicitHeight: Math.max(implicitBackgroundHeight + topInset + bottomInset,
+ implicitContentHeight + topPadding + bottomPadding)
+
+ handle: Rectangle {
+ implicitWidth: control.orientation === Qt.Horizontal ? 6 : control.width
+ implicitHeight: control.orientation === Qt.Horizontal ? control.height : 6
+ color: T.SplitHandle.pressed ? control.palette.mid
+ : (T.SplitHandle.hovered ? control.palette.midlight : control.palette.button)
+ }
+}
diff --git a/src/imports/controls/controls.pri b/src/imports/controls/controls.pri
index 675fcf39..fbf5d075 100644
--- a/src/imports/controls/controls.pri
+++ b/src/imports/controls/controls.pri
@@ -53,6 +53,7 @@ QML_FILES += \
$$PWD/ScrollView.qml \
$$PWD/Slider.qml \
$$PWD/SpinBox.qml \
+ $$PWD/SplitView.qml \
$$PWD/StackView.qml \
$$PWD/SwipeDelegate.qml \
$$PWD/Switch.qml \
diff --git a/src/imports/controls/controls.pro b/src/imports/controls/controls.pro
index db0d14ae..2aeaf9ab 100644
--- a/src/imports/controls/controls.pro
+++ b/src/imports/controls/controls.pro
@@ -1,6 +1,6 @@
TARGET = qtquickcontrols2plugin
TARGETPATH = QtQuick/Controls.2
-IMPORT_VERSION = 2.5
+IMPORT_VERSION = 2.$$QT_MINOR_VERSION
QT += qml quick
QT_PRIVATE += core-private gui-private qml-private quick-private quicktemplates2-private quickcontrols2-private
diff --git a/src/imports/controls/doc/images/qtquickcontrols2-splitview-custom.png b/src/imports/controls/doc/images/qtquickcontrols2-splitview-custom.png
new file mode 100644
index 00000000..7afd3ff8
--- /dev/null
+++ b/src/imports/controls/doc/images/qtquickcontrols2-splitview-custom.png
Binary files differ
diff --git a/src/imports/controls/doc/snippets/qtquickcontrols2-splitview-custom.qml b/src/imports/controls/doc/snippets/qtquickcontrols2-splitview-custom.qml
new file mode 100644
index 00000000..96e8ad2f
--- /dev/null
+++ b/src/imports/controls/doc/snippets/qtquickcontrols2-splitview-custom.qml
@@ -0,0 +1,57 @@
+/****************************************************************************
+**
+** Copyright (C) 2018 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the documentation of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:FDL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Free Documentation License Usage
+** Alternatively, this file may be used under the terms of the GNU Free
+** Documentation License version 1.3 as published by the Free Software
+** Foundation and appearing in the file included in the packaging of
+** this file. Please review the following information to ensure
+** the GNU Free Documentation License version 1.3 requirements
+** will be met: https://www.gnu.org/licenses/fdl-1.3.html.
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick 2.13
+import QtQuick.Controls 2.13
+
+Item {
+ width: 200
+ height: 100
+
+ //! [1]
+ SplitView {
+ id: splitView
+ anchors.fill: parent
+
+ handle: Rectangle {
+ implicitWidth: 4
+ implicitHeight: 4
+ color: SplitHandle.pressed ? "#81e889"
+ : (SplitHandle.hovered ? Qt.lighter("#c2f4c6", 1.1) : "#c2f4c6")
+ }
+
+ Rectangle {
+ implicitWidth: 150
+ color: "#444"
+ }
+ Rectangle {
+ implicitWidth: 50
+ color: "#666"
+ }
+ }
+ //! [1]
+}
diff --git a/src/imports/controls/doc/src/includes/qquickicon.qdocinc b/src/imports/controls/doc/src/includes/qquickicon.qdocinc
index a6ab90bb..ba7cede9 100644
--- a/src/imports/controls/doc/src/includes/qquickicon.qdocinc
+++ b/src/imports/controls/doc/src/includes/qquickicon.qdocinc
@@ -38,5 +38,11 @@
The icon is tinted with the specified color, unless the color is
set to \c "transparent".
+
+\row
+ \li cache
+ \li This property specifies whether the icon should be cached.
+
+ The default value is true.
\endtable
//! [grouped-properties]
diff --git a/src/imports/controls/doc/src/qtquickcontrols2-customize.qdoc b/src/imports/controls/doc/src/qtquickcontrols2-customize.qdoc
index d50e4c83..958cc358 100644
--- a/src/imports/controls/doc/src/qtquickcontrols2-customize.qdoc
+++ b/src/imports/controls/doc/src/qtquickcontrols2-customize.qdoc
@@ -736,6 +736,15 @@
\snippet qtquickcontrols2-spinbox-custom.qml file
+ \section2 Customizing SplitView
+
+ SplitView consists of a visual \l {SplitView::handle}{handle} delegate.
+
+ \image qtquickcontrols2-splitview-custom.png
+
+ \snippet qtquickcontrols2-splitview-custom.qml 1
+
+
\section2 Customizing StackView
StackView can have a visual \l {Control::background}{background}
diff --git a/src/imports/controls/doc/src/qtquickcontrols2-differences.qdoc b/src/imports/controls/doc/src/qtquickcontrols2-differences.qdoc
index 0b09edf6..40080840 100644
--- a/src/imports/controls/doc/src/qtquickcontrols2-differences.qdoc
+++ b/src/imports/controls/doc/src/qtquickcontrols2-differences.qdoc
@@ -27,7 +27,7 @@
/*!
\page qtquickcontrols2-differences.html
- \title Differences between Qt Quick Controls 1
+ \title Differences with Qt Quick Controls 1
Qt Quick Controls 1 was originally developed to support desktop platforms,
with mobile and embedded support coming shortly afterwards. They have a
@@ -338,9 +338,19 @@
\li
\row
\li \l [QML QtQuickControls1] {SplitView}
- \li \mdash
- \li
+ \li \l [QML QtQuickControls2] {SplitView}
\li
+ \li \list
+ \li \b {Qt Quick Controls 1}: Uses \l Layout attached properties
+ to specify size hints.
+ \li \b {Qt Quick Controls 2}: Uses dedicated
+ \l [QML QtQuickControls2] {SplitView} attached properties
+ to specify size hints.
+ Allows \l {SplitView::saveState()}{saving} and
+ \l {SplitView::restoreState()}{restoring} state.
+ Separate attached \l SplitHandle API for managing split
+ handles.
+ \endlist
\row
\li \l [QML QtQuickControls1] {StackView},\br
\l [QML QtQuickControls1] {StackViewDelegate},\br
@@ -377,7 +387,8 @@
\row
\li \l [QML QtQuickControls1] {TableView}
\li \mdash
- \li
+ \li The new \l [QML QtQuick] {TableView} can be found in the Qt Quick
+ module.
\li
\row
\li \l [QML QtQuickControls1] {TextArea}
diff --git a/src/imports/controls/doc/src/qtquickcontrols2-index.qdoc b/src/imports/controls/doc/src/qtquickcontrols2-index.qdoc
index f95db512..d425f421 100644
--- a/src/imports/controls/doc/src/qtquickcontrols2-index.qdoc
+++ b/src/imports/controls/doc/src/qtquickcontrols2-index.qdoc
@@ -154,7 +154,7 @@
\li \l{Deploying Qt Quick Controls 2 Applications}{Deployment}
\li \l{Qt Quick Controls 2 Configuration File}{Configuration File}
\li \l{Supported Environment Variables in Qt Quick Controls 2}{Environment Variables}
- \li \l{Differences between Qt Quick Controls 1}
+ \li \l{Differences with Qt Quick Controls 1}
\endlist
\section1 Reference
diff --git a/src/imports/controls/fusion/SplitView.qml b/src/imports/controls/fusion/SplitView.qml
new file mode 100644
index 00000000..6a04b4da
--- /dev/null
+++ b/src/imports/controls/fusion/SplitView.qml
@@ -0,0 +1,56 @@
+/****************************************************************************
+**
+** Copyright (C) 2018 The Qt Company Ltd.
+** Contact: http://www.qt.io/licensing/
+**
+** This file is part of the Qt Quick Controls 2 module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL3$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see http://www.qt.io/terms-conditions. For further
+** information use the contact form at http://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPLv3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or later as published by the Free
+** Software Foundation and appearing in the file LICENSE.GPL included in
+** the packaging of this file. Please review the following information to
+** ensure the GNU General Public License version 2.0 requirements will be
+** met: http://www.gnu.org/licenses/gpl-2.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick 2.13
+import QtQuick.Templates 2.13 as T
+import QtQuick.Controls 2.13
+import QtQuick.Controls.impl 2.13
+import QtQuick.Controls.Fusion 2.13
+
+T.SplitView {
+ id: control
+ implicitWidth: Math.max(implicitBackgroundWidth + leftInset + rightInset,
+ implicitContentWidth + leftPadding + rightPadding)
+ implicitHeight: Math.max(implicitBackgroundHeight + topInset + bottomInset,
+ implicitContentHeight + topPadding + bottomPadding)
+
+ handle: Rectangle {
+ implicitWidth: control.orientation === Qt.Horizontal ? 2 : control.width
+ implicitHeight: control.orientation === Qt.Horizontal ? control.height : 2
+ color: T.SplitHandle.pressed ? palette.dark
+ : (T.SplitHandle.hovered ? control.palette.midlight : control.palette.mid)
+ }
+}
diff --git a/src/imports/controls/fusion/dependencies.json b/src/imports/controls/fusion/dependencies.json
new file mode 100644
index 00000000..21ded052
--- /dev/null
+++ b/src/imports/controls/fusion/dependencies.json
@@ -0,0 +1,7 @@
+[
+ {
+ "name": "QtQuick.Controls",
+ "type": "module",
+ "version": "2.0"
+ }
+]
diff --git a/src/imports/controls/fusion/fusion.pri b/src/imports/controls/fusion/fusion.pri
index c4493c09..72978db5 100644
--- a/src/imports/controls/fusion/fusion.pri
+++ b/src/imports/controls/fusion/fusion.pri
@@ -51,6 +51,7 @@ QML_FILES += \
$$PWD/SliderGroove.qml \
$$PWD/SliderHandle.qml \
$$PWD/SpinBox.qml \
+ $$PWD/SplitView.qml \
$$PWD/SwipeDelegate.qml \
$$PWD/SwitchDelegate.qml \
$$PWD/SwitchIndicator.qml \
diff --git a/src/imports/controls/fusion/fusion.pro b/src/imports/controls/fusion/fusion.pro
index 4bc9fcc1..663636da 100644
--- a/src/imports/controls/fusion/fusion.pro
+++ b/src/imports/controls/fusion/fusion.pro
@@ -1,6 +1,8 @@
TARGET = qtquickcontrols2fusionstyleplugin
TARGETPATH = QtQuick/Controls.2/Fusion
-IMPORT_VERSION = 2.5
+
+IMPORT_NAME = QtQuick.Controls.Fusion
+IMPORT_VERSION = 2.$$QT_MINOR_VERSION
QT += qml quick
QT_PRIVATE += core-private gui-private qml-private quick-private quicktemplates2-private quickcontrols2-private
diff --git a/src/imports/controls/fusion/plugins.qmltypes b/src/imports/controls/fusion/plugins.qmltypes
index e6c350d6..a70b4901 100644
--- a/src/imports/controls/fusion/plugins.qmltypes
+++ b/src/imports/controls/fusion/plugins.qmltypes
@@ -4,10 +4,10 @@ import QtQuick.tooling 1.2
// It is used for QML tooling purposes only.
//
// This file was auto-generated by:
-// 'qmlplugindump -nonrelocatable QtQuick.Controls.Fusion 2.3'
+// 'qmlplugindump -nonrelocatable -dependencies dependencies.json QtQuick.Controls.Fusion 2.13'
Module {
- dependencies: [ ]
+ dependencies: ["QtQuick.Controls 2.0"]
Component {
name: "QQuickFusionBusyIndicator"
defaultProperty: "data"
@@ -143,4 +143,72 @@ Module {
Parameter { name: "palette"; type: "QPalette" }
}
}
+ Component {
+ prototype: "QQuickRectangle"
+ name: "QtQuick.Controls.Fusion.impl/ButtonPanel 2.3"
+ exports: ["QtQuick.Controls.Fusion.impl/ButtonPanel 2.3"]
+ exportMetaObjectRevisions: [3]
+ isComposite: true
+ defaultProperty: "data"
+ Property { name: "control"; type: "QQuickItem"; isPointer: true }
+ Property { name: "highlighted"; type: "bool" }
+ }
+ Component {
+ prototype: "QQuickRectangle"
+ name: "QtQuick.Controls.Fusion.impl/CheckIndicator 2.3"
+ exports: ["QtQuick.Controls.Fusion.impl/CheckIndicator 2.3"]
+ exportMetaObjectRevisions: [3]
+ isComposite: true
+ defaultProperty: "data"
+ Property { name: "control"; type: "QQuickItem"; isPointer: true }
+ Property { name: "pressedColor"; type: "QColor"; isReadonly: true }
+ Property { name: "checkMarkColor"; type: "QColor"; isReadonly: true }
+ }
+ Component {
+ prototype: "QQuickRectangle"
+ name: "QtQuick.Controls.Fusion.impl/RadioIndicator 2.3"
+ exports: ["QtQuick.Controls.Fusion.impl/RadioIndicator 2.3"]
+ exportMetaObjectRevisions: [3]
+ isComposite: true
+ defaultProperty: "data"
+ Property { name: "control"; type: "QQuickItem"; isPointer: true }
+ Property { name: "pressedColor"; type: "QColor"; isReadonly: true }
+ Property { name: "checkMarkColor"; type: "QColor"; isReadonly: true }
+ }
+ Component {
+ prototype: "QQuickRectangle"
+ name: "QtQuick.Controls.Fusion.impl/SliderGroove 2.3"
+ exports: ["QtQuick.Controls.Fusion.impl/SliderGroove 2.3"]
+ exportMetaObjectRevisions: [3]
+ isComposite: true
+ defaultProperty: "data"
+ Property { name: "control"; type: "QQuickItem"; isPointer: true }
+ Property { name: "offset"; type: "double" }
+ Property { name: "progress"; type: "double" }
+ Property { name: "visualProgress"; type: "double" }
+ }
+ Component {
+ prototype: "QQuickRectangle"
+ name: "QtQuick.Controls.Fusion.impl/SliderHandle 2.3"
+ exports: ["QtQuick.Controls.Fusion.impl/SliderHandle 2.3"]
+ exportMetaObjectRevisions: [3]
+ isComposite: true
+ defaultProperty: "data"
+ Property { name: "palette"; type: "QVariant" }
+ Property { name: "pressed"; type: "bool" }
+ Property { name: "hovered"; type: "bool" }
+ Property { name: "vertical"; type: "bool" }
+ Property { name: "visualFocus"; type: "bool" }
+ }
+ Component {
+ prototype: "QQuickRectangle"
+ name: "QtQuick.Controls.Fusion.impl/SwitchIndicator 2.3"
+ exports: ["QtQuick.Controls.Fusion.impl/SwitchIndicator 2.3"]
+ exportMetaObjectRevisions: [3]
+ isComposite: true
+ defaultProperty: "data"
+ Property { name: "control"; type: "QQuickItem"; isPointer: true }
+ Property { name: "pressedColor"; type: "QColor"; isReadonly: true }
+ Property { name: "checkMarkColor"; type: "QColor"; isReadonly: true }
+ }
}
diff --git a/src/imports/controls/fusion/qquickfusionstyle.cpp b/src/imports/controls/fusion/qquickfusionstyle.cpp
index 98c1894f..7797463a 100644
--- a/src/imports/controls/fusion/qquickfusionstyle.cpp
+++ b/src/imports/controls/fusion/qquickfusionstyle.cpp
@@ -82,7 +82,7 @@ QColor QQuickFusionStyle::outline(const QPalette &palette)
{
if (palette.window().style() == Qt::TexturePattern)
return QColor(0, 0, 0, 160);
- return palette.background().color().darker(140);
+ return palette.window().color().darker(140);
}
QColor QQuickFusionStyle::highlightedOutline(const QPalette &palette)
diff --git a/src/imports/controls/imagine/SplitView.qml b/src/imports/controls/imagine/SplitView.qml
new file mode 100644
index 00000000..a4a858f4
--- /dev/null
+++ b/src/imports/controls/imagine/SplitView.qml
@@ -0,0 +1,63 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: http://www.qt.io/licensing/
+**
+** This file is part of the Qt Quick Controls 2 module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL3$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see http://www.qt.io/terms-conditions. For further
+** information use the contact form at http://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPLv3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or later as published by the Free
+** Software Foundation and appearing in the file LICENSE.GPL included in
+** the packaging of this file. Please review the following information to
+** ensure the GNU General Public License version 2.0 requirements will be
+** met: http://www.gnu.org/licenses/gpl-2.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick 2.13
+import QtQuick.Templates 2.13 as T
+import QtQuick.Controls.Imagine 2.13
+import QtQuick.Controls.Imagine.impl 2.13
+
+T.SplitView {
+ id: control
+
+ implicitWidth: Math.max(implicitBackgroundWidth + leftInset + rightInset,
+ implicitContentWidth + leftPadding + rightPadding)
+ implicitHeight: Math.max(implicitBackgroundHeight + topInset + bottomInset,
+ implicitContentHeight + topPadding + bottomPadding)
+
+ handle: NinePatchImage {
+ source: Imagine.url + "splitview-handle"
+ NinePatchImageSelector on source {
+ states: [
+ {"vertical": control.orientation === Qt.Vertical},
+ {"horizontal":control.orientation === Qt.Horizontal},
+ {"disabled": !control.enabled},
+ {"pressed": T.SplitHandle.pressed},
+ {"mirrored": control.mirrored},
+ {"hovered": T.SplitHandle.hovered}
+ ]
+ }
+ }
+}
diff --git a/src/imports/controls/imagine/dependencies.json b/src/imports/controls/imagine/dependencies.json
new file mode 100644
index 00000000..21ded052
--- /dev/null
+++ b/src/imports/controls/imagine/dependencies.json
@@ -0,0 +1,7 @@
+[
+ {
+ "name": "QtQuick.Controls",
+ "type": "module",
+ "version": "2.0"
+ }
+]
diff --git a/src/imports/controls/imagine/design/imagine.sketch b/src/imports/controls/imagine/design/imagine.sketch
index ecb437f7..f3535b37 100644
--- a/src/imports/controls/imagine/design/imagine.sketch
+++ b/src/imports/controls/imagine/design/imagine.sketch
Binary files differ
diff --git a/src/imports/controls/imagine/images/splitview-handle-disabled.png b/src/imports/controls/imagine/images/splitview-handle-disabled.png
new file mode 100644
index 00000000..0071c196
--- /dev/null
+++ b/src/imports/controls/imagine/images/splitview-handle-disabled.png
Binary files differ
diff --git a/src/imports/controls/imagine/images/splitview-handle-disabled@2x.png b/src/imports/controls/imagine/images/splitview-handle-disabled@2x.png
new file mode 100644
index 00000000..67cee407
--- /dev/null
+++ b/src/imports/controls/imagine/images/splitview-handle-disabled@2x.png
Binary files differ
diff --git a/src/imports/controls/imagine/images/splitview-handle-disabled@3x.png b/src/imports/controls/imagine/images/splitview-handle-disabled@3x.png
new file mode 100644
index 00000000..84752ba9
--- /dev/null
+++ b/src/imports/controls/imagine/images/splitview-handle-disabled@3x.png
Binary files differ
diff --git a/src/imports/controls/imagine/images/splitview-handle-disabled@4x.png b/src/imports/controls/imagine/images/splitview-handle-disabled@4x.png
new file mode 100644
index 00000000..e4be8597
--- /dev/null
+++ b/src/imports/controls/imagine/images/splitview-handle-disabled@4x.png
Binary files differ
diff --git a/src/imports/controls/imagine/images/splitview-handle-hovered.png b/src/imports/controls/imagine/images/splitview-handle-hovered.png
new file mode 100644
index 00000000..1386d213
--- /dev/null
+++ b/src/imports/controls/imagine/images/splitview-handle-hovered.png
Binary files differ
diff --git a/src/imports/controls/imagine/images/splitview-handle-hovered@2x.png b/src/imports/controls/imagine/images/splitview-handle-hovered@2x.png
new file mode 100644
index 00000000..4708a47b
--- /dev/null
+++ b/src/imports/controls/imagine/images/splitview-handle-hovered@2x.png
Binary files differ
diff --git a/src/imports/controls/imagine/images/splitview-handle-hovered@3x.png b/src/imports/controls/imagine/images/splitview-handle-hovered@3x.png
new file mode 100644
index 00000000..2ccc1ff5
--- /dev/null
+++ b/src/imports/controls/imagine/images/splitview-handle-hovered@3x.png
Binary files differ
diff --git a/src/imports/controls/imagine/images/splitview-handle-hovered@4x.png b/src/imports/controls/imagine/images/splitview-handle-hovered@4x.png
new file mode 100644
index 00000000..6929da70
--- /dev/null
+++ b/src/imports/controls/imagine/images/splitview-handle-hovered@4x.png
Binary files differ
diff --git a/src/imports/controls/imagine/images/splitview-handle-pressed.png b/src/imports/controls/imagine/images/splitview-handle-pressed.png
new file mode 100644
index 00000000..7face6b4
--- /dev/null
+++ b/src/imports/controls/imagine/images/splitview-handle-pressed.png
Binary files differ
diff --git a/src/imports/controls/imagine/images/splitview-handle-pressed@2x.png b/src/imports/controls/imagine/images/splitview-handle-pressed@2x.png
new file mode 100644
index 00000000..ad940d0f
--- /dev/null
+++ b/src/imports/controls/imagine/images/splitview-handle-pressed@2x.png
Binary files differ
diff --git a/src/imports/controls/imagine/images/splitview-handle-pressed@3x.png b/src/imports/controls/imagine/images/splitview-handle-pressed@3x.png
new file mode 100644
index 00000000..d4e19dc2
--- /dev/null
+++ b/src/imports/controls/imagine/images/splitview-handle-pressed@3x.png
Binary files differ
diff --git a/src/imports/controls/imagine/images/splitview-handle-pressed@4x.png b/src/imports/controls/imagine/images/splitview-handle-pressed@4x.png
new file mode 100644
index 00000000..8ccbbebc
--- /dev/null
+++ b/src/imports/controls/imagine/images/splitview-handle-pressed@4x.png
Binary files differ
diff --git a/src/imports/controls/imagine/images/splitview-handle.png b/src/imports/controls/imagine/images/splitview-handle.png
new file mode 100644
index 00000000..c1dffa67
--- /dev/null
+++ b/src/imports/controls/imagine/images/splitview-handle.png
Binary files differ
diff --git a/src/imports/controls/imagine/images/splitview-handle@2x.png b/src/imports/controls/imagine/images/splitview-handle@2x.png
new file mode 100644
index 00000000..180e266a
--- /dev/null
+++ b/src/imports/controls/imagine/images/splitview-handle@2x.png
Binary files differ
diff --git a/src/imports/controls/imagine/images/splitview-handle@3x.png b/src/imports/controls/imagine/images/splitview-handle@3x.png
new file mode 100644
index 00000000..35ea51db
--- /dev/null
+++ b/src/imports/controls/imagine/images/splitview-handle@3x.png
Binary files differ
diff --git a/src/imports/controls/imagine/images/splitview-handle@4x.png b/src/imports/controls/imagine/images/splitview-handle@4x.png
new file mode 100644
index 00000000..3a1e7e9f
--- /dev/null
+++ b/src/imports/controls/imagine/images/splitview-handle@4x.png
Binary files differ
diff --git a/src/imports/controls/imagine/imagine.pri b/src/imports/controls/imagine/imagine.pri
index cb6857a5..081a509e 100644
--- a/src/imports/controls/imagine/imagine.pri
+++ b/src/imports/controls/imagine/imagine.pri
@@ -30,6 +30,7 @@ QML_FILES += \
$$PWD/ScrollIndicator.qml \
$$PWD/Slider.qml \
$$PWD/SpinBox.qml \
+ $$PWD/SplitView.qml \
$$PWD/StackView.qml \
$$PWD/SwipeDelegate.qml \
$$PWD/SwipeView.qml \
diff --git a/src/imports/controls/imagine/imagine.pro b/src/imports/controls/imagine/imagine.pro
index 2368c0a4..f16bd081 100644
--- a/src/imports/controls/imagine/imagine.pro
+++ b/src/imports/controls/imagine/imagine.pro
@@ -1,6 +1,8 @@
TARGET = qtquickcontrols2imaginestyleplugin
TARGETPATH = QtQuick/Controls.2/Imagine
-IMPORT_VERSION = 2.5
+
+IMPORT_NAME = QtQuick.Controls.Imagine
+IMPORT_VERSION = 2.$$QT_MINOR_VERSION
QT += qml quick
QT_PRIVATE += core-private gui-private qml-private quick-private quicktemplates2-private quickcontrols2-private
diff --git a/src/imports/controls/imagine/plugins.qmltypes b/src/imports/controls/imagine/plugins.qmltypes
index b09ae141..014714f3 100644
--- a/src/imports/controls/imagine/plugins.qmltypes
+++ b/src/imports/controls/imagine/plugins.qmltypes
@@ -4,12 +4,30 @@ import QtQuick.tooling 1.2
// It is used for QML tooling purposes only.
//
// This file was auto-generated by:
-// 'qmlplugindump -nonrelocatable QtQuick.Controls.Imagine 2.3'
+// 'qmlplugindump -nonrelocatable -dependencies dependencies.json QtQuick.Controls.Imagine 2.13'
Module {
- dependencies: []
+ dependencies: ["QtQuick.Controls 2.0"]
+ Component {
+ name: "QQuickAnimatedImageSelector"
+ prototype: "QQuickImageSelector"
+ exports: ["QtQuick.Controls.Imagine.impl/AnimatedImageSelector 2.3"]
+ exportMetaObjectRevisions: [0]
+ }
Component { name: "QQuickAttachedObject"; prototype: "QObject" }
Component {
+ name: "QQuickImageSelector"
+ prototype: "QObject"
+ exports: ["QtQuick.Controls.Imagine.impl/ImageSelector 2.3"]
+ exportMetaObjectRevisions: [0]
+ Property { name: "source"; type: "QUrl"; isReadonly: true }
+ Property { name: "name"; type: "string" }
+ Property { name: "path"; type: "string" }
+ Property { name: "states"; type: "QVariantList" }
+ Property { name: "separator"; type: "string" }
+ Property { name: "cache"; type: "bool" }
+ }
+ Component {
name: "QQuickImagineStyle"
prototype: "QQuickAttachedObject"
exports: ["QtQuick.Controls.Imagine/Imagine 2.3"]
@@ -18,4 +36,25 @@ Module {
Property { name: "path"; type: "string" }
Property { name: "url"; type: "QUrl"; isReadonly: true }
}
+ Component {
+ name: "QQuickNinePatchImage"
+ defaultProperty: "data"
+ prototype: "QQuickImage"
+ exports: ["QtQuick.Controls.Imagine.impl/NinePatchImage 2.3"]
+ exportMetaObjectRevisions: [0]
+ Property { name: "topPadding"; type: "double"; isReadonly: true }
+ Property { name: "leftPadding"; type: "double"; isReadonly: true }
+ Property { name: "rightPadding"; type: "double"; isReadonly: true }
+ Property { name: "bottomPadding"; type: "double"; isReadonly: true }
+ Property { name: "topInset"; type: "double"; isReadonly: true }
+ Property { name: "leftInset"; type: "double"; isReadonly: true }
+ Property { name: "rightInset"; type: "double"; isReadonly: true }
+ Property { name: "bottomInset"; type: "double"; isReadonly: true }
+ }
+ Component {
+ name: "QQuickNinePatchImageSelector"
+ prototype: "QQuickImageSelector"
+ exports: ["QtQuick.Controls.Imagine.impl/NinePatchImageSelector 2.3"]
+ exportMetaObjectRevisions: [0]
+ }
}
diff --git a/src/imports/controls/material/SplitView.qml b/src/imports/controls/material/SplitView.qml
new file mode 100644
index 00000000..5544e833
--- /dev/null
+++ b/src/imports/controls/material/SplitView.qml
@@ -0,0 +1,74 @@
+/****************************************************************************
+**
+** Copyright (C) 2018 The Qt Company Ltd.
+** Contact: http://www.qt.io/licensing/
+**
+** This file is part of the Qt Quick Controls 2 module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL3$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see http://www.qt.io/terms-conditions. For further
+** information use the contact form at http://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPLv3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or later as published by the Free
+** Software Foundation and appearing in the file LICENSE.GPL included in
+** the packaging of this file. Please review the following information to
+** ensure the GNU General Public License version 2.0 requirements will be
+** met: http://www.gnu.org/licenses/gpl-2.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick 2.13
+import QtQuick.Templates 2.13 as T
+import QtQuick.Controls 2.13
+import QtQuick.Controls.impl 2.13
+import QtQuick.Controls.Material 2.13
+
+T.SplitView {
+ id: control
+ implicitWidth: Math.max(implicitBackgroundWidth + leftInset + rightInset,
+ implicitContentWidth + leftPadding + rightPadding)
+ implicitHeight: Math.max(implicitBackgroundHeight + topInset + bottomInset,
+ implicitContentHeight + topPadding + bottomPadding)
+
+ handle: Rectangle {
+ implicitWidth: control.orientation === Qt.Horizontal ? 6 : control.width
+ implicitHeight: control.orientation === Qt.Horizontal ? control.height : 6
+ color: T.SplitHandle.pressed ? control.Material.background
+ : Qt.lighter(control.Material.background, T.SplitHandle.hovered ? 1.2 : 1.1)
+
+ Rectangle {
+ color: control.Material.secondaryTextColor
+ width: control.orientation === Qt.Horizontal ? thickness : length
+ height: control.orientation === Qt.Horizontal ? length : thickness
+ radius: thickness
+ x: (parent.width - width) / 2
+ y: (parent.height - height) / 2
+
+ property int length: parent.T.SplitHandle.pressed ? 3 : 8
+ readonly property int thickness: parent.T.SplitHandle.pressed ? 3 : 1
+
+ Behavior on length {
+ NumberAnimation {
+ duration: 100
+ }
+ }
+ }
+ }
+}
diff --git a/src/imports/controls/material/dependencies.json b/src/imports/controls/material/dependencies.json
new file mode 100644
index 00000000..21ded052
--- /dev/null
+++ b/src/imports/controls/material/dependencies.json
@@ -0,0 +1,7 @@
+[
+ {
+ "name": "QtQuick.Controls",
+ "type": "module",
+ "version": "2.0"
+ }
+]
diff --git a/src/imports/controls/material/material.pri b/src/imports/controls/material/material.pri
index ab925aa2..bda1fb21 100644
--- a/src/imports/controls/material/material.pri
+++ b/src/imports/controls/material/material.pri
@@ -53,6 +53,7 @@ QML_FILES += \
$$PWD/Slider.qml \
$$PWD/SliderHandle.qml \
$$PWD/SpinBox.qml \
+ $$PWD/SplitView.qml \
$$PWD/StackView.qml \
$$PWD/SwipeDelegate.qml \
$$PWD/SwipeView.qml \
diff --git a/src/imports/controls/material/material.pro b/src/imports/controls/material/material.pro
index c3cbb355..cf08b925 100644
--- a/src/imports/controls/material/material.pro
+++ b/src/imports/controls/material/material.pro
@@ -1,6 +1,8 @@
TARGET = qtquickcontrols2materialstyleplugin
TARGETPATH = QtQuick/Controls.2/Material
-IMPORT_VERSION = 2.5
+
+IMPORT_NAME = QtQuick.Controls.Material
+IMPORT_VERSION = 2.$$QT_MINOR_VERSION
QT += qml quick
QT_PRIVATE += core-private gui-private qml-private quick-private quicktemplates2-private quickcontrols2-private
diff --git a/src/imports/controls/material/plugins.qmltypes b/src/imports/controls/material/plugins.qmltypes
index 2ddf99a7..3e95fa44 100644
--- a/src/imports/controls/material/plugins.qmltypes
+++ b/src/imports/controls/material/plugins.qmltypes
@@ -4,12 +4,51 @@ import QtQuick.tooling 1.2
// It is used for QML tooling purposes only.
//
// This file was auto-generated by:
-// 'qmlplugindump -nonrelocatable QtQuick.Controls.Material 2.3'
+// 'qmlplugindump -nonrelocatable -dependencies dependencies.json QtQuick.Controls.Material 2.13'
Module {
- dependencies: []
+ dependencies: ["QtQuick.Controls 2.0"]
Component { name: "QQuickAttachedObject"; prototype: "QObject" }
Component {
+ name: "QQuickMaterialBusyIndicator"
+ defaultProperty: "data"
+ prototype: "QQuickItem"
+ exports: ["QtQuick.Controls.Material.impl/BusyIndicatorImpl 2.0"]
+ exportMetaObjectRevisions: [0]
+ Property { name: "color"; type: "QColor" }
+ Property { name: "running"; type: "bool" }
+ }
+ Component {
+ name: "QQuickMaterialProgressBar"
+ defaultProperty: "data"
+ prototype: "QQuickItem"
+ exports: ["QtQuick.Controls.Material.impl/ProgressBarImpl 2.0"]
+ exportMetaObjectRevisions: [0]
+ Property { name: "color"; type: "QColor" }
+ Property { name: "progress"; type: "double" }
+ Property { name: "indeterminate"; type: "bool" }
+ }
+ Component {
+ name: "QQuickMaterialRipple"
+ defaultProperty: "data"
+ prototype: "QQuickItem"
+ exports: ["QtQuick.Controls.Material.impl/Ripple 2.0"]
+ exportMetaObjectRevisions: [0]
+ Enum {
+ name: "Trigger"
+ values: {
+ "Press": 0,
+ "Release": 1
+ }
+ }
+ Property { name: "color"; type: "QColor" }
+ Property { name: "clipRadius"; type: "double" }
+ Property { name: "pressed"; type: "bool" }
+ Property { name: "active"; type: "bool" }
+ Property { name: "anchor"; type: "QQuickItem"; isPointer: true }
+ Property { name: "trigger"; type: "Trigger" }
+ }
+ Component {
name: "QQuickMaterialStyle"
prototype: "QQuickAttachedObject"
exports: ["QtQuick.Controls.Material/Material 2.0"]
@@ -24,6 +63,13 @@ Module {
}
}
Enum {
+ name: "Variant"
+ values: {
+ "Normal": 0,
+ "Dense": 1
+ }
+ }
+ Enum {
name: "Color"
values: {
"Red": 0,
@@ -72,6 +118,49 @@ Module {
Property { name: "foreground"; type: "QVariant" }
Property { name: "background"; type: "QVariant" }
Property { name: "elevation"; type: "int" }
+ Property { name: "primaryColor"; type: "QColor"; isReadonly: true }
+ Property { name: "accentColor"; type: "QColor"; isReadonly: true }
+ Property { name: "backgroundColor"; type: "QColor"; isReadonly: true }
+ Property { name: "primaryTextColor"; type: "QColor"; isReadonly: true }
+ Property { name: "primaryHighlightedTextColor"; type: "QColor"; isReadonly: true }
+ Property { name: "secondaryTextColor"; type: "QColor"; isReadonly: true }
+ Property { name: "hintTextColor"; type: "QColor"; isReadonly: true }
+ Property { name: "textSelectionColor"; type: "QColor"; isReadonly: true }
+ Property { name: "dropShadowColor"; type: "QColor"; isReadonly: true }
+ Property { name: "dividerColor"; type: "QColor"; isReadonly: true }
+ Property { name: "iconColor"; type: "QColor"; isReadonly: true }
+ Property { name: "iconDisabledColor"; type: "QColor"; isReadonly: true }
+ Property { name: "buttonColor"; type: "QColor"; isReadonly: true }
+ Property { name: "buttonDisabledColor"; type: "QColor"; isReadonly: true }
+ Property { name: "highlightedButtonColor"; type: "QColor"; isReadonly: true }
+ Property { name: "frameColor"; type: "QColor"; isReadonly: true }
+ Property { name: "rippleColor"; type: "QColor"; isReadonly: true }
+ Property { name: "highlightedRippleColor"; type: "QColor"; isReadonly: true }
+ Property { name: "switchUncheckedTrackColor"; type: "QColor"; isReadonly: true }
+ Property { name: "switchCheckedTrackColor"; type: "QColor"; isReadonly: true }
+ Property { name: "switchUncheckedHandleColor"; type: "QColor"; isReadonly: true }
+ Property { name: "switchCheckedHandleColor"; type: "QColor"; isReadonly: true }
+ Property { name: "switchDisabledTrackColor"; type: "QColor"; isReadonly: true }
+ Property { name: "switchDisabledHandleColor"; type: "QColor"; isReadonly: true }
+ Property { name: "scrollBarColor"; type: "QColor"; isReadonly: true }
+ Property { name: "scrollBarHoveredColor"; type: "QColor"; isReadonly: true }
+ Property { name: "scrollBarPressedColor"; type: "QColor"; isReadonly: true }
+ Property { name: "dialogColor"; type: "QColor"; isReadonly: true }
+ Property { name: "backgroundDimColor"; type: "QColor"; isReadonly: true }
+ Property { name: "listHighlightColor"; type: "QColor"; isReadonly: true }
+ Property { name: "tooltipColor"; type: "QColor"; isReadonly: true }
+ Property { name: "toolBarColor"; type: "QColor"; isReadonly: true }
+ Property { name: "toolTextColor"; type: "QColor"; isReadonly: true }
+ Property { name: "spinBoxDisabledIconColor"; type: "QColor"; isReadonly: true }
+ Property { name: "touchTarget"; type: "int"; isReadonly: true }
+ Property { name: "buttonHeight"; type: "int"; isReadonly: true }
+ Property { name: "delegateHeight"; type: "int"; isReadonly: true }
+ Property { name: "dialogButtonBoxHeight"; type: "int"; isReadonly: true }
+ Property { name: "frameVerticalPadding"; type: "int"; isReadonly: true }
+ Property { name: "menuItemHeight"; type: "int"; isReadonly: true }
+ Property { name: "menuItemVerticalPadding"; type: "int"; isReadonly: true }
+ Property { name: "switchDelegateVerticalPadding"; type: "int"; isReadonly: true }
+ Property { name: "tooltipHeight"; type: "int"; isReadonly: true }
Signal { name: "paletteChanged" }
Method {
name: "color"
@@ -91,4 +180,103 @@ Module {
Parameter { name: "shade"; type: "Shade" }
}
}
+ Component {
+ prototype: "QQuickItem"
+ name: "QtQuick.Controls.Material.impl/BoxShadow 2.0"
+ exports: ["QtQuick.Controls.Material.impl/BoxShadow 2.0"]
+ exportMetaObjectRevisions: [0]
+ isComposite: true
+ defaultProperty: "data"
+ Property { name: "offsetX"; type: "int" }
+ Property { name: "offsetY"; type: "int" }
+ Property { name: "blurRadius"; type: "int" }
+ Property { name: "spreadRadius"; type: "int" }
+ Property { name: "source"; type: "QQuickItem"; isPointer: true }
+ Property { name: "fullWidth"; type: "bool" }
+ Property { name: "fullHeight"; type: "bool" }
+ Property { name: "glowRadius"; type: "double" }
+ Property { name: "spread"; type: "double" }
+ Property { name: "color"; type: "QColor" }
+ Property { name: "cornerRadius"; type: "double" }
+ Property { name: "cached"; type: "bool" }
+ }
+ Component {
+ prototype: "QQuickRectangle"
+ name: "QtQuick.Controls.Material.impl/CheckIndicator 2.0"
+ exports: ["QtQuick.Controls.Material.impl/CheckIndicator 2.0"]
+ exportMetaObjectRevisions: [0]
+ isComposite: true
+ defaultProperty: "data"
+ Property { name: "control"; type: "QQuickItem"; isPointer: true }
+ Property { name: "checkState"; type: "int" }
+ }
+ Component {
+ prototype: "QQuickRectangle"
+ name: "QtQuick.Controls.Material.impl/CursorDelegate 2.0"
+ exports: ["QtQuick.Controls.Material.impl/CursorDelegate 2.0"]
+ exportMetaObjectRevisions: [0]
+ isComposite: true
+ defaultProperty: "data"
+ }
+ Component {
+ prototype: "QQuickItem"
+ name: "QtQuick.Controls.Material.impl/ElevationEffect 2.0"
+ exports: ["QtQuick.Controls.Material.impl/ElevationEffect 2.0"]
+ exportMetaObjectRevisions: [0]
+ isComposite: true
+ defaultProperty: "data"
+ Property { name: "source"; type: "QVariant" }
+ Property { name: "elevation"; type: "int" }
+ Property { name: "fullWidth"; type: "bool" }
+ Property { name: "fullHeight"; type: "bool" }
+ Property { name: "sourceItem"; type: "QQuickItem"; isReadonly: true; isPointer: true }
+ Property { name: "_shadows"; type: "QVariant"; isReadonly: true }
+ Property { name: "_shadow"; type: "QVariant"; isReadonly: true }
+ }
+ Component {
+ prototype: "QQuickRectangle"
+ name: "QtQuick.Controls.Material.impl/RadioIndicator 2.0"
+ exports: ["QtQuick.Controls.Material.impl/RadioIndicator 2.0"]
+ exportMetaObjectRevisions: [0]
+ isComposite: true
+ defaultProperty: "data"
+ Property { name: "control"; type: "QQuickItem"; isPointer: true }
+ }
+ Component {
+ prototype: "QQuickItem"
+ name: "QtQuick.Controls.Material.impl/RectangularGlow 2.0"
+ exports: ["QtQuick.Controls.Material.impl/RectangularGlow 2.0"]
+ exportMetaObjectRevisions: [0]
+ isComposite: true
+ defaultProperty: "data"
+ Property { name: "glowRadius"; type: "double" }
+ Property { name: "spread"; type: "double" }
+ Property { name: "color"; type: "QColor" }
+ Property { name: "cornerRadius"; type: "double" }
+ Property { name: "cached"; type: "bool" }
+ }
+ Component {
+ prototype: "QQuickItem"
+ name: "QtQuick.Controls.Material.impl/SliderHandle 2.0"
+ exports: ["QtQuick.Controls.Material.impl/SliderHandle 2.0"]
+ exportMetaObjectRevisions: [0]
+ isComposite: true
+ defaultProperty: "data"
+ Property { name: "value"; type: "double" }
+ Property { name: "handleHasFocus"; type: "bool" }
+ Property { name: "handlePressed"; type: "bool" }
+ Property { name: "handleHovered"; type: "bool" }
+ Property { name: "initialSize"; type: "int"; isReadonly: true }
+ Property { name: "control"; type: "QVariant"; isReadonly: true }
+ }
+ Component {
+ prototype: "QQuickItem"
+ name: "QtQuick.Controls.Material.impl/SwitchIndicator 2.0"
+ exports: ["QtQuick.Controls.Material.impl/SwitchIndicator 2.0"]
+ exportMetaObjectRevisions: [0]
+ isComposite: true
+ defaultProperty: "data"
+ Property { name: "control"; type: "QQuickItem"; isPointer: true }
+ Property { name: "handle"; type: "QQuickRectangle"; isReadonly: true; isPointer: true }
+ }
}
diff --git a/src/imports/controls/plugins.qmltypes b/src/imports/controls/plugins.qmltypes
index 4585a9a6..9b4610f0 100644
--- a/src/imports/controls/plugins.qmltypes
+++ b/src/imports/controls/plugins.qmltypes
@@ -4,7 +4,7 @@ import QtQuick.tooling 1.2
// It is used for QML tooling purposes only.
//
// This file was auto-generated by:
-// 'qmlplugindump -nonrelocatable QtQuick.Controls 2.5 -merge ../templates/plugins.qmltypes -dependencies dependencies.json'
+// 'qmlplugindump -nonrelocatable -dependencies dependencies.json QtQuick.Controls 2.13'
Module {
dependencies: [
@@ -538,6 +538,14 @@ Module {
defaultProperty: "data"
}
Component {
+ prototype: "QQuickSplitView"
+ name: "QtQuick.Controls/SplitView 2.13"
+ exports: ["QtQuick.Controls/SplitView 2.13"]
+ exportMetaObjectRevisions: [13]
+ isComposite: true
+ defaultProperty: "contentData"
+ }
+ Component {
prototype: "QQuickStackView"
name: "QtQuick.Controls/StackView 2.0"
exports: ["QtQuick.Controls/StackView 2.0"]
@@ -649,1831 +657,4 @@ Module {
isComposite: true
defaultProperty: "data"
}
-
- Component {
- name: "QQuickAbstractButton"
- defaultProperty: "data"
- prototype: "QQuickControl"
- exports: [
- "QtQuick.Templates/AbstractButton 2.0",
- "QtQuick.Templates/AbstractButton 2.2",
- "QtQuick.Templates/AbstractButton 2.3",
- "QtQuick.Templates/AbstractButton 2.4",
- "QtQuick.Templates/AbstractButton 2.5"
- ]
- exportMetaObjectRevisions: [0, 2, 3, 4, 5]
- Enum {
- name: "Display"
- values: {
- "IconOnly": 0,
- "TextOnly": 1,
- "TextBesideIcon": 2,
- "TextUnderIcon": 3
- }
- }
- Property { name: "text"; type: "string" }
- Property { name: "down"; type: "bool" }
- Property { name: "pressed"; type: "bool"; isReadonly: true }
- Property { name: "checked"; type: "bool" }
- Property { name: "checkable"; type: "bool" }
- Property { name: "autoExclusive"; type: "bool" }
- Property { name: "autoRepeat"; type: "bool" }
- Property { name: "indicator"; type: "QQuickItem"; isPointer: true }
- Property { name: "icon"; revision: 3; type: "QQuickIcon" }
- Property { name: "display"; revision: 3; type: "Display" }
- Property { name: "action"; revision: 3; type: "QQuickAction"; isPointer: true }
- Property { name: "autoRepeatDelay"; revision: 4; type: "int" }
- Property { name: "autoRepeatInterval"; revision: 4; type: "int" }
- Property { name: "pressX"; revision: 4; type: "double"; isReadonly: true }
- Property { name: "pressY"; revision: 4; type: "double"; isReadonly: true }
- Property { name: "implicitIndicatorWidth"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitIndicatorHeight"; revision: 5; type: "double"; isReadonly: true }
- Signal { name: "pressed" }
- Signal { name: "released" }
- Signal { name: "canceled" }
- Signal { name: "clicked" }
- Signal { name: "pressAndHold" }
- Signal { name: "doubleClicked" }
- Signal { name: "toggled"; revision: 2 }
- Signal { name: "iconChanged"; revision: 3 }
- Signal { name: "displayChanged"; revision: 3 }
- Signal { name: "actionChanged"; revision: 3 }
- Signal { name: "autoRepeatDelayChanged"; revision: 4 }
- Signal { name: "autoRepeatIntervalChanged"; revision: 4 }
- Signal { name: "pressXChanged"; revision: 4 }
- Signal { name: "pressYChanged"; revision: 4 }
- Signal { name: "implicitIndicatorWidthChanged"; revision: 5 }
- Signal { name: "implicitIndicatorHeightChanged"; revision: 5 }
- Method { name: "toggle" }
- }
- Component {
- name: "QQuickAction"
- prototype: "QObject"
- exports: ["QtQuick.Templates/Action 2.3"]
- exportMetaObjectRevisions: [0]
- Property { name: "text"; type: "string" }
- Property { name: "icon"; type: "QQuickIcon" }
- Property { name: "enabled"; type: "bool" }
- Property { name: "checked"; type: "bool" }
- Property { name: "checkable"; type: "bool" }
- Property { name: "shortcut"; type: "QVariant" }
- Signal {
- name: "textChanged"
- Parameter { name: "text"; type: "string" }
- }
- Signal {
- name: "iconChanged"
- Parameter { name: "icon"; type: "QQuickIcon" }
- }
- Signal {
- name: "enabledChanged"
- Parameter { name: "enabled"; type: "bool" }
- }
- Signal {
- name: "checkedChanged"
- Parameter { name: "checked"; type: "bool" }
- }
- Signal {
- name: "checkableChanged"
- Parameter { name: "checkable"; type: "bool" }
- }
- Signal {
- name: "shortcutChanged"
- Parameter { name: "shortcut"; type: "QKeySequence" }
- }
- Signal {
- name: "toggled"
- Parameter { name: "source"; type: "QObject"; isPointer: true }
- }
- Signal { name: "toggled" }
- Signal {
- name: "triggered"
- Parameter { name: "source"; type: "QObject"; isPointer: true }
- }
- Signal { name: "triggered" }
- Method {
- name: "toggle"
- Parameter { name: "source"; type: "QObject"; isPointer: true }
- }
- Method { name: "toggle" }
- Method {
- name: "trigger"
- Parameter { name: "source"; type: "QObject"; isPointer: true }
- }
- Method { name: "trigger" }
- }
- Component {
- name: "QQuickActionGroup"
- defaultProperty: "actions"
- prototype: "QObject"
- exports: ["QtQuick.Templates/ActionGroup 2.3"]
- exportMetaObjectRevisions: [0]
- attachedType: "QQuickActionGroupAttached"
- Property { name: "checkedAction"; type: "QQuickAction"; isPointer: true }
- Property { name: "actions"; type: "QQuickAction"; isList: true; isReadonly: true }
- Property { name: "exclusive"; type: "bool" }
- Property { name: "enabled"; type: "bool" }
- Signal {
- name: "triggered"
- Parameter { name: "action"; type: "QQuickAction"; isPointer: true }
- }
- Method {
- name: "addAction"
- Parameter { name: "action"; type: "QQuickAction"; isPointer: true }
- }
- Method {
- name: "removeAction"
- Parameter { name: "action"; type: "QQuickAction"; isPointer: true }
- }
- }
- Component {
- name: "QQuickActionGroupAttached"
- prototype: "QObject"
- Property { name: "group"; type: "QQuickActionGroup"; isPointer: true }
- }
- Component {
- name: "QQuickApplicationWindow"
- defaultProperty: "contentData"
- prototype: "QQuickWindowQmlImpl"
- exports: [
- "QtQuick.Templates/ApplicationWindow 2.0",
- "QtQuick.Templates/ApplicationWindow 2.3"
- ]
- exportMetaObjectRevisions: [0, 3]
- attachedType: "QQuickApplicationWindowAttached"
- Property { name: "background"; type: "QQuickItem"; isPointer: true }
- Property { name: "contentItem"; type: "QQuickItem"; isReadonly: true; isPointer: true }
- Property { name: "contentData"; type: "QObject"; isList: true; isReadonly: true }
- Property { name: "activeFocusControl"; type: "QQuickItem"; isReadonly: true; isPointer: true }
- Property { name: "header"; type: "QQuickItem"; isPointer: true }
- Property { name: "footer"; type: "QQuickItem"; isPointer: true }
- Property { name: "overlay"; type: "QQuickOverlay"; isReadonly: true; isPointer: true }
- Property { name: "font"; type: "QFont" }
- Property { name: "locale"; type: "QLocale" }
- Property { name: "palette"; revision: 3; type: "QPalette" }
- Property { name: "menuBar"; revision: 3; type: "QQuickItem"; isPointer: true }
- Signal { name: "paletteChanged"; revision: 3 }
- Signal { name: "menuBarChanged"; revision: 3 }
- }
- Component {
- name: "QQuickApplicationWindowAttached"
- prototype: "QObject"
- Property { name: "window"; type: "QQuickApplicationWindow"; isReadonly: true; isPointer: true }
- Property { name: "contentItem"; type: "QQuickItem"; isReadonly: true; isPointer: true }
- Property { name: "activeFocusControl"; type: "QQuickItem"; isReadonly: true; isPointer: true }
- Property { name: "header"; type: "QQuickItem"; isReadonly: true; isPointer: true }
- Property { name: "footer"; type: "QQuickItem"; isReadonly: true; isPointer: true }
- Property { name: "overlay"; type: "QQuickOverlay"; isReadonly: true; isPointer: true }
- Property { name: "menuBar"; type: "QQuickItem"; isReadonly: true; isPointer: true }
- }
- Component {
- name: "QQuickBusyIndicator"
- defaultProperty: "data"
- prototype: "QQuickControl"
- exports: ["QtQuick.Templates/BusyIndicator 2.0"]
- exportMetaObjectRevisions: [0]
- Property { name: "running"; type: "bool" }
- }
- Component {
- name: "QQuickButton"
- defaultProperty: "data"
- prototype: "QQuickAbstractButton"
- exports: ["QtQuick.Templates/Button 2.0"]
- exportMetaObjectRevisions: [0]
- Property { name: "highlighted"; type: "bool" }
- Property { name: "flat"; type: "bool" }
- }
- Component {
- name: "QQuickButtonGroup"
- prototype: "QObject"
- exports: [
- "QtQuick.Templates/ButtonGroup 2.0",
- "QtQuick.Templates/ButtonGroup 2.1",
- "QtQuick.Templates/ButtonGroup 2.3",
- "QtQuick.Templates/ButtonGroup 2.4"
- ]
- exportMetaObjectRevisions: [0, 1, 3, 4]
- attachedType: "QQuickButtonGroupAttached"
- Property { name: "checkedButton"; type: "QQuickAbstractButton"; isPointer: true }
- Property { name: "buttons"; type: "QQuickAbstractButton"; isList: true; isReadonly: true }
- Property { name: "exclusive"; revision: 3; type: "bool" }
- Property { name: "checkState"; revision: 4; type: "Qt::CheckState" }
- Signal {
- name: "clicked"
- revision: 1
- Parameter { name: "button"; type: "QQuickAbstractButton"; isPointer: true }
- }
- Signal { name: "exclusiveChanged"; revision: 3 }
- Signal { name: "checkStateChanged"; revision: 4 }
- Method {
- name: "addButton"
- Parameter { name: "button"; type: "QQuickAbstractButton"; isPointer: true }
- }
- Method {
- name: "removeButton"
- Parameter { name: "button"; type: "QQuickAbstractButton"; isPointer: true }
- }
- }
- Component {
- name: "QQuickButtonGroupAttached"
- prototype: "QObject"
- Property { name: "group"; type: "QQuickButtonGroup"; isPointer: true }
- }
- Component {
- name: "QQuickCheckBox"
- defaultProperty: "data"
- prototype: "QQuickAbstractButton"
- exports: [
- "QtQuick.Templates/CheckBox 2.0",
- "QtQuick.Templates/CheckBox 2.4"
- ]
- exportMetaObjectRevisions: [0, 4]
- Property { name: "tristate"; type: "bool" }
- Property { name: "checkState"; type: "Qt::CheckState" }
- Property { name: "nextCheckState"; revision: 4; type: "QJSValue" }
- Signal { name: "nextCheckStateChanged"; revision: 4 }
- }
- Component {
- name: "QQuickCheckDelegate"
- defaultProperty: "data"
- prototype: "QQuickItemDelegate"
- exports: [
- "QtQuick.Templates/CheckDelegate 2.0",
- "QtQuick.Templates/CheckDelegate 2.4"
- ]
- exportMetaObjectRevisions: [0, 4]
- Property { name: "tristate"; type: "bool" }
- Property { name: "checkState"; type: "Qt::CheckState" }
- Property { name: "nextCheckState"; revision: 4; type: "QJSValue" }
- Signal { name: "nextCheckStateChanged"; revision: 4 }
- }
- Component {
- name: "QQuickComboBox"
- defaultProperty: "data"
- prototype: "QQuickControl"
- exports: [
- "QtQuick.Templates/ComboBox 2.0",
- "QtQuick.Templates/ComboBox 2.1",
- "QtQuick.Templates/ComboBox 2.2",
- "QtQuick.Templates/ComboBox 2.5"
- ]
- exportMetaObjectRevisions: [0, 1, 2, 5]
- Property { name: "count"; type: "int"; isReadonly: true }
- Property { name: "model"; type: "QVariant" }
- Property { name: "delegateModel"; type: "QQmlInstanceModel"; isReadonly: true; isPointer: true }
- Property { name: "pressed"; type: "bool" }
- Property { name: "highlightedIndex"; type: "int"; isReadonly: true }
- Property { name: "currentIndex"; type: "int" }
- Property { name: "currentText"; type: "string"; isReadonly: true }
- Property { name: "displayText"; type: "string" }
- Property { name: "textRole"; type: "string" }
- Property { name: "delegate"; type: "QQmlComponent"; isPointer: true }
- Property { name: "indicator"; type: "QQuickItem"; isPointer: true }
- Property { name: "popup"; type: "QQuickPopup"; isPointer: true }
- Property { name: "flat"; revision: 1; type: "bool" }
- Property { name: "down"; revision: 2; type: "bool" }
- Property { name: "editable"; revision: 2; type: "bool" }
- Property { name: "editText"; revision: 2; type: "string" }
- Property { name: "validator"; revision: 2; type: "QValidator"; isPointer: true }
- Property { name: "inputMethodHints"; revision: 2; type: "Qt::InputMethodHints" }
- Property { name: "inputMethodComposing"; revision: 2; type: "bool"; isReadonly: true }
- Property { name: "acceptableInput"; revision: 2; type: "bool"; isReadonly: true }
- Property { name: "implicitIndicatorWidth"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitIndicatorHeight"; revision: 5; type: "double"; isReadonly: true }
- Signal {
- name: "activated"
- Parameter { name: "index"; type: "int" }
- }
- Signal {
- name: "highlighted"
- Parameter { name: "index"; type: "int" }
- }
- Signal { name: "flatChanged"; revision: 1 }
- Signal { name: "accepted"; revision: 2 }
- Signal { name: "downChanged"; revision: 2 }
- Signal { name: "editableChanged"; revision: 2 }
- Signal { name: "editTextChanged"; revision: 2 }
- Signal { name: "validatorChanged"; revision: 2 }
- Signal { name: "inputMethodHintsChanged"; revision: 2 }
- Signal { name: "inputMethodComposingChanged"; revision: 2 }
- Signal { name: "acceptableInputChanged"; revision: 2 }
- Signal { name: "implicitIndicatorWidthChanged"; revision: 5 }
- Signal { name: "implicitIndicatorHeightChanged"; revision: 5 }
- Method { name: "incrementCurrentIndex" }
- Method { name: "decrementCurrentIndex" }
- Method { name: "selectAll"; revision: 2 }
- Method {
- name: "textAt"
- type: "string"
- Parameter { name: "index"; type: "int" }
- }
- Method {
- name: "find"
- type: "int"
- Parameter { name: "text"; type: "string" }
- Parameter { name: "flags"; type: "Qt::MatchFlags" }
- }
- Method {
- name: "find"
- type: "int"
- Parameter { name: "text"; type: "string" }
- }
- }
- Component {
- name: "QQuickContainer"
- defaultProperty: "contentData"
- prototype: "QQuickControl"
- exports: [
- "QtQuick.Templates/Container 2.0",
- "QtQuick.Templates/Container 2.1",
- "QtQuick.Templates/Container 2.3",
- "QtQuick.Templates/Container 2.5"
- ]
- exportMetaObjectRevisions: [0, 1, 3, 5]
- Property { name: "count"; type: "int"; isReadonly: true }
- Property { name: "contentModel"; type: "QVariant"; isReadonly: true }
- Property { name: "contentData"; type: "QObject"; isList: true; isReadonly: true }
- Property { name: "contentChildren"; type: "QQuickItem"; isList: true; isReadonly: true }
- Property { name: "currentIndex"; type: "int" }
- Property { name: "currentItem"; type: "QQuickItem"; isReadonly: true; isPointer: true }
- Property { name: "contentWidth"; revision: 5; type: "double" }
- Property { name: "contentHeight"; revision: 5; type: "double" }
- Signal { name: "contentWidthChanged"; revision: 5 }
- Signal { name: "contentHeightChanged"; revision: 5 }
- Method {
- name: "setCurrentIndex"
- Parameter { name: "index"; type: "int" }
- }
- Method { name: "incrementCurrentIndex"; revision: 1 }
- Method { name: "decrementCurrentIndex"; revision: 1 }
- Method {
- name: "itemAt"
- type: "QQuickItem*"
- Parameter { name: "index"; type: "int" }
- }
- Method {
- name: "addItem"
- Parameter { name: "item"; type: "QQuickItem"; isPointer: true }
- }
- Method {
- name: "insertItem"
- Parameter { name: "index"; type: "int" }
- Parameter { name: "item"; type: "QQuickItem"; isPointer: true }
- }
- Method {
- name: "moveItem"
- Parameter { name: "from"; type: "int" }
- Parameter { name: "to"; type: "int" }
- }
- Method {
- name: "removeItem"
- Parameter { name: "item"; type: "QVariant" }
- }
- Method {
- name: "takeItem"
- revision: 3
- type: "QQuickItem*"
- Parameter { name: "index"; type: "int" }
- }
- }
- Component { name: "QQuickContentItem"; defaultProperty: "data"; prototype: "QQuickItem" }
- Component {
- name: "QQuickControl"
- defaultProperty: "data"
- prototype: "QQuickItem"
- exports: [
- "QtQuick.Templates/Control 2.0",
- "QtQuick.Templates/Control 2.3",
- "QtQuick.Templates/Control 2.5"
- ]
- exportMetaObjectRevisions: [0, 3, 5]
- Property { name: "font"; type: "QFont" }
- Property { name: "availableWidth"; type: "double"; isReadonly: true }
- Property { name: "availableHeight"; type: "double"; isReadonly: true }
- Property { name: "padding"; type: "double" }
- Property { name: "topPadding"; type: "double" }
- Property { name: "leftPadding"; type: "double" }
- Property { name: "rightPadding"; type: "double" }
- Property { name: "bottomPadding"; type: "double" }
- Property { name: "spacing"; type: "double" }
- Property { name: "locale"; type: "QLocale" }
- Property { name: "mirrored"; type: "bool"; isReadonly: true }
- Property { name: "focusPolicy"; type: "Qt::FocusPolicy" }
- Property { name: "focusReason"; type: "Qt::FocusReason" }
- Property { name: "visualFocus"; type: "bool"; isReadonly: true }
- Property { name: "hovered"; type: "bool"; isReadonly: true }
- Property { name: "hoverEnabled"; type: "bool" }
- Property { name: "wheelEnabled"; type: "bool" }
- Property { name: "background"; type: "QQuickItem"; isPointer: true }
- Property { name: "contentItem"; type: "QQuickItem"; isPointer: true }
- Property { name: "baselineOffset"; type: "double" }
- Property { name: "palette"; revision: 3; type: "QPalette" }
- Property { name: "horizontalPadding"; revision: 5; type: "double" }
- Property { name: "verticalPadding"; revision: 5; type: "double" }
- Property { name: "implicitContentWidth"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitContentHeight"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitBackgroundWidth"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitBackgroundHeight"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "topInset"; revision: 5; type: "double" }
- Property { name: "leftInset"; revision: 5; type: "double" }
- Property { name: "rightInset"; revision: 5; type: "double" }
- Property { name: "bottomInset"; revision: 5; type: "double" }
- Signal { name: "paletteChanged"; revision: 3 }
- Signal { name: "horizontalPaddingChanged"; revision: 5 }
- Signal { name: "verticalPaddingChanged"; revision: 5 }
- Signal { name: "implicitContentWidthChanged"; revision: 5 }
- Signal { name: "implicitContentHeightChanged"; revision: 5 }
- Signal { name: "implicitBackgroundWidthChanged"; revision: 5 }
- Signal { name: "implicitBackgroundHeightChanged"; revision: 5 }
- Signal { name: "topInsetChanged"; revision: 5 }
- Signal { name: "leftInsetChanged"; revision: 5 }
- Signal { name: "rightInsetChanged"; revision: 5 }
- Signal { name: "bottomInsetChanged"; revision: 5 }
- }
- Component {
- name: "QQuickDelayButton"
- defaultProperty: "data"
- prototype: "QQuickAbstractButton"
- exports: ["QtQuick.Templates/DelayButton 2.2"]
- exportMetaObjectRevisions: [0]
- Property { name: "delay"; type: "int" }
- Property { name: "progress"; type: "double" }
- Property { name: "transition"; type: "QQuickTransition"; isPointer: true }
- Signal { name: "activated" }
- }
- Component {
- name: "QQuickDial"
- defaultProperty: "data"
- prototype: "QQuickControl"
- exports: [
- "QtQuick.Templates/Dial 2.0",
- "QtQuick.Templates/Dial 2.2",
- "QtQuick.Templates/Dial 2.5"
- ]
- exportMetaObjectRevisions: [0, 2, 5]
- Enum {
- name: "SnapMode"
- values: {
- "NoSnap": 0,
- "SnapAlways": 1,
- "SnapOnRelease": 2
- }
- }
- Enum {
- name: "InputMode"
- values: {
- "Circular": 0,
- "Horizontal": 1,
- "Vertical": 2
- }
- }
- Property { name: "from"; type: "double" }
- Property { name: "to"; type: "double" }
- Property { name: "value"; type: "double" }
- Property { name: "position"; type: "double"; isReadonly: true }
- Property { name: "angle"; type: "double"; isReadonly: true }
- Property { name: "stepSize"; type: "double" }
- Property { name: "snapMode"; type: "SnapMode" }
- Property { name: "wrap"; type: "bool" }
- Property { name: "pressed"; type: "bool"; isReadonly: true }
- Property { name: "handle"; type: "QQuickItem"; isPointer: true }
- Property { name: "live"; revision: 2; type: "bool" }
- Property { name: "inputMode"; revision: 5; type: "InputMode" }
- Signal { name: "moved"; revision: 2 }
- Signal { name: "liveChanged"; revision: 2 }
- Signal { name: "inputModeChanged"; revision: 5 }
- Method { name: "increase" }
- Method { name: "decrease" }
- }
- Component {
- name: "QQuickDialog"
- defaultProperty: "contentData"
- prototype: "QQuickPopup"
- exports: [
- "QtQuick.Templates/Dialog 2.1",
- "QtQuick.Templates/Dialog 2.3",
- "QtQuick.Templates/Dialog 2.5"
- ]
- exportMetaObjectRevisions: [0, 3, 5]
- Enum {
- name: "StandardCode"
- values: {
- "Rejected": 0,
- "Accepted": 1
- }
- }
- Property { name: "title"; type: "string" }
- Property { name: "header"; type: "QQuickItem"; isPointer: true }
- Property { name: "footer"; type: "QQuickItem"; isPointer: true }
- Property { name: "standardButtons"; type: "QPlatformDialogHelper::StandardButtons" }
- Property { name: "result"; revision: 3; type: "int" }
- Property { name: "implicitHeaderWidth"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitHeaderHeight"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitFooterWidth"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitFooterHeight"; revision: 5; type: "double"; isReadonly: true }
- Signal { name: "accepted" }
- Signal { name: "rejected" }
- Signal { name: "applied"; revision: 3 }
- Signal { name: "reset"; revision: 3 }
- Signal { name: "discarded"; revision: 3 }
- Signal { name: "helpRequested"; revision: 3 }
- Signal { name: "resultChanged"; revision: 3 }
- Method { name: "accept" }
- Method { name: "reject" }
- Method {
- name: "done"
- Parameter { name: "result"; type: "int" }
- }
- Method {
- name: "standardButton"
- revision: 3
- type: "QQuickAbstractButton*"
- Parameter { name: "button"; type: "QPlatformDialogHelper::StandardButton" }
- }
- }
- Component {
- name: "QQuickDialogButtonBox"
- defaultProperty: "contentData"
- prototype: "QQuickContainer"
- exports: [
- "QtQuick.Templates/DialogButtonBox 2.1",
- "QtQuick.Templates/DialogButtonBox 2.3",
- "QtQuick.Templates/DialogButtonBox 2.5"
- ]
- exportMetaObjectRevisions: [0, 3, 5]
- attachedType: "QQuickDialogButtonBoxAttached"
- Enum {
- name: "Position"
- values: {
- "Header": 0,
- "Footer": 1
- }
- }
- Property { name: "position"; type: "Position" }
- Property { name: "alignment"; type: "Qt::Alignment" }
- Property { name: "standardButtons"; type: "QPlatformDialogHelper::StandardButtons" }
- Property { name: "delegate"; type: "QQmlComponent"; isPointer: true }
- Property { name: "buttonLayout"; revision: 5; type: "QPlatformDialogHelper::ButtonLayout" }
- Signal { name: "accepted" }
- Signal { name: "rejected" }
- Signal { name: "helpRequested" }
- Signal {
- name: "clicked"
- Parameter { name: "button"; type: "QQuickAbstractButton"; isPointer: true }
- }
- Signal { name: "applied"; revision: 3 }
- Signal { name: "reset"; revision: 3 }
- Signal { name: "discarded"; revision: 3 }
- Signal { name: "buttonLayoutChanged"; revision: 5 }
- Method {
- name: "standardButton"
- type: "QQuickAbstractButton*"
- Parameter { name: "button"; type: "QPlatformDialogHelper::StandardButton" }
- }
- }
- Component {
- name: "QQuickDialogButtonBoxAttached"
- prototype: "QObject"
- Property { name: "buttonBox"; type: "QQuickDialogButtonBox"; isReadonly: true; isPointer: true }
- Property { name: "buttonRole"; type: "QPlatformDialogHelper::ButtonRole" }
- }
- Component {
- name: "QQuickDrawer"
- defaultProperty: "contentData"
- prototype: "QQuickPopup"
- exports: [
- "QtQuick.Templates/Drawer 2.0",
- "QtQuick.Templates/Drawer 2.2"
- ]
- exportMetaObjectRevisions: [0, 2]
- Property { name: "edge"; type: "Qt::Edge" }
- Property { name: "position"; type: "double" }
- Property { name: "dragMargin"; type: "double" }
- Property { name: "interactive"; revision: 2; type: "bool" }
- Signal { name: "interactiveChanged"; revision: 2 }
- }
- Component {
- name: "QQuickFrame"
- defaultProperty: "contentData"
- prototype: "QQuickPane"
- exports: ["QtQuick.Templates/Frame 2.0"]
- exportMetaObjectRevisions: [0]
- }
- Component {
- name: "QQuickGroupBox"
- defaultProperty: "contentData"
- prototype: "QQuickFrame"
- exports: [
- "QtQuick.Templates/GroupBox 2.0",
- "QtQuick.Templates/GroupBox 2.5"
- ]
- exportMetaObjectRevisions: [0, 5]
- Property { name: "title"; type: "string" }
- Property { name: "label"; type: "QQuickItem"; isPointer: true }
- Property { name: "implicitLabelWidth"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitLabelHeight"; revision: 5; type: "double"; isReadonly: true }
- Signal { name: "implicitLabelWidthChanged"; revision: 5 }
- Signal { name: "implicitLabelHeightChanged"; revision: 5 }
- }
- Component {
- name: "QQuickIcon"
- Property { name: "name"; type: "string" }
- Property { name: "source"; type: "QUrl" }
- Property { name: "width"; type: "int" }
- Property { name: "height"; type: "int" }
- Property { name: "color"; type: "QColor" }
- }
- Component {
- name: "QQuickItemDelegate"
- defaultProperty: "data"
- prototype: "QQuickAbstractButton"
- exports: ["QtQuick.Templates/ItemDelegate 2.0"]
- exportMetaObjectRevisions: [0]
- Property { name: "highlighted"; type: "bool" }
- }
- Component {
- name: "QQuickLabel"
- defaultProperty: "data"
- prototype: "QQuickText"
- exports: [
- "QtQuick.Templates/Label 2.0",
- "QtQuick.Templates/Label 2.3",
- "QtQuick.Templates/Label 2.5"
- ]
- exportMetaObjectRevisions: [0, 3, 5]
- Property { name: "font"; type: "QFont" }
- Property { name: "background"; type: "QQuickItem"; isPointer: true }
- Property { name: "palette"; revision: 3; type: "QPalette" }
- Property { name: "implicitBackgroundWidth"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitBackgroundHeight"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "topInset"; revision: 5; type: "double" }
- Property { name: "leftInset"; revision: 5; type: "double" }
- Property { name: "rightInset"; revision: 5; type: "double" }
- Property { name: "bottomInset"; revision: 5; type: "double" }
- Signal { name: "paletteChanged"; revision: 3 }
- Signal { name: "implicitBackgroundWidthChanged"; revision: 5 }
- Signal { name: "implicitBackgroundHeightChanged"; revision: 5 }
- Signal { name: "topInsetChanged"; revision: 5 }
- Signal { name: "leftInsetChanged"; revision: 5 }
- Signal { name: "rightInsetChanged"; revision: 5 }
- Signal { name: "bottomInsetChanged"; revision: 5 }
- }
- Component {
- name: "QQuickMenu"
- defaultProperty: "contentData"
- prototype: "QQuickPopup"
- exports: ["QtQuick.Templates/Menu 2.0", "QtQuick.Templates/Menu 2.3"]
- exportMetaObjectRevisions: [0, 3]
- Property { name: "contentModel"; type: "QVariant"; isReadonly: true }
- Property { name: "contentData"; type: "QObject"; isList: true; isReadonly: true }
- Property { name: "title"; type: "string" }
- Property { name: "count"; revision: 3; type: "int"; isReadonly: true }
- Property { name: "cascade"; revision: 3; type: "bool" }
- Property { name: "overlap"; revision: 3; type: "double" }
- Property { name: "delegate"; revision: 3; type: "QQmlComponent"; isPointer: true }
- Property { name: "currentIndex"; revision: 3; type: "int" }
- Signal {
- name: "titleChanged"
- Parameter { name: "title"; type: "string" }
- }
- Signal { name: "countChanged"; revision: 3 }
- Signal {
- name: "cascadeChanged"
- revision: 3
- Parameter { name: "cascade"; type: "bool" }
- }
- Signal { name: "overlapChanged"; revision: 3 }
- Signal { name: "delegateChanged"; revision: 3 }
- Signal { name: "currentIndexChanged"; revision: 3 }
- Method {
- name: "itemAt"
- type: "QQuickItem*"
- Parameter { name: "index"; type: "int" }
- }
- Method {
- name: "addItem"
- Parameter { name: "item"; type: "QQuickItem"; isPointer: true }
- }
- Method {
- name: "insertItem"
- Parameter { name: "index"; type: "int" }
- Parameter { name: "item"; type: "QQuickItem"; isPointer: true }
- }
- Method {
- name: "moveItem"
- Parameter { name: "from"; type: "int" }
- Parameter { name: "to"; type: "int" }
- }
- Method {
- name: "removeItem"
- Parameter { name: "item"; type: "QVariant" }
- }
- Method {
- name: "takeItem"
- revision: 3
- type: "QQuickItem*"
- Parameter { name: "index"; type: "int" }
- }
- Method {
- name: "menuAt"
- revision: 3
- type: "QQuickMenu*"
- Parameter { name: "index"; type: "int" }
- }
- Method {
- name: "addMenu"
- revision: 3
- Parameter { name: "menu"; type: "QQuickMenu"; isPointer: true }
- }
- Method {
- name: "insertMenu"
- revision: 3
- Parameter { name: "index"; type: "int" }
- Parameter { name: "menu"; type: "QQuickMenu"; isPointer: true }
- }
- Method {
- name: "removeMenu"
- revision: 3
- Parameter { name: "menu"; type: "QQuickMenu"; isPointer: true }
- }
- Method {
- name: "takeMenu"
- revision: 3
- type: "QQuickMenu*"
- Parameter { name: "index"; type: "int" }
- }
- Method {
- name: "actionAt"
- revision: 3
- type: "QQuickAction*"
- Parameter { name: "index"; type: "int" }
- }
- Method {
- name: "addAction"
- revision: 3
- Parameter { name: "action"; type: "QQuickAction"; isPointer: true }
- }
- Method {
- name: "insertAction"
- revision: 3
- Parameter { name: "index"; type: "int" }
- Parameter { name: "action"; type: "QQuickAction"; isPointer: true }
- }
- Method {
- name: "removeAction"
- revision: 3
- Parameter { name: "action"; type: "QQuickAction"; isPointer: true }
- }
- Method {
- name: "takeAction"
- revision: 3
- type: "QQuickAction*"
- Parameter { name: "index"; type: "int" }
- }
- Method {
- name: "popup"
- revision: 3
- Parameter { name: "args"; type: "QQmlV4Function"; isPointer: true }
- }
- Method { name: "dismiss"; revision: 3 }
- }
- Component {
- name: "QQuickMenuBar"
- defaultProperty: "contentData"
- prototype: "QQuickContainer"
- exports: ["QtQuick.Templates/MenuBar 2.3"]
- exportMetaObjectRevisions: [0]
- Property { name: "delegate"; type: "QQmlComponent"; isPointer: true }
- Property { name: "contentWidth"; type: "double" }
- Property { name: "contentHeight"; type: "double" }
- Property { name: "menus"; type: "QQuickMenu"; isList: true; isReadonly: true }
- Property { name: "contentData"; type: "QObject"; isList: true; isReadonly: true }
- Method {
- name: "menuAt"
- type: "QQuickMenu*"
- Parameter { name: "index"; type: "int" }
- }
- Method {
- name: "addMenu"
- Parameter { name: "menu"; type: "QQuickMenu"; isPointer: true }
- }
- Method {
- name: "insertMenu"
- Parameter { name: "index"; type: "int" }
- Parameter { name: "menu"; type: "QQuickMenu"; isPointer: true }
- }
- Method {
- name: "removeMenu"
- Parameter { name: "menu"; type: "QQuickMenu"; isPointer: true }
- }
- Method {
- name: "takeMenu"
- type: "QQuickMenu*"
- Parameter { name: "index"; type: "int" }
- }
- }
- Component {
- name: "QQuickMenuBarItem"
- defaultProperty: "data"
- prototype: "QQuickAbstractButton"
- exports: ["QtQuick.Templates/MenuBarItem 2.3"]
- exportMetaObjectRevisions: [0]
- Property { name: "menuBar"; type: "QQuickMenuBar"; isReadonly: true; isPointer: true }
- Property { name: "menu"; type: "QQuickMenu"; isPointer: true }
- Property { name: "highlighted"; type: "bool" }
- Signal { name: "triggered" }
- }
- Component {
- name: "QQuickMenuItem"
- defaultProperty: "data"
- prototype: "QQuickAbstractButton"
- exports: [
- "QtQuick.Templates/MenuItem 2.0",
- "QtQuick.Templates/MenuItem 2.3"
- ]
- exportMetaObjectRevisions: [0, 3]
- Property { name: "highlighted"; type: "bool" }
- Property { name: "arrow"; revision: 3; type: "QQuickItem"; isPointer: true }
- Property { name: "menu"; revision: 3; type: "QQuickMenu"; isReadonly: true; isPointer: true }
- Property { name: "subMenu"; revision: 3; type: "QQuickMenu"; isReadonly: true; isPointer: true }
- Signal { name: "triggered" }
- Signal { name: "arrowChanged"; revision: 3 }
- Signal { name: "menuChanged"; revision: 3 }
- Signal { name: "subMenuChanged"; revision: 3 }
- }
- Component {
- name: "QQuickMenuSeparator"
- defaultProperty: "data"
- prototype: "QQuickControl"
- exports: ["QtQuick.Templates/MenuSeparator 2.1"]
- exportMetaObjectRevisions: [0]
- }
- Component {
- name: "QQuickOverlay"
- defaultProperty: "data"
- prototype: "QQuickItem"
- exports: ["QtQuick.Templates/Overlay 2.3"]
- isCreatable: false
- exportMetaObjectRevisions: [0]
- attachedType: "QQuickOverlayAttached"
- Property { name: "modal"; type: "QQmlComponent"; isPointer: true }
- Property { name: "modeless"; type: "QQmlComponent"; isPointer: true }
- Signal { name: "pressed" }
- Signal { name: "released" }
- }
- Component {
- name: "QQuickOverlayAttached"
- prototype: "QObject"
- Property { name: "overlay"; type: "QQuickOverlay"; isReadonly: true; isPointer: true }
- Property { name: "modal"; type: "QQmlComponent"; isPointer: true }
- Property { name: "modeless"; type: "QQmlComponent"; isPointer: true }
- Signal { name: "pressed" }
- Signal { name: "released" }
- }
- Component {
- name: "QQuickPage"
- defaultProperty: "contentData"
- prototype: "QQuickPane"
- exports: [
- "QtQuick.Templates/Page 2.0",
- "QtQuick.Templates/Page 2.1",
- "QtQuick.Templates/Page 2.5"
- ]
- exportMetaObjectRevisions: [0, 1, 5]
- Property { name: "title"; type: "string" }
- Property { name: "header"; type: "QQuickItem"; isPointer: true }
- Property { name: "footer"; type: "QQuickItem"; isPointer: true }
- Property { name: "contentWidth"; revision: 1; type: "double" }
- Property { name: "contentHeight"; revision: 1; type: "double" }
- Property { name: "implicitHeaderWidth"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitHeaderHeight"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitFooterWidth"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitFooterHeight"; revision: 5; type: "double"; isReadonly: true }
- }
- Component {
- name: "QQuickPageIndicator"
- defaultProperty: "data"
- prototype: "QQuickControl"
- exports: ["QtQuick.Templates/PageIndicator 2.0"]
- exportMetaObjectRevisions: [0]
- Property { name: "count"; type: "int" }
- Property { name: "currentIndex"; type: "int" }
- Property { name: "interactive"; type: "bool" }
- Property { name: "delegate"; type: "QQmlComponent"; isPointer: true }
- }
- Component {
- name: "QQuickPane"
- defaultProperty: "contentData"
- prototype: "QQuickControl"
- exports: ["QtQuick.Templates/Pane 2.0"]
- exportMetaObjectRevisions: [0]
- Property { name: "contentWidth"; type: "double" }
- Property { name: "contentHeight"; type: "double" }
- Property { name: "contentData"; type: "QObject"; isList: true; isReadonly: true }
- Property { name: "contentChildren"; type: "QQuickItem"; isList: true; isReadonly: true }
- }
- Component {
- name: "QQuickPopup"
- defaultProperty: "contentData"
- prototype: "QObject"
- exports: [
- "QtQuick.Templates/Popup 2.0",
- "QtQuick.Templates/Popup 2.1",
- "QtQuick.Templates/Popup 2.3",
- "QtQuick.Templates/Popup 2.5"
- ]
- exportMetaObjectRevisions: [0, 1, 3, 5]
- Enum {
- name: "ClosePolicy"
- values: {
- "NoAutoClose": 0,
- "CloseOnPressOutside": 1,
- "CloseOnPressOutsideParent": 2,
- "CloseOnReleaseOutside": 4,
- "CloseOnReleaseOutsideParent": 8,
- "CloseOnEscape": 16
- }
- }
- Enum {
- name: "TransformOrigin"
- values: {
- "TopLeft": 0,
- "Top": 1,
- "TopRight": 2,
- "Left": 3,
- "Center": 4,
- "Right": 5,
- "BottomLeft": 6,
- "Bottom": 7,
- "BottomRight": 8
- }
- }
- Property { name: "x"; type: "double" }
- Property { name: "y"; type: "double" }
- Property { name: "z"; type: "double" }
- Property { name: "width"; type: "double" }
- Property { name: "height"; type: "double" }
- Property { name: "implicitWidth"; type: "double" }
- Property { name: "implicitHeight"; type: "double" }
- Property { name: "contentWidth"; type: "double" }
- Property { name: "contentHeight"; type: "double" }
- Property { name: "availableWidth"; type: "double"; isReadonly: true }
- Property { name: "availableHeight"; type: "double"; isReadonly: true }
- Property { name: "margins"; type: "double" }
- Property { name: "topMargin"; type: "double" }
- Property { name: "leftMargin"; type: "double" }
- Property { name: "rightMargin"; type: "double" }
- Property { name: "bottomMargin"; type: "double" }
- Property { name: "padding"; type: "double" }
- Property { name: "topPadding"; type: "double" }
- Property { name: "leftPadding"; type: "double" }
- Property { name: "rightPadding"; type: "double" }
- Property { name: "bottomPadding"; type: "double" }
- Property { name: "locale"; type: "QLocale" }
- Property { name: "font"; type: "QFont" }
- Property { name: "parent"; type: "QQuickItem"; isPointer: true }
- Property { name: "background"; type: "QQuickItem"; isPointer: true }
- Property { name: "contentItem"; type: "QQuickItem"; isPointer: true }
- Property { name: "contentData"; type: "QObject"; isList: true; isReadonly: true }
- Property { name: "contentChildren"; type: "QQuickItem"; isList: true; isReadonly: true }
- Property { name: "clip"; type: "bool" }
- Property { name: "focus"; type: "bool" }
- Property { name: "activeFocus"; type: "bool"; isReadonly: true }
- Property { name: "modal"; type: "bool" }
- Property { name: "dim"; type: "bool" }
- Property { name: "visible"; type: "bool" }
- Property { name: "opacity"; type: "double" }
- Property { name: "scale"; type: "double" }
- Property { name: "closePolicy"; type: "ClosePolicy" }
- Property { name: "transformOrigin"; type: "TransformOrigin" }
- Property { name: "enter"; type: "QQuickTransition"; isPointer: true }
- Property { name: "exit"; type: "QQuickTransition"; isPointer: true }
- Property { name: "spacing"; revision: 1; type: "double" }
- Property { name: "opened"; revision: 3; type: "bool"; isReadonly: true }
- Property { name: "mirrored"; revision: 3; type: "bool"; isReadonly: true }
- Property { name: "enabled"; revision: 3; type: "bool" }
- Property { name: "palette"; revision: 3; type: "QPalette" }
- Property { name: "horizontalPadding"; type: "double" }
- Property { name: "verticalPadding"; type: "double" }
- Property {
- name: "anchors"
- revision: 5
- type: "QQuickPopupAnchors"
- isReadonly: true
- isPointer: true
- }
- Property { name: "implicitContentWidth"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitContentHeight"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitBackgroundWidth"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitBackgroundHeight"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "topInset"; revision: 5; type: "double" }
- Property { name: "leftInset"; revision: 5; type: "double" }
- Property { name: "rightInset"; revision: 5; type: "double" }
- Property { name: "bottomInset"; revision: 5; type: "double" }
- Signal { name: "opened" }
- Signal { name: "closed" }
- Signal { name: "aboutToShow" }
- Signal { name: "aboutToHide" }
- Signal {
- name: "windowChanged"
- Parameter { name: "window"; type: "QQuickWindow"; isPointer: true }
- }
- Signal { name: "spacingChanged"; revision: 1 }
- Signal { name: "openedChanged"; revision: 3 }
- Signal { name: "mirroredChanged"; revision: 3 }
- Signal { name: "enabledChanged"; revision: 3 }
- Signal { name: "paletteChanged"; revision: 3 }
- Signal { name: "horizontalPaddingChanged"; revision: 5 }
- Signal { name: "verticalPaddingChanged"; revision: 5 }
- Signal { name: "implicitContentWidthChanged"; revision: 5 }
- Signal { name: "implicitContentHeightChanged"; revision: 5 }
- Signal { name: "implicitBackgroundWidthChanged"; revision: 5 }
- Signal { name: "implicitBackgroundHeightChanged"; revision: 5 }
- Signal { name: "topInsetChanged"; revision: 5 }
- Signal { name: "leftInsetChanged"; revision: 5 }
- Signal { name: "rightInsetChanged"; revision: 5 }
- Signal { name: "bottomInsetChanged"; revision: 5 }
- Method { name: "open" }
- Method { name: "close" }
- Method {
- name: "forceActiveFocus"
- Parameter { name: "reason"; type: "Qt::FocusReason" }
- }
- Method { name: "forceActiveFocus" }
- }
- Component {
- name: "QQuickPopupAnchors"
- prototype: "QObject"
- Property { name: "centerIn"; type: "QQuickItem"; isPointer: true }
- }
- Component { name: "QQuickPopupItem"; defaultProperty: "contentData"; prototype: "QQuickPage" }
- Component {
- name: "QQuickProgressBar"
- defaultProperty: "data"
- prototype: "QQuickControl"
- exports: ["QtQuick.Templates/ProgressBar 2.0"]
- exportMetaObjectRevisions: [0]
- Property { name: "from"; type: "double" }
- Property { name: "to"; type: "double" }
- Property { name: "value"; type: "double" }
- Property { name: "position"; type: "double"; isReadonly: true }
- Property { name: "visualPosition"; type: "double"; isReadonly: true }
- Property { name: "indeterminate"; type: "bool" }
- }
- Component {
- name: "QQuickRadioButton"
- defaultProperty: "data"
- prototype: "QQuickAbstractButton"
- exports: ["QtQuick.Templates/RadioButton 2.0"]
- exportMetaObjectRevisions: [0]
- }
- Component {
- name: "QQuickRadioDelegate"
- defaultProperty: "data"
- prototype: "QQuickItemDelegate"
- exports: ["QtQuick.Templates/RadioDelegate 2.0"]
- exportMetaObjectRevisions: [0]
- }
- Component {
- name: "QQuickRangeSlider"
- defaultProperty: "data"
- prototype: "QQuickControl"
- exports: [
- "QtQuick.Templates/RangeSlider 2.0",
- "QtQuick.Templates/RangeSlider 2.1",
- "QtQuick.Templates/RangeSlider 2.2",
- "QtQuick.Templates/RangeSlider 2.3",
- "QtQuick.Templates/RangeSlider 2.5"
- ]
- exportMetaObjectRevisions: [0, 1, 2, 3, 5]
- Enum {
- name: "SnapMode"
- values: {
- "NoSnap": 0,
- "SnapAlways": 1,
- "SnapOnRelease": 2
- }
- }
- Property { name: "from"; type: "double" }
- Property { name: "to"; type: "double" }
- Property { name: "first"; type: "QQuickRangeSliderNode"; isReadonly: true; isPointer: true }
- Property { name: "second"; type: "QQuickRangeSliderNode"; isReadonly: true; isPointer: true }
- Property { name: "stepSize"; type: "double" }
- Property { name: "snapMode"; type: "SnapMode" }
- Property { name: "orientation"; type: "Qt::Orientation" }
- Property { name: "live"; revision: 2; type: "bool" }
- Property { name: "horizontal"; revision: 3; type: "bool"; isReadonly: true }
- Property { name: "vertical"; revision: 3; type: "bool"; isReadonly: true }
- Property { name: "touchDragThreshold"; revision: 5; type: "double" }
- Signal { name: "liveChanged"; revision: 2 }
- Signal { name: "touchDragThresholdChanged"; revision: 5 }
- Method {
- name: "setValues"
- Parameter { name: "firstValue"; type: "double" }
- Parameter { name: "secondValue"; type: "double" }
- }
- Method {
- name: "valueAt"
- revision: 5
- type: "double"
- Parameter { name: "position"; type: "double" }
- }
- }
- Component {
- name: "QQuickRangeSliderNode"
- prototype: "QObject"
- Property { name: "value"; type: "double" }
- Property { name: "position"; type: "double"; isReadonly: true }
- Property { name: "visualPosition"; type: "double"; isReadonly: true }
- Property { name: "handle"; type: "QQuickItem"; isPointer: true }
- Property { name: "pressed"; type: "bool" }
- Property { name: "hovered"; revision: 1; type: "bool" }
- Property { name: "implicitHandleWidth"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitHandleHeight"; revision: 5; type: "double"; isReadonly: true }
- Signal { name: "hoveredChanged"; revision: 1 }
- Signal { name: "moved" }
- Method { name: "increase" }
- Method { name: "decrease" }
- }
- Component {
- name: "QQuickRoundButton"
- defaultProperty: "data"
- prototype: "QQuickButton"
- exports: ["QtQuick.Templates/RoundButton 2.1"]
- exportMetaObjectRevisions: [0]
- Property { name: "radius"; type: "double" }
- }
- Component {
- name: "QQuickScrollBar"
- defaultProperty: "data"
- prototype: "QQuickControl"
- exports: [
- "QtQuick.Templates/ScrollBar 2.0",
- "QtQuick.Templates/ScrollBar 2.2",
- "QtQuick.Templates/ScrollBar 2.3",
- "QtQuick.Templates/ScrollBar 2.4"
- ]
- exportMetaObjectRevisions: [0, 2, 3, 4]
- attachedType: "QQuickScrollBarAttached"
- Enum {
- name: "SnapMode"
- values: {
- "NoSnap": 0,
- "SnapAlways": 1,
- "SnapOnRelease": 2
- }
- }
- Enum {
- name: "Policy"
- values: {
- "AsNeeded": 0,
- "AlwaysOff": 1,
- "AlwaysOn": 2
- }
- }
- Property { name: "size"; type: "double" }
- Property { name: "position"; type: "double" }
- Property { name: "stepSize"; type: "double" }
- Property { name: "active"; type: "bool" }
- Property { name: "pressed"; type: "bool" }
- Property { name: "orientation"; type: "Qt::Orientation" }
- Property { name: "snapMode"; revision: 2; type: "SnapMode" }
- Property { name: "interactive"; revision: 2; type: "bool" }
- Property { name: "policy"; revision: 2; type: "Policy" }
- Property { name: "horizontal"; revision: 3; type: "bool"; isReadonly: true }
- Property { name: "vertical"; revision: 3; type: "bool"; isReadonly: true }
- Property { name: "minimumSize"; revision: 4; type: "double" }
- Property { name: "visualSize"; revision: 4; type: "double"; isReadonly: true }
- Property { name: "visualPosition"; revision: 4; type: "double"; isReadonly: true }
- Signal { name: "snapModeChanged"; revision: 2 }
- Signal { name: "interactiveChanged"; revision: 2 }
- Signal { name: "policyChanged"; revision: 2 }
- Signal { name: "minimumSizeChanged"; revision: 4 }
- Signal { name: "visualSizeChanged"; revision: 4 }
- Signal { name: "visualPositionChanged"; revision: 4 }
- Method { name: "increase" }
- Method { name: "decrease" }
- Method {
- name: "setSize"
- Parameter { name: "size"; type: "double" }
- }
- Method {
- name: "setPosition"
- Parameter { name: "position"; type: "double" }
- }
- }
- Component {
- name: "QQuickScrollBarAttached"
- prototype: "QObject"
- Property { name: "horizontal"; type: "QQuickScrollBar"; isPointer: true }
- Property { name: "vertical"; type: "QQuickScrollBar"; isPointer: true }
- }
- Component {
- name: "QQuickScrollIndicator"
- defaultProperty: "data"
- prototype: "QQuickControl"
- exports: [
- "QtQuick.Templates/ScrollIndicator 2.0",
- "QtQuick.Templates/ScrollIndicator 2.3",
- "QtQuick.Templates/ScrollIndicator 2.4"
- ]
- exportMetaObjectRevisions: [0, 3, 4]
- attachedType: "QQuickScrollIndicatorAttached"
- Property { name: "size"; type: "double" }
- Property { name: "position"; type: "double" }
- Property { name: "active"; type: "bool" }
- Property { name: "orientation"; type: "Qt::Orientation" }
- Property { name: "horizontal"; revision: 3; type: "bool"; isReadonly: true }
- Property { name: "vertical"; revision: 3; type: "bool"; isReadonly: true }
- Property { name: "minimumSize"; revision: 4; type: "double" }
- Property { name: "visualSize"; revision: 4; type: "double"; isReadonly: true }
- Property { name: "visualPosition"; revision: 4; type: "double"; isReadonly: true }
- Signal { name: "minimumSizeChanged"; revision: 4 }
- Signal { name: "visualSizeChanged"; revision: 4 }
- Signal { name: "visualPositionChanged"; revision: 4 }
- Method {
- name: "setSize"
- Parameter { name: "size"; type: "double" }
- }
- Method {
- name: "setPosition"
- Parameter { name: "position"; type: "double" }
- }
- }
- Component {
- name: "QQuickScrollIndicatorAttached"
- prototype: "QObject"
- Property { name: "horizontal"; type: "QQuickScrollIndicator"; isPointer: true }
- Property { name: "vertical"; type: "QQuickScrollIndicator"; isPointer: true }
- }
- Component {
- name: "QQuickScrollView"
- defaultProperty: "contentData"
- prototype: "QQuickPane"
- exports: ["QtQuick.Templates/ScrollView 2.2"]
- exportMetaObjectRevisions: [0]
- }
- Component {
- name: "QQuickSlider"
- defaultProperty: "data"
- prototype: "QQuickControl"
- exports: [
- "QtQuick.Templates/Slider 2.0",
- "QtQuick.Templates/Slider 2.1",
- "QtQuick.Templates/Slider 2.2",
- "QtQuick.Templates/Slider 2.3",
- "QtQuick.Templates/Slider 2.5"
- ]
- exportMetaObjectRevisions: [0, 1, 2, 3, 5]
- Enum {
- name: "SnapMode"
- values: {
- "NoSnap": 0,
- "SnapAlways": 1,
- "SnapOnRelease": 2
- }
- }
- Property { name: "from"; type: "double" }
- Property { name: "to"; type: "double" }
- Property { name: "value"; type: "double" }
- Property { name: "position"; type: "double"; isReadonly: true }
- Property { name: "visualPosition"; type: "double"; isReadonly: true }
- Property { name: "stepSize"; type: "double" }
- Property { name: "snapMode"; type: "SnapMode" }
- Property { name: "pressed"; type: "bool" }
- Property { name: "orientation"; type: "Qt::Orientation" }
- Property { name: "handle"; type: "QQuickItem"; isPointer: true }
- Property { name: "live"; revision: 2; type: "bool" }
- Property { name: "horizontal"; revision: 3; type: "bool"; isReadonly: true }
- Property { name: "vertical"; revision: 3; type: "bool"; isReadonly: true }
- Property { name: "touchDragThreshold"; revision: 5; type: "double" }
- Property { name: "implicitHandleWidth"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitHandleHeight"; revision: 5; type: "double"; isReadonly: true }
- Signal { name: "moved"; revision: 2 }
- Signal { name: "liveChanged"; revision: 2 }
- Signal { name: "touchDragThresholdChanged"; revision: 5 }
- Signal { name: "implicitHandleWidthChanged"; revision: 5 }
- Signal { name: "implicitHandleHeightChanged"; revision: 5 }
- Method { name: "increase" }
- Method { name: "decrease" }
- Method {
- name: "valueAt"
- revision: 1
- type: "double"
- Parameter { name: "position"; type: "double" }
- }
- }
- Component {
- name: "QQuickSpinBox"
- defaultProperty: "data"
- prototype: "QQuickControl"
- exports: [
- "QtQuick.Templates/SpinBox 2.0",
- "QtQuick.Templates/SpinBox 2.1",
- "QtQuick.Templates/SpinBox 2.2",
- "QtQuick.Templates/SpinBox 2.3",
- "QtQuick.Templates/SpinBox 2.4",
- "QtQuick.Templates/SpinBox 2.5"
- ]
- exportMetaObjectRevisions: [0, 1, 2, 3, 4, 5]
- Property { name: "from"; type: "int" }
- Property { name: "to"; type: "int" }
- Property { name: "value"; type: "int" }
- Property { name: "stepSize"; type: "int" }
- Property { name: "editable"; type: "bool" }
- Property { name: "validator"; type: "QValidator"; isPointer: true }
- Property { name: "textFromValue"; type: "QJSValue" }
- Property { name: "valueFromText"; type: "QJSValue" }
- Property { name: "up"; type: "QQuickSpinButton"; isReadonly: true; isPointer: true }
- Property { name: "down"; type: "QQuickSpinButton"; isReadonly: true; isPointer: true }
- Property { name: "inputMethodHints"; revision: 2; type: "Qt::InputMethodHints" }
- Property { name: "inputMethodComposing"; revision: 2; type: "bool"; isReadonly: true }
- Property { name: "wrap"; revision: 3; type: "bool" }
- Property { name: "displayText"; revision: 4; type: "string"; isReadonly: true }
- Signal { name: "valueModified"; revision: 2 }
- Signal { name: "inputMethodHintsChanged"; revision: 2 }
- Signal { name: "inputMethodComposingChanged"; revision: 2 }
- Signal { name: "wrapChanged"; revision: 3 }
- Signal { name: "displayTextChanged"; revision: 4 }
- Method { name: "increase" }
- Method { name: "decrease" }
- }
- Component {
- name: "QQuickSpinButton"
- prototype: "QObject"
- Property { name: "pressed"; type: "bool" }
- Property { name: "indicator"; type: "QQuickItem"; isPointer: true }
- Property { name: "hovered"; revision: 1; type: "bool" }
- Property { name: "implicitIndicatorWidth"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitIndicatorHeight"; revision: 5; type: "double"; isReadonly: true }
- Signal { name: "hoveredChanged"; revision: 1 }
- Signal { name: "implicitIndicatorWidthChanged"; revision: 5 }
- Signal { name: "implicitIndicatorHeightChanged"; revision: 5 }
- }
- Component {
- name: "QQuickStackView"
- defaultProperty: "data"
- prototype: "QQuickControl"
- exports: [
- "QtQuick.Templates/StackView 2.0",
- "QtQuick.Templates/StackView 2.1"
- ]
- exportMetaObjectRevisions: [0, 1]
- attachedType: "QQuickStackViewAttached"
- Enum {
- name: "Status"
- values: {
- "Inactive": 0,
- "Deactivating": 1,
- "Activating": 2,
- "Active": 3
- }
- }
- Enum {
- name: "LoadBehavior"
- values: {
- "DontLoad": 0,
- "ForceLoad": 1
- }
- }
- Enum {
- name: "Operation"
- values: {
- "Transition": -1,
- "Immediate": 0,
- "PushTransition": 1,
- "ReplaceTransition": 2,
- "PopTransition": 3
- }
- }
- Property { name: "busy"; type: "bool"; isReadonly: true }
- Property { name: "depth"; type: "int"; isReadonly: true }
- Property { name: "currentItem"; type: "QQuickItem"; isReadonly: true; isPointer: true }
- Property { name: "initialItem"; type: "QJSValue" }
- Property { name: "popEnter"; type: "QQuickTransition"; isPointer: true }
- Property { name: "popExit"; type: "QQuickTransition"; isPointer: true }
- Property { name: "pushEnter"; type: "QQuickTransition"; isPointer: true }
- Property { name: "pushExit"; type: "QQuickTransition"; isPointer: true }
- Property { name: "replaceEnter"; type: "QQuickTransition"; isPointer: true }
- Property { name: "replaceExit"; type: "QQuickTransition"; isPointer: true }
- Property { name: "empty"; revision: 3; type: "bool"; isReadonly: true }
- Signal { name: "emptyChanged"; revision: 3 }
- Method {
- name: "clear"
- Parameter { name: "operation"; type: "Operation" }
- }
- Method { name: "clear" }
- Method {
- name: "get"
- type: "QQuickItem*"
- Parameter { name: "index"; type: "int" }
- Parameter { name: "behavior"; type: "LoadBehavior" }
- }
- Method {
- name: "get"
- type: "QQuickItem*"
- Parameter { name: "index"; type: "int" }
- }
- Method {
- name: "find"
- type: "QQuickItem*"
- Parameter { name: "callback"; type: "QJSValue" }
- Parameter { name: "behavior"; type: "LoadBehavior" }
- }
- Method {
- name: "find"
- type: "QQuickItem*"
- Parameter { name: "callback"; type: "QJSValue" }
- }
- Method {
- name: "push"
- Parameter { name: "args"; type: "QQmlV4Function"; isPointer: true }
- }
- Method {
- name: "pop"
- Parameter { name: "args"; type: "QQmlV4Function"; isPointer: true }
- }
- Method {
- name: "replace"
- Parameter { name: "args"; type: "QQmlV4Function"; isPointer: true }
- }
- }
- Component {
- name: "QQuickStackViewAttached"
- prototype: "QObject"
- Property { name: "index"; type: "int"; isReadonly: true }
- Property { name: "view"; type: "QQuickStackView"; isReadonly: true; isPointer: true }
- Property { name: "status"; type: "QQuickStackView::Status"; isReadonly: true }
- Property { name: "visible"; type: "bool" }
- Signal { name: "activated" }
- Signal { name: "activating" }
- Signal { name: "deactivated" }
- Signal { name: "deactivating" }
- Signal { name: "removed" }
- }
- Component {
- name: "QQuickSwipe"
- prototype: "QObject"
- Property { name: "position"; type: "double" }
- Property { name: "complete"; type: "bool"; isReadonly: true }
- Property { name: "left"; type: "QQmlComponent"; isPointer: true }
- Property { name: "behind"; type: "QQmlComponent"; isPointer: true }
- Property { name: "right"; type: "QQmlComponent"; isPointer: true }
- Property { name: "leftItem"; type: "QQuickItem"; isReadonly: true; isPointer: true }
- Property { name: "behindItem"; type: "QQuickItem"; isReadonly: true; isPointer: true }
- Property { name: "rightItem"; type: "QQuickItem"; isReadonly: true; isPointer: true }
- Property { name: "enabled"; type: "bool" }
- Property { name: "transition"; type: "QQuickTransition"; isPointer: true }
- Signal { name: "completed" }
- Signal { name: "opened" }
- Signal { name: "closed" }
- Method { name: "close"; revision: 1 }
- Method {
- name: "open"
- revision: 2
- Parameter { name: "side"; type: "QQuickSwipeDelegate::Side" }
- }
- }
- Component {
- name: "QQuickSwipeDelegate"
- defaultProperty: "data"
- prototype: "QQuickItemDelegate"
- exports: [
- "QtQuick.Templates/SwipeDelegate 2.0",
- "QtQuick.Templates/SwipeDelegate 2.1",
- "QtQuick.Templates/SwipeDelegate 2.2"
- ]
- exportMetaObjectRevisions: [0, 1, 2]
- attachedType: "QQuickSwipeDelegateAttached"
- Enum {
- name: "Side"
- values: {
- "Left": 1,
- "Right": -1
- }
- }
- Property { name: "swipe"; type: "QQuickSwipe"; isReadonly: true; isPointer: true }
- }
- Component {
- name: "QQuickSwipeDelegateAttached"
- prototype: "QObject"
- Property { name: "pressed"; type: "bool"; isReadonly: true }
- Signal { name: "clicked" }
- }
- Component {
- name: "QQuickSwipeView"
- defaultProperty: "contentData"
- prototype: "QQuickContainer"
- exports: [
- "QtQuick.Templates/SwipeView 2.0",
- "QtQuick.Templates/SwipeView 2.1",
- "QtQuick.Templates/SwipeView 2.2"
- ]
- exportMetaObjectRevisions: [0, 1, 2]
- attachedType: "QQuickSwipeViewAttached"
- Property { name: "interactive"; revision: 1; type: "bool" }
- Property { name: "orientation"; revision: 2; type: "Qt::Orientation" }
- Property { name: "horizontal"; revision: 3; type: "bool"; isReadonly: true }
- Property { name: "vertical"; revision: 3; type: "bool"; isReadonly: true }
- Signal { name: "interactiveChanged"; revision: 1 }
- Signal { name: "orientationChanged"; revision: 2 }
- }
- Component {
- name: "QQuickSwipeViewAttached"
- prototype: "QObject"
- Property { name: "index"; type: "int"; isReadonly: true }
- Property { name: "isCurrentItem"; type: "bool"; isReadonly: true }
- Property { name: "view"; type: "QQuickSwipeView"; isReadonly: true; isPointer: true }
- Property { name: "isNextItem"; revision: 1; type: "bool"; isReadonly: true }
- Property { name: "isPreviousItem"; revision: 1; type: "bool"; isReadonly: true }
- }
- Component {
- name: "QQuickSwitch"
- defaultProperty: "data"
- prototype: "QQuickAbstractButton"
- exports: ["QtQuick.Templates/Switch 2.0"]
- exportMetaObjectRevisions: [0]
- Property { name: "position"; type: "double" }
- Property { name: "visualPosition"; type: "double"; isReadonly: true }
- }
- Component {
- name: "QQuickSwitchDelegate"
- defaultProperty: "data"
- prototype: "QQuickItemDelegate"
- exports: ["QtQuick.Templates/SwitchDelegate 2.0"]
- exportMetaObjectRevisions: [0]
- Property { name: "position"; type: "double" }
- Property { name: "visualPosition"; type: "double"; isReadonly: true }
- }
- Component {
- name: "QQuickTabBar"
- defaultProperty: "contentData"
- prototype: "QQuickContainer"
- exports: [
- "QtQuick.Templates/TabBar 2.0",
- "QtQuick.Templates/TabBar 2.2"
- ]
- exportMetaObjectRevisions: [0, 2]
- attachedType: "QQuickTabBarAttached"
- Enum {
- name: "Position"
- values: {
- "Header": 0,
- "Footer": 1
- }
- }
- Property { name: "position"; type: "Position" }
- Property { name: "contentWidth"; revision: 2; type: "double" }
- Property { name: "contentHeight"; revision: 2; type: "double" }
- }
- Component {
- name: "QQuickTabBarAttached"
- prototype: "QObject"
- Property { name: "index"; type: "int"; isReadonly: true }
- Property { name: "tabBar"; type: "QQuickTabBar"; isReadonly: true; isPointer: true }
- Property { name: "position"; type: "QQuickTabBar::Position"; isReadonly: true }
- }
- Component {
- name: "QQuickTabButton"
- defaultProperty: "data"
- prototype: "QQuickAbstractButton"
- exports: ["QtQuick.Templates/TabButton 2.0"]
- exportMetaObjectRevisions: [0]
- }
- Component {
- name: "QQuickTextArea"
- defaultProperty: "data"
- prototype: "QQuickTextEdit"
- exports: [
- "QtQuick.Templates/TextArea 2.0",
- "QtQuick.Templates/TextArea 2.1",
- "QtQuick.Templates/TextArea 2.3",
- "QtQuick.Templates/TextArea 2.5"
- ]
- exportMetaObjectRevisions: [0, 1, 3, 5]
- attachedType: "QQuickTextAreaAttached"
- Property { name: "font"; type: "QFont" }
- Property { name: "implicitWidth"; type: "double" }
- Property { name: "implicitHeight"; type: "double" }
- Property { name: "background"; type: "QQuickItem"; isPointer: true }
- Property { name: "placeholderText"; type: "string" }
- Property { name: "focusReason"; type: "Qt::FocusReason" }
- Property { name: "hovered"; revision: 1; type: "bool"; isReadonly: true }
- Property { name: "hoverEnabled"; revision: 1; type: "bool" }
- Property { name: "palette"; revision: 3; type: "QPalette" }
- Property { name: "placeholderTextColor"; revision: 5; type: "QColor" }
- Property { name: "implicitBackgroundWidth"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitBackgroundHeight"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "topInset"; revision: 5; type: "double" }
- Property { name: "leftInset"; revision: 5; type: "double" }
- Property { name: "rightInset"; revision: 5; type: "double" }
- Property { name: "bottomInset"; revision: 5; type: "double" }
- Signal { name: "implicitWidthChanged3" }
- Signal { name: "implicitHeightChanged3" }
- Signal {
- name: "pressAndHold"
- Parameter { name: "event"; type: "QQuickMouseEvent"; isPointer: true }
- }
- Signal {
- name: "pressed"
- revision: 1
- Parameter { name: "event"; type: "QQuickMouseEvent"; isPointer: true }
- }
- Signal {
- name: "released"
- revision: 1
- Parameter { name: "event"; type: "QQuickMouseEvent"; isPointer: true }
- }
- Signal { name: "hoveredChanged"; revision: 1 }
- Signal { name: "hoverEnabledChanged"; revision: 1 }
- Signal { name: "paletteChanged"; revision: 3 }
- Signal { name: "placeholderTextColorChanged"; revision: 5 }
- Signal { name: "implicitBackgroundWidthChanged"; revision: 5 }
- Signal { name: "implicitBackgroundHeightChanged"; revision: 5 }
- Signal { name: "topInsetChanged"; revision: 5 }
- Signal { name: "leftInsetChanged"; revision: 5 }
- Signal { name: "rightInsetChanged"; revision: 5 }
- Signal { name: "bottomInsetChanged"; revision: 5 }
- }
- Component {
- name: "QQuickTextAreaAttached"
- prototype: "QObject"
- Property { name: "flickable"; type: "QQuickTextArea"; isPointer: true }
- }
- Component {
- name: "QQuickTextField"
- defaultProperty: "data"
- prototype: "QQuickTextInput"
- exports: [
- "QtQuick.Templates/TextField 2.0",
- "QtQuick.Templates/TextField 2.1",
- "QtQuick.Templates/TextField 2.3",
- "QtQuick.Templates/TextField 2.5"
- ]
- exportMetaObjectRevisions: [0, 1, 3, 5]
- Property { name: "font"; type: "QFont" }
- Property { name: "implicitWidth"; type: "double" }
- Property { name: "implicitHeight"; type: "double" }
- Property { name: "background"; type: "QQuickItem"; isPointer: true }
- Property { name: "placeholderText"; type: "string" }
- Property { name: "focusReason"; type: "Qt::FocusReason" }
- Property { name: "hovered"; revision: 1; type: "bool"; isReadonly: true }
- Property { name: "hoverEnabled"; revision: 1; type: "bool" }
- Property { name: "palette"; revision: 3; type: "QPalette" }
- Property { name: "placeholderTextColor"; revision: 5; type: "QColor" }
- Property { name: "implicitBackgroundWidth"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "implicitBackgroundHeight"; revision: 5; type: "double"; isReadonly: true }
- Property { name: "topInset"; revision: 5; type: "double" }
- Property { name: "leftInset"; revision: 5; type: "double" }
- Property { name: "rightInset"; revision: 5; type: "double" }
- Property { name: "bottomInset"; revision: 5; type: "double" }
- Signal { name: "implicitWidthChanged3" }
- Signal { name: "implicitHeightChanged3" }
- Signal {
- name: "pressAndHold"
- Parameter { name: "event"; type: "QQuickMouseEvent"; isPointer: true }
- }
- Signal {
- name: "pressed"
- revision: 1
- Parameter { name: "event"; type: "QQuickMouseEvent"; isPointer: true }
- }
- Signal {
- name: "released"
- revision: 1
- Parameter { name: "event"; type: "QQuickMouseEvent"; isPointer: true }
- }
- Signal { name: "hoveredChanged"; revision: 1 }
- Signal { name: "hoverEnabledChanged"; revision: 1 }
- Signal { name: "paletteChanged"; revision: 3 }
- Signal { name: "placeholderTextColorChanged"; revision: 5 }
- Signal { name: "implicitBackgroundWidthChanged"; revision: 5 }
- Signal { name: "implicitBackgroundHeightChanged"; revision: 5 }
- Signal { name: "topInsetChanged"; revision: 5 }
- Signal { name: "leftInsetChanged"; revision: 5 }
- Signal { name: "rightInsetChanged"; revision: 5 }
- Signal { name: "bottomInsetChanged"; revision: 5 }
- }
- Component {
- name: "QQuickToolBar"
- defaultProperty: "contentData"
- prototype: "QQuickPane"
- exports: ["QtQuick.Templates/ToolBar 2.0"]
- exportMetaObjectRevisions: [0]
- Enum {
- name: "Position"
- values: {
- "Header": 0,
- "Footer": 1
- }
- }
- Property { name: "position"; type: "Position" }
- }
- Component {
- name: "QQuickToolButton"
- defaultProperty: "data"
- prototype: "QQuickButton"
- exports: ["QtQuick.Templates/ToolButton 2.0"]
- exportMetaObjectRevisions: [0]
- }
- Component {
- name: "QQuickToolSeparator"
- defaultProperty: "data"
- prototype: "QQuickControl"
- exports: ["QtQuick.Templates/ToolSeparator 2.1"]
- exportMetaObjectRevisions: [0]
- Property { name: "orientation"; type: "Qt::Orientation" }
- Property { name: "horizontal"; type: "bool"; isReadonly: true }
- Property { name: "vertical"; type: "bool"; isReadonly: true }
- }
- Component {
- name: "QQuickToolTip"
- defaultProperty: "contentData"
- prototype: "QQuickPopup"
- exports: [
- "QtQuick.Templates/ToolTip 2.0",
- "QtQuick.Templates/ToolTip 2.5"
- ]
- exportMetaObjectRevisions: [0, 5]
- attachedType: "QQuickToolTipAttached"
- Property { name: "delay"; type: "int" }
- Property { name: "timeout"; type: "int" }
- Property { name: "text"; type: "string" }
- Method {
- name: "show"
- revision: 5
- Parameter { name: "text"; type: "string" }
- Parameter { name: "ms"; type: "int" }
- }
- Method {
- name: "show"
- revision: 5
- Parameter { name: "text"; type: "string" }
- }
- Method { name: "hide"; revision: 5 }
- }
- Component {
- name: "QQuickToolTipAttached"
- prototype: "QObject"
- Property { name: "text"; type: "string" }
- Property { name: "delay"; type: "int" }
- Property { name: "timeout"; type: "int" }
- Property { name: "visible"; type: "bool" }
- Property { name: "toolTip"; type: "QQuickToolTip"; isReadonly: true; isPointer: true }
- Method {
- name: "show"
- Parameter { name: "text"; type: "string" }
- Parameter { name: "ms"; type: "int" }
- }
- Method {
- name: "show"
- Parameter { name: "text"; type: "string" }
- }
- Method { name: "hide" }
- }
- Component {
- name: "QQuickTumbler"
- defaultProperty: "data"
- prototype: "QQuickControl"
- exports: [
- "QtQuick.Templates/Tumbler 2.0",
- "QtQuick.Templates/Tumbler 2.1",
- "QtQuick.Templates/Tumbler 2.2"
- ]
- exportMetaObjectRevisions: [0, 1, 2]
- attachedType: "QQuickTumblerAttached"
- Enum {
- name: "PositionMode"
- values: {
- "Beginning": 0,
- "Center": 1,
- "End": 2,
- "Visible": 3,
- "Contain": 4,
- "SnapPosition": 5
- }
- }
- Property { name: "model"; type: "QVariant" }
- Property { name: "count"; type: "int"; isReadonly: true }
- Property { name: "currentIndex"; type: "int" }
- Property { name: "currentItem"; type: "QQuickItem"; isReadonly: true; isPointer: true }
- Property { name: "delegate"; type: "QQmlComponent"; isPointer: true }
- Property { name: "visibleItemCount"; type: "int" }
- Property { name: "wrap"; revision: 1; type: "bool" }
- Property { name: "moving"; revision: 2; type: "bool"; isReadonly: true }
- Signal { name: "wrapChanged"; revision: 1 }
- Signal { name: "movingChanged"; revision: 2 }
- Method {
- name: "positionViewAtIndex"
- revision: 5
- Parameter { name: "index"; type: "int" }
- Parameter { name: "mode"; type: "PositionMode" }
- }
- }
- Component {
- name: "QQuickTumblerAttached"
- prototype: "QObject"
- Property { name: "tumbler"; type: "QQuickTumbler"; isReadonly: true; isPointer: true }
- Property { name: "displacement"; type: "double"; isReadonly: true }
- }
}
diff --git a/src/imports/controls/qtquickcontrols2plugin.cpp b/src/imports/controls/qtquickcontrols2plugin.cpp
index 5e9f253d..260e7297 100644
--- a/src/imports/controls/qtquickcontrols2plugin.cpp
+++ b/src/imports/controls/qtquickcontrols2plugin.cpp
@@ -56,6 +56,7 @@
#include <QtQuickControls2/private/qquicktumblerview_p.h>
#endif
#include <QtQuickTemplates2/private/qquickoverlay_p.h>
+#include <QtQuickTemplates2/private/qquicksplitview_p.h>
#include <QtQuickControls2/private/qquickclippedtext_p.h>
#include <QtQuickControls2/private/qquickitemgroup_p.h>
#include <QtQuickTemplates2/private/qquicktheme_p_p.h>
@@ -192,6 +193,11 @@ void QtQuickControls2Plugin::registerTypes(const char *uri)
qmlRegisterType(resolvedUrl(QStringLiteral("MenuBarItem.qml")), uri, 2, 3, "MenuBarItem");
qmlRegisterUncreatableType<QQuickOverlay>(uri, 2, 3, "Overlay", QStringLiteral("Overlay is only available as an attached property."));
+ // QtQuick.Controls 2.13 (new types in Qt 5.13)
+ qmlRegisterType(resolvedUrl(QStringLiteral("SplitView.qml")), uri, 2, 13, "SplitView");
+ qmlRegisterUncreatableType<QQuickSplitHandleAttached>(uri, 2, 13, "SplitHandle",
+ QStringLiteral("SplitHandle is only available as an attached property."));
+
// Register the latest version, even if there are no new types or new revisions for existing types yet.
// Before Qt 5.12, we would do the following:
//
diff --git a/src/imports/controls/universal/SplitView.qml b/src/imports/controls/universal/SplitView.qml
new file mode 100644
index 00000000..a4ed22dd
--- /dev/null
+++ b/src/imports/controls/universal/SplitView.qml
@@ -0,0 +1,56 @@
+/****************************************************************************
+**
+** Copyright (C) 2018 The Qt Company Ltd.
+** Contact: http://www.qt.io/licensing/
+**
+** This file is part of the Qt Quick Controls 2 module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL3$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see http://www.qt.io/terms-conditions. For further
+** information use the contact form at http://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPLv3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or later as published by the Free
+** Software Foundation and appearing in the file LICENSE.GPL included in
+** the packaging of this file. Please review the following information to
+** ensure the GNU General Public License version 2.0 requirements will be
+** met: http://www.gnu.org/licenses/gpl-2.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick 2.13
+import QtQuick.Templates 2.13 as T
+import QtQuick.Controls 2.13
+import QtQuick.Controls.impl 2.13
+import QtQuick.Controls.Universal 2.13
+
+T.SplitView {
+ id: control
+ implicitWidth: Math.max(implicitBackgroundWidth + leftInset + rightInset,
+ implicitContentWidth + leftPadding + rightPadding)
+ implicitHeight: Math.max(implicitBackgroundHeight + topInset + bottomInset,
+ implicitContentHeight + topPadding + bottomPadding)
+
+ handle: Rectangle {
+ implicitWidth: control.orientation === Qt.Horizontal ? 6 : control.width
+ implicitHeight: control.orientation === Qt.Horizontal ? control.height : 6
+ color: T.SplitHandle.pressed ? control.Universal.baseMediumColor
+ : (T.SplitHandle.hovered ? control.Universal.baseMediumLowColor : control.Universal.chromeHighColor)
+ }
+}
diff --git a/src/imports/controls/universal/dependencies.json b/src/imports/controls/universal/dependencies.json
new file mode 100644
index 00000000..21ded052
--- /dev/null
+++ b/src/imports/controls/universal/dependencies.json
@@ -0,0 +1,7 @@
+[
+ {
+ "name": "QtQuick.Controls",
+ "type": "module",
+ "version": "2.0"
+ }
+]
diff --git a/src/imports/controls/universal/plugins.qmltypes b/src/imports/controls/universal/plugins.qmltypes
index 979e8437..c80ff1d4 100644
--- a/src/imports/controls/universal/plugins.qmltypes
+++ b/src/imports/controls/universal/plugins.qmltypes
@@ -4,12 +4,38 @@ import QtQuick.tooling 1.2
// It is used for QML tooling purposes only.
//
// This file was auto-generated by:
-// 'qmlplugindump -nonrelocatable QtQuick.Controls.Universal 2.3'
+// 'qmlplugindump -nonrelocatable -dependencies dependencies.json QtQuick.Controls.Universal 2.13'
Module {
- dependencies: []
+ dependencies: ["QtQuick.Controls 2.0"]
Component { name: "QQuickAttachedObject"; prototype: "QObject" }
Component {
+ name: "QQuickUniversalBusyIndicator"
+ defaultProperty: "data"
+ prototype: "QQuickItem"
+ exports: ["QtQuick.Controls.Universal.impl/BusyIndicatorImpl 2.0"]
+ exportMetaObjectRevisions: [0]
+ Property { name: "count"; type: "int" }
+ Property { name: "color"; type: "QColor" }
+ }
+ Component {
+ name: "QQuickUniversalFocusRectangle"
+ defaultProperty: "data"
+ prototype: "QQuickPaintedItem"
+ exports: ["QtQuick.Controls.Universal.impl/FocusRectangle 2.0"]
+ exportMetaObjectRevisions: [0]
+ }
+ Component {
+ name: "QQuickUniversalProgressBar"
+ defaultProperty: "data"
+ prototype: "QQuickItem"
+ exports: ["QtQuick.Controls.Universal.impl/ProgressBarImpl 2.0"]
+ exportMetaObjectRevisions: [0]
+ Property { name: "color"; type: "QColor" }
+ Property { name: "progress"; type: "double" }
+ Property { name: "indeterminate"; type: "bool" }
+ }
+ Component {
name: "QQuickUniversalStyle"
prototype: "QQuickAttachedObject"
exports: ["QtQuick.Controls.Universal/Universal 2.0"]
@@ -52,6 +78,30 @@ Module {
Property { name: "accent"; type: "QVariant" }
Property { name: "foreground"; type: "QVariant" }
Property { name: "background"; type: "QVariant" }
+ Property { name: "altHighColor"; type: "QColor"; isReadonly: true }
+ Property { name: "altLowColor"; type: "QColor"; isReadonly: true }
+ Property { name: "altMediumColor"; type: "QColor"; isReadonly: true }
+ Property { name: "altMediumHighColor"; type: "QColor"; isReadonly: true }
+ Property { name: "altMediumLowColor"; type: "QColor"; isReadonly: true }
+ Property { name: "baseHighColor"; type: "QColor"; isReadonly: true }
+ Property { name: "baseLowColor"; type: "QColor"; isReadonly: true }
+ Property { name: "baseMediumColor"; type: "QColor"; isReadonly: true }
+ Property { name: "baseMediumHighColor"; type: "QColor"; isReadonly: true }
+ Property { name: "baseMediumLowColor"; type: "QColor"; isReadonly: true }
+ Property { name: "chromeAltLowColor"; type: "QColor"; isReadonly: true }
+ Property { name: "chromeBlackHighColor"; type: "QColor"; isReadonly: true }
+ Property { name: "chromeBlackLowColor"; type: "QColor"; isReadonly: true }
+ Property { name: "chromeBlackMediumLowColor"; type: "QColor"; isReadonly: true }
+ Property { name: "chromeBlackMediumColor"; type: "QColor"; isReadonly: true }
+ Property { name: "chromeDisabledHighColor"; type: "QColor"; isReadonly: true }
+ Property { name: "chromeDisabledLowColor"; type: "QColor"; isReadonly: true }
+ Property { name: "chromeHighColor"; type: "QColor"; isReadonly: true }
+ Property { name: "chromeLowColor"; type: "QColor"; isReadonly: true }
+ Property { name: "chromeMediumColor"; type: "QColor"; isReadonly: true }
+ Property { name: "chromeMediumLowColor"; type: "QColor"; isReadonly: true }
+ Property { name: "chromeWhiteColor"; type: "QColor"; isReadonly: true }
+ Property { name: "listLowColor"; type: "QColor"; isReadonly: true }
+ Property { name: "listMediumColor"; type: "QColor"; isReadonly: true }
Signal { name: "paletteChanged" }
Method {
name: "color"
@@ -59,4 +109,32 @@ Module {
Parameter { name: "color"; type: "Color" }
}
}
+ Component {
+ prototype: "QQuickRectangle"
+ name: "QtQuick.Controls.Universal.impl/CheckIndicator 2.0"
+ exports: ["QtQuick.Controls.Universal.impl/CheckIndicator 2.0"]
+ exportMetaObjectRevisions: [0]
+ isComposite: true
+ defaultProperty: "data"
+ Property { name: "control"; type: "QQuickItem"; isPointer: true }
+ Property { name: "partiallyChecked"; type: "bool"; isReadonly: true }
+ }
+ Component {
+ prototype: "QQuickRectangle"
+ name: "QtQuick.Controls.Universal.impl/RadioIndicator 2.0"
+ exports: ["QtQuick.Controls.Universal.impl/RadioIndicator 2.0"]
+ exportMetaObjectRevisions: [0]
+ isComposite: true
+ defaultProperty: "data"
+ Property { name: "control"; type: "QVariant" }
+ }
+ Component {
+ prototype: "QQuickItem"
+ name: "QtQuick.Controls.Universal.impl/SwitchIndicator 2.0"
+ exports: ["QtQuick.Controls.Universal.impl/SwitchIndicator 2.0"]
+ exportMetaObjectRevisions: [0]
+ isComposite: true
+ defaultProperty: "data"
+ Property { name: "control"; type: "QQuickItem"; isPointer: true }
+ }
}
diff --git a/src/imports/controls/universal/universal.pri b/src/imports/controls/universal/universal.pri
index 33d0dcb0..4440acbf 100644
--- a/src/imports/controls/universal/universal.pri
+++ b/src/imports/controls/universal/universal.pri
@@ -34,6 +34,7 @@ QML_FILES += \
$$PWD/ScrollIndicator.qml \
$$PWD/Slider.qml \
$$PWD/SpinBox.qml \
+ $$PWD/SplitView.qml \
$$PWD/StackView.qml \
$$PWD/SwipeDelegate.qml \
$$PWD/SwitchDelegate.qml \
diff --git a/src/imports/controls/universal/universal.pro b/src/imports/controls/universal/universal.pro
index 399de032..99bad4da 100644
--- a/src/imports/controls/universal/universal.pro
+++ b/src/imports/controls/universal/universal.pro
@@ -1,6 +1,8 @@
TARGET = qtquickcontrols2universalstyleplugin
TARGETPATH = QtQuick/Controls.2/Universal
-IMPORT_VERSION = 2.5
+
+IMPORT_NAME = QtQuick.Controls.Universal
+IMPORT_VERSION = 2.$$QT_MINOR_VERSION
QT += qml quick
QT_PRIVATE += core-private gui-private qml-private quick-private quicktemplates2-private quickcontrols2-private
diff --git a/src/imports/platform/plugins.qmltypes b/src/imports/platform/plugins.qmltypes
index 6913405b..7b165ef3 100644
--- a/src/imports/platform/plugins.qmltypes
+++ b/src/imports/platform/plugins.qmltypes
@@ -7,7 +7,7 @@ import QtQuick.tooling 1.2
// 'qmlplugindump -nonrelocatable Qt.labs.platform 1.0'
Module {
- dependencies: ["QtQuick 2.8"]
+ dependencies: ["QtQuick 2.0"]
Component {
name: "QPlatformDialogHelper"
prototype: "QObject"
@@ -63,6 +63,18 @@ Module {
"EOL": -1
}
}
+ Enum {
+ name: "ButtonLayout"
+ values: {
+ "UnknownLayout": -1,
+ "WinLayout": 0,
+ "MacLayout": 1,
+ "KdeLayout": 2,
+ "GnomeLayout": 3,
+ "MacModelessLayout": 4,
+ "AndroidLayout": 5
+ }
+ }
Signal { name: "accept" }
Signal { name: "reject" }
}
@@ -182,6 +194,12 @@ Module {
Property { name: "options"; type: "QFontDialogOptions::FontDialogOptions" }
}
Component {
+ name: "QQuickPlatformIcon"
+ Property { name: "source"; type: "QUrl" }
+ Property { name: "name"; type: "string" }
+ Property { name: "mask"; type: "bool" }
+ }
+ Component {
name: "QQuickPlatformMenu"
defaultProperty: "data"
prototype: "QObject"
@@ -206,8 +224,10 @@ Module {
Property { name: "iconSource"; type: "QUrl" }
Property { name: "iconName"; type: "string" }
Property { name: "font"; type: "QFont" }
+ Property { name: "icon"; revision: 1; type: "QQuickPlatformIcon" }
Signal { name: "aboutToShow" }
Signal { name: "aboutToHide" }
+ Signal { name: "iconChanged"; revision: 1 }
Method {
name: "open"
Parameter { name: "args"; type: "QQmlV4Function"; isPointer: true }
@@ -284,8 +304,10 @@ Module {
Property { name: "iconName"; type: "string" }
Property { name: "shortcut"; type: "QVariant" }
Property { name: "font"; type: "QFont" }
+ Property { name: "icon"; revision: 1; type: "QQuickPlatformIcon" }
Signal { name: "triggered" }
Signal { name: "hovered" }
+ Signal { name: "iconChanged"; revision: 1 }
Method { name: "toggle" }
}
Component {
@@ -422,8 +444,11 @@ Module {
Component {
name: "QQuickPlatformSystemTrayIcon"
prototype: "QObject"
- exports: ["Qt.labs.platform/SystemTrayIcon 1.0"]
- exportMetaObjectRevisions: [0]
+ exports: [
+ "Qt.labs.platform/SystemTrayIcon 1.0",
+ "Qt.labs.platform/SystemTrayIcon 1.1"
+ ]
+ exportMetaObjectRevisions: [0, 1]
Property { name: "available"; type: "bool"; isReadonly: true }
Property { name: "supportsMessages"; type: "bool"; isReadonly: true }
Property { name: "visible"; type: "bool" }
@@ -431,11 +456,15 @@ Module {
Property { name: "iconName"; type: "string" }
Property { name: "tooltip"; type: "string" }
Property { name: "menu"; type: "QQuickPlatformMenu"; isPointer: true }
+ Property { name: "geometry"; revision: 1; type: "QRect"; isReadonly: true }
+ Property { name: "icon"; revision: 1; type: "QQuickPlatformIcon" }
Signal {
name: "activated"
Parameter { name: "reason"; type: "QPlatformSystemTrayIcon::ActivationReason" }
}
Signal { name: "messageClicked" }
+ Signal { name: "geometryChanged"; revision: 1 }
+ Signal { name: "iconChanged"; revision: 1 }
Method { name: "show" }
Method { name: "hide" }
Method {
diff --git a/src/imports/templates/plugins.qmltypes b/src/imports/templates/plugins.qmltypes
index e9404fea..48e23edd 100644
--- a/src/imports/templates/plugins.qmltypes
+++ b/src/imports/templates/plugins.qmltypes
@@ -4,7 +4,7 @@ import QtQuick.tooling 1.2
// It is used for QML tooling purposes only.
//
// This file was auto-generated by:
-// 'qmlplugindump -nonrelocatable -dependencies dependencies.json QtQuick.Templates 2.5'
+// 'qmlplugindump -nonrelocatable -dependencies dependencies.json QtQuick.Templates 2.13'
Module {
dependencies: ["QtQuick 2.9", "QtQuick.Window 2.2"]
@@ -640,6 +640,7 @@ Module {
Property { name: "width"; type: "int" }
Property { name: "height"; type: "int" }
Property { name: "color"; type: "QColor" }
+ Property { name: "cache"; type: "bool" }
}
Component {
name: "QQuickItemDelegate"
@@ -1064,7 +1065,6 @@ Module {
prototype: "QObject"
Property { name: "centerIn"; type: "QQuickItem"; isPointer: true }
}
- Component { name: "QQuickPopupItem"; defaultProperty: "contentData"; prototype: "QQuickPage" }
Component {
name: "QQuickProgressBar"
defaultProperty: "data"
@@ -1369,6 +1369,45 @@ Module {
Signal { name: "implicitIndicatorHeightChanged"; revision: 5 }
}
Component {
+ name: "QQuickSplitHandleAttached"
+ prototype: "QObject"
+ exports: ["QtQuick.Templates/SplitHandle 2.13"]
+ isCreatable: false
+ exportMetaObjectRevisions: [0]
+ Property { name: "hovered"; type: "bool"; isReadonly: true }
+ Property { name: "pressed"; type: "bool"; isReadonly: true }
+ }
+ Component {
+ name: "QQuickSplitView"
+ defaultProperty: "contentData"
+ prototype: "QQuickContainer"
+ exports: ["QtQuick.Templates/SplitView 2.13"]
+ exportMetaObjectRevisions: [0]
+ attachedType: "QQuickSplitViewAttached"
+ Property { name: "orientation"; type: "Qt::Orientation" }
+ Property { name: "resizing"; type: "bool"; isReadonly: true }
+ Property { name: "handle"; type: "QQmlComponent"; isPointer: true }
+ Method { name: "saveState"; type: "QVariant" }
+ Method {
+ name: "restoreState"
+ type: "bool"
+ Parameter { name: "state"; type: "QVariant" }
+ }
+ }
+ Component {
+ name: "QQuickSplitViewAttached"
+ prototype: "QObject"
+ Property { name: "view"; type: "QQuickSplitView"; isReadonly: true; isPointer: true }
+ Property { name: "minimumWidth"; type: "double" }
+ Property { name: "minimumHeight"; type: "double" }
+ Property { name: "preferredWidth"; type: "double" }
+ Property { name: "preferredHeight"; type: "double" }
+ Property { name: "maximumWidth"; type: "double" }
+ Property { name: "maximumHeight"; type: "double" }
+ Property { name: "fillHeight"; type: "bool" }
+ Property { name: "fillWidth"; type: "bool" }
+ }
+ Component {
name: "QQuickStackView"
defaultProperty: "data"
prototype: "QQuickControl"
diff --git a/src/imports/templates/qtquicktemplates2plugin.cpp b/src/imports/templates/qtquicktemplates2plugin.cpp
index c4ff68fc..10f9b8dd 100644
--- a/src/imports/templates/qtquicktemplates2plugin.cpp
+++ b/src/imports/templates/qtquicktemplates2plugin.cpp
@@ -82,6 +82,7 @@
#include <QtQuickTemplates2/private/qquickshortcutcontext_p_p.h>
#include <QtQuickTemplates2/private/qquickslider_p.h>
#include <QtQuickTemplates2/private/qquickspinbox_p.h>
+#include <QtQuickTemplates2/private/qquicksplitview_p.h>
#include <QtQuickTemplates2/private/qquickstackview_p.h>
#include <QtQuickTemplates2/private/qquickswipe_p.h>
#include <QtQuickTemplates2/private/qquickswipedelegate_p.h>
@@ -347,6 +348,13 @@ void QtQuickTemplates2Plugin::registerTypes(const char *uri)
qmlRegisterType<QQuickTextArea, 5>(uri, 2, 5, "TextArea");
qmlRegisterType<QQuickTextField, 5>(uri, 2, 5, "TextField");
qmlRegisterType<QQuickToolTip, 5>(uri, 2, 5, "ToolTip");
+
+ // QtQuick.Templates 2.13 (new types and revisions in Qt 5.13)
+ qmlRegisterType<QQuickSplitView>(uri, 2, 13, "SplitView");
+ qmlRegisterType<QQuickSplitViewAttached>();
+ qmlRegisterUncreatableType<QQuickSplitHandleAttached>(uri, 2, 13, "SplitHandle",
+ QStringLiteral("SplitHandle is only available as an attached property."));
+ qmlRegisterType<QQuickSplitHandleAttached>();
}
QT_END_NAMESPACE
diff --git a/src/imports/templates/templates.pro b/src/imports/templates/templates.pro
index b132f47d..3447ef90 100644
--- a/src/imports/templates/templates.pro
+++ b/src/imports/templates/templates.pro
@@ -1,6 +1,6 @@
TARGET = qtquicktemplates2plugin
TARGETPATH = QtQuick/Templates.2
-IMPORT_VERSION = 2.5
+IMPORT_VERSION = 2.$$QT_MINOR_VERSION
QT += qml quick
QT_PRIVATE += core-private gui-private qml-private quick-private quicktemplates2-private
diff --git a/src/quickcontrols2/qquickiconlabel.cpp b/src/quickcontrols2/qquickiconlabel.cpp
index 37e6060a..b246621b 100644
--- a/src/quickcontrols2/qquickiconlabel.cpp
+++ b/src/quickcontrols2/qquickiconlabel.cpp
@@ -81,6 +81,7 @@ bool QQuickIconLabelPrivate::createImage()
image->setSource(icon.source());
image->setSourceSize(QSize(icon.width(), icon.height()));
image->setColor(icon.color());
+ image->setCache(icon.cache());
QQmlEngine::setContextForObject(image, qmlContext(q));
if (componentComplete)
completeComponent(image);
@@ -114,6 +115,7 @@ void QQuickIconLabelPrivate::syncImage()
image->setSource(icon.source());
image->setSourceSize(QSize(icon.width(), icon.height()));
image->setColor(icon.color());
+ image->setCache(icon.cache());
const int valign = alignment & Qt::AlignVertical_Mask;
image->setVerticalAlignment(static_cast<QQuickImage::VAlignment>(valign));
const int halign = alignment & Qt::AlignHorizontal_Mask;
diff --git a/src/quickcontrols2/qquicktumblerview.cpp b/src/quickcontrols2/qquicktumblerview.cpp
index a510a1fe..5f5c065d 100644
--- a/src/quickcontrols2/qquicktumblerview.cpp
+++ b/src/quickcontrols2/qquicktumblerview.cpp
@@ -36,6 +36,7 @@
#include "qquicktumblerview_p.h"
+#include <QtCore/qloggingcategory.h>
#include <QtQuick/private/qquickitem_p.h>
#include <QtQuick/private/qquicklistview_p.h>
#include <QtQuick/private/qquickpathview_p.h>
@@ -45,6 +46,8 @@
QT_BEGIN_NAMESPACE
+Q_LOGGING_CATEGORY(lcTumblerView, "qt.quick.controls.tumblerview")
+
QQuickTumblerView::QQuickTumblerView(QQuickItem *parent) :
QQuickItem(parent)
{
@@ -59,6 +62,8 @@ QVariant QQuickTumblerView::model() const
void QQuickTumblerView::setModel(const QVariant &model)
{
+ qCDebug(lcTumblerView) << "setting model to:" << model << "on"
+ << (m_pathView ? static_cast<QObject*>(m_pathView) : static_cast<QObject*>(m_listView));
if (model == m_model)
return;
@@ -85,6 +90,8 @@ QQmlComponent *QQuickTumblerView::delegate() const
void QQuickTumblerView::setDelegate(QQmlComponent *delegate)
{
+ qCDebug(lcTumblerView) << "setting delegate to:" << delegate << "on"
+ << (m_pathView ? static_cast<QObject*>(m_pathView) : static_cast<QObject*>(m_listView));
if (delegate == m_delegate)
return;
@@ -135,6 +142,8 @@ void QQuickTumblerView::createView()
}
if (!m_pathView) {
+ qCDebug(lcTumblerView) << "creating PathView";
+
m_pathView = new QQuickPathView;
QQmlEngine::setContextForObject(m_pathView, qmlContext(this));
QQml_setParent_noEvent(m_pathView, this);
@@ -150,6 +159,8 @@ void QQuickTumblerView::createView()
updateView();
// Set the model.
updateModel();
+
+ qCDebug(lcTumblerView) << "finished creating PathView";
}
} else {
if (m_pathView) {
@@ -162,6 +173,8 @@ void QQuickTumblerView::createView()
}
if (!m_listView) {
+ qCDebug(lcTumblerView) << "creating ListView";
+
m_listView = new QQuickListView;
QQmlEngine::setContextForObject(m_listView, qmlContext(this));
QQml_setParent_noEvent(m_listView, this);
@@ -181,6 +194,8 @@ void QQuickTumblerView::createView()
// which we don't want when the contentItem has just been created.
m_listView->setDelegate(m_delegate);
m_listView->setHighlightMoveDuration(1000);
+
+ qCDebug(lcTumblerView) << "finished creating ListView";
}
}
}
diff --git a/src/quicktemplates2/qquickicon.cpp b/src/quicktemplates2/qquickicon.cpp
index 1b8f4797..5a689108 100644
--- a/src/quicktemplates2/qquickicon.cpp
+++ b/src/quicktemplates2/qquickicon.cpp
@@ -46,6 +46,7 @@ public:
int width = 0;
int height = 0;
QColor color = Qt::transparent;
+ bool cache = true;
enum ResolveProperties {
NameResolved = 0x0001,
@@ -53,6 +54,7 @@ public:
WidthResolved = 0x0004,
HeightResolved = 0x0008,
ColorResolved = 0x0010,
+ CacheResolved = 0x0020,
AllPropertiesResolved = 0x1ffff
};
@@ -86,7 +88,8 @@ bool QQuickIcon::operator==(const QQuickIcon &other) const
&& d->source == other.d->source
&& d->width == other.d->width
&& d->height == other.d->height
- && d->color == other.d->color);
+ && d->color == other.d->color
+ && d->cache == other.d->cache);
}
bool QQuickIcon::operator!=(const QQuickIcon &other) const
@@ -199,6 +202,26 @@ void QQuickIcon::resetColor()
d->resolveMask &= ~QQuickIconPrivate::ColorResolved;
}
+bool QQuickIcon::cache() const
+{
+ return d->cache;
+}
+
+void QQuickIcon::setCache(bool cache)
+{
+ if ((d->resolveMask & QQuickIconPrivate::CacheResolved) && d->cache == cache)
+ return;
+
+ d->cache = cache;
+ d->resolveMask |= QQuickIconPrivate::CacheResolved;
+}
+
+void QQuickIcon::resetCache()
+{
+ d->cache = true;
+ d->resolveMask &= ~QQuickIconPrivate::CacheResolved;
+}
+
QQuickIcon QQuickIcon::resolve(const QQuickIcon &other) const
{
QQuickIcon resolved = *this;
@@ -218,6 +241,9 @@ QQuickIcon QQuickIcon::resolve(const QQuickIcon &other) const
if (!(d->resolveMask & QQuickIconPrivate::ColorResolved))
resolved.setColor(other.color());
+ if (!(d->resolveMask & QQuickIconPrivate::CacheResolved))
+ resolved.setCache(other.cache());
+
return resolved;
}
diff --git a/src/quicktemplates2/qquickicon_p.h b/src/quicktemplates2/qquickicon_p.h
index 2c95bc9d..57cab720 100644
--- a/src/quicktemplates2/qquickicon_p.h
+++ b/src/quicktemplates2/qquickicon_p.h
@@ -67,6 +67,7 @@ class Q_QUICKTEMPLATES2_PRIVATE_EXPORT QQuickIcon
Q_PROPERTY(int width READ width WRITE setWidth RESET resetWidth FINAL)
Q_PROPERTY(int height READ height WRITE setHeight RESET resetHeight FINAL)
Q_PROPERTY(QColor color READ color WRITE setColor RESET resetColor FINAL)
+ Q_PROPERTY(bool cache READ cache WRITE setCache RESET resetCache FINAL)
public:
QQuickIcon();
@@ -99,6 +100,10 @@ public:
void setColor(const QColor &color);
void resetColor();
+ bool cache() const;
+ void setCache(bool cache);
+ void resetCache();
+
QQuickIcon resolve(const QQuickIcon &other) const;
private:
diff --git a/src/quicktemplates2/qquicksplitview.cpp b/src/quicktemplates2/qquicksplitview.cpp
new file mode 100644
index 00000000..cbba1671
--- /dev/null
+++ b/src/quicktemplates2/qquicksplitview.cpp
@@ -0,0 +1,2049 @@
+/****************************************************************************
+**
+** Copyright (C) 2018 The Qt Company Ltd.
+** Contact: http://www.qt.io/licensing/
+**
+** This file is part of the Qt Quick Templates 2 module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL3$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see http://www.qt.io/terms-conditions. For further
+** information use the contact form at http://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPLv3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or later as published by the Free
+** Software Foundation and appearing in the file LICENSE.GPL included in
+** the packaging of this file. Please review the following information to
+** ensure the GNU General Public License version 2.0 requirements will be
+** met: http://www.gnu.org/licenses/gpl-2.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "qquicksplitview_p.h"
+#include "qquicksplitview_p_p.h"
+#include "qquickcontentitem_p.h"
+
+#include <QtCore/qdebug.h>
+#include <QtCore/qloggingcategory.h>
+#include <QtCore/qcborarray.h>
+#include <QtCore/qcbormap.h>
+#include <QtCore/qcborvalue.h>
+#include <QtQml/QQmlInfo>
+
+QT_BEGIN_NAMESPACE
+
+/*!
+ \qmltype SplitView
+ \inherits Control
+ \instantiates QQuickSplitView
+ \inqmlmodule QtQuick.Controls
+ \since 5.13
+ \ingroup qtquickcontrols2-containers
+ \ingroup qtquickcontrols2-focusscopes
+ \brief Lays out items with a draggable splitter between each item
+
+ SplitView is a control that lays out items horizontally or vertically with
+ a draggable splitter between each item.
+
+ SplitView supports the following attached properties on items it manages:
+
+ \list
+ \li \l SplitView.minimumWidth
+ \li \l SplitView.minimumHeight
+ \li \l SplitView.preferredWidth
+ \li \l SplitView.preferredHeight
+ \li \l SplitView.maximumWidth
+ \li \l SplitView.maximumHeight
+ \li \l SplitView.fillWidth (true for only one child)
+ \li \l SplitView.fillHeight (true for only one child)
+ \endlist
+
+ In addition, each handle has the following read-only attached properties:
+
+ \list
+ \li \l SplitHandle.hovered
+ \li \l SplitHandle.pressed
+ \endlist
+
+ The preferred size of items in a SplitView can be specified via
+ \l {Item::}{implicitWidth} and \l {Item::}{implicitHeight} or
+ \c SplitView.preferredWidth and \c SplitView.preferredHeight:
+
+ \code
+ SplitView {
+ anchors.fill: parent
+
+ Item {
+ SplitView.preferredWidth: 50
+ }
+
+ // ...
+ }
+ \endcode
+
+ For a horizontal SplitView, it's not necessary to specify the preferred
+ height of each item, as they will be resized to the height of the view.
+ This applies in reverse for vertical views.
+
+ When a split handle is dragged, the \c SplitView.preferredWidth or
+ \c SplitView.preferredHeight property is overwritten, depending on the
+ \l orientation of the view.
+
+ To limit the size of items in a horizontal view, use the following
+ properties:
+
+ \code
+ SplitView {
+ anchors.fill: parent
+
+ Item {
+ SplitView.minimumWidth: 25
+ SplitView.preferredWidth: 50
+ SplitView.maximumWidth: 100
+ }
+
+ // ...
+ }
+ \endcode
+
+ To limit the size of items in a vertical view, use the following
+ properties:
+
+ \code
+ SplitView {
+ anchors.fill: parent
+ orientation: Qt.Vertical
+
+ Item {
+ SplitView.minimumHeight: 25
+ SplitView.preferredHeight: 50
+ SplitView.maximumHeight: 100
+ }
+
+ // ...
+ }
+ \endcode
+
+ There will always be one item (the fill item) in the SplitView that has
+ \c SplitView.fillWidth set to \c true (or \c SplitView.fillHeight, if
+ \l orientation is \c Qt.Vertical). This means that the item will get all
+ leftover space when other items have been laid out. By default, the last
+ visible child of the SplitView will have this set, but it can be changed by
+ explicitly setting \c fillWidth to \c true on another item.
+
+ A handle can belong to the item either on the left or top side, or on the
+ right or bottom side:
+
+ \list
+ \li If the fill item is to the right: the handle belongs to the left
+ item.
+ \li If the fill item is on the left: the handle belongs to the right
+ item.
+ \endlist
+
+ To create a SplitView with three items, and let the center item get
+ superfluous space, one could do the following:
+
+ \code
+ SplitView {
+ anchors.fill: parent
+ orientation: Qt.Horizontal
+
+ Rectangle {
+ implicitWidth: 200
+ SplitView.maximumWidth: 400
+ color: "lightblue"
+ Label {
+ text: "View 1"
+ anchors.centerIn: parent
+ }
+ }
+ Rectangle {
+ id: centerItem
+ SplitView.minimumWidth: 50
+ SplitView.fillWidth: true
+ color: "lightgray"
+ Label {
+ text: "View 2"
+ anchors.centerIn: parent
+ }
+ }
+ Rectangle {
+ implicitWidth: 200
+ color: "lightgreen"
+ Label {
+ text: "View 3"
+ anchors.centerIn: parent
+ }
+ }
+ }
+ \endcode
+
+ \section1 Serializing SplitView's State
+
+ The main purpose of SplitView is to allow users to easily configure the
+ size of various UI elements. In addition, the user's preferred sizes should
+ be remembered across sessions. To achieve this, the values of the \c
+ SplitView.preferredWidth and \c SplitView.preferredHeight properties can be
+ serialized using the \l saveState() and \l restoreState() functions:
+
+ \code
+ import QtQuick.Controls 2.5
+ import Qt.labs.settings 1.0
+
+ ApplicationWindow {
+ // ...
+
+ Component.onCompleted: splitView.restoreState(settings.splitView)
+ Component.onDestruction: settings.splitView = splitView.saveState()
+
+ Settings {
+ id: settings
+ property var splitView
+ }
+
+ SplitView {
+ id: splitView
+ // ...
+ }
+ }
+ \endcode
+
+ Alternatively, the \l {Settings::}{value()} and \l {Settings::}{setValue()}
+ functions of \l Settings can be used:
+
+ \code
+ import QtQuick.Controls 2.5
+ import Qt.labs.settings 1.0
+
+ ApplicationWindow {
+ // ...
+
+ Component.onCompleted: splitView.restoreState(settings.value("ui/splitview"))
+ Component.onDestruction: settings.setValue("ui/splitview", splitView.saveState())
+
+ Settings {
+ id: settings
+ }
+
+ SplitView {
+ id: splitView
+ // ...
+ }
+ }
+ \endcode
+
+ \sa SplitHandle, {Customizing SplitView}, {Container Controls}
+*/
+
+Q_LOGGING_CATEGORY(qlcQQuickSplitView, "qt.quick.controls.splitview")
+Q_LOGGING_CATEGORY(qlcQQuickSplitViewMouse, "qt.quick.controls.splitview.mouse")
+Q_LOGGING_CATEGORY(qlcQQuickSplitViewState, "qt.quick.controls.splitview.state")
+
+void QQuickSplitViewPrivate::updateFillIndex()
+{
+ const int count = contentModel->count();
+ const bool horizontal = isHorizontal();
+
+ qCDebug(qlcQQuickSplitView) << "looking for fillWidth/Height item amongst" << count << "items";
+
+ m_fillIndex = -1;
+ int i = 0;
+ int lastVisibleIndex = -1;
+ for (; i < count; ++i) {
+ QQuickItem *item = qobject_cast<QQuickItem*>(contentModel->object(i));
+ if (!item->isVisible())
+ continue;
+
+ lastVisibleIndex = i;
+
+ const QQuickSplitViewAttached *attached = qobject_cast<QQuickSplitViewAttached*>(
+ qmlAttachedPropertiesObject<QQuickSplitView>(item, false));
+ if (!attached)
+ continue;
+
+ if ((horizontal && attached->fillWidth()) || (!horizontal && attached->fillHeight())) {
+ m_fillIndex = i;
+ qCDebug(qlcQQuickSplitView) << "found fillWidth/Height item at index" << m_fillIndex;
+ break;
+ }
+ }
+
+ if (m_fillIndex == -1) {
+ // If there was no item with fillWidth/fillHeight set, m_fillIndex will be -1,
+ // and we'll set it to the last visible item.
+ // If there was an item with fillWidth/fillHeight set, we were already done and this will be skipped.
+ m_fillIndex = lastVisibleIndex != -1 ? lastVisibleIndex : count - 1;
+ qCDebug(qlcQQuickSplitView) << "found no fillWidth/Height item; using last item at index" << m_fillIndex;
+ }
+}
+
+/*
+ Resizes split items according to their preferred size and any constraints.
+
+ If a split item is being resized due to a split handle being dragged,
+ it will be resized accordingly.
+
+ Items that aren't visible are skipped.
+*/
+void QQuickSplitViewPrivate::layoutResizeSplitItems(qreal &usedWidth, qreal &usedHeight, int &indexBeingResizedDueToDrag)
+{
+ const int count = contentModel->count();
+ const bool horizontal = isHorizontal();
+ for (int index = 0; index < count; ++index) {
+ QQuickItem *item = qobject_cast<QQuickItem*>(contentModel->object(index));
+ if (!item->isVisible()) {
+ // The item is not visible, so skip it.
+ qCDebug(qlcQQuickSplitView).nospace() << " - " << index << ": split item " << item
+ << " at index " << index << " is not visible; skipping it and its handles (if any)";
+ continue;
+ }
+
+ const QQuickItemPrivate *itemPrivate = QQuickItemPrivate::get(item);
+ QQuickSplitViewAttached *attached = qobject_cast<QQuickSplitViewAttached*>(
+ qmlAttachedPropertiesObject<QQuickSplitView>(item, false));
+ const auto sizeData = effectiveSizeData(itemPrivate, attached);
+
+ const bool resizeLeftItem = m_fillIndex > m_pressedHandleIndex;
+ // True if any handle is pressed.
+ const bool isAHandlePressed = m_pressedHandleIndex != -1;
+ // True if this particular item is being resized as a result of a handle being dragged.
+ const bool isBeingResized = isAHandlePressed && ((resizeLeftItem && index == m_pressedHandleIndex)
+ || (!resizeLeftItem && index == m_pressedHandleIndex + 1));
+ if (isBeingResized) {
+ indexBeingResizedDueToDrag = index;
+ qCDebug(qlcQQuickSplitView).nospace() << " - " << index << ": dragging handle for item";
+ }
+
+ const qreal size = horizontal ? width : height;
+ qreal requestedSize = 0;
+ if (isBeingResized) {
+ // Don't let the mouse go past either edge of the SplitView.
+ const qreal clampedMousePos = horizontal
+ ? qBound(0.0, m_mousePos.x(), width)
+ : qBound(0.0, m_mousePos.y(), height);
+
+ // We also need to ensure that the item's edge doesn't go too far
+ // out and hence give the item more space than is available.
+ const int firstIndex = resizeLeftItem ? m_pressedHandleIndex + 1 : 0;
+ const int lastIndex = resizeLeftItem ? contentModel->count() - 1 : m_pressedHandleIndex;
+ const qreal accumulated = accumulatedSize(firstIndex, lastIndex);
+
+ const qreal mousePosRelativeToLeftHandleEdge = horizontal
+ ? m_pressPos.x() - m_handlePosBeforePress.x()
+ : m_pressPos.y() - m_handlePosBeforePress.y();
+
+ const QQuickItem *pressedHandleItem = m_handleItems.at(m_pressedHandleIndex);
+ const qreal pressedHandleSize = horizontal ? pressedHandleItem->width() : pressedHandleItem->height();
+
+ if (resizeLeftItem) {
+ // The handle shouldn't cross other handles, so use the right edge of
+ // the first handle to the left as the left edge.
+ qreal leftEdge = 0;
+ if (m_pressedHandleIndex - 1 >= 0) {
+ const QQuickItem *leftHandle = m_handleItems.at(m_pressedHandleIndex - 1);
+ leftEdge = horizontal
+ ? leftHandle->x() + leftHandle->width()
+ : leftHandle->y() + leftHandle->height();
+ }
+
+ // The mouse can be clicked anywhere in the handle, and if we don't account for
+ // its position within the handle, the handle will jump when dragged.
+ const qreal pressedHandlePos = clampedMousePos - mousePosRelativeToLeftHandleEdge;
+
+ const qreal rightStop = size - accumulated - pressedHandleSize;
+ qreal leftStop = qMax(leftEdge, pressedHandlePos);
+ // qBound() doesn't care if min is greater than max, but we do.
+ if (leftStop > rightStop)
+ leftStop = rightStop;
+ const qreal newHandlePos = qBound(leftStop, pressedHandlePos, rightStop);
+ const qreal newItemSize = newHandlePos - leftEdge;
+
+ // Modify the preferredWidth, otherwise the original implicitWidth/preferredWidth
+ // will be used on the next layout (when it's no longer being resized).
+ if (!attached) {
+ // Force the attached object to be created since we rely on it.
+ attached = qobject_cast<QQuickSplitViewAttached*>(
+ qmlAttachedPropertiesObject<QQuickSplitView>(item, true));
+ }
+
+ /*
+ Users could conceivably respond to size changes in items by setting attached
+ SplitView properties:
+
+ onWidthChanged: if (width < 10) secondItem.SplitView.preferredWidth = 100
+
+ We handle this by doing another layout after the current layout if the
+ attached/implicit size properties are set during this layout. However, we also
+ need to set preferredWidth/Height here (for reasons mentioned in the comment above),
+ but we don't want this to count as a request for a delayed layout, so we guard against it.
+ */
+ m_ignoreNextLayoutRequest = true;
+
+ if (horizontal)
+ attached->setPreferredWidth(newItemSize);
+ else
+ attached->setPreferredHeight(newItemSize);
+
+ // We still need to use requestedWidth in the setWidth() call below,
+ // because sizeData has already been calculated and now contains an old
+ // effectivePreferredWidth value.
+ requestedSize = newItemSize;
+
+ qCDebug(qlcQQuickSplitView).nospace() << " - " << index << ": resized (dragged) " << item
+ << " (clampedMousePos=" << clampedMousePos
+ << " pressedHandlePos=" << pressedHandlePos
+ << " accumulated=" << accumulated
+ << " leftEdge=" << leftEdge
+ << " leftStop=" << leftStop
+ << " rightStop=" << rightStop
+ << " newHandlePos=" << newHandlePos
+ << " newItemSize=" << newItemSize << ")";
+ } else { // Resizing the item on the right.
+ // The handle shouldn't cross other handles, so use the left edge of
+ // the first handle to the right as the right edge.
+ qreal rightEdge = size;
+ if (m_pressedHandleIndex + 1 < m_handleItems.size()) {
+ const QQuickItem *rightHandle = m_handleItems.at(m_pressedHandleIndex + 1);
+ rightEdge = horizontal ? rightHandle->x() : rightHandle->y();
+ }
+
+ // The mouse can be clicked anywhere in the handle, and if we don't account for
+ // its position within the handle, the handle will jump when dragged.
+ const qreal pressedHandlePos = clampedMousePos - mousePosRelativeToLeftHandleEdge;
+
+ const qreal leftStop = accumulated - pressedHandleSize;
+ qreal rightStop = qMin(rightEdge - pressedHandleSize, pressedHandlePos);
+ // qBound() doesn't care if min is greater than max, but we do.
+ if (rightStop < leftStop)
+ rightStop = leftStop;
+ const qreal newHandlePos = qBound(leftStop, pressedHandlePos, rightStop);
+ const qreal newItemSize = rightEdge - (newHandlePos + pressedHandleSize);
+
+ // Modify the preferredWidth, otherwise the original implicitWidth/preferredWidth
+ // will be used on the next layout (when it's no longer being resized).
+ if (!attached) {
+ // Force the attached object to be created since we rely on it.
+ attached = qobject_cast<QQuickSplitViewAttached*>(
+ qmlAttachedPropertiesObject<QQuickSplitView>(item, true));
+ }
+
+ m_ignoreNextLayoutRequest = true;
+
+ if (horizontal)
+ attached->setPreferredWidth(newItemSize);
+ else
+ attached->setPreferredHeight(newItemSize);
+
+ // We still need to use requestedSize in the setWidth()/setHeight() call below,
+ // because sizeData has already been calculated and now contains an old
+ // effectivePreferredWidth/Height value.
+ requestedSize = newItemSize;
+
+ qCDebug(qlcQQuickSplitView).nospace() << " - " << index << ": resized (dragged) " << item
+ << " (clampedMousePos=" << clampedMousePos
+ << " pressedHandlePos=" << pressedHandlePos
+ << " accumulated=" << accumulated
+ << " leftEdge=" << rightEdge
+ << " leftStop=" << leftStop
+ << " rightStop=" << rightStop
+ << " newHandlePos=" << newHandlePos
+ << " newItemSize=" << newItemSize << ")";
+ }
+ } else if (index != m_fillIndex) {
+ // No handle is being dragged and we're not the fill item,
+ // so set our preferred size as we normally would.
+ requestedSize = horizontal
+ ? sizeData.effectivePreferredWidth : sizeData.effectivePreferredHeight;
+ }
+
+ if (index != m_fillIndex) {
+ if (horizontal) {
+ item->setWidth(qBound(
+ sizeData.effectiveMinimumWidth,
+ requestedSize,
+ sizeData.effectiveMaximumWidth));
+ item->setHeight(height);
+ } else {
+ item->setWidth(width);
+ item->setHeight(qBound(
+ sizeData.effectiveMinimumHeight,
+ requestedSize,
+ sizeData.effectiveMaximumHeight));
+ }
+
+ qCDebug(qlcQQuickSplitView).nospace() << " - " << index << ": resized split item " << item
+ << " (effective"
+ << " minW=" << sizeData.effectiveMinimumWidth
+ << ", minH=" << sizeData.effectiveMinimumHeight
+ << ", prfW=" << sizeData.effectivePreferredWidth
+ << ", prfH=" << sizeData.effectivePreferredHeight
+ << ", maxW=" << sizeData.effectiveMaximumWidth
+ << ", maxH=" << sizeData.effectiveMaximumHeight << ")";
+
+ // Keep track of how much space has been used so far.
+ if (horizontal)
+ usedWidth += item->width();
+ else
+ usedHeight += item->height();
+ } else if (indexBeingResizedDueToDrag != m_fillIndex) {
+ // The fill item is resized afterwards, outside of the loop.
+ qCDebug(qlcQQuickSplitView).nospace() << " - " << index << ": skipping fill item as we resize it last";
+ }
+
+ // Also account for the size of the handle for this item (if any).
+ // We do this for the fill item too, which is why it's outside of the check above.
+ if (index < count - 1 && m_handle) {
+ QQuickItem *handleItem = m_handleItems.at(index);
+ // The handle for an item that's not visible will usually already be skipped
+ // with the item visibility check higher up, but if the view looks like this
+ // [ visible ] | [ visible (fill) ] | [ hidden ]
+ // ^
+ // hidden
+ // and we're iterating over the second item (which is visible but has no handle),
+ // we need to add an extra check for it to avoid it still taking up space.
+ if (handleItem->isVisible()) {
+ if (horizontal) {
+ qCDebug(qlcQQuickSplitView).nospace() << " - " << index
+ << ": handle takes up " << handleItem->width() << " width";
+ usedWidth += handleItem->width();
+ } else {
+ qCDebug(qlcQQuickSplitView).nospace() << " - " << index
+ << ": handle takes up " << handleItem->height() << " height";
+ usedHeight += handleItem->height();
+ }
+ } else {
+ qCDebug(qlcQQuickSplitView).nospace() << " - " << index << ": handle is not visible; skipping it";
+ }
+ }
+ }
+}
+
+/*
+ Resizes the fill item by giving it the remaining space
+ after all other items have been resized.
+
+ Items that aren't visible are skipped.
+*/
+void QQuickSplitViewPrivate::layoutResizeFillItem(QQuickItem *fillItem,
+ qreal &usedWidth, qreal &usedHeight, int indexBeingResizedDueToDrag)
+{
+ // Only bother resizing if it it's visible. Also, if it's being resized due to a drag,
+ // then we've already set its size in layoutResizeSplitItems(), so no need to do it here.
+ if (!fillItem->isVisible() || indexBeingResizedDueToDrag == m_fillIndex) {
+ qCDebug(qlcQQuickSplitView).nospace() << m_fillIndex << ": - fill item " << fillItem
+ << " is not visible or was already resized due to a drag;"
+ << " skipping it and its handles (if any)";
+ return;
+ }
+
+ const QQuickItemPrivate *fillItemPrivate = QQuickItemPrivate::get(fillItem);
+ const QQuickSplitViewAttached *attached = qobject_cast<QQuickSplitViewAttached*>(
+ qmlAttachedPropertiesObject<QQuickSplitView>(fillItem, false));
+ const auto fillSizeData = effectiveSizeData(fillItemPrivate, attached);
+ if (isHorizontal()) {
+ fillItem->setWidth(qBound(
+ fillSizeData.effectiveMinimumWidth,
+ width - usedWidth,
+ fillSizeData.effectiveMaximumWidth));
+ fillItem->setHeight(height);
+ } else {
+ fillItem->setWidth(width);
+ fillItem->setHeight(qBound(
+ fillSizeData.effectiveMinimumHeight,
+ height - usedHeight,
+ fillSizeData.effectiveMaximumHeight));
+ }
+
+ qCDebug(qlcQQuickSplitView).nospace() << " - " << m_fillIndex
+ << ": resized split fill item " << fillItem << " (effective"
+ << " minW=" << fillSizeData.effectiveMinimumWidth
+ << ", minH=" << fillSizeData.effectiveMinimumHeight
+ << ", maxW=" << fillSizeData.effectiveMaximumWidth
+ << ", maxH=" << fillSizeData.effectiveMaximumHeight << ")";
+}
+
+/*
+ Positions items by laying them out in a row or column.
+
+ Items that aren't visible are skipped.
+*/
+void QQuickSplitViewPrivate::layoutPositionItems(const QQuickItem *fillItem)
+{
+ const bool horizontal = isHorizontal();
+ const int count = contentModel->count();
+ qreal usedWidth = 0;
+ qreal usedHeight = 0;
+
+ for (int i = 0; i < count; ++i) {
+ QQuickItem *item = qobject_cast<QQuickItem*>(contentModel->object(i));
+ if (!item->isVisible()) {
+ qCDebug(qlcQQuickSplitView).nospace() << " - " << i << ": split item " << item
+ << " is not visible; skipping it and its handles (if any)";
+ continue;
+ }
+
+ // Position the item.
+ if (horizontal) {
+ item->setX(usedWidth);
+ item->setY(0);
+ } else {
+ item->setX(0);
+ item->setY(usedHeight);
+ }
+
+ // Keep track of how much space has been used so far.
+ if (horizontal)
+ usedWidth += item->width();
+ else
+ usedHeight += item->height();
+
+ if (Q_UNLIKELY(qlcQQuickSplitView().isDebugEnabled())) {
+ const QQuickItemPrivate *fillItemPrivate = QQuickItemPrivate::get(fillItem);
+ const QQuickSplitViewAttached *attached = qobject_cast<QQuickSplitViewAttached*>(
+ qmlAttachedPropertiesObject<QQuickSplitView>(fillItem, false));
+ const auto sizeData = effectiveSizeData(fillItemPrivate, attached);
+ qCDebug(qlcQQuickSplitView).nospace() << " - " << i << ": positioned "
+ << (i == m_fillIndex ? "fill item " : "item ") << item << " (effective"
+ << " minW=" << sizeData.effectiveMinimumWidth
+ << ", minH=" << sizeData.effectiveMinimumHeight
+ << ", prfW=" << sizeData.effectivePreferredWidth
+ << ", prfH=" << sizeData.effectivePreferredHeight
+ << ", maxW=" << sizeData.effectiveMaximumWidth
+ << ", maxH=" << sizeData.effectiveMaximumHeight << ")";
+ }
+
+ // Position the handle for this item (if any).
+ if (i < count - 1 && m_handle) {
+ // Position the handle.
+ QQuickItem *handleItem = m_handleItems.at(i);
+ handleItem->setX(horizontal ? usedWidth : 0);
+ handleItem->setY(horizontal ? 0 : usedHeight);
+
+ if (horizontal)
+ usedWidth += handleItem->width();
+ else
+ usedHeight += handleItem->height();
+
+ qCDebug(qlcQQuickSplitView).nospace() << " - " << i << ": positioned handle " << handleItem;
+ }
+ }
+}
+
+void QQuickSplitViewPrivate::requestLayout()
+{
+ Q_Q(QQuickSplitView);
+ q->polish();
+}
+
+void QQuickSplitViewPrivate::layout()
+{
+ if (!componentComplete)
+ return;
+
+ if (m_layingOut)
+ return;
+
+ const int count = contentModel->count();
+ if (count <= 0)
+ return;
+
+ Q_ASSERT_X(m_fillIndex < count, Q_FUNC_INFO, qPrintable(
+ QString::fromLatin1("m_fillIndex is %1 but our count is %2").arg(m_fillIndex).arg(count)));
+
+ Q_ASSERT_X(!m_handle || m_handleItems.size() == count - 1, Q_FUNC_INFO, qPrintable(QString::fromLatin1(
+ "Expected %1 handle items, but there are %2").arg(count - 1).arg(m_handleItems.size())));
+
+ // We allow mouse events to instantly trigger layouts, whereas with e.g.
+ // attached properties being set, we require a delayed layout.
+ // To prevent recursive calls during mouse events, we need this guard.
+ QBoolBlocker guard(m_layingOut, true);
+
+ const bool horizontal = isHorizontal();
+ qCDebug(qlcQQuickSplitView) << "laying out" << count << "split items"
+ << (horizontal ? "horizontally" : "vertically") << "in SplitView" << q_func();
+
+ qreal usedWidth = 0;
+ qreal usedHeight = 0;
+ int indexBeingResizedDueToDrag = -1;
+
+ qCDebug(qlcQQuickSplitView) << " resizing:";
+
+ // First, resize the items. We need to do this first because otherwise fill
+ // items would take up all of the remaining space as soon as they are encountered.
+ layoutResizeSplitItems(usedWidth, usedHeight, indexBeingResizedDueToDrag);
+
+ qCDebug(qlcQQuickSplitView).nospace()
+ << " - (remaining width=" << width - usedWidth
+ << " remaining height=" << height - usedHeight << ")";
+
+ // Give the fill item the remaining space.
+ QQuickItem *fillItem = qobject_cast<QQuickItem*>(contentModel->object(m_fillIndex));
+ layoutResizeFillItem(fillItem, usedWidth, usedHeight, indexBeingResizedDueToDrag);
+
+ qCDebug(qlcQQuickSplitView) << " positioning:";
+
+ // Position the items.
+ layoutPositionItems(fillItem);
+
+ qCDebug(qlcQQuickSplitView).nospace() << "finished layouting";
+}
+
+void QQuickSplitViewPrivate::createHandles()
+{
+ Q_ASSERT(m_handle);
+ // A handle only makes sense if there are two items on either side.
+ if (contentModel->count() <= 1)
+ return;
+
+ // Create new handle items if there aren't enough.
+ const int count = contentModel->count() - 1;
+ qCDebug(qlcQQuickSplitView) << "creating" << count << "handles";
+ m_handleItems.reserve(count);
+ for (int i = 0; i < count; ++i)
+ createHandleItem(i);
+}
+
+void QQuickSplitViewPrivate::createHandleItem(int index)
+{
+ Q_Q(QQuickSplitView);
+ if (contentModel->count() <= 1)
+ return;
+
+ qCDebug(qlcQQuickSplitView) << "- creating handle for split item at index" << index
+ << "from handle component" << m_handle;
+
+ // If we don't use the correct context, it won't be possible to refer to
+ // the control's id from within the delegate.
+ QQmlContext *creationContext = m_handle->creationContext();
+ // The component might not have been created in QML, in which case
+ // the creation context will be null and we have to create it ourselves.
+ if (!creationContext)
+ creationContext = qmlContext(q);
+ QQmlContext *context = new QQmlContext(creationContext, q);
+ context->setContextObject(q);
+ QQuickItem *item = qobject_cast<QQuickItem*>(m_handle->beginCreate(context));
+ if (item) {
+ // Insert the item to our list of items *before* its parent is set to us,
+ // so that we can avoid it being added as a content item by checking
+ // if it is in the list in isContent().
+ m_handleItems.insert(index, item);
+
+ item->setParentItem(q);
+
+ m_handle->completeCreate();
+ resizeHandle(item);
+ }
+}
+
+void QQuickSplitViewPrivate::removeExcessHandles()
+{
+ int excess = m_handleItems.size() - qMax(0, contentModel->count() - 1);
+ for (; excess > 0; --excess) {
+ QQuickItem *handleItem = m_handleItems.takeLast();
+ delete handleItem;
+ }
+}
+
+qreal QQuickSplitViewPrivate::accumulatedSize(int firstIndex, int lastIndex) const
+{
+ qreal size = 0.0;
+ const bool horizontal = isHorizontal();
+ for (int i = firstIndex; i <= lastIndex; ++i) {
+ QQuickItem *item = qobject_cast<QQuickItem*>(contentModel->object(i));
+ if (item->isVisible()) {
+ if (i != m_fillIndex) {
+ size += horizontal ? item->width() : item->height();
+ } else {
+ // If the fill item has a minimum size specified, we must respect it.
+ const QQuickSplitViewAttached *attached = qobject_cast<QQuickSplitViewAttached*>(
+ qmlAttachedPropertiesObject<QQuickSplitView>(item, false));
+ if (attached) {
+ const QQuickSplitViewAttachedPrivate *attachedPrivate
+ = QQuickSplitViewAttachedPrivate::get(attached);
+ if (horizontal && attachedPrivate->m_isMinimumWidthSet)
+ size += attachedPrivate->m_minimumWidth;
+ else if (!horizontal && attachedPrivate->m_isMinimumHeightSet)
+ size += attachedPrivate->m_minimumHeight;
+ }
+ }
+ }
+
+ // Only add the handle's width if there's actually a handle for this split item index.
+ if (i < lastIndex || lastIndex < contentModel->count() - 1) {
+ const QQuickItem *handleItem = m_handleItems.at(i);
+ if (handleItem->isVisible())
+ size += horizontal ? handleItem->width() : handleItem->height();
+ }
+ }
+ return size;
+}
+
+qreal effectiveMinimumWidth(const QQuickSplitViewAttachedPrivate *attachedPrivate)
+{
+ return attachedPrivate && attachedPrivate->m_isMinimumWidthSet ? attachedPrivate->m_minimumWidth : 0;
+}
+
+qreal effectiveMinimumHeight(const QQuickSplitViewAttachedPrivate *attachedPrivate)
+{
+ return attachedPrivate && attachedPrivate->m_isMinimumHeightSet ? attachedPrivate->m_minimumHeight : 0;
+}
+
+qreal effectivePreferredWidth(const QQuickSplitViewAttachedPrivate *attachedPrivate,
+ const QQuickItemPrivate *itemPrivate)
+{
+ return attachedPrivate && attachedPrivate->m_isPreferredWidthSet
+ ? attachedPrivate->m_preferredWidth : itemPrivate->implicitWidth;
+}
+
+qreal effectivePreferredHeight(const QQuickSplitViewAttachedPrivate *attachedPrivate,
+ const QQuickItemPrivate *itemPrivate)
+{
+ return attachedPrivate && attachedPrivate->m_isPreferredHeightSet
+ ? attachedPrivate->m_preferredHeight : itemPrivate->implicitHeight;
+}
+
+qreal effectiveMaximumWidth(const QQuickSplitViewAttachedPrivate *attachedPrivate)
+{
+ return attachedPrivate && attachedPrivate->m_isMaximumWidthSet
+ ? attachedPrivate->m_maximumWidth : std::numeric_limits<qreal>::infinity();
+}
+
+qreal effectiveMaximumHeight(const QQuickSplitViewAttachedPrivate *attachedPrivate)
+{
+ return attachedPrivate && attachedPrivate->m_isMaximumHeightSet
+ ? attachedPrivate->m_maximumHeight : std::numeric_limits<qreal>::infinity();
+}
+
+// We don't just take an index, because the item and attached properties object
+// will both be used outside of this function by calling code, so save some
+// time by not accessing them twice.
+QQuickSplitViewPrivate::EffectiveSizeData QQuickSplitViewPrivate::effectiveSizeData(
+ const QQuickItemPrivate *itemPrivate, const QQuickSplitViewAttached *attached) const
+{
+ EffectiveSizeData data;
+ const QQuickSplitViewAttachedPrivate *attachedPrivate = attached ? QQuickSplitViewAttachedPrivate::get(attached) : nullptr;
+ data.effectiveMinimumWidth = effectiveMinimumWidth(attachedPrivate);
+ data.effectiveMinimumHeight = effectiveMinimumHeight(attachedPrivate);
+ data.effectivePreferredWidth = effectivePreferredWidth(attachedPrivate, itemPrivate);
+ data.effectivePreferredHeight = effectivePreferredHeight(attachedPrivate, itemPrivate);
+ data.effectiveMaximumWidth = effectiveMaximumWidth(attachedPrivate);
+ data.effectiveMaximumHeight = effectiveMaximumHeight(attachedPrivate);
+ return data;
+}
+
+int QQuickSplitViewPrivate::handleIndexForSplitIndex(int splitIndex) const
+{
+ // If it's the last item in the view, it doesn't have a handle, so use
+ // the handle for the previous item.
+ return splitIndex == contentModel->count() - 1 ? splitIndex - 1 : splitIndex;
+}
+
+void QQuickSplitViewPrivate::destroyHandles()
+{
+ qDeleteAll(m_handleItems);
+ m_handleItems.clear();
+}
+
+void QQuickSplitViewPrivate::resizeHandle(QQuickItem *handleItem)
+{
+ const bool horizontal = isHorizontal();
+ handleItem->setWidth(horizontal ? handleItem->implicitWidth() : width);
+ handleItem->setHeight(horizontal ? height : handleItem->implicitHeight());
+}
+
+void QQuickSplitViewPrivate::resizeHandles()
+{
+ for (QQuickItem *handleItem : m_handleItems)
+ resizeHandle(handleItem);
+}
+
+void QQuickSplitViewPrivate::updateHandleVisibilities()
+{
+ // If this is the first item that is visible, we won't have any
+ // handles yet, because we don't create a handle if we only have one item.
+ if (m_handleItems.isEmpty())
+ return;
+
+ // If the visibility/children change makes any item the last (right/bottom-most)
+ // visible item, we don't want to display a handle for it either:
+ // [ visible (fill) ] | [ hidden ] | [ hidden ]
+ // ^ ^
+ // hidden hidden
+ const int count = contentModel->count();
+ int lastVisibleItemIndex = -1;
+ for (int i = count - 1; i >= 0; --i) {
+ const QQuickItem *item = qobject_cast<QQuickItem*>(contentModel->object(i));
+ if (item->isVisible()) {
+ lastVisibleItemIndex = i;
+ break;
+ }
+ }
+
+ for (int i = 0; i < count - 1; ++i) {
+ const QQuickItem *item = qobject_cast<QQuickItem*>(contentModel->object(i));
+ QQuickItem *handleItem = m_handleItems.at(i);
+ if (i != lastVisibleItemIndex)
+ handleItem->setVisible(item->isVisible());
+ else
+ handleItem->setVisible(false);
+ qCDebug(qlcQQuickSplitView) << "set visible property of handle at index"
+ << i << "to" << handleItem->isVisible();
+ }
+}
+
+void QQuickSplitViewPrivate::setResizing(bool resizing)
+{
+ Q_Q(QQuickSplitView);
+ if (resizing == m_resizing)
+ return;
+
+ m_resizing = resizing;
+ emit q->resizingChanged();
+}
+
+bool QQuickSplitViewPrivate::isHorizontal() const
+{
+ return m_orientation == Qt::Horizontal;
+}
+
+QQuickItem *QQuickSplitViewPrivate::getContentItem()
+{
+ Q_Q(QQuickSplitView);
+ if (QQuickItem *item = QQuickContainerPrivate::getContentItem())
+ return item;
+
+ // TODO: why are several created?
+ return new QQuickContentItem(q);
+}
+
+void QQuickSplitViewPrivate::handlePress(const QPointF &point)
+{
+ Q_Q(QQuickSplitView);
+ QQuickContainerPrivate::handlePress(point);
+
+ QQuickItem *pressedItem = q->childAt(point.x(), point.y());
+ const int pressedHandleIndex = m_handleItems.indexOf(pressedItem);
+ if (pressedHandleIndex != -1) {
+ m_pressedHandleIndex = pressedHandleIndex;
+ m_pressPos = point;
+ m_mousePos = point;
+
+ const QQuickItem *leftOrTopItem = qobject_cast<QQuickItem*>(contentModel->object(m_pressedHandleIndex));
+ const QQuickItem *rightOrBottomItem = qobject_cast<QQuickItem*>(contentModel->object(m_pressedHandleIndex + 1));
+ const bool isHorizontal = m_orientation == Qt::Horizontal;
+ m_leftOrTopItemSizeBeforePress = isHorizontal ? leftOrTopItem->width() : leftOrTopItem->height();
+ m_rightOrBottomItemSizeBeforePress = isHorizontal ? rightOrBottomItem->width() : rightOrBottomItem->height();
+ m_handlePosBeforePress = pressedItem->position();
+
+ // Avoid e.g. Flickable stealing our drag if we're inside it.
+ q->setKeepMouseGrab(true);
+
+ // Force the attached object to be created since we rely on it.
+ QQuickSplitHandleAttached *handleAttached = qobject_cast<QQuickSplitHandleAttached*>(
+ qmlAttachedPropertiesObject<QQuickSplitHandleAttached>(pressedItem, true));
+ QQuickSplitHandleAttachedPrivate::get(handleAttached)->setPressed(true);
+
+ setResizing(true);
+
+ qCDebug(qlcQQuickSplitViewMouse).nospace() << "handled press -"
+ << " left/top index=" << m_pressedHandleIndex << ","
+ << " size before press=" << m_leftOrTopItemSizeBeforePress << ","
+ << " right/bottom index=" << m_pressedHandleIndex + 1 << ","
+ << " size before press=" << m_rightOrBottomItemSizeBeforePress;
+ }
+}
+
+void QQuickSplitViewPrivate::handleMove(const QPointF &point)
+{
+ QQuickContainerPrivate::handleMove(point);
+
+ if (m_pressedHandleIndex != -1) {
+ m_mousePos = point;
+ // Don't request layouts for input events because we want
+ // resizing to be as responsive and smooth as possible.
+ updatePolish();
+ }
+}
+
+void QQuickSplitViewPrivate::handleRelease(const QPointF &point)
+{
+ Q_Q(QQuickSplitView);
+ QQuickContainerPrivate::handleRelease(point);
+
+ if (m_pressedHandleIndex != -1) {
+ QQuickItem *pressedHandle = m_handleItems.at(m_pressedHandleIndex);
+ QQuickSplitHandleAttached *handleAttached = qobject_cast<QQuickSplitHandleAttached*>(
+ qmlAttachedPropertiesObject<QQuickSplitHandleAttached>(pressedHandle, true));
+ QQuickSplitHandleAttachedPrivate::get(handleAttached)->setPressed(false);
+ }
+
+ setResizing(false);
+
+ m_pressedHandleIndex = -1;
+ m_pressPos = QPointF();
+ m_mousePos = QPointF();
+ m_handlePosBeforePress = QPointF();
+ m_leftOrTopItemSizeBeforePress = 0.0;
+ m_rightOrBottomItemSizeBeforePress = 0.0;
+ q->setKeepMouseGrab(false);
+}
+
+void QQuickSplitViewPrivate::itemVisibilityChanged(QQuickItem *item)
+{
+ const int itemIndex = contentModel->indexOf(item, nullptr);
+ Q_ASSERT(itemIndex != -1);
+
+ qCDebug(qlcQQuickSplitView) << "visible property of split item"
+ << item << "at index" << itemIndex << "changed to" << item->isVisible();
+
+ // The visibility of an item just changed, so we need to update the visibility
+ // of the corresponding handle (if one exists).
+
+ const int handleIndex = handleIndexForSplitIndex(itemIndex);
+ QQuickItem *handleItem = m_handleItems.at(handleIndex);
+ handleItem->setVisible(item->isVisible());
+
+ qCDebug(qlcQQuickSplitView) << "set visible property of handle item"
+ << handleItem << "at index" << handleIndex << "to" << item->isVisible();
+
+ updateHandleVisibilities();
+ updateFillIndex();
+ requestLayout();
+}
+
+void QQuickSplitViewPrivate::itemImplicitWidthChanged(QQuickItem *)
+{
+ requestLayout();
+}
+
+void QQuickSplitViewPrivate::itemImplicitHeightChanged(QQuickItem *)
+{
+ requestLayout();
+}
+
+void QQuickSplitViewPrivate::updatePolish()
+{
+ layout();
+}
+
+QQuickSplitViewPrivate *QQuickSplitViewPrivate::get(QQuickSplitView *splitView)
+{
+ return splitView->d_func();
+}
+
+QQuickSplitView::QQuickSplitView(QQuickItem *parent)
+ : QQuickContainer(*(new QQuickSplitViewPrivate), parent)
+{
+ Q_D(QQuickSplitView);
+ d->changeTypes |= QQuickItemPrivate::Visibility;
+
+ setAcceptedMouseButtons(Qt::LeftButton);
+}
+
+QQuickSplitView::QQuickSplitView(QQuickSplitViewPrivate &dd, QQuickItem *parent)
+ : QQuickContainer(dd, parent)
+{
+ Q_D(QQuickSplitView);
+ d->changeTypes |= QQuickItemPrivate::Visibility;
+
+ setAcceptedMouseButtons(Qt::LeftButton);
+}
+
+QQuickSplitView::~QQuickSplitView()
+{
+ Q_D(QQuickSplitView);
+ for (int i = 0; i < d->contentModel->count(); ++i) {
+ QQuickItem *item = qobject_cast<QQuickItem*>(d->contentModel->object(i));
+ d->removeImplicitSizeListener(item);
+ }
+}
+
+/*!
+ \qmlproperty enumeration QtQuick.Controls::SplitView::orientation
+
+ This property holds the orientation of the SplitView.
+
+ The orientation determines how the split items are laid out:
+
+ Possible values:
+ \value Qt.Horizontal The items are laid out horizontally (default).
+ \value Qt.Vertical The items are laid out vertically.
+*/
+Qt::Orientation QQuickSplitView::orientation() const
+{
+ Q_D(const QQuickSplitView);
+ return d->m_orientation;
+}
+
+void QQuickSplitView::setOrientation(Qt::Orientation orientation)
+{
+ Q_D(QQuickSplitView);
+ if (orientation == d->m_orientation)
+ return;
+
+ d->m_orientation = orientation;
+ d->resizeHandles();
+ d->requestLayout();
+ emit orientationChanged();
+}
+
+/*!
+ \qmlproperty bool QtQuick.Controls::SplitView::resizing
+ \readonly
+
+ This property is \c true when the user is resizing
+ split items by dragging on the splitter handles.
+*/
+bool QQuickSplitView::isResizing() const
+{
+ Q_D(const QQuickSplitView);
+ return d->m_resizing;
+}
+
+/*!
+ \qmlproperty Component QtQuick.Controls::SplitView::handle
+
+ This property holds the handle component.
+
+ An instance of this component will be instantiated \c {count - 1}
+ times, as long as \l count is greater than than \c {1}.
+
+ The following table explains how each handle will be resized
+ depending on the orientation of the split view:
+
+ \table
+ \header
+ \li Orientation
+ \li Handle Width
+ \li Handle Height
+ \row
+ \li \c Qt.Horizontal
+ \li \c implicitWidth
+ \li The \l height of the SplitView.
+ \row
+ \li \c Qt.Vertical
+ \li The \l width of the SplitView.
+ \li \c implicitHeight
+ \endtable
+
+ \sa {Customizing SplitView}
+*/
+QQmlComponent *QQuickSplitView::handle()
+{
+ Q_D(const QQuickSplitView);
+ return d->m_handle;
+}
+
+void QQuickSplitView::setHandle(QQmlComponent *handle)
+{
+ Q_D(QQuickSplitView);
+ if (handle == d->m_handle)
+ return;
+
+ qCDebug(qlcQQuickSplitView) << "setting handle" << handle;
+
+ if (d->m_handle)
+ d->destroyHandles();
+
+ d->m_handle = handle;
+
+ if (d->m_handle)
+ d->createHandles();
+
+ d->requestLayout();
+
+ emit handleChanged();
+}
+
+bool QQuickSplitView::isContent(QQuickItem *item) const
+{
+ Q_D(const QQuickSplitView);
+ if (!qmlContext(item))
+ return false;
+
+ if (QQuickItemPrivate::get(item)->isTransparentForPositioner())
+ return false;
+
+ return !d->m_handleItems.contains(item);
+}
+
+QQuickSplitViewAttached *QQuickSplitView::qmlAttachedProperties(QObject *object)
+{
+ return new QQuickSplitViewAttached(object);
+}
+
+/*!
+ \qmlmethod var QtQuick.Controls::SplitView::saveState()
+
+ Saves the preferred sizes of split items into a byte array and returns it.
+
+ \sa {Serializing SplitView's State}, restoreState()
+*/
+QVariant QQuickSplitView::saveState()
+{
+ Q_D(QQuickSplitView);
+ qCDebug(qlcQQuickSplitViewState) << "saving state for split items in" << this;
+
+ // Save the preferred sizes of each split item.
+ QCborArray cborArray;
+ for (int i = 0; i < d->contentModel->count(); ++i) {
+ const QQuickItem *item = qobject_cast<QQuickItem*>(d->contentModel->object(i));
+ const QQuickSplitViewAttached *attached = qobject_cast<QQuickSplitViewAttached*>(
+ qmlAttachedPropertiesObject<QQuickSplitView>(item, false));
+ // Don't serialise stuff if we don't need to. If a split item was given a preferred
+ // size in QML or it was dragged, it will have an attached object and either
+ // m_isPreferredWidthSet or m_isPreferredHeightSet (or both) will be true,
+ // so items without these can be skipped. We write the index of each item
+ // that has data so that we know which item to set it on when restoring.
+ if (!attached)
+ continue;
+
+ const QQuickSplitViewAttachedPrivate *attachedPrivate = QQuickSplitViewAttachedPrivate::get(attached);
+ if (!attachedPrivate->m_isPreferredWidthSet && !attachedPrivate->m_isPreferredHeightSet)
+ continue;
+
+ QCborMap cborMap;
+ cborMap[QLatin1String("index")] = i;
+ if (attachedPrivate->m_isPreferredWidthSet) {
+ cborMap[QLatin1String("preferredWidth")] = static_cast<double>(attachedPrivate->m_preferredWidth);
+
+ qCDebug(qlcQQuickSplitViewState).nospace() << "- wrote preferredWidth of "
+ << attachedPrivate->m_preferredWidth << " for split item at index " << i;
+ }
+ if (attachedPrivate->m_isPreferredHeightSet) {
+ cborMap[QLatin1String("preferredHeight")] = static_cast<double>(attachedPrivate->m_preferredHeight);
+
+ qCDebug(qlcQQuickSplitViewState).nospace() << "- wrote preferredHeight of "
+ << attachedPrivate->m_preferredHeight << " for split item at index " << i;
+ }
+
+ cborArray.append(cborMap);
+ }
+
+ const QByteArray byteArray = cborArray.toCborValue().toCbor();
+ qCDebug(qlcQQuickSplitViewState) << "the resulting byte array is:" << byteArray;
+ return QVariant(byteArray);
+}
+
+/*!
+ \qmlmethod bool QtQuick.Controls::SplitView::restoreState(state)
+
+ Reads the preferred sizes from \a state and applies them to the split items.
+
+ Returns \c true if the state was successfully restored, otherwise \c false.
+
+ \sa {Serializing SplitView's State}, saveState()
+*/
+bool QQuickSplitView::restoreState(const QVariant &state)
+{
+ const QByteArray cborByteArray = state.toByteArray();
+ Q_D(QQuickSplitView);
+ if (cborByteArray.isEmpty())
+ return false;
+
+ QCborParserError parserError;
+ const QCborValue cborValue(QCborValue::fromCbor(cborByteArray, &parserError));
+ if (parserError.error != QCborError::NoError) {
+ qmlWarning(this) << "Error reading SplitView state:" << parserError.errorString();
+ return false;
+ }
+
+ qCDebug(qlcQQuickSplitViewState) << "restoring state for split items of" << this
+ << "from the following string:" << state;
+
+ const QCborArray cborArray(cborValue.toArray());
+ const int ourCount = d->contentModel->count();
+ // This could conceivably happen if items were removed from the SplitView since the state was last saved.
+ if (cborArray.size() > ourCount) {
+ qmlWarning(this) << "Error reading SplitView state: expected "
+ << ourCount << " or less split items but got " << cborArray.size();
+ return false;
+ }
+
+ for (auto it = cborArray.constBegin(); it != cborArray.constEnd(); ++it) {
+ QCborMap cborMap(it->toMap());
+ const int splitItemIndex = cborMap.value(QLatin1String("index")).toInteger();
+ const bool isPreferredWidthSet = cborMap.contains(QLatin1String("preferredWidth"));
+ const bool isPreferredHeightSet = cborMap.contains(QLatin1String("preferredWidth"));
+
+ QQuickItem *item = qobject_cast<QQuickItem*>(d->contentModel->object(splitItemIndex));
+ // If the split item does not have a preferred size specified in QML, it could still have
+ // been resized via dragging before it was saved. In this case, it won't have an
+ // attached object upon application startup, so we create it.
+ QQuickSplitViewAttached *attached = qobject_cast<QQuickSplitViewAttached*>(
+ qmlAttachedPropertiesObject<QQuickSplitView>(item, true));
+ if (isPreferredWidthSet) {
+ const qreal preferredWidth = cborMap.value(QLatin1String("preferredWidth")).toDouble();
+ attached->setPreferredWidth(preferredWidth);
+ }
+ if (isPreferredHeightSet) {
+ const qreal preferredHeight = cborMap.value(QLatin1String("preferredHeight")).toDouble();
+ attached->setPreferredHeight(preferredHeight);
+ }
+
+ const QQuickSplitViewAttachedPrivate *attachedPrivate = QQuickSplitViewAttachedPrivate::get(attached);
+ qCDebug(qlcQQuickSplitViewState).nospace()
+ << "- restored the following state for split item at index " << splitItemIndex
+ << ": preferredWidthSet=" << attachedPrivate->m_isPreferredWidthSet
+ << " preferredWidth=" << attachedPrivate->m_preferredWidth
+ << " preferredHeightSet=" << attachedPrivate->m_isPreferredHeightSet
+ << " preferredHeight=" << attachedPrivate->m_preferredHeight;
+ }
+
+ return true;
+}
+
+void QQuickSplitView::componentComplete()
+{
+ Q_D(QQuickSplitView);
+ QQuickControl::componentComplete();
+ d->resizeHandles();
+ d->updateFillIndex();
+ d->updatePolish();
+}
+
+void QQuickSplitView::hoverMoveEvent(QHoverEvent *event)
+{
+ Q_D(QQuickSplitView);
+ QQuickContainer::hoverMoveEvent(event);
+
+ QQuickItem *hoveredItem = childAt(event->pos().x(), event->pos().y());
+ if (!hoveredItem) {
+ // No handle is hovered.
+ if (d->m_hoveredHandleIndex != -1) {
+ // The previously-hovered handle is no longer hovered.
+ QQuickItem *oldHoveredHandle = d->m_handleItems.at(d->m_hoveredHandleIndex);
+ QQuickSplitHandleAttached *handleAttached = qobject_cast<QQuickSplitHandleAttached*>(
+ qmlAttachedPropertiesObject<QQuickSplitHandleAttached>(oldHoveredHandle, true));
+ QQuickSplitHandleAttachedPrivate::get(handleAttached)->setHovered(false);
+ }
+
+ qCDebug(qlcQQuickSplitViewMouse) << "handle item at index" << d->m_hoveredHandleIndex << "is no longer hovered";
+
+ d->m_hoveredHandleIndex = -1;
+
+#if QT_CONFIG(cursor)
+ setCursor(Qt::ArrowCursor);
+#endif
+ } else {
+ // A child item of ours is hovered.
+
+ // First, clear the hovered flag of any previously-hovered handle.
+ if (d->m_hoveredHandleIndex != -1) {
+ QQuickItem *oldHoveredHandle = d->m_handleItems.at(d->m_hoveredHandleIndex);
+ QQuickSplitHandleAttached *handleAttached = qobject_cast<QQuickSplitHandleAttached*>(
+ qmlAttachedPropertiesObject<QQuickSplitHandleAttached>(oldHoveredHandle, true));
+ QQuickSplitHandleAttachedPrivate::get(handleAttached)->setHovered(false);
+ }
+
+ // Now check if the newly hovered item is actually a handle.
+ const int hoveredHandleIndex = d->m_handleItems.indexOf(hoveredItem);
+ if (hoveredHandleIndex == -1)
+ return;
+
+ // It's a handle, so it's now hovered.
+ d->m_hoveredHandleIndex = hoveredHandleIndex;
+
+ QQuickSplitHandleAttached *handleAttached = qobject_cast<QQuickSplitHandleAttached*>(
+ qmlAttachedPropertiesObject<QQuickSplitHandleAttached>(hoveredItem, true));
+ QQuickSplitHandleAttachedPrivate::get(handleAttached)->setHovered(true);
+
+#if QT_CONFIG(cursor)
+ setCursor(d->m_orientation == Qt::Horizontal ? Qt::SplitHCursor : Qt::SplitVCursor);
+#endif
+
+ qCDebug(qlcQQuickSplitViewMouse) << "handle item at index" << d->m_hoveredHandleIndex << "is now hovered";
+ }
+}
+
+void QQuickSplitView::geometryChanged(const QRectF &newGeometry, const QRectF &oldGeometry)
+{
+ Q_D(QQuickSplitView);
+ QQuickControl::geometryChanged(newGeometry, oldGeometry);
+ d->resizeHandles();
+ d->requestLayout();
+}
+
+void QQuickSplitView::itemAdded(int index, QQuickItem *item)
+{
+ Q_D(QQuickSplitView);
+ if (QQuickItemPrivate::get(item)->isTransparentForPositioner())
+ return;
+
+ const int count = d->contentModel->count();
+ qCDebug(qlcQQuickSplitView).nospace() << "split item " << item << " added at index " << index
+ << "; there are now " << count << " items";
+
+ QQuickSplitViewAttached *attached = qobject_cast<QQuickSplitViewAttached*>(
+ qmlAttachedPropertiesObject<QQuickSplitView>(item, false));
+ if (attached)
+ QQuickSplitViewAttachedPrivate::get(attached)->setView(this);
+
+ // Only need to add handles if we have more than one split item.
+ if (count > 1) {
+ // If the item was added at the end, it shouldn't get a handle;
+ // the handle always goes to the split item on the left.
+ d->createHandleItem(index < count - 1 ? index : index - 1);
+ }
+
+ d->addImplicitSizeListener(item);
+
+ d->updateHandleVisibilities();
+ d->updateFillIndex();
+ d->requestLayout();
+}
+
+void QQuickSplitView::itemMoved(int index, QQuickItem *item)
+{
+ Q_D(QQuickSplitView);
+ if (QQuickItemPrivate::get(item)->isTransparentForPositioner())
+ return;
+
+ qCDebug(qlcQQuickSplitView) << "split item" << item << "moved to index" << index;
+
+ d->updateHandleVisibilities();
+ d->updateFillIndex();
+ d->requestLayout();
+}
+
+void QQuickSplitView::itemRemoved(int index, QQuickItem *item)
+{
+ Q_D(QQuickSplitView);
+ if (QQuickItemPrivate::get(item)->isTransparentForPositioner())
+ return;
+
+ qCDebug(qlcQQuickSplitView).nospace() << "split item " << item << " removed from index " << index
+ << "; there are now " << d->contentModel->count() << " items";
+
+ // Clear hovered/pressed handle if there are any.
+ if (d->m_hoveredHandleIndex != -1 || d->m_pressedHandleIndex != -1) {
+ const int handleIndex = d->m_hoveredHandleIndex != -1 ? d->m_hoveredHandleIndex : d->m_pressedHandleIndex;
+ QQuickItem *itemHandle = d->m_handleItems.at(handleIndex);
+ QQuickSplitHandleAttached *handleAttached = qobject_cast<QQuickSplitHandleAttached*>(
+ qmlAttachedPropertiesObject<QQuickSplitHandleAttached>(itemHandle, false));
+ if (handleAttached) {
+ auto handleAttachedPrivate = QQuickSplitHandleAttachedPrivate::get(handleAttached);
+ handleAttachedPrivate->setHovered(false);
+ handleAttachedPrivate->setPressed(false);
+ }
+
+ setKeepMouseGrab(false);
+ d->m_hoveredHandleIndex = -1;
+ d->m_pressedHandleIndex = -1;
+ }
+
+ // Unset any attached properties since the item is no longer owned by us.
+ QQuickSplitViewAttached *attached = qobject_cast<QQuickSplitViewAttached*>(
+ qmlAttachedPropertiesObject<QQuickSplitView>(item, false));
+ if (attached)
+ QQuickSplitViewAttachedPrivate::get(attached)->setView(this);
+
+ d->removeImplicitSizeListener(item);
+
+ d->removeExcessHandles();
+ d->updateHandleVisibilities();
+ d->updateFillIndex();
+ d->requestLayout();
+}
+
+#if QT_CONFIG(accessibility)
+QAccessible::Role QQuickSplitView::accessibleRole() const
+{
+ return QAccessible::Pane;
+}
+#endif
+
+QQuickSplitViewAttached::QQuickSplitViewAttached(QObject *parent)
+ : QObject(*(new QQuickSplitViewAttachedPrivate), parent)
+{
+ Q_D(QQuickSplitViewAttached);
+ QQuickItem *item = qobject_cast<QQuickItem *>(parent);
+ if (!item) {
+ qmlWarning(parent) << "SplitView: attached properties can only be used on Items";
+ return;
+ }
+
+ if (QQuickItemPrivate::get(item)->isTransparentForPositioner())
+ return;
+
+ d->m_splitItem = item;
+
+ // Child items get added to SplitView's contentItem, so we have to ensure
+ // that exists first before trying to set m_splitView.
+ // Apparently, in some cases it's normal for the parent item
+ // to not exist until shortly after this constructor has run.
+ if (!item->parentItem())
+ return;
+
+ // This will get hit when attached SplitView properties are imperatively set
+ // on an item that previously had none set, for example.
+ QQuickSplitView *splitView = qobject_cast<QQuickSplitView*>(item->parentItem()->parentItem());
+ if (!splitView) {
+ qmlWarning(parent) << "SplitView: attached properties must be accessed through a direct child of SplitView";
+ return;
+ }
+
+ d->setView(splitView);
+}
+
+/*!
+ \qmlattachedproperty SplitView QtQuick.Controls::SplitView::view
+
+ This attached property holds the split view of the item it is
+ attached to, or \c null if the item is not in a split view.
+*/
+QQuickSplitView *QQuickSplitViewAttached::view() const
+{
+ Q_D(const QQuickSplitViewAttached);
+ return d->m_splitView;
+}
+
+/*!
+ \qmlattachedproperty real QtQuick.Controls::SplitView::minimumWidth
+
+ This attached property controls the minimum width of the split item.
+ The \l preferredWidth is bound within the \l minimumWidth and
+ \l maximumWidth. A split item cannot be dragged to be smaller than
+ its \c minimumWidth.
+
+ The default value is \c 0. To reset this property to its default value,
+ set it to \c undefined.
+
+ \sa maximumWidth, preferredWidth, fillWidth, minimumHeight
+*/
+qreal QQuickSplitViewAttached::minimumWidth() const
+{
+ Q_D(const QQuickSplitViewAttached);
+ return d->m_minimumWidth;
+}
+
+void QQuickSplitViewAttached::setMinimumWidth(qreal width)
+{
+ Q_D(QQuickSplitViewAttached);
+ d->m_isMinimumWidthSet = true;
+ if (qFuzzyCompare(width, d->m_minimumWidth))
+ return;
+
+ d->m_minimumWidth = width;
+ d->requestLayoutView();
+ emit minimumWidthChanged();
+}
+
+void QQuickSplitViewAttached::resetMinimumWidth()
+{
+ Q_D(QQuickSplitViewAttached);
+ const qreal oldEffectiveMinimumWidth = effectiveMinimumWidth(d);
+
+ d->m_isMinimumWidthSet = false;
+ d->m_minimumWidth = -1;
+
+ const qreal newEffectiveMinimumWidth = effectiveMinimumWidth(d);
+ if (qFuzzyCompare(newEffectiveMinimumWidth, oldEffectiveMinimumWidth))
+ return;
+
+ d->requestLayoutView();
+ emit minimumWidthChanged();
+}
+
+/*!
+ \qmlattachedproperty real QtQuick.Controls::SplitView::minimumHeight
+
+ This attached property controls the minimum height of the split item.
+ The \l preferredHeight is bound within the \l minimumHeight and
+ \l maximumHeight. A split item cannot be dragged to be smaller than
+ its \c minimumHeight.
+
+ The default value is \c 0. To reset this property to its default value,
+ set it to \c undefined.
+
+ \sa maximumHeight, preferredHeight, fillHeight, minimumWidth
+*/
+qreal QQuickSplitViewAttached::minimumHeight() const
+{
+ Q_D(const QQuickSplitViewAttached);
+ return d->m_minimumHeight;
+}
+
+void QQuickSplitViewAttached::setMinimumHeight(qreal height)
+{
+ Q_D(QQuickSplitViewAttached);
+ d->m_isMinimumHeightSet = true;
+ if (qFuzzyCompare(height, d->m_minimumHeight))
+ return;
+
+ d->m_minimumHeight = height;
+ d->requestLayoutView();
+ emit minimumHeightChanged();
+}
+
+void QQuickSplitViewAttached::resetMinimumHeight()
+{
+ Q_D(QQuickSplitViewAttached);
+ const qreal oldEffectiveMinimumHeight = effectiveMinimumHeight(d);
+
+ d->m_isMinimumHeightSet = false;
+ d->m_minimumHeight = -1;
+
+ const qreal newEffectiveMinimumHeight = effectiveMinimumHeight(d);
+ if (qFuzzyCompare(newEffectiveMinimumHeight, oldEffectiveMinimumHeight))
+ return;
+
+ d->requestLayoutView();
+ emit minimumHeightChanged();
+}
+
+/*!
+ \qmlattachedproperty real QtQuick.Controls::SplitView::preferredWidth
+
+ This attached property controls the preferred width of the split item. The
+ preferred width will be used as the size of the item, and will be bound
+ within the \l minimumWidth and \l maximumWidth. If the preferred width
+ is not set, the item's \l {Item::}{implicitWidth} will be used.
+
+ When a split item is resized, the preferredWidth will be set in order
+ to keep track of the new size.
+
+ By default, this property is not set, and therefore
+ \l {Item::}{implicitWidth} will be used instead. To reset this property to
+ its default value, set it to \c undefined.
+
+ \note Do not set the \l width property of a split item, as it will be
+ overwritten upon each layout of the SplitView.
+
+ \sa minimumWidth, maximumWidth, fillWidth, preferredHeight
+*/
+qreal QQuickSplitViewAttached::preferredWidth() const
+{
+ Q_D(const QQuickSplitViewAttached);
+ return d->m_preferredWidth;
+}
+
+void QQuickSplitViewAttached::setPreferredWidth(qreal width)
+{
+ Q_D(QQuickSplitViewAttached);
+ d->m_isPreferredWidthSet = true;
+ // Make sure that we clear this flag now, before we emit the change signals
+ // which could cause another setter to be called.
+ auto splitViewPrivate = d->m_splitView ? QQuickSplitViewPrivate::get(d->m_splitView) : nullptr;
+ const bool ignoreNextLayoutRequest = splitViewPrivate && splitViewPrivate->m_ignoreNextLayoutRequest;
+ if (splitViewPrivate)
+ splitViewPrivate->m_ignoreNextLayoutRequest = false;
+
+ if (qFuzzyCompare(width, d->m_preferredWidth))
+ return;
+
+ d->m_preferredWidth = width;
+
+ if (!ignoreNextLayoutRequest) {
+ // We are currently in the middle of performing a layout, and the user (not our internal code)
+ // changed the preferred width of one of the split items, so request another layout.
+ d->requestLayoutView();
+ }
+
+ emit preferredWidthChanged();
+}
+
+void QQuickSplitViewAttached::resetPreferredWidth()
+{
+ Q_D(QQuickSplitViewAttached);
+ const qreal oldEffectivePreferredWidth = effectivePreferredWidth(
+ d, QQuickItemPrivate::get(d->m_splitItem));
+
+ d->m_isPreferredWidthSet = false;
+ d->m_preferredWidth = -1;
+
+ const qreal newEffectivePreferredWidth = effectivePreferredWidth(
+ d, QQuickItemPrivate::get(d->m_splitItem));
+ if (qFuzzyCompare(newEffectivePreferredWidth, oldEffectivePreferredWidth))
+ return;
+
+ d->requestLayoutView();
+ emit preferredWidthChanged();
+}
+
+/*!
+ \qmlattachedproperty real QtQuick.Controls::SplitView::preferredHeight
+
+ This attached property controls the preferred height of the split item. The
+ preferred height will be used as the size of the item, and will be bound
+ within the \l minimumHeight and \l maximumHeight. If the preferred height
+ is not set, the item's \l {Item::}{implicitHeight} will be used.
+
+ When a split item is resized, the preferredHeight will be set in order
+ to keep track of the new size.
+
+ By default, this property is not set, and therefore
+ \l {Item::}{implicitHeight} will be used instead. To reset this property to
+ its default value, set it to \c undefined.
+
+ \note Do not set the \l height property of a split item, as it will be
+ overwritten upon each layout of the SplitView.
+
+ \sa minimumHeight, maximumHeight, fillHeight, preferredWidth
+*/
+qreal QQuickSplitViewAttached::preferredHeight() const
+{
+ Q_D(const QQuickSplitViewAttached);
+ return d->m_preferredHeight;
+}
+
+void QQuickSplitViewAttached::setPreferredHeight(qreal height)
+{
+ Q_D(QQuickSplitViewAttached);
+ d->m_isPreferredHeightSet = true;
+ // Make sure that we clear this flag now, before we emit the change signals
+ // which could cause another setter to be called.
+ auto splitViewPrivate = d->m_splitView ? QQuickSplitViewPrivate::get(d->m_splitView) : nullptr;
+ const bool ignoreNextLayoutRequest = splitViewPrivate && splitViewPrivate->m_ignoreNextLayoutRequest;
+ if (splitViewPrivate)
+ splitViewPrivate->m_ignoreNextLayoutRequest = false;
+
+ if (qFuzzyCompare(height, d->m_preferredHeight))
+ return;
+
+ d->m_preferredHeight = height;
+
+ if (!ignoreNextLayoutRequest) {
+ // We are currently in the middle of performing a layout, and the user (not our internal code)
+ // changed the preferred height of one of the split items, so request another layout.
+ d->requestLayoutView();
+ }
+
+ emit preferredHeightChanged();
+}
+
+void QQuickSplitViewAttached::resetPreferredHeight()
+{
+ Q_D(QQuickSplitViewAttached);
+ const qreal oldEffectivePreferredHeight = effectivePreferredHeight(
+ d, QQuickItemPrivate::get(d->m_splitItem));
+
+ d->m_isPreferredHeightSet = false;
+ d->m_preferredHeight = -1;
+
+ const qreal newEffectivePreferredHeight = effectivePreferredHeight(
+ d, QQuickItemPrivate::get(d->m_splitItem));
+ if (qFuzzyCompare(newEffectivePreferredHeight, oldEffectivePreferredHeight))
+ return;
+
+ d->requestLayoutView();
+ emit preferredHeightChanged();
+}
+
+/*!
+ \qmlattachedproperty real QtQuick.Controls::SplitView::maximumWidth
+
+ This attached property controls the maximum width of the split item.
+ The \l preferredWidth is bound within the \l minimumWidth and
+ \l maximumWidth. A split item cannot be dragged to be larger than
+ its \c maximumWidth.
+
+ The default value is \c Infinity. To reset this property to its default
+ value, set it to \c undefined.
+
+ \sa minimumWidth, preferredWidth, fillWidth, maximumHeight
+*/
+qreal QQuickSplitViewAttached::maximumWidth() const
+{
+ Q_D(const QQuickSplitViewAttached);
+ return d->m_maximumWidth;
+}
+
+void QQuickSplitViewAttached::setMaximumWidth(qreal width)
+{
+ Q_D(QQuickSplitViewAttached);
+ d->m_isMaximumWidthSet = true;
+ if (qFuzzyCompare(width, d->m_maximumWidth))
+ return;
+
+ d->m_maximumWidth = width;
+ d->requestLayoutView();
+ emit maximumWidthChanged();
+}
+
+void QQuickSplitViewAttached::resetMaximumWidth()
+{
+ Q_D(QQuickSplitViewAttached);
+ const qreal oldEffectiveMaximumWidth = effectiveMaximumWidth(d);
+
+ d->m_isMaximumWidthSet = false;
+ d->m_maximumWidth = -1;
+
+ const qreal newEffectiveMaximumWidth = effectiveMaximumWidth(d);
+ if (qFuzzyCompare(newEffectiveMaximumWidth, oldEffectiveMaximumWidth))
+ return;
+
+ d->requestLayoutView();
+ emit maximumWidthChanged();
+}
+
+/*!
+ \qmlattachedproperty real QtQuick.Controls::SplitView::maximumHeight
+
+ This attached property controls the maximum height of the split item.
+ The \l preferredHeight is bound within the \l minimumHeight and
+ \l maximumHeight. A split item cannot be dragged to be larger than
+ its \c maximumHeight.
+
+ The default value is \c Infinity. To reset this property to its default
+ value, set it to \c undefined.
+
+ \sa minimumHeight, preferredHeight, fillHeight, maximumWidth
+*/
+qreal QQuickSplitViewAttached::maximumHeight() const
+{
+ Q_D(const QQuickSplitViewAttached);
+ return d->m_maximumHeight;
+}
+
+void QQuickSplitViewAttached::setMaximumHeight(qreal height)
+{
+ Q_D(QQuickSplitViewAttached);
+ d->m_isMaximumHeightSet = true;
+ if (qFuzzyCompare(height, d->m_maximumHeight))
+ return;
+
+ d->m_maximumHeight = height;
+ d->requestLayoutView();
+ emit maximumHeightChanged();
+}
+
+void QQuickSplitViewAttached::resetMaximumHeight()
+{
+ Q_D(QQuickSplitViewAttached);
+ const qreal oldEffectiveMaximumHeight = effectiveMaximumHeight(d);
+
+ d->m_isMaximumHeightSet = false;
+ d->m_maximumHeight = -1;
+
+ const qreal newEffectiveMaximumHeight = effectiveMaximumHeight(d);
+ if (qFuzzyCompare(newEffectiveMaximumHeight, oldEffectiveMaximumHeight))
+ return;
+
+ d->requestLayoutView();
+ emit maximumHeightChanged();
+}
+
+/*!
+ \qmlattachedproperty bool QtQuick.Controls::SplitView::fillWidth
+
+ This attached property controls whether the item takes the remaining space
+ in the split view after all other items have been laid out.
+
+ By default, the last visible child of the split view will have this set,
+ but it can be changed by explicitly setting \c fillWidth to \c true on
+ another item.
+
+ The width of a split item with \c fillWidth set to \c true is still
+ restricted within its \l minimumWidth and \l maximumWidth.
+
+ \sa minimumWidth, preferredWidth, maximumWidth, fillHeight
+*/
+bool QQuickSplitViewAttached::fillWidth() const
+{
+ Q_D(const QQuickSplitViewAttached);
+ return d->m_fillWidth;
+}
+
+void QQuickSplitViewAttached::setFillWidth(bool fill)
+{
+ Q_D(QQuickSplitViewAttached);
+ d->m_isFillWidthSet = true;
+ if (fill == d->m_fillWidth)
+ return;
+
+ d->m_fillWidth = fill;
+ if (d->m_splitView && d->m_splitView->orientation() == Qt::Horizontal)
+ QQuickSplitViewPrivate::get(d->m_splitView)->updateFillIndex();
+ d->requestLayoutView();
+ emit fillWidthChanged();
+}
+
+/*!
+ \qmlattachedproperty bool QtQuick.Controls::SplitView::fillHeight
+
+ This attached property controls whether the item takes the remaining space
+ in the split view after all other items have been laid out.
+
+ By default, the last visible child of the split view will have this set,
+ but it can be changed by explicitly setting \c fillHeight to \c true on
+ another item.
+
+ The height of a split item with \c fillHeight set to \c true is still
+ restricted within its \l minimumHeight and \l maximumHeight.
+
+ \sa minimumHeight, preferredHeight, maximumHeight, fillWidth
+*/
+bool QQuickSplitViewAttached::fillHeight() const
+{
+ Q_D(const QQuickSplitViewAttached);
+ return d->m_fillHeight;
+}
+
+void QQuickSplitViewAttached::setFillHeight(bool fill)
+{
+ Q_D(QQuickSplitViewAttached);
+ d->m_isFillHeightSet = true;
+ if (fill == d->m_fillHeight)
+ return;
+
+ d->m_fillHeight = fill;
+ if (d->m_splitView && d->m_splitView->orientation() == Qt::Vertical)
+ QQuickSplitViewPrivate::get(d->m_splitView)->updateFillIndex();
+ d->requestLayoutView();
+ emit fillHeightChanged();
+}
+
+QQuickSplitViewAttachedPrivate::QQuickSplitViewAttachedPrivate()
+ : m_fillWidth(false)
+ , m_fillHeight(false)
+ , m_isFillWidthSet(false)
+ , m_isFillHeightSet(false)
+ , m_isMinimumWidthSet(false)
+ , m_isMinimumHeightSet(false)
+ , m_isPreferredWidthSet(false)
+ , m_isPreferredHeightSet(false)
+ , m_isMaximumWidthSet(false)
+ , m_isMaximumHeightSet(false)
+ , m_minimumWidth(0)
+ , m_minimumHeight(0)
+ , m_preferredWidth(-1)
+ , m_preferredHeight(-1)
+ , m_maximumWidth(std::numeric_limits<qreal>::infinity())
+ , m_maximumHeight(std::numeric_limits<qreal>::infinity())
+{
+}
+
+void QQuickSplitViewAttachedPrivate::setView(QQuickSplitView *newView)
+{
+ Q_Q(QQuickSplitViewAttached);
+ if (newView == m_splitView)
+ return;
+
+ m_splitView = newView;
+ qCDebug(qlcQQuickSplitView) << "set SplitView" << newView << "on attached object" << this;
+ emit q->viewChanged();
+}
+
+void QQuickSplitViewAttachedPrivate::requestLayoutView()
+{
+ if (m_splitView)
+ QQuickSplitViewPrivate::get(m_splitView)->requestLayout();
+}
+
+QQuickSplitViewAttachedPrivate *QQuickSplitViewAttachedPrivate::get(QQuickSplitViewAttached *attached)
+{
+ return attached->d_func();
+}
+
+const QQuickSplitViewAttachedPrivate *QQuickSplitViewAttachedPrivate::get(const QQuickSplitViewAttached *attached)
+{
+ return attached->d_func();
+}
+
+QQuickSplitHandleAttachedPrivate::QQuickSplitHandleAttachedPrivate()
+ : m_hovered(false)
+ , m_pressed(false)
+{
+}
+
+void QQuickSplitHandleAttachedPrivate::setHovered(bool hovered)
+{
+ Q_Q(QQuickSplitHandleAttached);
+ if (hovered == m_hovered)
+ return;
+
+ m_hovered = hovered;
+ emit q->hoveredChanged();
+}
+
+void QQuickSplitHandleAttachedPrivate::setPressed(bool pressed)
+{
+ Q_Q(QQuickSplitHandleAttached);
+ if (pressed == m_pressed)
+ return;
+
+ m_pressed = pressed;
+ emit q->pressedChanged();
+}
+
+QQuickSplitHandleAttachedPrivate *QQuickSplitHandleAttachedPrivate::get(QQuickSplitHandleAttached *attached)
+{
+ return attached->d_func();
+}
+
+const QQuickSplitHandleAttachedPrivate *QQuickSplitHandleAttachedPrivate::get(const QQuickSplitHandleAttached *attached)
+{
+ return attached->d_func();
+}
+
+QQuickSplitHandleAttached::QQuickSplitHandleAttached(QObject *parent)
+ : QObject(*(new QQuickSplitViewAttachedPrivate), parent)
+{
+}
+
+/*!
+ \qmltype SplitHandle
+ \inherits QtObject
+ \instantiates QQuickSplitHandleAttached
+ \inqmlmodule QtQuick.Controls
+ \since 5.13
+ \brief Provides attached properties for SplitView handles
+
+ SplitHandle provides attached properties for \l SplitView handles.
+
+ For split items themselves, use the attached \l SplitView properties.
+
+ \sa SplitView
+*/
+
+/*!
+ \qmlattachedproperty bool QtQuick.Controls::SplitHandle::hovered
+
+ This attached property holds whether the split handle is hovered.
+
+ \sa pressed
+*/
+bool QQuickSplitHandleAttached::isHovered() const
+{
+ Q_D(const QQuickSplitHandleAttached);
+ return d->m_hovered;
+}
+
+/*!
+ \qmlattachedproperty bool QtQuick.Controls::SplitHandle::pressed
+
+ This attached property holds whether the split handle is pressed.
+
+ \sa hovered
+*/
+bool QQuickSplitHandleAttached::isPressed() const
+{
+ Q_D(const QQuickSplitHandleAttached);
+ return d->m_pressed;
+}
+
+QQuickSplitHandleAttached *QQuickSplitHandleAttached::qmlAttachedProperties(QObject *object)
+{
+ return new QQuickSplitHandleAttached(object);
+}
+
+QT_END_NAMESPACE
+
+#include "moc_qquicksplitview_p.cpp"
diff --git a/src/quicktemplates2/qquicksplitview_p.h b/src/quicktemplates2/qquicksplitview_p.h
new file mode 100644
index 00000000..99001615
--- /dev/null
+++ b/src/quicktemplates2/qquicksplitview_p.h
@@ -0,0 +1,218 @@
+/****************************************************************************
+**
+** Copyright (C) 2018 The Qt Company Ltd.
+** Contact: http://www.qt.io/licensing/
+**
+** This file is part of the Qt Quick Templates 2 module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL3$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see http://www.qt.io/terms-conditions. For further
+** information use the contact form at http://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPLv3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or later as published by the Free
+** Software Foundation and appearing in the file LICENSE.GPL included in
+** the packaging of this file. Please review the following information to
+** ensure the GNU General Public License version 2.0 requirements will be
+** met: http://www.gnu.org/licenses/gpl-2.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef QQUICKSPLITVIEW_P_H
+#define QQUICKSPLITVIEW_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 <QtQuickTemplates2/private/qquickcontainer_p.h>
+#include <QtQml/qqmllist.h>
+
+QT_BEGIN_NAMESPACE
+
+class QQuickSplitViewPrivate;
+class QQuickSplitViewAttached;
+class QQuickSplitViewAttachedPrivate;
+class QQuickSplitHandleAttached;
+class QQuickSplitHandleAttachedPrivate;
+
+class Q_QUICKTEMPLATES2_PRIVATE_EXPORT QQuickSplitView : public QQuickContainer
+{
+ Q_OBJECT
+ Q_PROPERTY(Qt::Orientation orientation READ orientation WRITE setOrientation NOTIFY orientationChanged FINAL)
+ Q_PROPERTY(bool resizing READ isResizing NOTIFY resizingChanged)
+ Q_PROPERTY(QQmlComponent *handle READ handle WRITE setHandle NOTIFY handleChanged FINAL)
+
+public:
+ explicit QQuickSplitView(QQuickItem *parent = nullptr);
+ ~QQuickSplitView() override;
+
+ Qt::Orientation orientation() const;
+ void setOrientation(Qt::Orientation orientation);
+
+ bool isResizing() const;
+
+ QQmlComponent *handle();
+ void setHandle(QQmlComponent *handle);
+
+ bool isContent(QQuickItem *item) const override;
+
+ static QQuickSplitViewAttached *qmlAttachedProperties(QObject *object);
+
+ // Based on the same code in QMainWindow.
+ enum VersionMarkers {
+ VersionMarker = 0xff
+ };
+ Q_INVOKABLE QVariant saveState();
+ Q_INVOKABLE bool restoreState(const QVariant &state);
+
+Q_SIGNALS:
+ void orientationChanged();
+ void resizingChanged();
+ void handleChanged();
+
+protected:
+ QQuickSplitView(QQuickSplitViewPrivate &dd, QQuickItem *parent);
+
+ void componentComplete() override;
+ void hoverMoveEvent(QHoverEvent *event) override;
+ void geometryChanged(const QRectF &newGeometry, const QRectF &oldGeometry) override;
+
+ void itemAdded(int index, QQuickItem *item) override;
+ void itemMoved(int index, QQuickItem *item) override;
+ void itemRemoved(int index, QQuickItem *item) override;
+
+#if QT_CONFIG(accessibility)
+ QAccessible::Role accessibleRole() const override;
+#endif
+
+private:
+ Q_DISABLE_COPY(QQuickSplitView)
+ Q_DECLARE_PRIVATE(QQuickSplitView)
+};
+
+class Q_QUICKTEMPLATES2_PRIVATE_EXPORT QQuickSplitViewAttached : public QObject
+{
+ Q_OBJECT
+ Q_PROPERTY(QQuickSplitView *view READ view NOTIFY viewChanged FINAL)
+ Q_PROPERTY(qreal minimumWidth READ minimumWidth WRITE setMinimumWidth
+ RESET resetMinimumWidth NOTIFY minimumWidthChanged FINAL)
+ Q_PROPERTY(qreal minimumHeight READ minimumHeight WRITE setMinimumHeight
+ RESET resetMinimumHeight NOTIFY minimumHeightChanged FINAL)
+ Q_PROPERTY(qreal preferredWidth READ preferredWidth WRITE setPreferredWidth
+ RESET resetPreferredWidth NOTIFY preferredWidthChanged FINAL)
+ Q_PROPERTY(qreal preferredHeight READ preferredHeight WRITE setPreferredHeight
+ RESET resetPreferredHeight NOTIFY preferredHeightChanged FINAL)
+ Q_PROPERTY(qreal maximumWidth READ maximumWidth WRITE setMaximumWidth
+ RESET resetMaximumWidth NOTIFY maximumWidthChanged FINAL)
+ Q_PROPERTY(qreal maximumHeight READ maximumHeight WRITE setMaximumHeight
+ RESET resetMaximumHeight NOTIFY maximumHeightChanged FINAL)
+ Q_PROPERTY(bool fillHeight READ fillHeight WRITE setFillHeight NOTIFY fillHeightChanged FINAL)
+ Q_PROPERTY(bool fillWidth READ fillWidth WRITE setFillWidth NOTIFY fillWidthChanged FINAL)
+
+public:
+ explicit QQuickSplitViewAttached(QObject *parent = nullptr);
+
+ QQuickSplitView *view() const;
+
+ qreal minimumWidth() const;
+ void setMinimumWidth(qreal width);
+ void resetMinimumWidth();
+
+ qreal minimumHeight() const;
+ void setMinimumHeight(qreal height);
+ void resetMinimumHeight();
+
+ qreal preferredWidth() const;
+ void setPreferredWidth(qreal width);
+ void resetPreferredWidth();
+
+ qreal preferredHeight() const;
+ void setPreferredHeight(qreal height);
+ void resetPreferredHeight();
+
+ qreal maximumWidth() const;
+ void setMaximumWidth(qreal width);
+ void resetMaximumWidth();
+
+ qreal maximumHeight() const;
+ void setMaximumHeight(qreal height);
+ void resetMaximumHeight();
+
+ bool fillWidth() const;
+ void setFillWidth(bool fill);
+
+ bool fillHeight() const;
+ void setFillHeight(bool fill);
+
+Q_SIGNALS:
+ void viewChanged();
+ void minimumWidthChanged();
+ void minimumHeightChanged();
+ void preferredWidthChanged();
+ void preferredHeightChanged();
+ void maximumWidthChanged();
+ void maximumHeightChanged();
+ void fillWidthChanged();
+ void fillHeightChanged();
+
+private:
+ Q_DISABLE_COPY(QQuickSplitViewAttached)
+ Q_DECLARE_PRIVATE(QQuickSplitViewAttached)
+};
+
+class Q_QUICKTEMPLATES2_PRIVATE_EXPORT QQuickSplitHandleAttached : public QObject
+{
+ Q_OBJECT
+ Q_PROPERTY(bool hovered READ isHovered NOTIFY hoveredChanged FINAL)
+ Q_PROPERTY(bool pressed READ isPressed NOTIFY pressedChanged FINAL)
+
+public:
+ explicit QQuickSplitHandleAttached(QObject *parent = nullptr);
+
+ bool isHovered() const;
+ bool isPressed() const;
+
+ static QQuickSplitHandleAttached *qmlAttachedProperties(QObject *object);
+
+Q_SIGNALS:
+ void hoveredChanged();
+ void pressedChanged();
+
+private:
+ Q_DISABLE_COPY(QQuickSplitHandleAttached)
+ Q_DECLARE_PRIVATE(QQuickSplitHandleAttached)
+};
+
+QT_END_NAMESPACE
+
+QML_DECLARE_TYPE(QQuickSplitView)
+QML_DECLARE_TYPEINFO(QQuickSplitView, QML_HAS_ATTACHED_PROPERTIES)
+
+QML_DECLARE_TYPE(QQuickSplitHandleAttached)
+QML_DECLARE_TYPEINFO(QQuickSplitHandleAttached, QML_HAS_ATTACHED_PROPERTIES)
+
+#endif // QQUICKSPLITVIEW_P_H
diff --git a/src/quicktemplates2/qquicksplitview_p_p.h b/src/quicktemplates2/qquicksplitview_p_p.h
new file mode 100644
index 00000000..5d71d461
--- /dev/null
+++ b/src/quicktemplates2/qquicksplitview_p_p.h
@@ -0,0 +1,178 @@
+/****************************************************************************
+**
+** Copyright (C) 2018 The Qt Company Ltd.
+** Contact: http://www.qt.io/licensing/
+**
+** This file is part of the Qt Quick Templates 2 module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL3$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see http://www.qt.io/terms-conditions. For further
+** information use the contact form at http://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPLv3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or later as published by the Free
+** Software Foundation and appearing in the file LICENSE.GPL included in
+** the packaging of this file. Please review the following information to
+** ensure the GNU General Public License version 2.0 requirements will be
+** met: http://www.gnu.org/licenses/gpl-2.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef QQUICKSPLITVIEW_P_P_H
+#define QQUICKSPLITVIEW_P_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 <QtQuickTemplates2/private/qquickcontainer_p_p.h>
+
+QT_BEGIN_NAMESPACE
+
+class QQuickSplitView;
+class QQuickSplitViewAttached;
+class QQuickSplitHandleAttached;
+
+class Q_QUICKTEMPLATES2_PRIVATE_EXPORT QQuickSplitViewPrivate : public QQuickContainerPrivate
+{
+ Q_DECLARE_PUBLIC(QQuickSplitView)
+
+public:
+ void updateFillIndex();
+ void layoutResizeSplitItems(qreal &usedWidth, qreal &usedHeight, int &indexBeingResizedDueToDrag);
+ void layoutResizeFillItem(QQuickItem *fillItem, qreal &usedWidth, qreal &usedHeight, int indexBeingResizedDueToDrag);
+ void layoutPositionItems(const QQuickItem *fillItem);
+ void requestLayout();
+ void layout();
+ void createHandles();
+ void createHandleItem(int index);
+ void removeExcessHandles();
+ void destroyHandles();
+ void resizeHandle(QQuickItem *handleItem);
+ void resizeHandles();
+ void updateHandleVisibilities();
+ void setResizing(bool resizing);
+
+ bool isHorizontal() const;
+ qreal accumulatedSize(int firstIndex, int lastIndex) const;
+
+ struct EffectiveSizeData {
+ qreal effectiveMinimumWidth;
+ qreal effectiveMinimumHeight;
+ qreal effectivePreferredWidth;
+ qreal effectivePreferredHeight;
+ qreal effectiveMaximumWidth;
+ qreal effectiveMaximumHeight;
+ };
+
+ EffectiveSizeData effectiveSizeData(const QQuickItemPrivate *itemPrivate,
+ const QQuickSplitViewAttached *attached) const;
+
+ int handleIndexForSplitIndex(int splitIndex) const;
+
+ QQuickItem *getContentItem() override;
+ void handlePress(const QPointF &point) override;
+ void handleMove(const QPointF &point) override;
+ void handleRelease(const QPointF &point) override;
+
+ void itemVisibilityChanged(QQuickItem *item) override;
+ void itemImplicitWidthChanged(QQuickItem *item) override;
+ void itemImplicitHeightChanged(QQuickItem *item) override;
+
+ void updatePolish() override;
+
+ static QQuickSplitViewPrivate *get(QQuickSplitView *splitView);
+
+ Qt::Orientation m_orientation = Qt::Horizontal;
+ QQmlComponent *m_handle = nullptr;
+ QVector<QQuickItem*> m_handleItems;
+ int m_hoveredHandleIndex = -1;
+ int m_pressedHandleIndex = -1;
+ QPointF m_pressPos;
+ QPointF m_mousePos;
+ QPointF m_handlePosBeforePress;
+ qreal m_leftOrTopItemSizeBeforePress = 0.0;
+ qreal m_rightOrBottomItemSizeBeforePress = 0.0;
+ int m_fillIndex = -1;
+ bool m_layingOut = false;
+ bool m_ignoreNextLayoutRequest = false;
+ bool m_resizing = false;
+};
+
+class QQuickSplitViewAttachedPrivate : public QObjectPrivate
+{
+ Q_DECLARE_PUBLIC(QQuickSplitViewAttached)
+
+public:
+ QQuickSplitViewAttachedPrivate();
+
+ void setView(QQuickSplitView *newView);
+ void requestLayoutView();
+
+ static QQuickSplitViewAttachedPrivate *get(QQuickSplitViewAttached *attached);
+ static const QQuickSplitViewAttachedPrivate *get(const QQuickSplitViewAttached *attached);
+
+ QQuickItem *m_splitItem = nullptr;
+ QQuickSplitView *m_splitView = nullptr;
+
+ unsigned m_fillWidth : 1;
+ unsigned m_fillHeight : 1;
+ unsigned m_isFillWidthSet : 1;
+ unsigned m_isFillHeightSet : 1;
+ unsigned m_isMinimumWidthSet : 1;
+ unsigned m_isMinimumHeightSet : 1;
+ unsigned m_isPreferredWidthSet : 1;
+ unsigned m_isPreferredHeightSet : 1;
+ unsigned m_isMaximumWidthSet : 1;
+ unsigned m_isMaximumHeightSet : 1;
+ qreal m_minimumWidth;
+ qreal m_minimumHeight;
+ qreal m_preferredWidth;
+ qreal m_preferredHeight;
+ qreal m_maximumWidth;
+ qreal m_maximumHeight;
+};
+
+class QQuickSplitHandleAttachedPrivate : public QObjectPrivate
+{
+ Q_DECLARE_PUBLIC(QQuickSplitHandleAttached)
+
+public:
+ QQuickSplitHandleAttachedPrivate();
+
+ void setHovered(bool hovered);
+ void setPressed(bool pressed);
+
+ static QQuickSplitHandleAttachedPrivate *get(QQuickSplitHandleAttached *attached);
+ static const QQuickSplitHandleAttachedPrivate *get(const QQuickSplitHandleAttached *attached);
+
+ unsigned m_hovered : 1;
+ unsigned m_pressed : 1;
+};
+
+QT_END_NAMESPACE
+
+#endif // QQUICKSPLITVIEW_P_P_H
diff --git a/src/quicktemplates2/qquicktumbler.cpp b/src/quicktemplates2/qquicktumbler.cpp
index 25710231..8b702c60 100644
--- a/src/quicktemplates2/qquicktumbler.cpp
+++ b/src/quicktemplates2/qquicktumbler.cpp
@@ -36,6 +36,7 @@
#include "qquicktumbler_p.h"
+#include <QtCore/qloggingcategory.h>
#include <QtGui/qpa/qplatformtheme.h>
#include <QtQml/qqmlinfo.h>
#include <QtQuick/private/qquickflickable_p.h>
@@ -44,6 +45,8 @@
QT_BEGIN_NAMESPACE
+Q_LOGGING_CATEGORY(lcTumbler, "qt.quick.controls.tumbler")
+
/*!
\qmltype Tumbler
\inherits Control
@@ -190,11 +193,22 @@ void QQuickTumblerPrivate::_q_onViewCurrentIndexChanged()
// If the user set currentIndex in the onModelChanged handler,
// we have to respect that currentIndex by ignoring changes in the view
// until the model has finished being set.
+ qCDebug(lcTumbler).nospace() << "view currentIndex changed to "
+ << (view ? view->property("currentIndex").toString() : QStringLiteral("unknown index (no view)"))
+ << ", but we're ignoring it because one or more of the following conditions are true:"
+ << "\n- !view: " << !view
+ << "\n- ignoreCurrentIndexChanges: " << ignoreCurrentIndexChanges
+ << "\n- currentIndexSetDuringModelChange: " << currentIndexSetDuringModelChange;
return;
}
const int oldCurrentIndex = currentIndex;
currentIndex = view->property("currentIndex").toInt();
+
+ qCDebug(lcTumbler).nospace() << "view currentIndex changed to "
+ << (view ? view->property("currentIndex").toString() : QStringLiteral("unknown index (no view)"))
+ << ", our old currentIndex was " << oldCurrentIndex;
+
if (oldCurrentIndex != currentIndex)
emit q->currentIndexChanged();
}
@@ -202,6 +216,7 @@ void QQuickTumblerPrivate::_q_onViewCurrentIndexChanged()
void QQuickTumblerPrivate::_q_onViewCountChanged()
{
Q_Q(QQuickTumbler);
+ qCDebug(lcTumbler) << "view count changed - ignoring signals?" << ignoreSignals;
if (ignoreSignals)
return;
@@ -513,10 +528,12 @@ void QQuickTumbler::geometryChanged(const QRectF &newGeometry, const QRectF &old
void QQuickTumbler::componentComplete()
{
Q_D(QQuickTumbler);
+ qCDebug(lcTumbler) << "componentComplete()";
QQuickControl::componentComplete();
if (!d->view) {
// Force the view to be created.
+ qCDebug(lcTumbler) << "emitting wrapChanged() to force view to be created";
emit wrapChanged();
// Determine the type of view for attached properties, etc.
d->setupViewData(d->contentItem);
@@ -532,6 +549,8 @@ void QQuickTumbler::componentComplete()
d->_q_updateItemHeights();
d->_q_updateItemWidths();
d->_q_onViewCountChanged();
+
+ qCDebug(lcTumbler) << "componentComplete() is done";
}
void QQuickTumbler::contentItemChange(QQuickItem *newItem, QQuickItem *oldItem)
@@ -659,18 +678,29 @@ void QQuickTumblerPrivate::syncCurrentIndex()
void QQuickTumblerPrivate::setPendingCurrentIndex(int index)
{
+ qCDebug(lcTumbler) << "setting pendingCurrentIndex to" << index;
pendingCurrentIndex = index;
}
+QString QQuickTumblerPrivate::propertyChangeReasonToString(
+ QQuickTumblerPrivate::PropertyChangeReason changeReason)
+{
+ return changeReason == UserChange ? QStringLiteral("UserChange") : QStringLiteral("InternalChange");
+}
+
void QQuickTumblerPrivate::setCurrentIndex(int newCurrentIndex,
QQuickTumblerPrivate::PropertyChangeReason changeReason)
{
Q_Q(QQuickTumbler);
+ qCDebug(lcTumbler).nospace() << "setting currentIndex to " << newCurrentIndex
+ << ", old currentIndex was " << currentIndex
+ << ", changeReason is " << propertyChangeReasonToString(changeReason);
if (newCurrentIndex == currentIndex || newCurrentIndex < -1)
return;
if (!q->isComponentComplete()) {
// Views can't set currentIndex until they're ready.
+ qCDebug(lcTumbler) << "we're not complete; setting pendingCurrentIndex instead";
setPendingCurrentIndex(newCurrentIndex);
return;
}
@@ -680,6 +710,7 @@ void QQuickTumblerPrivate::setCurrentIndex(int newCurrentIndex,
// the model is in the process of being set and the user has set
// the currentIndex in onModelChanged. We have to queue the currentIndex
// change until we're ready.
+ qCDebug(lcTumbler) << "a model is being set; setting pendingCurrentIndex instead";
setPendingCurrentIndex(newCurrentIndex);
return;
}
@@ -717,11 +748,16 @@ void QQuickTumblerPrivate::setCurrentIndex(int newCurrentIndex,
currentIndex = newCurrentIndex;
emit q->currentIndexChanged();
}
+
+ qCDebug(lcTumbler) << "view's currentIndex is now" << view->property("currentIndex").toInt()
+ << "and ours is" << currentIndex;
}
}
void QQuickTumblerPrivate::setCount(int newCount)
{
+ qCDebug(lcTumbler).nospace() << "setting count to " << newCount
+ << ", old count was " << count;
if (newCount == count)
return;
@@ -743,6 +779,7 @@ void QQuickTumblerPrivate::setWrapBasedOnCount()
void QQuickTumblerPrivate::setWrap(bool shouldWrap, bool isExplicit)
{
+ qCDebug(lcTumbler) << "setting wrap to" << shouldWrap << "- exlicit?" << isExplicit;
if (isExplicit)
explicitWrap = true;
diff --git a/src/quicktemplates2/qquicktumbler_p_p.h b/src/quicktemplates2/qquicktumbler_p_p.h
index 75c6cd1b..049ab8a1 100644
--- a/src/quicktemplates2/qquicktumbler_p_p.h
+++ b/src/quicktemplates2/qquicktumbler_p_p.h
@@ -111,6 +111,8 @@ public:
InternalChange
};
+ static QString propertyChangeReasonToString(PropertyChangeReason changeReason);
+
void setCurrentIndex(int newCurrentIndex, PropertyChangeReason changeReason = InternalChange);
void setCount(int newCount);
void setWrapBasedOnCount();
diff --git a/src/quicktemplates2/quicktemplates2.pri b/src/quicktemplates2/quicktemplates2.pri
index 33bc47ca..c145c20f 100644
--- a/src/quicktemplates2/quicktemplates2.pri
+++ b/src/quicktemplates2/quicktemplates2.pri
@@ -73,6 +73,7 @@ HEADERS += \
$$PWD/qquickshortcutcontext_p_p.h \
$$PWD/qquickslider_p.h \
$$PWD/qquickspinbox_p.h \
+ $$PWD/qquicksplitview_p.h \
$$PWD/qquickstackelement_p_p.h \
$$PWD/qquickstacktransition_p_p.h \
$$PWD/qquickstackview_p.h \
@@ -149,6 +150,7 @@ SOURCES += \
$$PWD/qquickshortcutcontext.cpp \
$$PWD/qquickslider.cpp \
$$PWD/qquickspinbox.cpp \
+ $$PWD/qquicksplitview.cpp \
$$PWD/qquickstackelement.cpp \
$$PWD/qquickstacktransition.cpp \
$$PWD/qquickstackview.cpp \
diff --git a/tests/auto/controls/data/splitview/fillItemInMiddle.qml b/tests/auto/controls/data/splitview/fillItemInMiddle.qml
new file mode 100644
index 00000000..174b6a2a
--- /dev/null
+++ b/tests/auto/controls/data/splitview/fillItemInMiddle.qml
@@ -0,0 +1,77 @@
+/****************************************************************************
+**
+** Copyright (C) 2018 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the test suite of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:BSD$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** BSD License Usage
+** Alternatively, you may use this file under the terms of the BSD license
+** as follows:
+**
+** "Redistribution and use in source and binary forms, with or without
+** modification, are permitted provided that the following conditions are
+** met:
+** * Redistributions of source code must retain the above copyright
+** notice, this list of conditions and the following disclaimer.
+** * Redistributions in binary form must reproduce the above copyright
+** notice, this list of conditions and the following disclaimer in
+** the documentation and/or other materials provided with the
+** distribution.
+** * Neither the name of The Qt Company Ltd nor the names of its
+** contributors may be used to endorse or promote products derived
+** from this software without specific prior written permission.
+**
+**
+** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick 2.13
+import QtQuick.Controls 2.13
+
+SplitView {
+ anchors.fill: parent
+
+ Rectangle {
+ objectName: "salmon"
+ color: objectName
+ implicitWidth: 25
+ implicitHeight: 25
+ }
+ Rectangle {
+ objectName: "navajowhite"
+ color: objectName
+ implicitWidth: 100
+ implicitHeight: 100
+
+ SplitView.fillWidth: true
+ }
+ Rectangle {
+ objectName: "steelblue"
+ color: objectName
+ implicitWidth: 200
+ implicitHeight: 200
+ }
+}
diff --git a/tests/auto/controls/data/splitview/fillItemOnLeft.qml b/tests/auto/controls/data/splitview/fillItemOnLeft.qml
new file mode 100644
index 00000000..dee68eac
--- /dev/null
+++ b/tests/auto/controls/data/splitview/fillItemOnLeft.qml
@@ -0,0 +1,77 @@
+/****************************************************************************
+**
+** Copyright (C) 2018 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the test suite of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:BSD$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** BSD License Usage
+** Alternatively, you may use this file under the terms of the BSD license
+** as follows:
+**
+** "Redistribution and use in source and binary forms, with or without
+** modification, are permitted provided that the following conditions are
+** met:
+** * Redistributions of source code must retain the above copyright
+** notice, this list of conditions and the following disclaimer.
+** * Redistributions in binary form must reproduce the above copyright
+** notice, this list of conditions and the following disclaimer in
+** the documentation and/or other materials provided with the
+** distribution.
+** * Neither the name of The Qt Company Ltd nor the names of its
+** contributors may be used to endorse or promote products derived
+** from this software without specific prior written permission.
+**
+**
+** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick 2.13
+import QtQuick.Controls 2.13
+
+SplitView {
+ anchors.fill: parent
+
+ Rectangle {
+ objectName: "salmon"
+ color: objectName
+ implicitWidth: 25
+ implicitHeight: 25
+
+ SplitView.fillWidth: true
+ }
+ Rectangle {
+ objectName: "navajowhite"
+ color: objectName
+ implicitWidth: 200
+ implicitHeight: 200
+ }
+ Rectangle {
+ objectName: "steelblue"
+ color: objectName
+ implicitWidth: 200
+ implicitHeight: 200
+ }
+}
diff --git a/tests/auto/controls/data/splitview/fillItemOnTop.qml b/tests/auto/controls/data/splitview/fillItemOnTop.qml
new file mode 100644
index 00000000..2fc6f4d0
--- /dev/null
+++ b/tests/auto/controls/data/splitview/fillItemOnTop.qml
@@ -0,0 +1,78 @@
+/****************************************************************************
+**
+** Copyright (C) 2018 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the test suite of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:BSD$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** BSD License Usage
+** Alternatively, you may use this file under the terms of the BSD license
+** as follows:
+**
+** "Redistribution and use in source and binary forms, with or without
+** modification, are permitted provided that the following conditions are
+** met:
+** * Redistributions of source code must retain the above copyright
+** notice, this list of conditions and the following disclaimer.
+** * Redistributions in binary form must reproduce the above copyright
+** notice, this list of conditions and the following disclaimer in
+** the documentation and/or other materials provided with the
+** distribution.
+** * Neither the name of The Qt Company Ltd nor the names of its
+** contributors may be used to endorse or promote products derived
+** from this software without specific prior written permission.
+**
+**
+** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick 2.13
+import QtQuick.Controls 2.13
+
+SplitView {
+ anchors.fill: parent
+ orientation: Qt.Vertical
+
+ Rectangle {
+ objectName: "salmon"
+ color: objectName
+ implicitWidth: 25
+ implicitHeight: 25
+
+ SplitView.fillHeight: true
+ }
+ Rectangle {
+ objectName: "navajowhite"
+ color: objectName
+ implicitWidth: 200
+ implicitHeight: 200
+ }
+ Rectangle {
+ objectName: "steelblue"
+ color: objectName
+ implicitWidth: 200
+ implicitHeight: 200
+ }
+}
diff --git a/tests/auto/controls/data/tst_splitview.qml b/tests/auto/controls/data/tst_splitview.qml
new file mode 100644
index 00000000..55592eee
--- /dev/null
+++ b/tests/auto/controls/data/tst_splitview.qml
@@ -0,0 +1,1953 @@
+/****************************************************************************
+**
+** Copyright (C) 2018 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the test suite of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:BSD$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** BSD License Usage
+** Alternatively, you may use this file under the terms of the BSD license
+** as follows:
+**
+** "Redistribution and use in source and binary forms, with or without
+** modification, are permitted provided that the following conditions are
+** met:
+** * Redistributions of source code must retain the above copyright
+** notice, this list of conditions and the following disclaimer.
+** * Redistributions in binary form must reproduce the above copyright
+** notice, this list of conditions and the following disclaimer in
+** the documentation and/or other materials provided with the
+** distribution.
+** * Neither the name of The Qt Company Ltd nor the names of its
+** contributors may be used to endorse or promote products derived
+** from this software without specific prior written permission.
+**
+**
+** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick 2.13
+import QtQuick.Controls 2.13
+import QtQuick.Window 2.13
+import QtTest 1.13
+import Qt.labs.settings 1.0
+
+TestCase {
+ id: testCase
+ width: 400
+ height: 400
+ visible: true
+ when: windowShown
+ name: "SplitView"
+
+ function initTestCase() {
+ // For the serialization tests.
+ Qt.application.name = "qtquickcontrols2-splitview-auto-test"
+ Qt.application.domain = "org.qt-project"
+ Qt.application.organization = "Qt Project"
+ }
+
+ function findHandles(splitView) {
+ var handles = []
+ for (var i = 0; i < splitView.children.length; ++i) {
+ var child = splitView.children[i]
+ if (child.objectName.toLowerCase().indexOf("handle") !== -1)
+ handles.push(child)
+ }
+ return handles
+ }
+
+ function compareSizes(control, expectedGeometries, context) {
+ if (context === undefined)
+ context = ""
+ else
+ context = " (" + context + ")"
+
+ compare(control.count, Math.floor(expectedGeometries.length / 2) + 1,
+ "Mismatch in actual vs expected number of split items" + context)
+
+ var handles = findHandles(control)
+ compare(handles.length, Math.floor(expectedGeometries.length / 2),
+ "Mismatch in actual vs expected number of handle items" + context)
+
+ for (var i = 0, splitItemIndex = 0, handleItemIndex = 0; i < expectedGeometries.length; ++i) {
+ var item = null
+ var itemType = ""
+ var typeSpecificIndex = -1
+ if (i % 2 == 0) {
+ item = control.itemAt(splitItemIndex)
+ itemType = "split item"
+ typeSpecificIndex = splitItemIndex
+ ++splitItemIndex
+ } else {
+ item = handles[handleItemIndex]
+ itemType = "handle item"
+ typeSpecificIndex = handleItemIndex
+ ++handleItemIndex
+ }
+
+ verify(item, itemType + " at index " + typeSpecificIndex + " should not be null" + context)
+
+ var expectedGeometry = expectedGeometries[i]
+ if (expectedGeometry.hasOwnProperty("hidden")) {
+ // It's geometry doesn't matter because it's hidden.
+ verify(!item.visible, itemType + " at index " + typeSpecificIndex + " should be hidden" + context)
+ continue
+ }
+
+ // Note that the indices mentioned here account for handles; they do not
+ // match the indices reported by QQuickSplitView's logging categories.
+ compare(item.x, expectedGeometry.x, "Mismatch in actual vs expected x value of "
+ + itemType + " at index " + typeSpecificIndex + context)
+ compare(item.y, expectedGeometry.y, "Mismatch in actual vs expected y value of "
+ + itemType + " at index " + typeSpecificIndex + context)
+ compare(item.width, expectedGeometry.width, "Mismatch in actual vs expected width value of "
+ + itemType + " at index " + typeSpecificIndex + context)
+ compare(item.height, expectedGeometry.height, "Mismatch in actual vs expected height value of "
+ + itemType + " at index " + typeSpecificIndex + context)
+ }
+ }
+
+ property real defaultHorizontalHandleWidth: 10
+ property real defaultVerticalHandleHeight: 10
+
+
+ Component {
+ id: signalSpyComponent
+ SignalSpy {}
+ }
+
+ Component {
+ id: handleComponent
+ Rectangle {
+ objectName: "handle"
+ implicitWidth: defaultHorizontalHandleWidth
+ implicitHeight: defaultVerticalHandleHeight
+ color: "#444"
+ }
+ }
+
+ SplitView {
+ id: dummyHorizontalSplitView
+ handle: handleComponent
+
+ Item { objectName: "dummyItem" }
+ Item { objectName: "dummyItem" }
+ }
+
+ SplitView {
+ id: dummyVerticalSplitView
+ orientation: Qt.Vertical
+ handle: handleComponent
+
+ Item { objectName: "dummyItem" }
+ Item { objectName: "dummyItem" }
+ }
+
+ Component {
+ id: splitViewComponent
+
+ SplitView {
+ anchors.fill: parent
+ handle: handleComponent
+ }
+ }
+
+ Component {
+ id: rectangleComponent
+
+ Rectangle {}
+ }
+
+ function test_addItemsAfterCompletion() {
+ var control = createTemporaryObject(splitViewComponent, testCase)
+ verify(control)
+
+ var item0 = rectangleComponent.createObject(control, { implicitWidth: 25, color: "salmon" })
+ verify(item0)
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ // The last item fills the width by default, and since there is only one item...
+ compare(item0.x, 0)
+ compare(item0.y, 0)
+ compare(item0.width, testCase.width)
+ compare(item0.height, testCase.height)
+
+ var item1 = rectangleComponent.createObject(control, { implicitWidth: 25, color: "steelblue" })
+ verify(item1)
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ // Now that a second item has been added, the first item goes back to its preferred (implicit) width.
+ compare(item0.x, 0)
+ compare(item0.y, 0)
+ compare(item0.width, item0.implicitWidth)
+ compare(item0.height, testCase.height)
+ var handles = findHandles(control)
+ var handle0 = handles[0]
+ compare(handle0.x, item0.implicitWidth)
+ compare(handle0.y, 0)
+ compare(handle0.width, defaultHorizontalHandleWidth)
+ compare(handle0.height, testCase.height)
+ compare(item1.x, item0.implicitWidth + defaultHorizontalHandleWidth)
+ compare(item1.y, 0)
+ compare(item1.width, testCase.width - item0.implicitWidth - defaultHorizontalHandleWidth)
+ compare(item1.height, testCase.height)
+ }
+
+ function test_addItemsWithNoSizeAfterCompletion() {
+ var control = createTemporaryObject(splitViewComponent, testCase)
+ verify(control)
+
+ var item0 = rectangleComponent.createObject(control, { color: "salmon" })
+ verify(item0)
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compare(item0.x, 0)
+ compare(item0.y, 0)
+ compare(item0.width, testCase.width)
+ compare(item0.height, testCase.height)
+
+ var item1 = rectangleComponent.createObject(control, { color: "steelblue" })
+ verify(item1)
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compare(item0.x, 0)
+ compare(item0.y, 0)
+ compare(item0.width, 0)
+ compare(item0.height, testCase.height)
+ var handles = findHandles(control)
+ var handle0 = handles[0]
+ compare(handle0.x, 0)
+ compare(handle0.y, 0)
+ compare(handle0.width, defaultHorizontalHandleWidth)
+ compare(handle0.height, testCase.height)
+ compare(item1.x, defaultHorizontalHandleWidth)
+ compare(item1.y, 0)
+ compare(item1.width, testCase.width - defaultHorizontalHandleWidth)
+ compare(item1.height, testCase.height)
+ }
+
+ Component {
+ id: threeZeroSizedItemsComponent
+
+ SplitView {
+ anchors.fill: parent
+ handle: handleComponent
+
+ Rectangle {
+ objectName: "salmon"
+ color: objectName
+ }
+ Rectangle {
+ objectName: "navajowhite"
+ color: objectName
+ }
+ Rectangle {
+ objectName: "steelblue"
+ color: objectName
+ }
+ }
+ }
+
+ function test_changeAttachedPropertiesAfterCompletion() {
+ var control = createTemporaryObject(threeZeroSizedItemsComponent, testCase)
+ verify(control)
+
+ var item0 = control.itemAt(0)
+ compare(item0.x, 0)
+ compare(item0.y, 0)
+ compare(item0.width, 0)
+ compare(item0.height, testCase.height)
+
+ var handles = findHandles(control)
+ var handle0 = handles[0]
+ compare(handle0.x, 0)
+ compare(handle0.y, 0)
+ compare(handle0.width, defaultHorizontalHandleWidth)
+ compare(handle0.height, testCase.height)
+
+ var item1 = control.itemAt(1)
+ compare(item1.x, defaultHorizontalHandleWidth)
+ compare(item1.y, 0)
+ compare(item1.width, 0)
+ compare(item1.height, testCase.height)
+
+ var handle1 = handles[1]
+ compare(handle1.x, defaultHorizontalHandleWidth)
+ compare(handle1.y, 0)
+ compare(handle1.width, defaultHorizontalHandleWidth)
+ compare(handle1.height, testCase.height)
+
+ var item2 = control.itemAt(2)
+ compare(item2.x, defaultHorizontalHandleWidth * 2)
+ compare(item2.y, 0)
+ compare(item2.width, testCase.width - item2.x)
+ compare(item2.height, testCase.height)
+
+ item0.SplitView.preferredWidth = 25
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compare(item0.x, 0)
+ compare(item0.y, 0)
+ compare(item0.width, 25)
+ compare(item0.height, testCase.height)
+ compare(handle0.x, item0.width)
+ compare(handle0.y, 0)
+ compare(handle0.width, defaultHorizontalHandleWidth)
+ compare(handle0.height, testCase.height)
+ compare(item1.x, 25 + defaultHorizontalHandleWidth)
+ compare(item1.y, 0)
+ compare(item1.width, 0)
+ compare(item1.height, testCase.height)
+ compare(handle1.x, item1.x + item1.width)
+ compare(handle1.y, 0)
+ compare(handle1.width, defaultHorizontalHandleWidth)
+ compare(handle1.height, testCase.height)
+ compare(item2.x, item1.x + item1.width + defaultHorizontalHandleWidth)
+ compare(item2.y, 0)
+ compare(item2.width, testCase.width - item2.x)
+ compare(item2.height, testCase.height)
+
+ item0.SplitView.minimumWidth = 50
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compare(item0.x, 0)
+ compare(item0.y, 0)
+ compare(item0.width, 50)
+ compare(item0.height, testCase.height)
+ compare(handle0.x, item0.width)
+ compare(handle0.y, 0)
+ compare(handle0.width, defaultHorizontalHandleWidth)
+ compare(handle0.height, testCase.height)
+ compare(item1.x, 50 + defaultHorizontalHandleWidth)
+ compare(item1.y, 0)
+ compare(item1.width, 0)
+ compare(item1.height, testCase.height)
+ compare(handle1.x, item1.x + item1.width)
+ compare(handle1.y, 0)
+ compare(handle1.width, defaultHorizontalHandleWidth)
+ compare(handle1.height, testCase.height)
+ compare(item2.x, item1.x + item1.width + defaultHorizontalHandleWidth)
+ compare(item2.y, 0)
+ compare(item2.width, testCase.width - item2.x)
+ compare(item2.height, testCase.height)
+
+ item0.SplitView.preferredWidth = 100
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compare(item0.x, 0)
+ compare(item0.y, 0)
+ compare(item0.width, 100)
+ compare(item0.height, testCase.height)
+ compare(handle0.x, item0.width)
+ compare(handle0.y, 0)
+ compare(handle0.width, defaultHorizontalHandleWidth)
+ compare(handle0.height, testCase.height)
+ compare(item1.x, 100 + defaultHorizontalHandleWidth)
+ compare(item1.y, 0)
+ compare(item1.width, 0)
+ compare(item1.height, testCase.height)
+ compare(handle1.x, item1.x + item1.width)
+ compare(handle1.y, 0)
+ compare(handle1.width, defaultHorizontalHandleWidth)
+ compare(handle1.height, testCase.height)
+ compare(item2.x, item1.x + item1.width + defaultHorizontalHandleWidth)
+ compare(item2.y, 0)
+ compare(item2.width, testCase.width - item2.x)
+ compare(item2.height, testCase.height)
+
+ item0.SplitView.maximumWidth = 75
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compare(item0.x, 0)
+ compare(item0.y, 0)
+ compare(item0.width, 75)
+ compare(item0.height, testCase.height)
+ compare(handle0.x, item0.width)
+ compare(handle0.y, 0)
+ compare(handle0.width, defaultHorizontalHandleWidth)
+ compare(handle0.height, testCase.height)
+ compare(item1.x, 75 + defaultHorizontalHandleWidth)
+ compare(item1.y, 0)
+ compare(item1.width, 0)
+ compare(item1.height, testCase.height)
+ compare(handle1.x, item1.x + item1.width)
+ compare(handle1.y, 0)
+ compare(handle1.width, defaultHorizontalHandleWidth)
+ compare(handle1.height, testCase.height)
+ compare(item2.x, item1.x + item1.width + defaultHorizontalHandleWidth)
+ compare(item2.y, 0)
+ compare(item2.width, testCase.width - item2.x)
+ compare(item2.height, testCase.height)
+
+ item1.SplitView.fillWidth = true
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compare(item0.x, 0)
+ compare(item0.y, 0)
+ compare(item0.width, 75)
+ compare(item0.height, testCase.height)
+ compare(handle0.x, item0.width)
+ compare(handle0.y, 0)
+ compare(handle0.width, defaultHorizontalHandleWidth)
+ compare(handle0.height, testCase.height)
+ compare(item1.x, 75 + defaultHorizontalHandleWidth)
+ compare(item1.y, 0)
+ compare(item1.width, testCase.width - 75 - defaultHorizontalHandleWidth * 2)
+ compare(item1.height, testCase.height)
+ compare(handle1.x, item1.x + item1.width)
+ compare(handle1.y, 0)
+ compare(handle1.width, defaultHorizontalHandleWidth)
+ compare(handle1.height, testCase.height)
+ compare(item2.x, testCase.width)
+ compare(item2.y, 0)
+ compare(item2.width, 0)
+ compare(item2.height, testCase.height)
+ }
+
+ Component {
+ id: itemComponent
+ Item {}
+ }
+
+ Component {
+ id: objectComponent
+ QtObject {}
+ }
+
+ function test_useAttachedPropertiesIncorrectly_data() {
+ var properties = [ "fillWidth", "fillHeight", "minimumWidth", "minimumHeight",
+ "preferredWidth", "preferredHeight", "maximumWidth", "maximumHeight" ]
+
+ var data = []
+
+ for (var i = 0; i < properties.length; ++i) {
+ var property = properties[i]
+ data.push({ tag: "Item," + property, component: itemComponent, property: property,
+ expectedWarning: /.*SplitView: attached properties must be accessed through a direct child of SplitView/ })
+ }
+
+ for (i = 0; i < properties.length; ++i) {
+ property = properties[i]
+ data.push({ tag: "QtObject," + property, component: objectComponent, property: property,
+ expectedWarning: /.*SplitView: attached properties can only be used on Items/ })
+ }
+
+ return data
+ }
+
+ function test_useAttachedPropertiesIncorrectly(data) {
+ // The object (whatever it may be) is not managed by a SplitView.
+ var object = createTemporaryObject(data.component, testCase, { objectName: data.tag })
+ verify(object)
+
+ ignoreWarning(data.expectedWarning)
+ // Should warn, but not crash.
+ object.SplitView[data.property] = 1;
+ }
+
+ function test_sizes_data() {
+ var splitViewWidth = testCase.width
+ var splitViewHeight = testCase.height
+ var data = [
+ {
+ // When the combined size of items is too large, the non-fill items should just exceed
+ // the size of the SplitView, exactly as they would were they in a RowLayout, for example.
+ tag: "fillItemOnLeft",
+ expectedGeometries: [
+ // We're the fill item, but since the combined implicitWidths
+ // of the other two items take up all the space, we get none.
+ { x: 0, y: 0, width: 0, height: splitViewHeight },
+ // First handle.
+ { x: 0, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ // The second item does not fill, so its width should be unchanged.
+ { x: defaultHorizontalHandleWidth, y: 0, width: 200, height: splitViewHeight },
+ // Second handle.
+ { x: 200 + defaultHorizontalHandleWidth, y: 0, width: defaultHorizontalHandleWidth,
+ height: splitViewHeight },
+ // The third item also gets its implicitWidth.
+ { x: 200 + defaultHorizontalHandleWidth * 2, y: 0, width: 200, height: splitViewHeight }
+ ]
+ },
+ {
+ // Same as above except vertical.
+ tag: "fillItemOnTop",
+ expectedGeometries: [
+ // We're the fill item, but since the combined implicitHeights
+ // of the other two items take up all the space, we get none.
+ { x: 0, y: 0, width: splitViewWidth, height: 0 },
+ // First handle.
+ { x: 0, y: 0, width: splitViewWidth, height: defaultVerticalHandleHeight },
+ // The second item does not fill, so its height should be unchanged.
+ { x: 0, y: defaultVerticalHandleHeight, width: splitViewWidth, height: 200 },
+ // Second handle.
+ { x: 0, y: 200 + defaultVerticalHandleHeight, width: splitViewWidth,
+ height: defaultVerticalHandleHeight },
+ // The third item also gets its implicitHeight.
+ { x: 0, y: 200 + defaultVerticalHandleHeight * 2, width: splitViewWidth, height: 200 }
+ ]
+ },
+ {
+ tag: "fillItemInMiddle",
+ expectedGeometries: [
+ // Our size is fixed.
+ { x: 0, y: 0, width: 25, height: splitViewHeight },
+ // First handle.
+ { x: 25, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ // The second item fills.
+ { x: 25 + defaultHorizontalHandleWidth, y: 0,
+ width: splitViewWidth - 25 - 200 - defaultHorizontalHandleWidth * 2, height: splitViewHeight },
+ // Second handle.
+ { x: splitViewWidth - 200 - defaultHorizontalHandleWidth, y: 0,
+ width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ // The third item's size is also fixed.
+ { x: splitViewWidth - 200, y: 0, width: 200, height: splitViewHeight }
+ ]
+ }
+ ]
+ return data
+ }
+
+ function test_sizes(data) {
+ var component = Qt.createComponent("splitview/" + data.tag + ".qml")
+ compare(component.status, Component.Ready, component.errorString());
+ var control = createTemporaryObject(component, testCase, { "handle": handleComponent })
+ verify(control)
+
+ compareSizes(control, data.expectedGeometries)
+ }
+
+ Component {
+ id: threeSizedItemsComponent
+
+ SplitView {
+ anchors.fill: parent
+ handle: handleComponent
+
+ Rectangle {
+ objectName: "salmon"
+ color: objectName
+ implicitWidth: 25
+ implicitHeight: 25
+ }
+ Rectangle {
+ objectName: "navajowhite"
+ color: objectName
+ implicitWidth: 100
+ implicitHeight: 100
+ }
+ Rectangle {
+ objectName: "steelblue"
+ color: objectName
+ implicitWidth: 200
+ implicitHeight: 200
+ }
+ }
+ }
+
+ function test_resetAttachedProperties_data() {
+ var splitViewWidth = testCase.width
+ var splitViewHeight = testCase.height
+ var data = [
+ {
+ tag: "resetMinimumWidth",
+ orientation: Qt.Horizontal,
+ // Set the minimumWidth to 50. It should be used instead of implicitWidth since it's greater than 25.
+ splitItemIndex: 0,
+ propertyName: "minimumWidth",
+ propertyValue: 50,
+ expectedGeometriesBefore: [
+ { x: 0, y: 0, width: 50, height: splitViewHeight },
+ { x: 50, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 50 + defaultHorizontalHandleWidth, y: 0, width: 100, height: splitViewHeight },
+ { x: 50 + 100 + defaultHorizontalHandleWidth, y: 0, width: defaultHorizontalHandleWidth,
+ height: splitViewHeight },
+ { x: 50 + 100 + defaultHorizontalHandleWidth * 2, y: 0,
+ width: splitViewWidth - 50 - 100 - defaultHorizontalHandleWidth * 2, height: splitViewHeight }
+ ],
+ // minimumWidth is now undefined, so implicitWidth should be used instead.
+ expectedGeometriesAfter: [
+ { x: 0, y: 0, width: 25, height: splitViewHeight },
+ { x: 25, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 25 + defaultHorizontalHandleWidth, y: 0, width: 100, height: splitViewHeight },
+ { x: 25 + 100 + defaultHorizontalHandleWidth, y: 0, width: defaultHorizontalHandleWidth,
+ height: splitViewHeight },
+ { x: 25 + 100 + defaultHorizontalHandleWidth * 2, y: 0,
+ width: splitViewWidth - 25 - 100 - defaultHorizontalHandleWidth * 2, height: splitViewHeight }
+ ]
+ },
+ {
+ tag: "resetMinimumHeight",
+ orientation: Qt.Vertical,
+ // Set the minimumHeight to 50. It should be used instead of implicitHeight since it's greater than 25.
+ splitItemIndex: 0,
+ propertyName: "minimumHeight",
+ propertyValue: 50,
+ expectedGeometriesBefore: [
+ { x: 0, y: 0, width: splitViewWidth, height: 50 },
+ { x: 0, y: 50, width: splitViewWidth, height: defaultVerticalHandleHeight },
+ { x: 0, y: 50 + defaultVerticalHandleHeight, width: splitViewWidth, height: 100 },
+ { x: 0, y: 50 + 100 + defaultVerticalHandleHeight, width: splitViewWidth,
+ height: defaultVerticalHandleHeight },
+ { x: 0, y: 50 + 100 + defaultVerticalHandleHeight * 2, width: splitViewWidth,
+ height: splitViewHeight - 50 - 100 - defaultVerticalHandleHeight * 2 }
+ ],
+ // preferredHeight is now undefined, so implicitHeight should be used instead.
+ expectedGeometriesAfter: [
+ { x: 0, y: 0, width: splitViewWidth, height: 25 },
+ { x: 0, y: 25, width: splitViewWidth, height: defaultVerticalHandleHeight },
+ { x: 0, y: 25 + defaultVerticalHandleHeight, width: splitViewWidth, height: 100 },
+ { x: 0, y: 25 + 100 + defaultVerticalHandleHeight, width: splitViewWidth,
+ height: defaultVerticalHandleHeight },
+ { x: 0, y: 25 + 100 + defaultVerticalHandleHeight * 2, width: splitViewWidth,
+ height: splitViewHeight - 25 - 100 - defaultVerticalHandleHeight * 2 }
+ ]
+ },
+ {
+ tag: "resetPreferredWidth",
+ orientation: Qt.Horizontal,
+ // Set the preferredWidth to 50; it should be used instead of implicitWidth.
+ splitItemIndex: 0,
+ propertyName: "preferredWidth",
+ propertyValue: 50,
+ expectedGeometriesBefore: [
+ { x: 0, y: 0, width: 50, height: splitViewHeight },
+ { x: 50, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 50 + defaultHorizontalHandleWidth, y: 0, width: 100, height: splitViewHeight },
+ { x: 50 + 100 + defaultHorizontalHandleWidth, y: 0, width: defaultHorizontalHandleWidth,
+ height: splitViewHeight },
+ { x: 50 + 100 + defaultHorizontalHandleWidth * 2, y: 0,
+ width: splitViewWidth - 50 - 100 - defaultHorizontalHandleWidth * 2, height: splitViewHeight }
+ ],
+ // preferredWidth is now undefined, so implicitWidth should be used instead.
+ expectedGeometriesAfter: [
+ { x: 0, y: 0, width: 25, height: splitViewHeight },
+ { x: 25, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 25 + defaultHorizontalHandleWidth, y: 0, width: 100, height: splitViewHeight },
+ { x: 25 + 100 + defaultHorizontalHandleWidth, y: 0, width: defaultHorizontalHandleWidth,
+ height: splitViewHeight },
+ { x: 25 + 100 + defaultHorizontalHandleWidth * 2, y: 0,
+ width: splitViewWidth - 25 - 100 - defaultHorizontalHandleWidth * 2, height: splitViewHeight }
+ ]
+ },
+ {
+ tag: "resetPreferredHeight",
+ orientation: Qt.Vertical,
+ // Set the preferredHeight to 50; it should be used instead of implicitHeight.
+ splitItemIndex: 0,
+ propertyName: "preferredHeight",
+ propertyValue: 50,
+ expectedGeometriesBefore: [
+ { x: 0, y: 0, width: splitViewWidth, height: 50 },
+ { x: 0, y: 50, width: splitViewWidth, height: defaultVerticalHandleHeight },
+ { x: 0, y: 50 + defaultVerticalHandleHeight, width: splitViewWidth, height: 100 },
+ { x: 0, y: 50 + 100 + defaultVerticalHandleHeight, width: splitViewWidth,
+ height: defaultVerticalHandleHeight },
+ { x: 0, y: 50 + 100 + defaultVerticalHandleHeight * 2, width: splitViewWidth,
+ height: splitViewHeight - 50 - 100 - defaultVerticalHandleHeight * 2 }
+ ],
+ // preferredHeight is now undefined, so implicitHeight should be used instead.
+ expectedGeometriesAfter: [
+ { x: 0, y: 0, width: splitViewWidth, height: 25 },
+ { x: 0, y: 25, width: splitViewWidth, height: defaultVerticalHandleHeight },
+ { x: 0, y: 25 + defaultVerticalHandleHeight, width: splitViewWidth, height: 100 },
+ { x: 0, y: 25 + 100 + defaultVerticalHandleHeight, width: splitViewWidth,
+ height: defaultVerticalHandleHeight },
+ { x: 0, y: 25 + 100 + defaultVerticalHandleHeight * 2, width: splitViewWidth,
+ height: splitViewHeight - 25 - 100 - defaultVerticalHandleHeight * 2 }
+ ]
+ },
+ {
+ tag: "resetMaximumWidth",
+ orientation: Qt.Horizontal,
+ // Set the maximumWidth to 15. It should be used instead of implicitWidth since it's less than 25.
+ splitItemIndex: 0,
+ propertyName: "maximumWidth",
+ propertyValue: 15,
+ expectedGeometriesBefore: [
+ { x: 0, y: 0, width: 15, height: splitViewHeight },
+ { x: 15, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 15 + defaultHorizontalHandleWidth, y: 0, width: 100, height: splitViewHeight },
+ { x: 15 + 100 + defaultHorizontalHandleWidth, y: 0, width: defaultHorizontalHandleWidth,
+ height: splitViewHeight },
+ { x: 15 + 100 + defaultHorizontalHandleWidth * 2, y: 0,
+ width: splitViewWidth - 15 - 100 - defaultHorizontalHandleWidth * 2, height: splitViewHeight }
+ ],
+ // maximumWidth is now undefined, so implicitWidth should be used instead.
+ expectedGeometriesAfter: [
+ { x: 0, y: 0, width: 25, height: splitViewHeight },
+ { x: 25, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 25 + defaultHorizontalHandleWidth, y: 0, width: 100, height: splitViewHeight },
+ { x: 25 + 100 + defaultHorizontalHandleWidth, y: 0, width: defaultHorizontalHandleWidth,
+ height: splitViewHeight },
+ { x: 25 + 100 + defaultHorizontalHandleWidth * 2, y: 0,
+ width: splitViewWidth - 25 - 100 - defaultHorizontalHandleWidth * 2, height: splitViewHeight }
+ ]
+ },
+ {
+ tag: "resetMaximumHeight",
+ orientation: Qt.Vertical,
+ // Set the preferredHeight to 15. It should be used instead of implicitHeight if it's not undefined.
+ splitItemIndex: 0,
+ propertyName: "maximumHeight",
+ propertyValue: 15,
+ expectedGeometriesBefore: [
+ { x: 0, y: 0, width: splitViewWidth, height: 15 },
+ { x: 0, y: 15, width: splitViewWidth, height: defaultVerticalHandleHeight },
+ { x: 0, y: 15 + defaultVerticalHandleHeight, width: splitViewWidth, height: 100 },
+ { x: 0, y: 15 + 100 + defaultVerticalHandleHeight, width: splitViewWidth,
+ height: defaultVerticalHandleHeight },
+ { x: 0, y: 15 + 100 + defaultVerticalHandleHeight * 2, width: splitViewWidth,
+ height: splitViewHeight - 15 - 100 - defaultVerticalHandleHeight * 2 }
+ ],
+ // preferredHeight is now undefined, so implicitHeight should be used instead.
+ expectedGeometriesAfter: [
+ { x: 0, y: 0, width: splitViewWidth, height: 25 },
+ { x: 0, y: 25, width: splitViewWidth, height: defaultVerticalHandleHeight },
+ { x: 0, y: 25 + defaultVerticalHandleHeight, width: splitViewWidth, height: 100 },
+ { x: 0, y: 25 + 100 + defaultVerticalHandleHeight, width: splitViewWidth,
+ height: defaultVerticalHandleHeight },
+ { x: 0, y: 25 + 100 + defaultVerticalHandleHeight * 2, width: splitViewWidth,
+ height: splitViewHeight - 25 - 100 - defaultVerticalHandleHeight * 2 }
+ ]
+ },
+ ]
+ return data;
+ }
+
+ function test_resetAttachedProperties(data) {
+ var control = createTemporaryObject(threeSizedItemsComponent, testCase,
+ { "orientation": data.orientation })
+ verify(control)
+
+ var splitItem = control.itemAt(data.splitItemIndex)
+ splitItem.SplitView[data.propertyName] = data.propertyValue
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compareSizes(control, data.expectedGeometriesBefore, "after setting attached property")
+
+ splitItem.SplitView[data.propertyName] = undefined
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compareSizes(control, data.expectedGeometriesAfter, "after resetting attached property")
+ }
+
+ function test_orientation() {
+ var control = createTemporaryObject(threeSizedItemsComponent, testCase)
+ verify(control)
+
+ var item0 = control.itemAt(0)
+ compare(item0.x, 0)
+ compare(item0.y, 0)
+ compare(item0.width, item0.implicitWidth)
+ compare(item0.height, testCase.height)
+
+ var handles = findHandles(control)
+ var handle0 = handles[0]
+ compare(handle0.x, item0.implicitWidth)
+ compare(handle0.y, 0)
+ compare(handle0.width, defaultHorizontalHandleWidth)
+ compare(handle0.height, testCase.height)
+
+ var item1 = control.itemAt(1)
+ compare(item1.x, item0.width + defaultHorizontalHandleWidth)
+ compare(item1.y, 0)
+ compare(item1.width, item1.implicitWidth)
+ compare(item1.height, testCase.height)
+
+ var handle1 = handles[1]
+ compare(handle1.x, item1.x + item1.width)
+ compare(handle1.y, 0)
+ compare(handle1.width, defaultHorizontalHandleWidth)
+ compare(handle1.height, testCase.height)
+
+ var item2 = control.itemAt(2)
+ compare(item2.x, item0.width + item1.width + defaultHorizontalHandleWidth * 2)
+ compare(item2.y, 0)
+ compare(item2.width, testCase.width - item2.x)
+ compare(item2.height, testCase.height)
+
+ control.orientation = Qt.Vertical
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compare(item0.x, 0)
+ compare(item0.y, 0)
+ compare(item0.width, testCase.width)
+ compare(item0.height, item0.implicitHeight)
+ handles = findHandles(control)
+ handle0 = handles[0]
+ compare(handle0.x, 0)
+ compare(handle0.y, item0.implicitHeight)
+ compare(handle0.width, testCase.width)
+ compare(handle0.height, defaultVerticalHandleHeight)
+ compare(item1.x, 0)
+ compare(item1.y, item0.height + defaultVerticalHandleHeight)
+ compare(item1.width, testCase.width)
+ compare(item1.height, item1.implicitHeight)
+ handle1 = handles[1]
+ compare(handle1.x, 0)
+ compare(handle1.y, item1.y + item1.height)
+ compare(handle1.width, testCase.width)
+ compare(handle1.height, defaultVerticalHandleHeight)
+ compare(item2.x, 0)
+ compare(item2.y, item0.height + item1.height + defaultVerticalHandleHeight * 2)
+ compare(item2.width, testCase.width)
+ compare(item2.height, testCase.height - item2.y)
+ }
+
+ readonly property int splitViewMargins: 50
+
+ Component {
+ id: threeItemsMinSizeAndFillComponent
+
+ SplitView {
+ anchors.fill: parent
+ handle: handleComponent
+
+ Rectangle {
+ objectName: "salmon"
+ color: objectName
+ implicitWidth: 25
+ implicitHeight: 25
+ SplitView.minimumWidth: 25
+ SplitView.minimumHeight: 25
+ SplitView.fillWidth: true
+ SplitView.fillHeight: true
+ }
+ Rectangle {
+ objectName: "navajowhite"
+ color: objectName
+ implicitWidth: 100
+ implicitHeight: 100
+ }
+ Rectangle {
+ objectName: "steelblue"
+ color: objectName
+ implicitWidth: 200
+ implicitHeight: 200
+ }
+ }
+ }
+
+ function test_dragHandle_data() {
+ var splitViewWidth = testCase.width - splitViewMargins * 2
+ var splitViewHeight = testCase.height - splitViewMargins * 2
+ var data = [
+ {
+ tag: "fillThirdItemAndDragFirstHandlePastRightSide",
+ component: threeSizedItemsComponent,
+ orientation: Qt.Horizontal,
+ // The index of the item that will fill.
+ fillIndex: 2,
+ // The index of the handle to be dragged.
+ handleIndex: 0,
+ // The position where the center of the handle will be.
+ newHandlePos: Qt.point(testCase.width + 20, testCase.height / 2),
+ // The expected geometry of each item managed by the SplitView before dragging the handle.
+ expectedGeometriesBeforeDrag: [
+ // First item.
+ { x: 0, y: 0, width: 25, height: splitViewHeight },
+ // First handle.
+ { x: 25, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ // Second item.
+ { x: 25 + defaultHorizontalHandleWidth, y: 0, width: 100, height: splitViewHeight },
+ // Second handle.
+ { x: 25 + 100 + defaultHorizontalHandleWidth, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ // Third item (fills).
+ { x: 25 + 100 + defaultHorizontalHandleWidth * 2, y: 0,
+ width: splitViewWidth - 25 - 100 - defaultHorizontalHandleWidth * 2, height: splitViewHeight }
+ ],
+ // The expected geometry of each item managed by the SplitView after dragging the handle.
+ expectedGeometriesAfterDrag: [
+ // The fill item is to the right of the handle at index 0, so the handle belongs
+ // to the left item: us. We should consume all of the fill item's width.
+ { x: 0, y: 0, width: splitViewWidth - 100 - defaultHorizontalHandleWidth * 2,
+ height: splitViewHeight },
+ // First handle.
+ { x: splitViewWidth - defaultHorizontalHandleWidth * 2 - 100,
+ y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ // The second item does not fill, so its width should be unchanged.
+ { x: splitViewWidth - 100 - defaultHorizontalHandleWidth,
+ y: 0, width: 100, height: splitViewHeight },
+ // Second handle.
+ { x: splitViewWidth - defaultHorizontalHandleWidth,
+ y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ // The last item does fill, so it should lose all of its width.
+ { x: splitViewWidth, y: 0, width: 0, height: splitViewHeight }
+ ]
+ },
+ {
+ tag: "fillThirdItemAndDragFirstHandlePastBottomSide",
+ component: threeSizedItemsComponent,
+ orientation: Qt.Vertical,
+ fillIndex: 2,
+ handleIndex: 0,
+ newHandlePos: Qt.point(testCase.width / 2, testCase.height + 20),
+ expectedGeometriesBeforeDrag: [
+ { x: 0, y: 0, width: splitViewWidth, height: 25 },
+ { x: 0, y: 25, width: splitViewWidth, height: defaultVerticalHandleHeight },
+ { x: 0, y: 25 + defaultVerticalHandleHeight, width: splitViewWidth, height: 100 },
+ { x: 0, y: 25 + 100 + defaultVerticalHandleHeight, width: splitViewWidth, height: defaultVerticalHandleHeight },
+ { x: 0, y: 25 + 100 + defaultVerticalHandleHeight * 2,
+ width: splitViewWidth, height: splitViewHeight - 25 - 100 - defaultVerticalHandleHeight * 2 }
+ ],
+ // The expected geometry of each item managed by the SplitView after dragging the handle.
+ expectedGeometriesAfterDrag: [
+ // The fill item is to the bottom of the handle at index 0, so the handle belongs
+ // to the top item: us. We should consume all of the fill item's width.
+ { x: 0, y: 0, width: splitViewWidth,
+ height: splitViewHeight - 100 - defaultVerticalHandleHeight * 2 },
+ // First handle.
+ { x: 0, y: splitViewHeight - defaultVerticalHandleHeight * 2 - 100,
+ width: splitViewWidth, height: defaultVerticalHandleHeight },
+ // The second item does not fill, so its height should be unchanged.
+ { x: 0, y: splitViewWidth - 100 - defaultVerticalHandleHeight,
+ width: splitViewWidth, height: 100 },
+ // Second handle.
+ { x: 0, y: splitViewHeight - defaultVerticalHandleHeight,
+ width: splitViewWidth, height: defaultVerticalHandleHeight },
+ // The last item does fill, so it should lose all of its width.
+ { x: 0, y: splitViewHeight, width: splitViewWidth, height: 0 }
+ ]
+ },
+ {
+ tag: "fillThirdItemAndDragSecondHandlePastLeftSide",
+ component: threeSizedItemsComponent,
+ orientation: Qt.Horizontal,
+ fillIndex: 2,
+ handleIndex: 1,
+ newHandlePos: Qt.point(-20, testCase.height / 2),
+ expectedGeometriesBeforeDrag: [
+ { x: 0, y: 0, width: 25, height: splitViewHeight },
+ { x: 25, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 25 + defaultHorizontalHandleWidth, y: 0, width: 100, height: splitViewHeight },
+ { x: 25 + 100 + defaultHorizontalHandleWidth, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 25 + 100 + defaultHorizontalHandleWidth * 2, y: 0,
+ width: splitViewWidth - 25 - 100 - defaultHorizontalHandleWidth * 2, height: splitViewHeight }
+ ],
+ expectedGeometriesAfterDrag: [
+ // The fill item is to the right of the handle at index 1, so the handle belongs
+ // to the second item; our width should be unchanged.
+ { x: 0, y: 0, width: 25, height: splitViewHeight },
+ // First handle.
+ { x: 25, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ // The second item is the one being resized, and since we're dragging its handle
+ // to the left, its width should decrease.
+ { x: 25 + defaultHorizontalHandleWidth, y: 0, width: 0, height: splitViewHeight },
+ // Second handle.
+ { x: 25 + defaultHorizontalHandleWidth, y: 0, width: defaultHorizontalHandleWidth,
+ height: splitViewHeight },
+ // The last item fills, so it should get the second item's lost width.
+ { x: 25 + defaultHorizontalHandleWidth * 2, y: 0,
+ width: splitViewWidth - 25 - defaultHorizontalHandleWidth * 2, height: splitViewHeight }
+ ]
+ },
+ {
+ tag: "fillThirdItemAndDragSecondHandlePastTopSide",
+ component: threeSizedItemsComponent,
+ orientation: Qt.Vertical,
+ fillIndex: 2,
+ handleIndex: 1,
+ newHandlePos: Qt.point(testCase.width / 2, -20),
+ expectedGeometriesBeforeDrag: [
+ { x: 0, y: 0, width: splitViewWidth, height: 25 },
+ { x: 0, y: 25, width: splitViewWidth, height: defaultVerticalHandleHeight },
+ { x: 0, y: 25 + defaultVerticalHandleHeight, width: splitViewWidth, height: 100 },
+ { x: 0, y: 25 + 100 + defaultVerticalHandleHeight, width: splitViewWidth, height: defaultVerticalHandleHeight },
+ { x: 0, y: 25 + 100 + defaultVerticalHandleHeight * 2,
+ width: splitViewWidth, height: splitViewHeight - 25 - 100 - defaultVerticalHandleHeight * 2 }
+ ],
+ expectedGeometriesAfterDrag: [
+ // The fill item is to the bottom of the handle at index 1, so the handle belongs
+ // to the second item; our height should be unchanged.
+ { x: 0, y: 0, width: splitViewWidth, height: 25 },
+ // First handle.
+ { x: 0, y: 25, width: splitViewWidth, height: defaultVerticalHandleHeight },
+ // The second item is the one being resized, and since we're dragging its handle
+ // to the top, its height should decrease.
+ { x: 0, y: 25 + defaultVerticalHandleHeight, width: splitViewWidth, height: 0 },
+ // Second handle.
+ { x: 0, y: 25 + defaultVerticalHandleHeight, width: splitViewWidth,
+ height: defaultVerticalHandleHeight },
+ // The last item fills, so it should get the second item's lost height.
+ { x: 0, y: 25 + defaultVerticalHandleHeight * 2,
+ width: splitViewWidth, height: splitViewHeight - 25 - defaultVerticalHandleHeight * 2 }
+ ]
+ },
+ {
+ // First item should start off empty and then eventually take up all of 3rd item's space
+ // as the handle is dragged past the right side.
+ tag: "fillFirstItemAndDragSecondHandlePastRightSide",
+ component: threeSizedItemsComponent,
+ orientation: Qt.Horizontal,
+ fillIndex: 0,
+ handleIndex: 1,
+ newHandlePos: Qt.point(testCase.width + 20, testCase.height / 2),
+ expectedGeometriesBeforeDrag: [
+ { x: 0, y: 0, width: 0, height: splitViewHeight },
+ { x: 0, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: defaultHorizontalHandleWidth, y: 0, width: 100, height: splitViewHeight },
+ { x: 100 + defaultHorizontalHandleWidth, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 100 + defaultHorizontalHandleWidth * 2, y: 0, width: 200, height: splitViewHeight }
+ ],
+ expectedGeometriesAfterDrag: [
+ // The fill item is to the left of the handle at index 1, so the handle belongs
+ // to the third item. Since we're moving the handle to the right side of the
+ // SplitView, our width should grow as we consume the width of the third item.
+ { x: 0, y: 0, width: splitViewWidth - 100 - defaultHorizontalHandleWidth * 2, height: splitViewHeight },
+ // First handle.
+ { x: splitViewWidth - 100 - defaultHorizontalHandleWidth * 2, y: 0,
+ width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ // The second item's width remains unchanged.
+ { x: splitViewWidth - 100 - defaultHorizontalHandleWidth, y: 0, width: 100, height: splitViewHeight },
+ // Second handle.
+ { x: splitViewWidth - defaultHorizontalHandleWidth, y: 0,
+ width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ // The last item loses its width.
+ { x: splitViewWidth, y: 0, width: 0, height: splitViewHeight }
+ ]
+ },
+ {
+ // First item should start off empty and then eventually take up all of 3rd item's space
+ // as the handle is dragged past the bottom side.
+ tag: "fillFirstItemAndDragSecondHandlePastBottomSide",
+ component: threeSizedItemsComponent,
+ orientation: Qt.Vertical,
+ fillIndex: 0,
+ handleIndex: 1,
+ newHandlePos: Qt.point(testCase.width / 2, testCase.height + 20),
+ expectedGeometriesBeforeDrag: [
+ { x: 0, y: 0, width: splitViewWidth, height: 0 },
+ { x: 0, y: 0, width: splitViewWidth, height: defaultVerticalHandleHeight },
+ { x: 0, y: defaultVerticalHandleHeight, width: splitViewWidth, height: 100 },
+ { x: 0, y: 100 + defaultVerticalHandleHeight, width: splitViewWidth, height: defaultVerticalHandleHeight },
+ { x: 0, y: 100 + defaultVerticalHandleHeight * 2, width: splitViewWidth, height: 200 }
+ ],
+ expectedGeometriesAfterDrag: [
+ // The fill item is to the top of the handle at index 1, so the handle belongs
+ // to the third item. Since we're moving the handle to the bottom side of the
+ // SplitView, our height should grow as we consume the height of the third item.
+ { x: 0, y: 0, width: splitViewWidth, height: splitViewHeight - 100 - defaultVerticalHandleHeight * 2 },
+ // First handle.
+ { x: 0, y: splitViewHeight - 100 - defaultVerticalHandleHeight * 2,
+ width: splitViewWidth, height: defaultVerticalHandleHeight },
+ // The second item's width remains unchanged.
+ { x: 0, y: splitViewHeight - 100 - defaultVerticalHandleHeight, width: splitViewWidth, height: 100 },
+ // Second handle.
+ { x: 0, y: splitViewHeight - defaultVerticalHandleHeight,
+ width: splitViewWidth, height: defaultVerticalHandleHeight },
+ // The last item loses its width.
+ { x: 0, y: splitViewHeight, width: splitViewHeight, height: 0 }
+ ]
+ },
+ {
+ tag: "fillFirstItemAndDragFirstHandlePastLeftSide",
+ component: threeSizedItemsComponent,
+ orientation: Qt.Horizontal,
+ fillIndex: 0,
+ handleIndex: 0,
+ newHandlePos: Qt.point(-20, testCase.height / 2),
+ expectedGeometriesBeforeDrag: [
+ { x: 0, y: 0, width: 0, height: splitViewHeight },
+ { x: 0, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: defaultHorizontalHandleWidth, y: 0, width: 100, height: splitViewHeight },
+ { x: 100 + defaultHorizontalHandleWidth, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ // The second item's implicitWidth is 100, and ours is 200. The available width is 300,
+ // so both items get their implicit widths.
+ { x: 100 + defaultHorizontalHandleWidth * 2, y: 0, width: splitViewWidth - 100, height: splitViewHeight }
+ ],
+ // Should be unchanged.
+ expectedGeometriesAfterDrag: [
+ { x: 0, y: 0, width: 0, height: splitViewHeight },
+ { x: 0, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: defaultHorizontalHandleWidth, y: 0, width: 100, height: splitViewHeight },
+ { x: 100 + defaultHorizontalHandleWidth, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 100 + defaultHorizontalHandleWidth * 2, y: 0, width: splitViewWidth - 100, height: splitViewHeight }
+ ]
+ },
+ {
+ tag: "fillFirstItemWithMinWidthAndDragFirstHandlePastLeftSide",
+ component: threeItemsMinSizeAndFillComponent,
+ orientation: Qt.Horizontal,
+ fillIndex: 0,
+ handleIndex: 0,
+ newHandlePos: Qt.point(-20, testCase.height / 2),
+ expectedGeometriesBeforeDrag: [
+ { x: 0, y: 0, width: 25, height: splitViewHeight },
+ { x: 25, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 25 + defaultHorizontalHandleWidth, y: 0, width: 100, height: splitViewHeight },
+ { x: 25 + 100 + defaultHorizontalHandleWidth, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 25 + 100 + defaultHorizontalHandleWidth * 2, y: 0, width: splitViewWidth - 100, height: splitViewHeight }
+ ],
+ // Should be unchanged.
+ expectedGeometriesAfterDrag: [
+ { x: 0, y: 0, width: 25, height: splitViewHeight },
+ { x: 25, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 25 + defaultHorizontalHandleWidth, y: 0, width: 100, height: splitViewHeight },
+ { x: 25 + 100 + defaultHorizontalHandleWidth, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 25 + 100 + defaultHorizontalHandleWidth * 2, y: 0, width: splitViewWidth - 100, height: splitViewHeight }
+ ]
+ }
+ ]
+ return data
+ }
+
+ function test_dragHandle(data) {
+ var control = createTemporaryObject(data.component, testCase)
+ verify(control)
+
+ control.orientation = data.orientation
+
+ // Ensure that there is space to drag outside of the SplitView.
+ control.anchors.margins = splitViewMargins
+
+ var fillItem = control.itemAt(data.fillIndex)
+ if (control.orientation === Qt.Horizontal)
+ fillItem.SplitView.fillWidth = true
+ else
+ fillItem.SplitView.fillHeight = true
+
+ // Check the sizes of the items before the drag.
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compareSizes(control, data.expectedGeometriesBeforeDrag, "before drag")
+
+ // Drag the handle.
+ var handles = findHandles(control)
+ var targetHandle = handles[data.handleIndex]
+ mousePress(targetHandle)
+ verify(control.resizing)
+ var localPos = testCase.mapToItem(targetHandle, data.newHandlePos.x, data.newHandlePos.y)
+ mouseMove(targetHandle, localPos.x - targetHandle.width / 2, localPos.y - targetHandle.height / 2)
+ verify(control.resizing)
+ compareSizes(control, data.expectedGeometriesAfterDrag, "after drag move")
+
+ // The geometries should remain unchanged after releasing.
+ mouseRelease(targetHandle, localPos.x - targetHandle.width / 2, localPos.y - targetHandle.height / 2, Qt.LeftButton)
+ verify(!control.resizing)
+ compareSizes(control, data.expectedGeometriesAfterDrag, "after drag release")
+ }
+
+ function test_splitViewGeometryChanges_data() {
+ var defaultSplitViewWidth = testCase.width
+ var defaultSplitViewHeight = testCase.height
+
+ var data = [
+ {
+ tag: "growWidth",
+ orientation: Qt.Horizontal,
+ splitViewWidth: 800,
+ expectedGeometries: [
+ { x: 0, y: 0, width: 25, height: defaultSplitViewHeight },
+ { x: 25, y: 0, width: defaultHorizontalHandleWidth, height: defaultSplitViewHeight },
+ { x: 25 + defaultHorizontalHandleWidth, y: 0, width: 100, height: defaultSplitViewHeight },
+ { x: 25 + 100 + defaultHorizontalHandleWidth, y: 0, width: defaultHorizontalHandleWidth,
+ height: defaultSplitViewHeight },
+ { x: 25 + 100 + defaultHorizontalHandleWidth * 2, y: 0,
+ width: 800 - 25 - 100 - defaultHorizontalHandleWidth * 2, height: defaultSplitViewHeight }
+ ]
+ },
+ {
+ // Same as above except vertical.
+ tag: "growHeight",
+ orientation: Qt.Vertical,
+ splitViewHeight: 800,
+ expectedGeometries: [
+ { x: 0, y: 0, width: defaultSplitViewWidth, height: 25 },
+ { x: 0, y: 25, width: defaultSplitViewWidth, height: defaultVerticalHandleHeight },
+ { x: 0, y: 25 + defaultVerticalHandleHeight, width: defaultSplitViewWidth, height: 100 },
+ { x: 0, y: 25 + 100 + defaultVerticalHandleHeight, width: defaultSplitViewWidth,
+ height: defaultVerticalHandleHeight },
+ { x: 0, y: 25 + 100 + defaultVerticalHandleHeight * 2, width: defaultSplitViewWidth,
+ height: 800 - 25 - 100 - defaultVerticalHandleHeight * 2 }
+ ]
+ },
+ {
+ tag: "shrinkWidth",
+ orientation: Qt.Horizontal,
+ splitViewWidth: 200,
+ expectedGeometries: [
+ { x: 0, y: 0, width: 25, height: defaultSplitViewHeight },
+ { x: 25, y: 0, width: defaultHorizontalHandleWidth, height: defaultSplitViewHeight },
+ { x: 25 + defaultHorizontalHandleWidth, y: 0, width: 100, height: defaultSplitViewHeight },
+ { x: 25 + 100 + defaultHorizontalHandleWidth, y: 0, width: defaultHorizontalHandleWidth,
+ height: defaultSplitViewHeight },
+ { x: 25 + 100 + defaultHorizontalHandleWidth * 2, y: 0,
+ width: 200 - 25 - 100 - defaultHorizontalHandleWidth * 2, height: defaultSplitViewHeight }
+ ]
+ },
+ {
+ // Same as above except vertical.
+ tag: "shrinkHeight",
+ orientation: Qt.Vertical,
+ splitViewHeight: 200,
+ expectedGeometries: [
+ { x: 0, y: 0, width: defaultSplitViewWidth, height: 25 },
+ { x: 0, y: 25, width: defaultSplitViewWidth, height: defaultVerticalHandleHeight },
+ { x: 0, y: 25 + defaultVerticalHandleHeight, width: defaultSplitViewWidth, height: 100 },
+ { x: 0, y: 25 + 100 + defaultVerticalHandleHeight, width: defaultSplitViewWidth,
+ height: defaultVerticalHandleHeight },
+ { x: 0, y: 25 + 100 + defaultVerticalHandleHeight * 2, width: defaultSplitViewWidth,
+ height: 200 - 25 - 100 - defaultVerticalHandleHeight * 2 }
+ ]
+ },
+ ]
+ return data
+ }
+
+ function test_splitViewGeometryChanges(data) {
+ var control = createTemporaryObject(threeSizedItemsComponent, testCase,
+ { "handle": handleComponent, "anchors.fill": undefined, "orientation": data.orientation })
+ verify(control)
+
+ if (data.hasOwnProperty("splitViewWidth"))
+ control.width = data.splitViewWidth
+ else
+ control.width = testCase.width
+
+ if (data.hasOwnProperty("splitViewHeight"))
+ control.height = data.splitViewHeight
+ else
+ control.height = testCase.height
+
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compareSizes(control, data.expectedGeometries)
+ }
+
+ function test_splitItemImplicitSizeChanges_data() {
+ var defaultSplitViewWidth = testCase.width
+ var defaultSplitViewHeight = testCase.height
+
+ var data = [
+ {
+ tag: "growImplicitWidth",
+ orientation: Qt.Horizontal,
+ splitItemImplicitWidth: 50,
+ expectedGeometries: [
+ { x: 0, y: 0, width: 50, height: defaultSplitViewHeight },
+ { x: 50, y: 0, width: defaultHorizontalHandleWidth, height: defaultSplitViewHeight },
+ { x: 50 + defaultHorizontalHandleWidth, y: 0, width: 100, height: defaultSplitViewHeight },
+ { x: 50 + 100 + defaultHorizontalHandleWidth, y: 0, width: defaultHorizontalHandleWidth,
+ height: defaultSplitViewHeight },
+ { x: 50 + 100 + defaultHorizontalHandleWidth * 2, y: 0,
+ width: defaultSplitViewWidth - 50 - 100 - defaultHorizontalHandleWidth * 2, height: defaultSplitViewHeight }
+ ]
+ },
+ {
+ tag: "growImplicitHeight",
+ orientation: Qt.Vertical,
+ splitItemImplicitHeight: 50,
+ expectedGeometries: [
+ { x: 0, y: 0, width: defaultSplitViewWidth, height: 50 },
+ { x: 0, y: 50, width: defaultSplitViewWidth, height: defaultVerticalHandleHeight },
+ { x: 0, y: 50 + defaultVerticalHandleHeight, width: defaultSplitViewWidth, height: 100 },
+ { x: 0, y: 50 + 100 + defaultVerticalHandleHeight, width: defaultSplitViewWidth,
+ height: defaultVerticalHandleHeight },
+ { x: 0, y: 50 + 100 + defaultVerticalHandleHeight * 2, width: defaultSplitViewWidth,
+ height: defaultSplitViewHeight - 50 - 100 - defaultVerticalHandleHeight * 2 }
+ ]
+ }
+ ]
+ return data
+ }
+
+ // Tests that implicitWidth/Height changes in items are noticed by SplitView.
+ function test_splitItemImplicitSizeChanges(data) {
+ var control = createTemporaryObject(threeSizedItemsComponent, testCase,
+ { "handle": handleComponent, "orientation": data.orientation })
+ verify(control)
+
+ var firstItem = control.itemAt(0)
+
+ if (data.hasOwnProperty("splitItemImplicitWidth"))
+ firstItem.implicitWidth = data.splitItemImplicitWidth
+
+ if (data.hasOwnProperty("splitItemImplicitHeight"))
+ firstItem.implicitHeight = data.splitItemImplicitHeight
+
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compareSizes(control, data.expectedGeometries)
+ }
+
+ Component {
+ id: largerHandle
+ Rectangle {
+ objectName: "largerHandle"
+ implicitWidth: 20
+ implicitHeight: 20
+ color: "#444"
+ }
+ }
+
+ Component {
+ id: smallerHandle
+ Rectangle {
+ objectName: "smallerHandle"
+ implicitWidth: 5
+ implicitHeight: 5
+ color: "#444"
+ }
+ }
+
+ function test_handleChanges_data() {
+ var splitViewWidth = testCase.width
+ var splitViewHeight = testCase.height
+
+ var data = [
+ {
+ tag: "growHandleWidth",
+ orientation: Qt.Horizontal,
+ handleComponent: largerHandle,
+ expectedGeometries: [
+ { x: 0, y: 0, width: 25, height: splitViewHeight },
+ { x: 25, y: 0, width: 20, height: splitViewHeight },
+ { x: 25 + 20, y: 0, width: 100, height: splitViewHeight },
+ { x: 25 + 100 + 20, y: 0, width: 20, height: splitViewHeight },
+ { x: 25 + 100 + 20 * 2, y: 0, width: splitViewWidth - 25 - 100 - 20 * 2,
+ height: splitViewHeight }
+ ]
+ },
+ {
+ // Same as above except vertical.
+ tag: "growHandleHeight",
+ orientation: Qt.Vertical,
+ handleComponent: largerHandle,
+ expectedGeometries: [
+ { x: 0, y: 0, width: splitViewWidth, height: 25 },
+ { x: 0, y: 25, width: splitViewWidth, height: 20 },
+ { x: 0, y: 25 + 20, width: splitViewWidth, height: 100 },
+ { x: 0, y: 25 + 100 + 20, width: splitViewWidth, height: 20 },
+ { x: 0, y: 25 + 100 + 20 * 2, width: splitViewWidth,
+ height: splitViewHeight - 25 - 100 - 20 * 2 }
+ ]
+ },
+ {
+ tag: "shrinkHandleWidth",
+ orientation: Qt.Horizontal,
+ handleComponent: smallerHandle,
+ expectedGeometries: [
+ { x: 0, y: 0, width: 25, height: splitViewHeight },
+ { x: 25, y: 0, width: 5, height: splitViewHeight },
+ { x: 25 + 5, y: 0, width: 100, height: splitViewHeight },
+ { x: 25 + 100 + 5, y: 0, width: 5, height: splitViewHeight },
+ { x: 25 + 100 + 5 * 2, y: 0, width: splitViewWidth - 25 - 100 - 5 * 2,
+ height: splitViewHeight }
+ ]
+ },
+ {
+ // Same as above except vertical.
+ tag: "shrinkHandleHeight",
+ orientation: Qt.Vertical,
+ handleComponent: smallerHandle,
+ expectedGeometries: [
+ { x: 0, y: 0, width: splitViewWidth, height: 25 },
+ { x: 0, y: 25, width: splitViewWidth, height: 5 },
+ { x: 0, y: 25 + 5, width: splitViewWidth, height: 100 },
+ { x: 0, y: 25 + 100 + 5, width: splitViewWidth, height: 5 },
+ { x: 0, y: 25 + 100 + 5 * 2, width: splitViewWidth,
+ height: splitViewHeight - 25 - 100 - 5 * 2 }
+ ]
+ }
+ ]
+ return data
+ }
+
+ function test_handleChanges(data) {
+ var control = createTemporaryObject(threeSizedItemsComponent, testCase,
+ { "orientation": data.orientation })
+ verify(control)
+
+ control.handle = data.handleComponent
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compareSizes(control, data.expectedGeometries)
+ }
+
+ function test_insertRemoveItems_data() {
+ var splitViewWidth = testCase.width
+ var splitViewHeight = testCase.height
+
+ var data = [
+ {
+ tag: "insertItemAtHorizontalEnd",
+ orientation: Qt.Horizontal,
+ insertItemAtIndex: 3,
+ expectedGeometries: [
+ { x: 0, y: 0, width: 25, height: splitViewHeight },
+ { x: 25, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 25 + defaultHorizontalHandleWidth, y: 0, width: 100, height: splitViewHeight },
+ { x: 25 + 100 + defaultHorizontalHandleWidth, y: 0,
+ width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ // This was the fill item originally, but since no fill item is explicitly
+ // specified, and we added an item to the right of it, it is no longer the fill item
+ // because it's no longer last.
+ { x: 25 + 100 + defaultHorizontalHandleWidth * 2, y: 0,
+ width: 200, height: splitViewHeight },
+ // Handle for newly added item.
+ { x: 25 + 100 + 200 + defaultHorizontalHandleWidth * 2, y: 0,
+ width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ // Newly added item.
+ { x: 25 + 100 + 200 + defaultHorizontalHandleWidth * 3, y: 0,
+ width: splitViewWidth - 25 - 100 - 200 - defaultHorizontalHandleWidth * 3,
+ height: splitViewHeight },
+ ]
+ },
+ {
+ tag: "insertItemAtHorizontalBeginning",
+ orientation: Qt.Horizontal,
+ insertItemAtIndex: 0,
+ expectedGeometries: [
+ // Newly added item.
+ { x: 0, y: 0, width: 25, height: splitViewHeight },
+ { x: 25, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 25 + defaultHorizontalHandleWidth, y: 0, width: 25, height: splitViewHeight },
+ { x: 25 * 2 + defaultHorizontalHandleWidth, y: 0,
+ width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 25 * 2 + defaultHorizontalHandleWidth * 2, y: 0, width: 100, height: splitViewHeight },
+ { x: 25 * 2 + 100 + defaultHorizontalHandleWidth * 2, y: 0,
+ width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ // Fill item doesn't change.
+ { x: 25 * 2 + 100 + defaultHorizontalHandleWidth * 3, y: 0,
+ width: splitViewWidth - 25 * 2 - 100 - defaultHorizontalHandleWidth * 3,
+ height: splitViewHeight },
+ ]
+ },
+ {
+ tag: "removeItemFromHorizontalEnd",
+ orientation: Qt.Horizontal,
+ removeItemAtIndex: 2,
+ expectedGeometries: [
+ { x: 0, y: 0, width: 25, height: splitViewHeight },
+ { x: 25, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 25 + defaultHorizontalHandleWidth, y: 0,
+ width: splitViewWidth - 25 - defaultHorizontalHandleWidth, height: splitViewHeight },
+ ]
+ },
+ {
+ tag: "removeItemFromHorizontalBeginning",
+ orientation: Qt.Horizontal,
+ removeItemAtIndex: 0,
+ expectedGeometries: [
+ { x: 0, y: 0, width: 100, height: splitViewHeight },
+ { x: 100, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 100 + defaultHorizontalHandleWidth, y: 0,
+ width: splitViewWidth - 100 - defaultHorizontalHandleWidth, height: splitViewHeight },
+ ]
+ }
+ ]
+ return data
+ }
+
+ Component {
+ id: smallRectComponent
+
+ Rectangle {
+ objectName: "darkseagreen"
+ color: objectName
+ implicitWidth: 25
+ implicitHeight: 25
+ }
+ }
+
+ function test_insertRemoveItems(data) {
+ var control = createTemporaryObject(threeSizedItemsComponent, testCase,
+ { "orientation": data.orientation })
+ verify(control)
+
+ if (data.hasOwnProperty("removeItemAtIndex")) {
+ var itemToRemove = control.itemAt(data.removeItemAtIndex)
+ verify(itemToRemove)
+
+ control.removeItem(itemToRemove)
+ } else if (data.hasOwnProperty("insertItemAtIndex")) {
+ var itemToAdd = smallRectComponent.createObject(control)
+ control.insertItem(data.insertItemAtIndex, itemToAdd)
+ }
+
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compareSizes(control, data.expectedGeometries)
+ }
+
+ function test_removeAllItems() {
+ var control = createTemporaryObject(threeSizedItemsComponent, testCase)
+ verify(control)
+
+ while (control.count > 0)
+ var itemToRemove = control.removeItem(0)
+ // Shouldn't crash.
+ }
+
+ function test_hideItems_data() {
+ var splitViewWidth = testCase.width
+ var splitViewHeight = testCase.height
+
+ var data = [
+ {
+ tag: "hideItemAtHorizontalEnd",
+ orientation: Qt.Horizontal,
+ hideIndices: [2],
+ expectedGeometries: [
+ { x: 0, y: 0, width: 25, height: splitViewHeight },
+ { x: 25, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 25 + defaultHorizontalHandleWidth, y: 0,
+ width: splitViewWidth - 25 - defaultHorizontalHandleWidth, height: splitViewHeight },
+ { hidden: true }, // Handle for second item should be hidden.
+ { hidden: true } // Last item should be hidden.
+ ]
+ },
+ {
+ tag: "hideItemAtHorizontalBeginning",
+ orientation: Qt.Horizontal,
+ hideIndices: [0],
+ expectedGeometries: [
+ { hidden: true }, // First item should be hidden.
+ { hidden: true }, // Handle for first item should be hidden.
+ { x: 0, y: 0, width: 100, height: splitViewHeight },
+ { x: 100, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 100 + defaultHorizontalHandleWidth, y: 0,
+ width: splitViewWidth - 100 - defaultHorizontalHandleWidth, height: splitViewHeight }
+ ]
+ },
+ {
+ tag: "hideItemAtVerticalEnd",
+ orientation: Qt.Vertical,
+ hideIndices: [2],
+ expectedGeometries: [
+ { x: 0, y: 0, width: splitViewWidth, height: 25 },
+ { x: 0, y: 25, width: splitViewWidth, height: defaultVerticalHandleHeight },
+ { x: 0, y: 25 + defaultVerticalHandleHeight,
+ width: splitViewWidth, height: splitViewHeight - 25 - defaultVerticalHandleHeight },
+ { hidden: true }, // Handle for second item should be hidden.
+ { hidden: true } // Last item should be hidden.
+ ]
+ },
+ {
+ tag: "hideItemAtVerticalBeginning",
+ orientation: Qt.Vertical,
+ hideIndices: [0],
+ expectedGeometries: [
+ { hidden: true }, // First item should be hidden.
+ { hidden: true }, // Handle for first item should be hidden.
+ { x: 0, y: 0, width: splitViewWidth, height: 100 },
+ { x: 0, y: 100, width: splitViewWidth, height: defaultVerticalHandleHeight },
+ { x: 0, y: 100 + defaultVerticalHandleHeight,
+ width: splitViewWidth, height: splitViewHeight - 100 - defaultVerticalHandleHeight }
+ ]
+ },
+ {
+ // No handles should be visible when there's only one item.
+ tag: "hideLastTwoHorizontalItems",
+ orientation: Qt.Horizontal,
+ hideIndices: [1, 2],
+ expectedGeometries: [
+ { x: 0, y: 0, width: splitViewWidth, height: splitViewHeight },
+ { hidden: true }, // Handle for first item should be hidden.
+ { hidden: true }, // Second item should be hidden.
+ { hidden: true }, // Handle for second item should be hidden.
+ { hidden: true } // Third item should be hidden.
+ ]
+ }
+ ]
+ return data
+ }
+
+ function test_hideItems(data) {
+ var control = createTemporaryObject(threeSizedItemsComponent, testCase,
+ { "orientation": data.orientation })
+ verify(control)
+
+ for (var i = 0; i < data.hideIndices.length; ++i) {
+ var itemToHide = control.itemAt(data.hideIndices[i])
+ verify(itemToHide)
+ itemToHide.visible = false
+ }
+
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compareSizes(control, data.expectedGeometries)
+ }
+
+ function test_hideAndShowItems_data() {
+ var splitViewWidth = testCase.width
+ var splitViewHeight = testCase.height
+
+ var data = [
+ {
+ tag: "hideLastTwoHorizontalItems",
+ orientation: Qt.Horizontal,
+ hideIndices: [1, 2],
+ expectedGeometriesAfterHiding: [
+ { x: 0, y: 0, width: splitViewWidth, height: splitViewHeight },
+ { hidden: true }, // Handle for first item should be hidden.
+ { hidden: true }, // Second item should be hidden.
+ { hidden: true }, // Handle for second item should be hidden.
+ { hidden: true } // Third item should be hidden.
+ ],
+ showIndices: [1],
+ expectedGeometriesAfterShowing: [
+ // First item should be visible with its implicit size.
+ { x: 0, y: 0, width: 25, height: splitViewHeight },
+ // Handle for first item should be visible.
+ { x: 25, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ // Second item should be visible and fill.
+ { x: 25 + defaultHorizontalHandleWidth, y: 0,
+ width: splitViewWidth - 25 - defaultHorizontalHandleWidth, height: splitViewHeight },
+ { hidden: true }, // Handle for second item should be hidden.
+ { hidden: true } // Third item should be hidden.
+ ]
+ }
+ ]
+ return data
+ }
+
+ function test_hideAndShowItems(data) {
+ var control = createTemporaryObject(threeSizedItemsComponent, testCase,
+ { "orientation": data.orientation })
+ verify(control)
+
+ for (var i = 0; i < data.hideIndices.length; ++i) {
+ var itemToHide = control.itemAt(data.hideIndices[i])
+ verify(itemToHide)
+ itemToHide.visible = false
+ }
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compareSizes(control, data.expectedGeometriesAfterHiding, "after hiding")
+
+ for (i = 0; i < data.showIndices.length; ++i) {
+ var itemToShow = control.itemAt(data.showIndices[i])
+ verify(itemToShow)
+ itemToShow.visible = true
+ }
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compareSizes(control, data.expectedGeometriesAfterShowing, "after showing")
+ }
+
+ function test_moveHiddenItems_data() {
+ var splitViewWidth = testCase.width
+ var splitViewHeight = testCase.height
+
+ var data = [
+ {
+ tag: "hideSecondItemAndMoveItToFirst",
+ orientation: Qt.Horizontal,
+ hideIndices: [1],
+ moveFromIndex: 1,
+ moveToIndex: 0,
+ expectedGeometriesAfterMoving: [
+ { hidden: true }, // First item (was second) should be hidden.
+ { hidden: true }, // Handle for first item should be hidden.
+ // Second item (was first) should get its implicit size.
+ { x: 0, y: 0, width: 25, height: splitViewHeight },
+ { x: 25, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 25 + defaultHorizontalHandleWidth, y: 0,
+ width: splitViewWidth - 25 - defaultHorizontalHandleWidth, height: splitViewHeight },
+ ],
+ showIndices: [0],
+ expectedGeometriesAfterShowing: [
+ // First item (was second) should be visible with its implicit size.
+ { x: 0, y: 0, width: 100, height: splitViewHeight },
+ // Handle for first item (was second) should be visible.
+ { x: 100, y: 0, width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ // Second item (was first) should be visible with its implicit size.
+ { x: 100 + defaultHorizontalHandleWidth, y: 0,
+ width: 25, height: splitViewHeight },
+ { x: 100 + 25 + defaultHorizontalHandleWidth, y: 0,
+ width: defaultHorizontalHandleWidth, height: splitViewHeight },
+ { x: 100 + 25 + defaultHorizontalHandleWidth * 2, y: 0,
+ width: splitViewWidth - 100 - 25 - defaultHorizontalHandleWidth * 2, height: splitViewHeight }
+ ]
+ }
+ ]
+ return data
+ }
+
+ function test_moveHiddenItems(data) {
+ var control = createTemporaryObject(threeSizedItemsComponent, testCase,
+ { "orientation": data.orientation })
+ verify(control)
+
+ for (var i = 0; i < data.hideIndices.length; ++i) {
+ var itemToHide = control.itemAt(data.hideIndices[i])
+ verify(itemToHide)
+ itemToHide.visible = false
+ }
+
+ control.moveItem(data.moveFromIndex, data.moveToIndex)
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compareSizes(control, data.expectedGeometriesAfterMoving, "after moving")
+
+ for (i = 0; i < data.showIndices.length; ++i) {
+ var itemToShow = control.itemAt(data.showIndices[i])
+ verify(itemToShow)
+ itemToShow.visible = true
+ }
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compareSizes(control, data.expectedGeometriesAfterShowing, "after showing")
+ }
+
+ Component {
+ id: flickableComponent
+
+ Flickable {
+ anchors.fill: parent
+ anchors.margins: 100
+ }
+ }
+
+ function test_draggingHandleInFlickable() {
+ var flickable = createTemporaryObject(flickableComponent, testCase)
+ verify(flickable)
+
+ var control = threeSizedItemsComponent.createObject(flickable.contentItem,
+ { "orientation": data.orientation })
+ verify(control)
+
+ control.anchors.fill = undefined
+ control.width = 400
+ control.height = control.parent.height - 100
+ flickable.contentWidth = control.width
+ flickable.contentHeight = control.height
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+
+ var contentXSpy = signalSpyComponent.createObject(flickable,
+ { target: flickable, signalName: "contentXChanged" })
+ verify(contentXSpy.valid)
+ var contentYSpy = signalSpyComponent.createObject(flickable,
+ { target: flickable, signalName: "contentYChanged" })
+ verify(contentYSpy.valid)
+
+ // Drag the first handle to the right;
+ // the flickable's contentX and contentY shouldn't change.
+ var firstItem = control.itemAt(0)
+ var firstItemOriginalWidth = firstItem.width
+ var handles = findHandles(control)
+ var firstHandle = handles[0]
+ // Add some vertical movement in there as well.
+ mouseDrag(firstHandle, firstHandle.width / 2, firstHandle.height / 2, 100, 50)
+ compare(contentXSpy.count, 0)
+ compare(contentYSpy.count, 0)
+ verify(firstItem.width > firstItemOriginalWidth)
+
+ // Now do the same except vertically.
+ control.orientation = Qt.Vertical
+ control.width = control.parent.width - 100
+ control.height = 400
+ var firstItemOriginalHeight = firstItem.height
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+
+ // Add some horizontal movement in there as well.
+ mouseDrag(firstHandle, firstHandle.width / 2, firstHandle.height / 2, 50, 100)
+ compare(contentXSpy.count, 0)
+ compare(contentYSpy.count, 0)
+ verify(firstItem.height > firstItemOriginalHeight)
+ }
+
+ function test_hoveredPressed() {
+ if ((Qt.platform.pluginName === "offscreen") || (Qt.platform.pluginName === "minimal"))
+ skip("Mouse hovering not functional on offscreen/minimal platforms")
+
+ var control = createTemporaryObject(threeSizedItemsComponent, testCase)
+ verify(control)
+ control.anchors.margins = 50
+
+ var handles = findHandles(control)
+ var firstHandle = handles[0]
+
+ var handleCenter = control.mapFromItem(firstHandle, firstHandle.width / 2, firstHandle.height / 2)
+ // Test fails if we don't do two moves for some reason...
+ mouseMove(control, handleCenter.x, handleCenter.y)
+ mouseMove(control, handleCenter.x, handleCenter.y)
+ verify(firstHandle.SplitHandle.hovered)
+ verify(!firstHandle.SplitHandle.pressed)
+
+ mousePress(control, handleCenter.x, handleCenter.y)
+ verify(firstHandle.SplitHandle.hovered)
+ verify(firstHandle.SplitHandle.pressed)
+
+ mouseRelease(control, handleCenter.x, handleCenter.y)
+ verify(firstHandle.SplitHandle.hovered)
+ verify(!firstHandle.SplitHandle.pressed)
+
+ mouseMove(control, 0, 0)
+ verify(!firstHandle.SplitHandle.hovered)
+ verify(!firstHandle.SplitHandle.pressed)
+ }
+
+ // Tests removing/adding/moving an item while it's pressed.
+ function test_modifyWhileHoveredPressed() {
+ if ((Qt.platform.pluginName === "offscreen") || (Qt.platform.pluginName === "minimal"))
+ skip("Mouse hovering not functional on offscreen/minimal platforms")
+
+ var control = createTemporaryObject(threeSizedItemsComponent, testCase)
+ verify(control)
+ control.anchors.margins = 50
+
+ var handles = findHandles(control)
+ var firstHandle = handles[0]
+
+ // First, ensure that the handle is hovered + pressed.
+ var handleCenter = control.mapFromItem(firstHandle, firstHandle.width / 2, firstHandle.height / 2)
+ // Test fails if we don't do two moves for some reason...
+ mouseMove(control, handleCenter.x, handleCenter.y)
+ mouseMove(control, handleCenter.x, handleCenter.y)
+ verify(firstHandle.SplitHandle.hovered)
+ verify(!firstHandle.SplitHandle.pressed)
+
+ mousePress(control, handleCenter.x, handleCenter.y)
+ verify(firstHandle.SplitHandle.hovered)
+ verify(firstHandle.SplitHandle.pressed)
+
+ // Then, remove it by removing the first item.
+ control.removeItem(0)
+ handles = findHandles(control)
+ firstHandle = null
+ compare(handles.length, 1)
+
+ // No handles should be hovered/pressed.
+ for (var i = 0; i < handles.length; ++i) {
+ var handle = handles[i]
+ verify(!handle.SplitHandle.hovered, "handle at index " + i + " should not be hovered")
+ verify(!handle.SplitHandle.pressed, "handle at index " + i + " should not be hovered")
+ }
+
+ mouseRelease(control, handleCenter.x, handleCenter.y)
+ }
+
+ Component {
+ id: settingsComponent
+ Settings {
+ id: settings
+ }
+ }
+
+ function test_saveAndRestoreState() {
+ var control = createTemporaryObject(threeSizedItemsComponent, testCase)
+ verify(control)
+
+ var lastItem = control.itemAt(2)
+ verify(lastItem)
+ lastItem.SplitView.preferredWidth = 123
+
+ // Save the state.
+ var settings = createTemporaryObject(settingsComponent, testCase)
+ verify(settings)
+ settings.setValue("splitView", control.saveState())
+
+ // Recreate the item to restore it to its "default" values.
+ control = createTemporaryObject(threeSizedItemsComponent, testCase)
+ lastItem = control.itemAt(2)
+ verify(lastItem)
+ compare(lastItem.SplitView.preferredWidth, -1)
+
+ settings = createTemporaryObject(settingsComponent, testCase)
+ verify(settings)
+
+ // Restore the state.
+ control.restoreState(settings.value("splitView"))
+ compare(lastItem.SplitView.preferredWidth, 123)
+ }
+
+ function test_changePreferredSizeDuringLayout() {
+ var control = createTemporaryObject(threeSizedItemsComponent, testCase)
+ verify(control)
+
+ var firstItem = control.itemAt(0)
+ var secondItem = control.itemAt(1)
+ secondItem.widthChanged.connect(function() {
+ if (secondItem.width < 10)
+ firstItem.SplitView.preferredWidth = 50
+ })
+
+ // Change the size of the item so that a layout happens, but
+ // make the size small enough that the item's onWidthChanged handler gets triggered.
+ // The onWidthChanged handler will set the preferredWidth of another item during the
+ // layout, so we need to make sure the assignment isn't lost since we return early in that case.
+ secondItem.implicitWidth = 5
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compare(secondItem.width, 5)
+ compare(firstItem.width, 50)
+
+ // Now do the same for height.
+ control.orientation = Qt.Vertical
+ secondItem.heightChanged.connect(function() {
+ if (secondItem.height < 10)
+ firstItem.SplitView.preferredHeight = 50
+ })
+ // Get the polishes for the orientation out of the way so that they
+ // don't intefere with our results.
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+
+ secondItem.implicitHeight = 5
+ verify(isPolishScheduled(control))
+ verify(waitForItemPolished(control))
+ compare(secondItem.height, 5)
+ compare(firstItem.height, 50)
+ }
+
+ // When the user drags a handle, we internally set preferredWidth/Height
+ // to reflect the new value. However, we also have to make sure that when
+ // we do so, it doesn't trigger a delayed layout. This is why we have
+ // m_ignoreNextDelayedLayoutRequest. This test checks that
+ // m_ignoreNextDelayedLayoutRequest doesn't interfere with any action from
+ // the user that results in a delayed layout.
+ function test_changePreferredSizeDuringLayoutWhileDraggingHandle() {
+ var control = createTemporaryObject(threeSizedItemsComponent, testCase)
+ verify(control)
+
+ var firstItem = control.itemAt(0)
+ var secondItem = control.itemAt(1)
+ firstItem.widthChanged.connect(function() {
+ if (firstItem.width === 0)
+ secondItem.SplitView.preferredWidth = 50
+ })
+
+ // Start dragging the handle.
+ var handles = findHandles(control)
+ var targetHandle = handles[0]
+ mousePress(targetHandle)
+ verify(control.resizing)
+ var localPos = testCase.mapToItem(targetHandle, 15, testCase.height / 2)
+
+ // Move the handle to the very left, so that the item's width becomes zero.
+ mouseMove(targetHandle, -100, targetHandle.height / 2)
+ verify(control.resizing)
+ compare(firstItem.width, 0)
+ compare(secondItem.SplitView.preferredWidth, 50)
+ compare(secondItem.width, 50)
+ mouseRelease(targetHandle, -100, targetHandle.height / 2, Qt.LeftButton)
+ verify(!control.resizing)
+ }
+}
diff --git a/tests/auto/controls/default/tst_default.cpp b/tests/auto/controls/default/tst_default.cpp
index d21f13ad..4c575ce6 100644
--- a/tests/auto/controls/default/tst_default.cpp
+++ b/tests/auto/controls/default/tst_default.cpp
@@ -38,7 +38,6 @@
int main(int argc, char *argv[])
{
- QTEST_ADD_GPU_BLACKLIST_SUPPORT
QTEST_SET_MAIN_SOURCE_PATH
qputenv("QML_NO_TOUCH_COMPRESSION", "1");
return quick_test_main(argc, argv, "tst_controls::Default", TST_CONTROLS_DATA);
diff --git a/tests/auto/controls/fusion/tst_fusion.cpp b/tests/auto/controls/fusion/tst_fusion.cpp
index 84f9c231..7528ccea 100644
--- a/tests/auto/controls/fusion/tst_fusion.cpp
+++ b/tests/auto/controls/fusion/tst_fusion.cpp
@@ -39,7 +39,6 @@
int main(int argc, char *argv[])
{
- QTEST_ADD_GPU_BLACKLIST_SUPPORT
QTEST_SET_MAIN_SOURCE_PATH
qputenv("QML_NO_TOUCH_COMPRESSION", "1");
QQuickStyle::setStyle("Fusion");
diff --git a/tests/auto/controls/imagine/tst_imagine.cpp b/tests/auto/controls/imagine/tst_imagine.cpp
index 9777c9c9..9db7ed4d 100644
--- a/tests/auto/controls/imagine/tst_imagine.cpp
+++ b/tests/auto/controls/imagine/tst_imagine.cpp
@@ -39,7 +39,6 @@
int main(int argc, char *argv[])
{
- QTEST_ADD_GPU_BLACKLIST_SUPPORT
QTEST_SET_MAIN_SOURCE_PATH
qputenv("QML_NO_TOUCH_COMPRESSION", "1");
QQuickStyle::setStyle("Imagine");
diff --git a/tests/auto/controls/material/tst_material.cpp b/tests/auto/controls/material/tst_material.cpp
index 7d1953c2..ae8bb3a1 100644
--- a/tests/auto/controls/material/tst_material.cpp
+++ b/tests/auto/controls/material/tst_material.cpp
@@ -39,7 +39,6 @@
int main(int argc, char *argv[])
{
- QTEST_ADD_GPU_BLACKLIST_SUPPORT
QTEST_SET_MAIN_SOURCE_PATH
qputenv("QML_NO_TOUCH_COMPRESSION", "1");
QQuickStyle::setStyle("Material");
diff --git a/tests/auto/controls/universal/tst_universal.cpp b/tests/auto/controls/universal/tst_universal.cpp
index d293dc4c..db5b560e 100644
--- a/tests/auto/controls/universal/tst_universal.cpp
+++ b/tests/auto/controls/universal/tst_universal.cpp
@@ -39,7 +39,6 @@
int main(int argc, char *argv[])
{
- QTEST_ADD_GPU_BLACKLIST_SUPPORT
QTEST_SET_MAIN_SOURCE_PATH
qputenv("QML_NO_TOUCH_COMPRESSION", "1");
QQuickStyle::setStyle("Universal");
diff --git a/tests/auto/shared/qtest_quickcontrols.h b/tests/auto/shared/qtest_quickcontrols.h
index 0ae74481..4a06c021 100644
--- a/tests/auto/shared/qtest_quickcontrols.h
+++ b/tests/auto/shared/qtest_quickcontrols.h
@@ -73,15 +73,11 @@ static int runTests(QObject *testObject, int argc, char *argv[])
}
#define QTEST_QUICKCONTROLS_MAIN(TestCase) \
-QT_BEGIN_NAMESPACE \
-QTEST_ADD_GPU_BLACKLIST_SUPPORT_DEFS \
-QT_END_NAMESPACE \
int main(int argc, char *argv[]) \
{ \
qputenv("QML_NO_TOUCH_COMPRESSION", "1"); \
QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling); \
QGuiApplication app(argc, argv); \
- QTEST_ADD_GPU_BLACKLIST_SUPPORT \
TestCase tc; \
QTEST_SET_MAIN_SOURCE_PATH \
return runTests(&tc, argc, argv); \
diff --git a/tests/manual/gifs/gifrecorder.cpp b/tests/manual/gifs/gifrecorder.cpp
index a1ad6957..a7a5b9d6 100644
--- a/tests/manual/gifs/gifrecorder.cpp
+++ b/tests/manual/gifs/gifrecorder.cpp
@@ -47,7 +47,7 @@
\note The following programs must be installed if \c setHighQuality(true)
is called:
- \li \e avconv (sudo apt-get install libav-tools)
+ \li \e ffmpeg (sudo apt-get install ffmpeg)
\li \e convert (sudo apt-get install imagemagick)
\li \e gifsicle (sudo apt-get install gifsicle)
@@ -142,29 +142,36 @@ QQuickWindow *GifRecorder::window() const
}
namespace {
- void startProcess(QProcess &process, const QString &processName, const QString &args)
+ struct ProcessWaitResult {
+ bool success;
+ QString errorMessage;
+ };
+
+ ProcessWaitResult waitForProcessToStart(QProcess &process, const QString &processName, const QString &args)
{
qCDebug(lcGifRecorder) << "Starting" << processName << "with the following arguments:" << args;
const QString command = processName + QLatin1Char(' ') + args;
process.start(command);
if (!process.waitForStarted(1000)) {
- QString message = QString::fromLatin1("Could not launch %1 with the following arguments: %2\nError:\n%3");
- message = message.arg(processName).arg(args).arg(process.errorString());
- QFAIL(qPrintable(message));
- } else {
- qCDebug(lcGifRecorder) << "Successfully started" << processName;
+ QString errorMessage = QString::fromLatin1("Could not launch %1 with the following arguments: %2\nError:\n%3");
+ errorMessage = errorMessage.arg(processName).arg(args).arg(process.errorString());
+ return { false, errorMessage };
}
+
+ qCDebug(lcGifRecorder) << "Successfully started" << processName;
+ return { true, QString() };
}
- void waitForProcessToFinish(QProcess &process, const QString &processName, int waitDuration)
+ ProcessWaitResult waitForProcessToFinish(QProcess &process, const QString &processName, int waitDuration)
{
if (!process.waitForFinished(waitDuration) || process.exitCode() != 0) {
- QString message = QString::fromLatin1("%1 failed to finish (exit code %2): %3");
- message = message.arg(processName).arg(process.exitCode()).arg(process.errorString());
- QFAIL(qPrintable(message));
- } else {
- qCDebug(lcGifRecorder) << processName << "finished";
+ QString errorMessage = QString::fromLatin1("\"%1\" failed to finish (exit code %2): %3");
+ errorMessage = errorMessage.arg(processName).arg(process.exitCode()).arg(process.errorString());
+ return { false, errorMessage };
}
+
+ qCDebug(lcGifRecorder) << processName << "finished";
+ return { true, QString() };
}
}
@@ -222,7 +229,9 @@ void GifRecorder::start()
connect(&mEventTimer, SIGNAL(timeout()), mWindow, SLOT(update()));
mEventTimer.start(100);
- startProcess(mByzanzProcess, byzanzProcessName, args);
+ const ProcessWaitResult result = waitForProcessToStart(mByzanzProcess, byzanzProcessName, args);
+ if (!result.success)
+ QFAIL(qPrintable(result.errorMessage));
}
void GifRecorder::waitForFinish()
@@ -252,20 +261,32 @@ void GifRecorder::waitForFinish()
QSignalSpy spy(mWindow, SIGNAL(frameSwapped()));
QVERIFY(spy.wait());
- QProcess avconvProcess;
+ // Start ffmpeg and send its output to imagemagick's convert command.
+ // Based on the example in the documentation for QProcess::setStandardOutputProcess().
+ QProcess ffmpegProcess;
QProcess convertProcess;
- avconvProcess.setStandardOutputProcess(&convertProcess);
+ ffmpegProcess.setStandardOutputProcess(&convertProcess);
- const QString avconvProcessName = QStringLiteral("avconv");
- const QString avconvArgs = QString::fromLatin1("-i %1 -r 20 -f image2pipe -vcodec ppm -").arg(mByzanzOutputFileName);
- startProcess(avconvProcess, avconvProcessName, avconvArgs);
+ const QString ffmpegProcessName = QStringLiteral("ffmpeg");
+ const QString ffmpegArgs = QString::fromLatin1("-i %1 -r 20 -f image2pipe -vcodec ppm -").arg(mByzanzOutputFileName);
+ ProcessWaitResult result = waitForProcessToStart(ffmpegProcess, ffmpegProcessName, ffmpegArgs);
+ if (!result.success)
+ QFAIL(qPrintable(result.errorMessage));
const QString convertProcessName = QStringLiteral("convert");
const QString convertArgs = QString::fromLatin1("-delay 5 -loop 0 - %1").arg(mGifFileName);
- startProcess(convertProcess, convertProcessName, convertArgs);
- waitForProcessToFinish(avconvProcess, avconvProcessName, waitDuration);
- waitForProcessToFinish(convertProcess, convertProcessName, waitDuration);
+ result = waitForProcessToStart(convertProcess, convertProcessName, convertArgs);
+ if (!result.success)
+ QFAIL(qPrintable(result.errorMessage));
+
+ result = waitForProcessToFinish(ffmpegProcess, ffmpegProcessName, waitDuration);
+ if (!result.success)
+ QFAIL(qPrintable(result.errorMessage));
+ // Conversion can take a bit longer, so double the wait time.
+ result = waitForProcessToFinish(convertProcess, convertProcessName, waitDuration * 2);
+ if (!result.success)
+ QFAIL(qPrintable(result.errorMessage));
const QString gifsicleProcessName = QStringLiteral("gifsicle");
const QString verbose = lcGifRecorder().isDebugEnabled() ? QStringLiteral("-V") : QString();
@@ -281,12 +302,15 @@ void GifRecorder::waitForFinish()
QProcess gifsicleProcess;
if (lcGifRecorder().isDebugEnabled())
gifsicleProcess.setProcessChannelMode(QProcess::ForwardedChannels);
- startProcess(gifsicleProcess, gifsicleProcessName, gifsicleArgs);
- waitForProcessToFinish(gifsicleProcess, gifsicleProcessName, waitDuration);
-
- if (QFile::exists(mByzanzOutputFileName)) {
+ result = waitForProcessToStart(gifsicleProcess, gifsicleProcessName, gifsicleArgs);
+ if (!result.success)
+ QFAIL(qPrintable(result.errorMessage));
+ result = waitForProcessToFinish(gifsicleProcess, gifsicleProcessName, waitDuration);
+ if (!result.success)
+ QFAIL(qPrintable(result.errorMessage));
+
+ if (QFile::exists(mByzanzOutputFileName))
QVERIFY(QFile::remove(mByzanzOutputFileName));
- }
}
}
diff --git a/tests/manual/gifs/tst_gifs.cpp b/tests/manual/gifs/tst_gifs.cpp
index 2a7d55bd..d7d8f98d 100644
--- a/tests/manual/gifs/tst_gifs.cpp
+++ b/tests/manual/gifs/tst_gifs.cpp
@@ -733,8 +733,8 @@ void tst_Gifs::checkables()
for (int i = 0; i < pressIndices.size(); ++i) {
const int pressIndex = pressIndices.at(i);
- const char *controlId = qPrintable(QString::fromLatin1("control%1").arg(pressIndex + 1));
- QQuickItem *control = window->property(controlId).value<QQuickItem*>();
+ const QString controlId = QString::fromLatin1("control%1").arg(pressIndex + 1);
+ QQuickItem *control = window->property(qPrintable(controlId)).value<QQuickItem*>();
QVERIFY(control);
const QPoint pos = control->mapToScene(QPointF(control->width() / 2, control->height() / 2)).toPoint();
diff --git a/tests/manual/testbench/controls/SplitView.qml b/tests/manual/testbench/controls/SplitView.qml
new file mode 100644
index 00000000..7d534de4
--- /dev/null
+++ b/tests/manual/testbench/controls/SplitView.qml
@@ -0,0 +1,79 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the test suite of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:BSD$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** BSD License Usage
+** Alternatively, you may use this file under the terms of the BSD license
+** as follows:
+**
+** "Redistribution and use in source and binary forms, with or without
+** modification, are permitted provided that the following conditions are
+** met:
+** * Redistributions of source code must retain the above copyright
+** notice, this list of conditions and the following disclaimer.
+** * Redistributions in binary form must reproduce the above copyright
+** notice, this list of conditions and the following disclaimer in
+** the documentation and/or other materials provided with the
+** distribution.
+** * Neither the name of The Qt Company Ltd nor the names of its
+** contributors may be used to endorse or promote products derived
+** from this software without specific prior written permission.
+**
+**
+** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick 2.12
+import QtQuick.Controls 2.5
+
+QtObject {
+ property var supportedStates: [
+ []
+ ]
+
+ property Component component: SplitView {
+ implicitWidth: 400
+ implicitHeight: 100
+
+ Rectangle {
+ color: "salmon"
+ implicitWidth: 25
+ implicitHeight: 25
+ }
+ Rectangle {
+ color: "navajowhite"
+ implicitWidth: 100
+ implicitHeight: 100
+ }
+ Rectangle {
+ color: "steelblue"
+ implicitWidth: 200
+ implicitHeight: 200
+ }
+ }
+}
diff --git a/tests/manual/testbench/qml.qrc b/tests/manual/testbench/qml.qrc
index a0927f35..743e6629 100644
--- a/tests/manual/testbench/qml.qrc
+++ b/tests/manual/testbench/qml.qrc
@@ -40,5 +40,6 @@
<file>controls/BusyIndicator.qml</file>
<file>testbench.qml</file>
<file>controls/MenuBar.qml</file>
+ <file>controls/SplitView.qml</file>
</qresource>
</RCC>