Как назначить QML-элемент для свойства компонента в QML, а затем использовать этот объект внутри компонента?
Я пытаюсь создать объект QML, который действует как оболочка для других объектов. Вот мой QML файл (Container.qml):
Item {
property string label
property Item control
Row {
Label {
text: label
}
// Not sure how to display the control assigned to the control property
}
}
То, что я хотел бы сделать (в моем QML, который потребляет этот компонент), выглядит примерно так:
Container {
label: "My Label"
control: Textbox {
text: "My Value"
}
}
При подаче этого QML результат (в интерфейсе) должен быть чем-то похожим на результат из этого QML:
Item {
Row {
Label {
text: "My Label"
}
Textbox {
text: "My Value"
}
}
}
Возможно ли это? Когда я пытаюсь это сделать, я получаю "не могу назначить объект для свойства" при назначении элемента элементу управления. Я искал форумы Qt и безжалостно искал эту игру, но ничего не добился. Если кто-нибудь знает ответ, мы будем очень благодарны.
Спасибо
Джек
Ответы
Ответ 1
Вы можете динамически загружать элементы с помощью элемента Loader, а затем установить свойство 'control' как alias, который напрямую ссылается на свойство loadComponent загрузчика.
Итак, ваш Container.qml может выглядеть так:
Item {
property string label
property alias control : loader.sourceComponent
width: 200; height: 200
Row {
Label { text: label }
Loader { id: loader }
}
}
Теперь, когда вы назначаете графический элемент свойству "control", он будет автоматически отображаться загрузчиком.
Ответ 2
Существует гораздо лучшее решение:
/* MyObject.qml */
Rectangle {
default property alias children /* name can be any */ : inner_space.children
/* ... You can put other elements here ... */
Item {
id: inner_space
/* ... Params ... */
}
/* ... You can put other elements here ... */
}
И теперь мы можем делать все, что хотим!
/* main.qml */
Rectangle {
MyObject {
Button {
/* ... */
}
}
}
ОБНОВЛЕНИЕ: Как уже упоминалось пользователем bobbaluba, лучше использовать элемент данных, а не дочерний элемент, поэтому MyObject.qml должен выглядите так:
Rectangle {
default property alias data /* name can be any */ : inner_space.data
/* ... You can put other elements here ... */
Item {
id: inner_space
/* ... Params ... */
}
/* ... You can put other elements here ... */
}
Ответ 3
Использую QML около месяца, не знаю, как это сделать, я боюсь.
Лучший план состоит в том, чтобы выяснить все возможные вещи, которые может быть в элементе управления (Textbox
в вашем примере), создать экземпляр каждого компонента в вашей строке и установить соответствующее состояние на Item
. Затем государство будет заботиться о том, чтобы желаемый компонент был видимым или невидимым в зависимости от ситуации.
Edit
Просто подумал. (Не пробовал, но дайте ему поработать!) В вашем обработчике Item
Component.onCompleted:
попробуйте позвонить control.createObject(rowID)
, где rowID
является id
для вашего объекта Row
(который вы хотите родительский элемент control
).
Ответ 4
Вы можете создать контейнер для других элементов с помощью настраиваемого свойства:
Item
{
id: root
property list<Item> rectList: [
Rectangle
{
parent: root
},
Rectangle
{
parent: root
},
Rectangle
{
parent: root
},
Rectangle
{
parent: root
}
]
}
Обратите внимание, что родительский элемент Rectangle Items устанавливается вручную, чтобы они были визуальными дочерними элементами контейнера.
Вы можете оценить их как массив javascript
for ( var i = 0; i < root.rectList.length; i++ )
{
var rect = root.rectList[i];
rect.visible = true;
}
или
rect.rectList[1].visible = false;