- 为QTableView控件添加ToolTips,可以重写QTableView的:
virtual bool viewportEvent(QEvent *) override;
事件处理函数,或者直接重写QTableView的:virtual bool event(QEvent*) overrode;
事件分发器。 - 需要注意的是,如果重写event方法,则需要将坐标转换为视口(viewport)坐标:
bool TableViewEx::event(QEvent *event)
{
if (event->type() == QEvent::ToolTip)
{
QHelpEvent* helperEvent = static_cast<QHelpEvent*>(event);
qDebug() << helperEvent->type();
if (helperEvent == nullptr) return false;
QPoint viewportPos = viewport()->mapFromGlobal(helperEvent->globalPos()); //将事件产生的坐标映射为视口坐标,否则indexAt无法获取到的模型索引
QModelIndex index = this->indexAt(viewportPos);
qDebug() << helperEvent->pos() << viewportPos; //打印坐标
if (index.isValid())
{
QString data = index.data(Qt::DisplayRole).toString();
QToolTip::showText(helperEvent->globalPos(), data);
return true;
}
return false;
}
return QTableView::event(event);
}
可以看到打印的坐标:
event pos: QPoint(120,280) , viewport pos: QPoint(119,254)
event pos: QPoint(133,250) , viewport pos: QPoint(132,224)
event pos: QPoint(142,218) , viewport pos: QPoint(141,192)
event pos: QPoint(149,185) , viewport pos: QPoint(148,159)
可以发现ToolTips事件产生的坐标的X和Y都比视口坐标大,多出的正是表头的宽高;所以如果使用事件产生的坐标来计算模型索引,会得到不正确的索引位置
- 如果直接重写viewportEvent事件处理函数,则不需要额外的坐标转换,因为这个事件中,事件产生的坐标就是视口坐标
bool CommonTableViewEx::viewportEvent(QEvent *event)
{
if (event->type() == QEvent::ToolTip)
{
QHelpEvent* helperEvent = static_cast<QHelpEvent*>(event);
if (helperEvent == nullptr) return false;
QPoint viewportPos = viewport()->mapFromGlobal(helperEvent->globalPos()); //将事件产生的坐标映射为视口坐标,否则indexAt无法获取到的模型索引
QModelIndex index = this->indexAt(viewportPos);
qDebug() << "event pos:" << helperEvent->pos() << "," << "viewport pos:" << viewportPos;
if (index.isValid())
{
QString data = index.data(Qt::DisplayRole).toString();
QToolTip::showText(helperEvent->globalPos(), data);
return true;
}
return false;
}
return QTableView::viewportEvent(event);
}
重写viewportEvent,同样的代码,打印的坐标如下:可以发现,ToolTips事件产生的坐标,就是视口的坐标
event pos: QPoint(53,12) , viewport pos: QPoint(53,12)
event pos: QPoint(52,11) , viewport pos: QPoint(52,11)
event pos: QPoint(49,25) , viewport pos: QPoint(49,25)
event pos: QPoint(49,26) , viewport pos: QPoint(49,26)
event pos: QPoint(49,29) , viewport pos: QPoint(49,29)
event pos: QPoint(50,55) , viewport pos: QPoint(50,55)
event pos: QPoint(52,55) , viewport pos: QPoint(52,55)
红色边框为视口区域: