QT中级(3)QTableView自定义委托(三)实现QCheckBox委托并且将QCheckBox居中

1 写在前面的话

我们在之前写的《QT(7)-初识委托》文章末尾提到,“使用一个类继承QStyledItemDelegate实现常用的控件委托,在使用时可以直接调用接口,灵活实现各种委托”。我们接下来几篇文章将先详细讲解各个控件的委托,最后整理成一个类,并分享源码。如果大家感兴趣,可以点个关注,后面我们一起学习!

讲解比较详细,大家可以跟着一步一步做,自己就可以实现了。

2 需要用到的部分知识

《QT(3)-QTableView》
《QT(4)-QAbstractItemView》
《QT(6)-QStandardItemModel》
《QT(7)-初识委托》

3 同系列文章

QT中级(1)QTableView自定义委托(一)实现QSpinBox、QDoubleSpinBox委托
QT中级(2)QTableView自定义委托(二)实现QProgressBar委托

4 实现QCheckBox委托

在QTableView中实现QCheckBox委托并居中显示,需要以下步骤:

  1. 创建一个自定义的委托类,继承自QStyledItemDelegate。
  2. 重写该委托类的paint函数,实现QCheckBox的居中显示。
  3. 重写该委托类的editorEvent函数,实现QCheckBox的状态改变。
  4. 为QTableView的相应单元格设置该委托类。
  5. 在数据模型中处理QCheckBox状态的更改,以便在重绘时正确显示。

4.1 第一步

和前几篇文章一样,我们需要建立一个项目,并且需要我们拖拽QTableView,以及对其初始化。我们在这里就不在赘述,大家可以参考前面几篇文章是如何创建的。

4.2 第二步

  1. 创建Delegate类,方法和前面几篇文章一样
  2. 需要我们先定义三函数
QWidget * createEditor(QWidget *parent, const QStyleOptionViewItem &option, const QModelIndex &index) const override;
void paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const override;
bool editorEvent(QEvent *event, QAbstractItemModel *model, const QStyleOptionViewItem &option, const QModelIndex &index) override;

这三个函数的含义前面几篇文章都已经提到了,不再赘述。

4.3 第三步

  1. 实现paint函数
void Delegate::paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const
{

    if(index.column() == 2)
    {
        bool value = index.data(Qt::UserRole).toInt();
        QStyleOptionButton checkBoxOption;
        QRect checkBoxRect = QApplication::style()->subElementRect(QStyle::SE_CheckBoxIndicator, &checkBoxOption);
        checkBoxOption.rect = option.rect;
        checkBoxOption.rect.setLeft(option.rect.left() + (option.rect.width() - checkBoxRect.width()) / 2);
        checkBoxOption.rect.setTop(option.rect.top() + (option.rect.height() - checkBoxRect.height()) / 2);
        checkBoxOption.state = value ? QStyle::State_On :QStyle::State_Off;
        checkBoxOption.state |= QStyle::State_Enabled;
        QApplication::style()->drawControl(QStyle::CE_CheckBox, &checkBoxOption, painter);
    }//if
    else
    {
        QStyledItemDelegate::paint(painter,option,index);
    }
}
  1. 实现editorEvent函数
bool Delegate::editorEvent(QEvent *event, QAbstractItemModel *model, const QStyleOptionViewItem &option, const QModelIndex &index)
{
    if(event->type() == QEvent::MouseButtonDblClick)//禁止双击编辑
        return true;
    //过滤鼠标松开
    if (event->type() == QEvent::MouseButtonRelease) {
        return false;
    }

    bool checked = index.data(Qt::UserRole).toBool();
    model->setData(index, !checked, Qt::UserRole);

    return QStyledItemDelegate::editorEvent(event,model,option,index);
}

4.4 最后一步

我们需要在mainwindow.cpp中的init()调用delegate类实现委托。我们将QTableView的第一列设置为委托:

更新mainwindow.cpp中的init()函数

void MainWindow::init()
{
    QStringList columnNames;
    columnNames<<"QSpinBox"<<"QComboBox"<<"QCheckBox"<<"QProgressBar"<<"···";

    model = new QStandardItemModel;
    model->setRowCount(10);
    model->setHorizontalHeaderLabels(columnNames);
    ui->tableView->setModel(model);

    Delegate *checkDelegate = new Delegate;
    ui->tableView->setItemDelegateForColumn(2,checkDelegate);
}

4.5 效果图

在这里插入图片描述

5 源码

源码

  • 3
    点赞
  • 21
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 2
    评论
QCheckBoxQt的一个复选框类,用于在界面上显示一个可选和取消选的选项。自定义委托类是指继承 QStyledItemDelegate 类并重写相关函数,实现对 QCheckBox 进行自定义显示和交互的效果。 自定义委托类可以用于在使用 QTableView 或 QListView 等控件展示复杂的数据模型时,将其的某一列显示为 QCheckBox。下面是一个简单的自定义委托类的示例代码,实现QTableView 显示 QCheckBox: ```cpp #include <QStyledItemDelegate> #include <QCheckBox> class CheckboxDelegate : public QStyledItemDelegate { public: CheckboxDelegate(QObject *parent = nullptr) : QStyledItemDelegate(parent) {} QWidget *createEditor(QWidget *parent, const QStyleOptionViewItem &option, const QModelIndex &index) const { QCheckBox *checkBox = new QCheckBox(parent); return checkBox; } void setEditorData(QWidget *editor, const QModelIndex &index) const { QCheckBox *checkBox = qobject_cast<QCheckBox *>(editor); if (checkBox) { bool isChecked = index.model()->data(index, Qt::EditRole).toBool(); checkBox->setChecked(isChecked); } } void setModelData(QWidget *editor, QAbstractItemModel *model, const QModelIndex &index) const { QCheckBox *checkBox = qobject_cast<QCheckBox *>(editor); if (checkBox) { bool isChecked = checkBox->isChecked(); model->setData(index, isChecked, Qt::EditRole); } } void updateEditorGeometry(QWidget *editor, const QStyleOptionViewItem &option, const QModelIndex &index) const { editor->setGeometry(option.rect); } }; ``` 以上代码,createEditor 函数创建一个 QCheckBox 对象作为编辑器,setEditorData 函数将模型的数据设置到编辑器,setModelData 函数将编辑器的数据设置回模型,updateEditorGeometry 函数设置编辑器的位置和大小。 使用这个自定义委托类的方式是,在初始化 QTableView 对象后,调用 setItemDelegateForColumn 函数将某一列的委托设置为 CheckboxDelegate,然后在模型将对应的数据以 bool 类型储存。 ```cpp QTableView *tableView = new QTableView(); CheckboxDelegate *checkboxDelegate = new CheckboxDelegate(); tableView->setItemDelegateForColumn(0, checkboxDelegate); ``` 通过以上方式,即可在 QTableView 的第一列显示为 QCheckBox,并实现相应的数据交互和显示效果。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

m晴朗

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值