我尝试用C ++中的模型构建简单的TableView。我的表包含尽可能多的行和列,如返回rowCount和columnCount方法。这意味着,模型与视图“连接”,但在每个单元格中都不显示消息:“某些数据”
这是我的代码:
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 }
}
我犯了哪个错误?
答案 0 :(得分:5)
因为您的QML没有要求Qt::DisplayRole
。将您的TableVievColumn
更改为
TableViewColumn { role: "display"; title: "xxx"; width: 20 }
QML现在要求Qt::DisplayRole
和"有些数据"如下所示。
QML要求三个用户定义的角色:" id"," name"和" duration"。但是,这三个角色不是凸出的角色。因此,您需要在模型类中实现三个角色。
首先,您应该为模型提供一组角色。模型使用QAbstractItemModel::data
函数将数据返回给视图。 role
的类型是int,我们可以在模型类中编写枚举:
class PlaylistModel : public QAbstractTableModel
{
Q_OBJECT
public:
enum MyTableRoles
{
IdRole = Qt::UserRole + 1,
NameRole,
DurationRole
}
//...
};
现在,在data
函数中,只要视图询问,就会返回相应的值:
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();
}
接下来,为每个角色提供字符串到int的映射。模型中的role
是int类型,但是在QML中role
是字符串的类型。 (请参阅TableViewColumn
中的role属性。)因此,我们应该为每个角色提供字符串到int的映射,以便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时,
您必须实现rowCount(),columnCount()和data()。 index()和parent()函数的默认实现由QAbstractTableModel提供。
通过重新实现QAbstractItemModel :: roleNames(),可以将QAbstractItemModel子类的角色公开给QML。
如果您不重新实现roleNames
函数,则只能使用QAbstractItemModel::roleNames中声明的默认角色。这就是简短回答的原因。
答案 1 :(得分:0)
您没有实施index
方法。
根据文件,
当继承QAbstractItemModel时,至少你必须这样做 实现 index(),parent(),rowCount(),columnCount()和data()。 这些函数用于所有只读模型,并构成基础 可编辑模型。
换句话说,你必须实现自己的低级项目管理,AbstractItemModel不会为你做。您应该使用createIndex
创建索引并在nesessary等时将其销毁。
如果您不想玩这些游戏并且只想实现自己的快速和肮脏模型,请考虑继承QStandardItemModel。