最近按部就班地写了QItemDelegate来实现QListView数据的编辑器功能,但运行后发现选中某一行数据编辑时,编辑器却没有正常显示出来。查看了之前写的代码才发现是因为自己漏掉了重写QAbstractListModel的flags虚函数的步骤,我觉得这是一个很重要的点,分享出来供大家参考。
如下面的代码,其中一个重写了flags虚函数,另一个没有重写flags虚函数,从后面的运行效果可知,如果没有重写flags虚函数返回正确的配置数据,QListView的数据是无法被正常编辑的。
main.cpp
#include
#include
#include
#include
#include
#include "mylistviewmodel.h"
#include "useriddelegate.h"
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
QWidget *mainWidget=new QWidget;
mainWidget->resize(300, 150);
mainWidget->setLayout(new QHBoxLayout);
MyListViewModel listViewModel1; //注意此处使用了MyListViewModel
QListView listView1;
UserIDDelegate delegate1;
listView1.setModel(&listViewModel1);
listView1.setItemDelegate(&delegate1);
listView1.setEditTriggers(QListView::AllEditTriggers);
MyListViewModelWithFlags listViewModel2; //注意此处使用了MyListViewModelWithFlags
QListView listView2;
UserIDDelegate delegate2;
listView2.setModel(&listViewModel2);
listView2.setItemDelegate(&delegate2);
listView2.setEditTriggers(QListView::AllEditTriggers);
mainWidget->layout()->addWidget(&listView1);
mainWidget->layout()->addWidget(&listView2);
mainWidget->show();
return a.exec();
}
mylistviewmodel.h
#ifndef MYLISTVIEWMODEL_H
#define MYLISTVIEWMODEL_H
#include
class MyListViewModel : public QAbstractListModel
{
Q_OBJECT
public:
MyListViewModel(QObject *parent = nullptr);
int rowCount(const QModelIndex &parent) const override;
int columnCount(const QModelIndex &parent) const override;
QVariant data(const QModelIndex &index, int role) const override;
bool setData(const QModelIndex &index, const QVariant &value, int role);
protected:
QList m_dataList;
};
class MyListViewModelWithFlags : public MyListViewModel
{
Q_OBJECT
public:
MyListViewModelWithFlags(QObject *parent = nullptr);
Qt::ItemFlags flags(const QModelIndex &index) const override;
};
#endif // MYLISTVIEWMODEL_H
mylistviewmodel.cpp
#include "mylistviewmodel.h"
MyListViewModel::MyListViewModel(QObject *parent)
: QAbstractListModel(parent)
{
for(int i=0; i<5; i++)
{
m_dataList.push_back(new QString(QString::number(i)));
}
}
int MyListViewModel::rowCount(const QModelIndex &parent) const
{
return m_dataList.size();
}
int MyListViewModel::columnCount(const QModelIndex &parent) const
{
return 1;
}
QVariant MyListViewModel::data(const QModelIndex &index, int role) const
{
switch (role) {
case Qt::DisplayRole:
case Qt::EditRole:
case Qt::UserRole:
return *(m_dataList.at(index.row()));
break;
default:
break;
}
return QVariant();
}
bool MyListViewModel::setData(const QModelIndex &index, const QVariant &value, int role)
{
if(role==Qt::EditRole)
{
*(m_dataList.at(index.row())) = value.toString();
}
return QAbstractListModel::setData(index, value, role);
}
MyListViewModelWithFlags::MyListViewModelWithFlags(QObject *parent)
: MyListViewModel(parent)
{
}
//重载这个flags虚函数,并在其中返回(Qt::ItemIsEditable | Qt::ItemIsEnabled),才能使编辑器生效
Qt::ItemFlags MyListViewModelWithFlags::flags(const QModelIndex &index) const
{
return (Qt::ItemIsEditable | Qt::ItemIsEnabled);
}
useriddelegate.h
#ifndef USERIDDELEGATE_H
#define USERIDDELEGATE_H
#include
#include
class UserIDDelegate : public QItemDelegate
{
Q_OBJECT
public :
UserIDDelegate(QObject *parent = nullptr);
QWidget *createEditor(QWidget *parent, const QStyleOptionViewItem &option, const QModelIndex &index) const override;
void setEditorData(QWidget *editor, const QModelIndex &index) const override;
void setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index) const override;
void updateEditorGeometry(QWidget *editor, const QStyleOptionViewItem &option, const QModelIndex &index) const override;
};
#endif // USERIDDELEGATE_H
useriddelegate.cpp
#include "useriddelegate.h"
#include
UserIDDelegate::UserIDDelegate(QObject *parent)
: QItemDelegate(parent)
{
}
QWidget *UserIDDelegate::createEditor(QWidget *parent, const QStyleOptionViewItem &option, const QModelIndex &index) const
{
QLineEdit *editor = new QLineEdit(parent);
QRegExp regExp( "[0-9]{0,10}" );
editor->setValidator( new QRegExpValidator(regExp, parent));
return editor;
}
void UserIDDelegate::setEditorData(QWidget *editor, const QModelIndex &index) const
{
QString text = index.model()->data(index, Qt::EditRole).toString();
QLineEdit *lineEdit = static_cast (editor);
lineEdit->setText(text);
}
void UserIDDelegate::setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index) const
{
QLineEdit *lineEdit = static_cast (editor);
QString text = lineEdit->text();
model->setData(index, text, Qt::EditRole);
}
void UserIDDelegate::updateEditorGeometry(QWidget *editor, const QStyleOptionViewItem &option, const QModelIndex &index) const
{
editor->setGeometry(option.rect);
}
运行效果:
(---------------------完-----------------)