如何在qml中添加另一个组件作为参数的新组件

时间:2019-02-01 10:49:18

标签: qt qml

我想做的是在一个组件内创建一个新对象,这可以用qml的Component组件来完成,但是作为参数,我想传递另一个将位于不同{{ 1}}文件。

我将说明我正在尝试做的事情。 我已经完成了一个标签栏手风琴组件: enter image description here

当我单击按钮时,我希望创建一个新的标签,它将具有自己的内容!

enter image description here

我提供下面使用的代码:

.qml

import QtQuick 2.7 import QtQuick.Dialogs 1.2 import QtQuick.Layouts 1.3 import QtQuick.Controls 2.3 import QtQuick.Window 2.3 ApplicationWindow { visible: true width: 640 height: 500 title: qsTr("Tabbars") Button{ id: button text: "add new tab dinamically" onClicked: item.createPanelItem() anchors.top:parent.top anchors.left:parent.left height: 20 width: parent.width } Item{ id:item //anchors.fill:parent anchors.top: button.bottom anchors.left: parent.left anchors.right: parent.right anchors.bottom: parent.bottom ScrollView{ anchors.fill:parent Column { id: column width:item.width property int currentItem: 0 PanelItem { id:panel1 index:0 title: "Panel 1" width:parent.width content: Item { property string title: "teste" height: configContent.implicitHeight width: configContent.implicitWidth ColumnLayout{ id:configContent anchors.topMargin: 10 anchors.bottomMargin: 10 anchors.fill:parent TextField { id: companyNameText1 placeholderText: qsTr("Company name") Layout.fillWidth: true selectByMouse: true } ComboBox { id: languagesComboBox1 textRole: "text" objectName: "language" Layout.fillWidth: true model: ListModel { ListElement {text: QT_TR_NOOP("English"); oid: 0} ListElement {text: QT_TR_NOOP("Portuguese"); oid: 1} ListElement {text: QT_TR_NOOP("Spanish"); oid: 2} ListElement {text: QT_TR_NOOP("Italian"); oid: 3} ListElement {text: QT_TR_NOOP("French"); oid: 4} ListElement {text: QT_TR_NOOP("Portuguese(Brasil)"); oid: 5} } } ComboBox { id: devSndrModeComboBox1 textRole: "text" objectName: "test_dev_sndr_mode" Layout.fillWidth: true model: ListModel { Component.onCompleted: { append({ text: QT_TR_NOOP("None"), oid: 0 }) append({ text: QT_TR_NOOP("Subpanel"), oid: 1 }) append({ text: QT_TR_NOOP("All"), oid: 2 }) } } } } } // onResetOtherPanels: function(indexClicked){ // if() // } } PanelItem { id:panel2 index:1 title: "Panel 2" width:parent.width content: Item { property string title: "teste" height: configContent2.implicitHeight width: configContent2.implicitWidth ColumnLayout{ id:configContent2 anchors.fill:parent ComboBox { id: sndrModeComboBox1 textRole: "text" Layout.fillWidth: true model: ListModel { Component.onCompleted: { append({ text: QT_TR_NOOP("Preset"), oid: 0 }) append({ text: QT_TR_NOOP("Programmed"), oid: 1 }) } } } } } Component.onCompleted: { //resetOtherAccordions.connect(panel1.resetHeight) console.log("panel 2 height "+panel2.height) } } PanelItem { id:panel3 index:2 title: "Panel 3" width:parent.width content: Item { property string title: "teste" height: configContent3.implicitHeight width: configContent3.implicitWidth ColumnLayout{ id:configContent3 anchors.fill:parent ComboBox { id: sndrModeComboBox2 textRole: "text" Layout.fillWidth: true model: ListModel { Component.onCompleted: { append({ text: QT_TR_NOOP("Preset"), oid: 0 }) append({ text: QT_TR_NOOP("Programmed"), oid: 1 }) } } } } } Component.onCompleted: { console.log("panel 3 height "+panel2.height) } } } } function createPanelItem(){ panelItem.createObject(column,{title:qsTr("newTest"),index:4 /*,content: Item{}*/ }) } Component { id: panelItem PanelItem { title: qsTr("Teste") width: parent.width } } } }

PanelItem.qml

我在这里的大问题是,我找不到在createObject函数中向import QtQuick 2.7 import QtQuick.Layouts 1.2 Item { id: root property Component content property string title: "panel" property bool isSelected: false property int index: 0 function toggleSelected() { root.isSelected = !root.isSelected if(root.isSelected){ parent.currentItem = index for(var i = 0;i<parent.children.length;i++) { if(parent.children[i].index !== parent.currentItem && parent.children[i].isSelected) { parent.children[i].toggleSelected() } } } } clip: true height: container.height + bar.height Rectangle{ id: bar anchors { top: parent.top left: parent.left right: parent.right } height: 30 color: root.isSelected ? "#81BEF7" : "#CEECF5" Text { anchors.fill: parent anchors.margins: 10 horizontalAlignment: Text.AlignLeft verticalAlignment: Text.AlignVCenter text: root.title } Text { anchors{ right: parent.right top: parent.top bottom: parent.bottom margins: 10 } horizontalAlignment: Text.AlignRight verticalAlignment: Text.AlignVCenter text: "^" rotation: root.isSelected ? "180" : 0 } MouseArea { id:panelAreaClick anchors.fill: parent cursorShape: Qt.PointingHandCursor onClicked: function(){ toggleSelected() } } } Rectangle{ id: container anchors.top: bar.bottom anchors.left: parent.left anchors.right: parent.right height: loader.item && isSelected ? loader.item.height : 0 Loader { id: loader visible: isSelected sourceComponent: content anchors.top: container.top } Behavior on height { PropertyAnimation { duration: 1000 } } } } 提供某些东西的方法。

我知道我可以通过类似的方式将内容传递给content

content

但这不是我想做的,因为我将在类似"content": "import QtQuick 2.0; Rectangle{}" 的文件上创建一个组件,这就是我想要传递给新标签的panellog.qml参数的内容,被创建。

1 个答案:

答案 0 :(得分:0)

在内联组件中简单指定它是最简单的:

        Component {
            id: panelItem
            PanelItem {
                title: qsTr("Teste")
                width: parent.width
                content: Item {}
            }
        }

或者您可以将content的类型设置为Component,以便可以向其传递其他一些内联组件,这实际上是差不多的事情。这看似有点费力,但实际上以一种还可以使您访问当前组件范围的方式自定义内容非常方便。

这里的问题是Qt有两种限制,这是一个阻碍:

  • 您不能在命令性(JS)代码中使用声明性组件语法
  • 您不能以声明方式实例化内联组件

这意味着:

  • 如果要引用声明性对象,则必须使用其id或属性-它仅适用于标识符,不适用于对象文字/实例

  • 如果要以标量方式创建对象,则必须将其保存在专用的qml文件中