c++ - 数据未显示在 TableView 中

标签 c++ qt view model qml

我尝试使用 C++ 模型构建简单的 TableView。我的表有与 return rowCount 和 columnCount 方法一样多的行和列。这意味着,模型与 View “连接”,但在每个单元格中不显示消息:“一些数据”

这是我的代码:

class PlaylistModel : public QAbstractTableModel
{
    Q_OBJECT
public:
    PlaylistModel(QObject *parent=0): QAbstractTableModel(parent), rows(0){}

    int rowCount(const QModelIndex & /*parent*/) const
    {
        return 5;
    }
    int columnCount(const QModelIndex & /*parent*/) const
    {
        return 3;
    }
    QModelIndex index(int row, int column, const QModelIndex &parent) const {
         return createIndex(row, column);
    }
    QModelIndex parent(const QModelIndex &child) const {
         return child.parent();
    }
    QVariant data(const QModelIndex &index, int role) const{
        if (role == Qt::DisplayRole)
             {
               return QString("Some data");
             }
        return QVariant();
    }
(...)
QGuiApplication app(argc, argv);
QQmlApplicationEngine engine;
PlaylistModel plModel(0);
engine.rootContext()->setContextProperty("myModel", &plModel);
engine.load(QUrl(QStringLiteral("qrc:///main.qml")));

和qml

TableView {
                id: trackList
                width: 100; height: 100
                model: myModel
                TableViewColumn { role: "id"; title: "Id"; width: 30 }
                TableViewColumn { role: "name"; title: "Name"; width: 100}
                TableViewColumn { role: "duration"; title: "Duration"; width: 20 }

            }

我哪里做错了?

最佳答案

简答

因为您的 QML 没有请求 Qt::DisplayRole。将您的 TableVievColumn 更改为

TableViewColumn { role: "display"; title: "xxx"; width: 20 }

QML 现在正在请求 Qt::DisplayRole,并且“一些数据”显示在此列中。

长答案

QML 要求三个用户定义的角色:“id”、“name”和“duration”。但是,这三个角色不是内置角色。因此,您需要在模型类中实现这三个角色。

首先,您应该为模型提供一组角色。该模型使用 QAbstractItemModel::data 函数将数据返回给 View 。 role的类型是int,我们可以在model类中写一个enum:

class PlaylistModel : public QAbstractTableModel
{
    Q_OBJECT
public:
    enum MyTableRoles 
    {
        IdRole = Qt::UserRole + 1,
        NameRole,
        DurationRole
    }
    //...
};

现在,在 data 函数中,每当 View 询问时返回相应的值:

QVariant PlaylistModel::data(const QModelIndex &index, int role) const
{
    if (!index.isValid()){return QVariant();}

    switch(role)
    {
    case IdRole:
        return GetIdFromMyTable(index);
    case NameRole:
        return GetNameFromMyTable(index);
    case DurationRole:
        return GetDurationFromMyTable(index);
    }
    //...
    return QVariant();
}

接下来,为每个角色提供一个字符串到整数的映射。模型中的role 是int 类型,而在QML 中role 是string 类型。 (请参阅 TableViewColumn 中的角色属性。)因此,我们应该为每个角色提供一个字符串到整数的映射,以便 QML 可以正确地请求所需的数据。映射应在 QAbstractItemModel::roleNames() 中提供:

QHash<int, QByteArray> PlaylistModel::roleNames() const
{
    QHash<int, QByteArray> roleNameMap;
    roleNameMap[IdRole] = "id";
    roleNameMap[NameRole] = "name";
    roleNameMap[DurationRole] = "duration";

    return roleNameMap;
}

现在您在 QML 中的表格终于可以显示您想要的内容了。

一些引用资料

子类化时 QAbstractTableModel ,

you must implement rowCount(), columnCount(), and data(). Default implementations of the index() and parent() functions are provided by QAbstractTableModel.

使用 C++ models in QML 时,

The roles of a QAbstractItemModel subclass can be exposed to QML by reimplementing QAbstractItemModel::roleNames().

如果不重新实现roleNames 函数,则只能使用QAbstractItemModel::roleNames 中声明的默认角色。 .这就是简短答案有效的原因。

关于c++ - 数据未显示在 TableView 中,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/25329517/

相关文章:

c++ - 运行后解析命令行参数

c++ - 在 Qt 信号/槽的上下文中使用观察者模式

qt - 如何在 Qt5 和 QML 中使用 QtQuick.Window 元素?

Objective-C 复制 View

c# - 如何使用 MVVM 将 UserControl 从插件传递到我的主窗口?

c++ - 通过Qt读取xml

c++ - 如何为 sprintf 制作可变大小的字符串

c++ - 将 HSV 值分配给特定像素?

c++ - 如何降低QT Gui线程优先级?

asp.net - Asp.NET MVC View 中的引号