可以向 ListModel 添加复杂类型的项目吗?

Can one add a complex type item to ListModel?

我想要一个类似于 ListModel 的结构来显示简单状态机的输入。每个输入可能包含几个 strings/ints。所以我需要 ListModel 的每个项目都能够存储数据列表(带有输入参数名称的字符串,或带有字符串的字典等)。目前我无法将带有列表 属性 的项目附加到 ListModel.

所以 ListModel 看起来像这样:

ListView {
    anchors.fill: parent

    model: ListModel {
        id: listModel
    }

    delegate: Text {
        text: inputs[0]['name']
    }
}

当状态发生变化时,我想更新模型并附加如下元素:

var state = {
    name: "abcd",
    inputs: [{name: 'a'}, {name: 'b'}, {name: 'c'}]
}
listModel.append(state);

当前版本代码returns错误TypeError: Cannot read property 'name' of undefined。它没有看到列表。

根据 this question,在 ListModel 的项目中使用列表可能会出现问题。但这似乎与我的情况无关。也许我需要在 QML 中以不同的方式使用列表和字典,也许我不得不在委托(我试过)或其他东西(建议?)中写 text: inputs[0].name

有人可以建议如何在 ListModel 中制作一个或多或少复杂的项目(基本上,它是标准的 JSON)吗?目前尚不清楚,因为文档和 blogs/questions 一直都在处理字符串。我错过了一些有用的文档吗?在 QML 中执行此操作有哪些好的做法?我应该使用一些自定义对象吗?

可以将列表数据添加到 ListElement,根据 documentation and as you correctly did in your imperative code. However, nested roles are not really arrays. They are ListModels themselves. That's because, by design,如果数组的元素发生变化,QML 不会产生通知,这将是一个 show-stopper模型视图委托设置。

由于嵌套角色是模型,所以可以使用模型的函数。例如,这个例子工作正常:

import QtQuick 2.5
import QtQuick.Window 2.2

Window {
    id: window
    width: 600
    height: 400
    visible: true

    ListView {
        anchors.fill: parent

        model: ListModel {
            id: listModel
        }

        delegate: Text {
            text: name + inputs.get(index % inputs.count).name  // accessing the inner model
        }
    }

    MouseArea {
        anchors.fill: parent
        onClicked: {
            var state = {
                name: "abcd",
                inputs: [{name: 'a'}, {name: 'b'}, {name: 'c'}]
            }
            listModel.append(state);
        }
    }
}

根据您的问题,输入是普通的 JSON。在这种情况下,请考虑使用 JSONListModel 代替 ListModel。它通过 JSON 路径公开了一组与 XMLListModel 匹配的 API,并且可能代表您的场景的完美解决方案。