QTableWidget表头加入QCheckBox(复选框表头)

最近发现在QTableWidget的表头中加入复选框这个需求较为普遍,网上相关的资料却很少,实现此功能所需相关的Qt方法也较为冷门,特作此分享。

主要实现方法为重写QHeaderView类的*void paintSection(QPainter painter, const QRect &rect, int logicalIndex) const; 函数和 *void mousePressEvent(QMouseEvent event); 函数,下面直接贴完整代码和示例,方便大家使用。

1.头文件如下:

#ifndef CHECKBOXHEADERVIEW_H
#define CHECKBOXHEADERVIEW_H

#include <QtGui>
#include <QPainter>
#include <QHeaderView>
#include <QStyleOptionButton>
#include <QStyle>
#include <QCheckBox>
#include <QEvent>

class CheckBoxHeaderView : public QHeaderView
{
    Q_OBJECT

public:
    CheckBoxHeaderView(int checkColumnIndex, QPoint topLeft, QSize size, 
    Qt::Orientation orientation, QWidget *parent = nullptr);

protected:
    void paintSection(QPainter *painter, const QRect &rect, int logicalIndex) const;
    void mousePressEvent(QMouseEvent *event);

private:
    int     checkColIndex;  //表头列下标
    QPoint  topLeft;        //勾选框起始屏幕坐标
    QSize   boxSize;        //勾选框大小
    bool    isChecked;      //勾选框状态

public:
    void setCheckState(bool state);             //设置复选框状态

signals:
    void signalCheckStateChanged(bool state);   //勾选状态发生改变信号
};

#endif // CHECKBOXHEADERVIEW_H

2.cpp文件如下:

#include "checkboxheaderview.h"

CheckBoxHeaderView::CheckBoxHeaderView(int checkColumnIndex, QPoint topLeft, QSize size, Qt::Orientation orientation, QWidget *parent) : QHeaderView(orientation, parent)
{
    checkColIndex = checkColumnIndex;
    this->topLeft = topLeft;
    boxSize = size;
    isChecked = false;
}

void CheckBoxHeaderView::setCheckState(bool state)
{
    isChecked = state;
}


void CheckBoxHeaderView::paintSection(QPainter *painter, const QRect &rect, int logicalIndex) const
{
    painter->save();
    QHeaderView::paintSection(painter, rect, logicalIndex);
    painter->restore();
    if (logicalIndex == checkColIndex)
    {
        QStyleOptionButton option;
        option.rect = QRect(topLeft.x(), topLeft.y(), boxSize.width(), boxSize.height());
        if (isChecked)
        {
            option.state = QStyle::State_On;
        }
        else
        {
            option.state = QStyle::State_Off;
        }
        //加入复选框,设置样式
        QCheckBox *check = new QCheckBox;
        QString sheet = QString("QCheckBox::indicator {width: %1px;  height: %2px;}").arg(boxSize.width()).arg(boxSize.height());
        check->setStyleSheet(sheet);
        this->style()->drawControl(QStyle::CE_CheckBox, &option, painter, check);
    }
}

void CheckBoxHeaderView::mousePressEvent(QMouseEvent *event)
{
    if (visualIndexAt(event->pos().x()) == checkColIndex)
    {
        isChecked = !isChecked;
        this->updateSection(checkColIndex);
        emit signalCheckStateChanged(isChecked);
    }
    //继承后此信号必须手动发送,否则无法响应
    emit QHeaderView::sectionClicked(visualIndexAt(event->pos().x()));
    QHeaderView::mousePressEvent(event);
}

3.使用示例:

    CheckBoxHeaderView *header = new CheckBoxHeaderView(0, QPoint(10, 5), QSize(20, 20), Qt::Horizontal, this);
    ui->tableWidget->setColumnCount(2);
    ui->tableWidget->setHorizontalHeaderLabels(QStringList() << "复选框" << "无复选框");
    ui->tableWidget->setHorizontalHeader(header);

    connect(header, &CheckBoxHeaderView::signalCheckStateChanged, [=](bool state)
    {
        qDebug() << "勾选状态:" << state;
    });

效果图:
在这里插入图片描述
什么?!你说懒得复制粘贴?OKOK,我上传demo,设置0积分,csdn系统会自动改积分,有积分的就直接下载,没积分的再@我。
点击这里去下载demo

  • 18
    点赞
  • 69
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 15
    评论
评论 15
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

为啥不吃肉捏

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

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

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

打赏作者

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

抵扣说明:

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

余额充值