您好,登錄后才能下訂單哦!
這期內(nèi)容當(dāng)中小編將會(huì)給大家?guī)?lái)有關(guān)怎么在Qt中通過(guò)自定義表頭實(shí)現(xiàn)過(guò)濾功能,文章內(nèi)容豐富且以專業(yè)的角度為大家分析和敘述,閱讀完這篇文章希望大家可以有所收獲。
1)hover狀態(tài)在鼠標(biāo)移動(dòng)事件中實(shí)現(xiàn)
void CFilterHeaderView::mouseMoveEvent(QMouseEvent *e) { m_hover = logicalIndexAt(e->pos()); if (m_hover != -1) updateSection(m_hover); QHeaderView::mouseMoveEvent(e); } bool CFilterHeaderView::event(QEvent *e) { switch(e->type()) { case QEvent::Leave: case QEvent::HoverLeave: if (m_hover != -1) updateSection(m_hover); m_hover = -1; break; default: break; } return QHeaderView::event(e); }
如果懸浮在某一列上,hover值等于該列的index,否則等于-1。如果hover值不等于-1,則刷新該列(updateSection)。
mouseMoveEvent中檢測(cè)鼠標(biāo)懸浮在那個(gè)表格列上。event函數(shù)中監(jiān)聽(tīng)Leave和HoverLeave事件。
2)press狀態(tài)在鼠標(biāo)點(diǎn)擊事件中實(shí)現(xiàn)
void CFilterHeaderView::mousePressEvent(QMouseEvent *e) { m_press = logicalIndexAt(e->pos()); if (m_press != -1) updateSection(m_press); QHeaderView::mousePressEvent(e); } void CFilterHeaderView::mouseReleaseEvent(QMouseEvent *e) { m_press = -1; QHeaderView::mouseReleaseEvent(e); }
press的實(shí)現(xiàn)較為簡(jiǎn)單,鼠標(biāo)點(diǎn)擊更新press,鼠標(biāo)釋放press置為-1。
3)過(guò)濾提示的實(shí)現(xiàn)。
過(guò)濾提示在paintSection函數(shù)中實(shí)現(xiàn),首先是調(diào)用基類paintSection實(shí)現(xiàn)表頭的繪制,然后是檢測(cè)有沒(méi)有定義過(guò)濾角色。如果有定義過(guò)濾角色,則根據(jù)三態(tài)選擇對(duì)應(yīng)的圖標(biāo),繪制位置默認(rèn)水平靠右垂直居住,也可以自己指定位置。最后是繪制過(guò)濾提示。具體實(shí)現(xiàn)如下:
void CFilterHeaderView::paintSection(QPainter *painter, const QRect &rect, int logicalIndex) const { painter->save(); QHeaderView::paintSection(painter, rect, logicalIndex); painter->restore(); QVariant filterVar = model()->headerData(logicalIndex, orientation(), FilterRole); if (filterVar.isValid() && filterVar.toBool()) { QPixmap pix = m_norFilterPix; bool b_contain = getFilterRect(rect).contains(cursor().pos()); if (logicalIndex == m_hover && b_contain) { pix = m_hovFilterPix; } if (logicalIndex == m_press && b_contain) { pix = m_preFilterPix; } int align = Qt::AlignRight | Qt::AlignVCenter; QVariant alignVar = model()->headerData(logicalIndex, orientation(), FilterAlignmentRole); if (alignVar.isValid()) { align = alignVar.toInt(); } style()->drawItemPixmap(painter, rect, align, pix); } }
表格繪制的區(qū)域和過(guò)濾提示繪制的區(qū)域不一致,要根據(jù)過(guò)濾圖標(biāo)大小進(jìn)行計(jì)算過(guò)濾提示的區(qū)域。只有當(dāng)鼠標(biāo)在過(guò)濾區(qū)域位置上方,hover和press才有效,否則仍然是normal狀態(tài)。過(guò)濾區(qū)域繪制的位置可以從外面獲取,也可以使用默認(rèn)位置。最后style()->drawItemPixmap進(jìn)行繪制。
調(diào)用基類paintSection方法前后調(diào)用QPainter::save()和QPainter::restore()是必要的。如果不調(diào)用,style()->drawItemPixmap是不會(huì)起作用的。
4)過(guò)濾提示點(diǎn)擊信號(hào)
點(diǎn)擊過(guò)濾提示會(huì)發(fā)出信號(hào),連接此信號(hào)可以進(jìn)行過(guò)濾功能的實(shí)現(xiàn)。具體實(shí)現(xiàn)如下:
void CFilterHeaderView::mouseReleaseEvent(QMouseEvent *e) { if (e->button() == Qt::LeftButton) { int section = logicalIndexAt(e->pos()); QVariant filterVar = model()->headerData(section, orientation(), FilterRole); if (filterVar.isValid() && filterVar.toBool()) { QRect rect(sectionViewportPosition(section), 0, sectionSize(section), height()); if (getFilterRect(rect).contains(cursor().pos())) { emit filterClicked(section); } } } QHeaderView::mouseReleaseEvent(e); }
過(guò)濾信號(hào)發(fā)出的條件:1. 左鍵點(diǎn)擊,2. 定義了過(guò)濾功能,3. 鼠標(biāo)在過(guò)濾提示區(qū)域中
3. 使用過(guò)濾功能
使用過(guò)濾表頭的方法如下:
m_tableView = new QTableView(this); m_model = new QStandardItemModel(this); m_filterModel = new QSortFilterProxyModel(this); m_filterModel->setSourceModel(m_model); m_filterModel->setSortRole(Qt::ToolTipRole); m_tableView->setModel(m_filterModel); QHBoxLayout* mainLayout = new QHBoxLayout(this); mainLayout->setMargin(0); mainLayout->addWidget(m_tableView); setLayout(mainLayout); m_tableView->setEditTriggers(QAbstractItemView::NoEditTriggers); m_tableView->setSelectionMode(QAbstractItemView::SingleSelection); m_tableView->setSelectionBehavior(QAbstractItemView::SelectRows); m_tableView->verticalHeader()->hide(); CFilterHeaderView* pHeader = new CFilterHeaderView(this); connect(pHeader, &CFilterHeaderView::filterClicked, this, &Widget::onFilterClicked); m_tableView->setHorizontalHeader(pHeader);
使用過(guò)濾表頭和使用普通表頭沒(méi)有太大的差別。這里過(guò)濾功能有QSortFilterProxyModel實(shí)現(xiàn),水平表頭替換成自定義的CFilterHeaderView。
上述就是小編為大家分享的怎么在Qt中通過(guò)自定義表頭實(shí)現(xiàn)過(guò)濾功能了,如果剛好有類似的疑惑,不妨參照上述分析進(jìn)行理解。如果想知道更多相關(guān)知識(shí),歡迎關(guān)注億速云行業(yè)資訊頻道。
免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如果涉及侵權(quán)請(qǐng)聯(lián)系站長(zhǎng)郵箱:is@yisu.com進(jìn)行舉報(bào),并提供相關(guān)證據(jù),一經(jīng)查實(shí),將立刻刪除涉嫌侵權(quán)內(nèi)容。