如果你想要复用QTreeView原有的selectionModel,并将选中状态显示为复选框,可以自定义一个代理类(QStyledItemDelegate的子类),然后在其paint()方法中绘制复选框来替换原有的选中状态显示。以下是一个示例代码:
#include <QApplication>
#include <QStandardItemModel>
#include <QTreeView>
#include <QStyledItemDelegate>
#include <QStyleOptionButton>
#include <QCheckBox>
class CheckboxDelegate : public QStyledItemDelegate {
public:
CheckboxDelegate(QObject *parent = nullptr) : QStyledItemDelegate(parent) {}
void paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const override {
if (index.column() == 1) { // 只在第二列绘制复选框
bool checked = index.data(Qt::CheckStateRole).toBool();
QStyleOptionButton opt;
opt.rect = option.rect;
opt.state |= QStyle::State_Enabled;
if (checked)
opt.state |= QStyle::State_On;
else
opt.state |= QStyle::State_Off;
QApplication::style()->drawControl(QStyle::CE_CheckBox, &opt, painter);
} else {
QStyledItemDelegate::paint(painter, option, index);
}
}
QSize sizeHint(const QStyleOptionViewItem &option, const QModelIndex &index) const override {
return QSize(20, 20); // 设置合适的复选框大小
}
};
int main(int argc, char *argv[])
{
QApplication app(argc, argv);
QStandardItemModel model(4, 2);
model.setHorizontalHeaderLabels(QStringList() << "Name" << "Checked");
// 设置所有项为可选中
for (int row = 0; row < model.rowCount(); ++row)
for (int col = 0; col < model.columnCount(); ++col)
model.setItem(row, col, new QStandardItem());
QTreeView treeView;
treeView.setModel(&model);
treeView.setRootIsDecorated(false); // 隐藏根节点的展开/折叠图标
// 使用自定义的代理类
CheckboxDelegate delegate;
treeView.setItemDelegateForColumn(1, &delegate);
// 获取选择模型并设置为多选模式
QItemSelectionModel *selectionModel = treeView.selectionModel();
selectionModel->setSelectionMode(QAbstractItemView::MultiSelection);
treeView.show();
return app.exec();
}
在上述示例中,我们自定义了一个CheckboxDelegate代理类,并重写了paint()方法来绘制复选框。只有第二列才会显示复选框,其他列保持默认的显示方式。
然后将该代理类应用到第二列(索引为1)的项上,通过setItemDelegateForColumn()方法进行设置。
这样,原有的QTreeView中选中状态的显示就会被替换成复选框。
希望这能满足你的需求!
内容由零声教学AI助手提供,问题来源于学员提问