书接上文,我们继续来聊聊 QTableView 上可以自定义的新功能
QTableView 可以通过 style sheet 来配置 hover 和 selected 的颜色
1setStyleSheet("::item:hover{background-color:rgba(222,100,123,100);}"2"::item:selected{background-color:rgb(100,200,100)}");在 setSelectionBehavior``(``SelectItems``); 时,即只 hover 单个单元格时是有效的
在 setSelectionBehavior(SelectRows); 或 setSelectionBehavior(SelectColumns); 时,
styleSheet 中 hover 不生效,即鼠标移动时,不能做到整行或整列的高亮
要解决这个 bug,我们可以通过自定义 QStyledItemDelegate 实现
xxxxxxxxxx241void StyledItemDelegate::paint(QPainter *painter, const QStyleOptionViewItem &option, const QModelIndex &index) const {2 QStyleOptionViewItem opt(option);3 opt.state &= ~QStyle::State_HasFocus;4 TableView *view = qobject_cast<TableView *>(opt.styleObject);5 QModelIndex hoverIndex = view->hoverIndex();6 QAbstractItemView::SelectionBehavior behavior = view->selectionBehavior();7 if (!(option.state & QStyle::State_Selected) && behavior != QTableView::SelectItems) {8 if (behavior == QTableView::SelectRows) {9 if(hoverIndex.row() == index.row()) {10 opt.state |= QStyle::State_MouseOver;11 } else {12 opt.state &= ~ QStyle::State_MouseOver;13 }14 }15 if (behavior == QTableView::SelectColumns) {16 if(hoverIndex.column() == index.column()) {17 opt.state |= QStyle::State_MouseOver;18 } else {19 opt.state &= ~ QStyle::State_MouseOver;20 }21 }22 }23 QStyledItemDelegate::paint(painter, opt, index);24}主要是通过修改 QStyle::State_MouseOver 实现
表格复选框,包括行选择,列选择,单元格选择,全选
QHeaderView 没有提供复选框的功能,我们可以通过自定义 QHeaderView 类,实现它的 paintSection 函数,也可以通过 Qt::DecorationRole 来模拟表头的复选框功能
这里采用了后者,代码量很少,只要修改 model 的 headerData 及 setHeaderData 函数就行了
单元格选择可以通过修改 model 的 flags、data、setData 函数实现
全选按钮是通过 findChild 查找到对应的 button,然后在里面 layout 一个 QCheckbox 实现的
xxxxxxxxxx101QAbstractButton* button = findChild< QAbstractButton* >();2if (button) {3 QHBoxLayout* layout = new QHBoxLayout(button);4 layout->setContentsMargins(0, 0, 0, 0);5 checkBox = new QCheckBox(this);6 checkBox->setFocusPolicy(Qt::NoFocus);7 checkBox->setFixedSize(13, 13);8 checkBox->setContentsMargins(0, 0, 0, 0);9 layout->addWidget(checkBox);10}