我想向QFileSystemModel(可能是派生模型(添加一个自定义角色。我想使用此角色来保存复选框的检查状态,该复选框显示在自定义委托中的文件名旁边。如何做到这一点?
我使用示例Qt快速控件 - 文件系统浏览器示例删除了选择的一部分。
步骤如下:
-
在
roleNames
中添加新角色:QHash<int,QByteArray> roleNames() const Q_DECL_OVERRIDE { QHash<int, QByteArray> result = QFileSystemModel::roleNames(); result.insert(SizeRole, QByteArrayLiteral("size")); result.insert(DisplayableFilePermissionsRole, QByteArrayLiteral("displayableFilePermissions")); result.insert(LastModifiedRole, QByteArrayLiteral("lastModified")); result.insert(Qt::CheckStateRole, QByteArrayLiteral("checkRole")); return result; }
-
创建一个存储选择信息的容器,在这种情况下,我将使用
QMap
:QMap<QPersistentModelIndex, Qt::CheckState> m_checks;
-
覆盖返回状态的
data()
方法(如果它存储在容器中(,如果它没有作为默认值Qt::UnChecked
返回:QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const Q_DECL_OVERRIDE { if (index.isValid() && role >= SizeRole) { ... } else if (role == Qt::CheckStateRole) { QPersistentModelIndex pix(index); if(m_checks.contains(pix)){ return m_checks[pix]; } return Qt::Unchecked; } return QFileSystemModel::data(index, role); }
-
覆盖
setData()
方法,如有必要,必须对其进行修改并创建数据。bool setData(const QModelIndex &index, const QVariant &value, int role=Qt::EditRole){ if(role == Qt::CheckStateRole && index.isValid()){ Qt::CheckState current = value.value<Qt::CheckState>(); if(m_checks.contains(index)){ Qt::CheckState last = m_checks[index]; if(last == current) return false; m_checks[index] = current; } else{ m_checks.insert(index, current); } emit dataChanged(index, index, {role}); return true; } return QFileSystemModel::setData(index, value, role); }
-
我添加了一个新列,在其中建立了对
CheckBox
的委托,并使用onCheckedChanged
槽使用setData()
方法设置值,传递QModelIndex
,数据和角色,在这种情况下,传递 10,因为它是Qt::CheckStateRole
的值数。TreeView { id: view model: fileSystemModel ... TableViewColumn { role: "checkRole" delegate: Component { CheckBox { id: mycbx checked: styleData.value onCheckedChanged: view.model.setData(styleData.index, checked, 10) } } } ...
完整的示例可以在以下链接中找到。