如何获取QAbstractItemView中可见的QModelIndex列表

问题描述 投票:0回答:5

有什么方法可以获取

QAbstractItemView
中当前可见项目的列表吗?并且,如果可能的话,接收有关更改此列表的任何通知。

更新: 我问的是非普通结构的

QAbstractItemView
QTreeView
,而不是
QTableView

更新2: 我正在实现带有复选框的树视图模型。我想要下一个行为(与检查/取消检查相同):

  • 如果选中其中一个复选框 - 则必须选中所有子项
  • 如果所有子复选框都被选中 - 那么父复选框也应该被选中。对于父母的父母也是如此......

检查状态由外部数据源监控/修改,因此我需要一种机制来更新所有更改的子项/父项。

dataChanged
信号对我来说还不够,因为构建所有更改的
QModelIndex
列表以进行更新非常广泛。而且根本没有必要,因为所有新鲜数据都将从
QAbstractItemModel::data
中选取。

我发现了下一个肮脏的黑客来更新所有项目:

emit dataChanged( QModelIndex(), QModelIndex() );
但它没有记录无效索引。

因此,我需要一种方法来强制所有可见项目用新数据重新绘制它们的内容。

qt model-view-controller qmodelindex qabstractitemview
5个回答
13
投票

您可以通过调用以下方式获取左上角和右下角的单元格:

tableview->indexAt(tableview->rect().topLeft())
tableview->indexAt(tableview->rect().bottomRight())

要获取更改通知,请重新实现 qabstractscrollarea 的虚函数

scrollContentsBy

当视口滚动时调用此函数。 调用 QTableView::scrollContentsBy ,然后执行您需要执行的操作。


4
投票

对于

QTreeView
,可见项列表可以这样遍历:

QTreeView& tv (yourTreeView);

// Get model index for first visible item
QModelIndex modelIndex = tv.indexAt(tv.rect().topLeft());

while (modelIndex.isValid())
{
    // do something with the item indexed by modelIndex
    ...
    // This navigates to the next visible item
    modelIndex = tv.indexBelow(modelIndex);
}

1
投票

方法1

i, j = table.indexAt(table.rect().topLeft()).row(), table.indexAt(table.rect().bottomLeft()).row() - 1

方法2

i, j = table.rowAt(0), table.rowAt(table.height()) - 1

0
投票

我总是用以下内容更新整个 QAbstractTableModel:

emit dataChanged(index(0, 0), index(rowCount(), columnCount()-1)); // update whole view

0
投票

我认为不存在需要可见项目列表的情况。如果模型实现正确,所有项目都会自动更新。

实施的难点——强迫孩子和家长更新。我写了以下代码:

bool TreeModel::setData( const QModelIndex &index, const QVariant &value, int role )
    case Qt::CheckStateRole:
    {
        TreeItemList updateRangeList;  // Filled with items, in which all childred must be updated
        TreeItemList updateSingleList; // Filled with items, which must be updated
        item->setCheckState( value.toBool(), updateRangeList, updateSingleList ); // All magic there
        
        foreach ( TreeAbstractItem *i, updateRangeList )
        {
            const int nRows = i->rowCount();
            QModelIndex topLeft = indexForItem( i->m_childs[0] );
            QModelIndex bottomRight = indexForItem( i->m_childs[nRows - 1] );
            emit dataChanged( topLeft, bottomRight );
        }
        foreach ( TreeAbstractItem *i, updateSingleList )
        {
            QModelIndex updateIndex = indexForItem( i );
            emit dataChanged( updateIndex, updateIndex );
        }
    }
© www.soinside.com 2019 - 2024. All rights reserved.