diff options
-rw-r--r-- | src/gui/itemviews/qlistview.cpp | 14 | ||||
-rw-r--r-- | tests/auto/qlistview/tst_qlistview.cpp | 52 |
2 files changed, 63 insertions, 3 deletions
diff --git a/src/gui/itemviews/qlistview.cpp b/src/gui/itemviews/qlistview.cpp index 6db979c..e6949fd 100644 --- a/src/gui/itemviews/qlistview.cpp +++ b/src/gui/itemviews/qlistview.cpp @@ -2558,13 +2558,21 @@ int QListModeViewBase::perItemScrollToValue(int index, int scrollValue, int view { if (index < 0) return scrollValue; + + QVector<int> visibleFlowPositions; + visibleFlowPositions.reserve(flowPositions.count() - 1); + for (int i = 0; i < flowPositions.count() - 1; i++) { // flowPositions count is +1 larger than actual row count + if (!isHidden(i)) + visibleFlowPositions.append(flowPositions.at(i)); + } + if (!wrap) { int topIndex = index; const int bottomIndex = topIndex; - const int bottomCoordinate = flowPositions.at(index); + const int bottomCoordinate = visibleFlowPositions.at(index); while (topIndex > 0 && - (bottomCoordinate - flowPositions.at(topIndex-1) + itemExtent) <= (viewportSize)) { + (bottomCoordinate - visibleFlowPositions.at(topIndex - 1) + itemExtent) <= (viewportSize)) { topIndex--; } @@ -2584,7 +2592,7 @@ int QListModeViewBase::perItemScrollToValue(int index, int scrollValue, int view ? Qt::Horizontal : Qt::Vertical); if (flowOrientation == orientation) { // scrolling in the "flow" direction // ### wrapped scrolling in the flow direction - return flowPositions.at(index); // ### always pixel based for now + return visibleFlowPositions.at(index); // ### always pixel based for now } else if (!segmentStartRows.isEmpty()) { // we are scrolling in the "segment" direction int segment = qBinarySearch<int>(segmentStartRows, index, 0, segmentStartRows.count() - 1); int leftSegment = segment; diff --git a/tests/auto/qlistview/tst_qlistview.cpp b/tests/auto/qlistview/tst_qlistview.cpp index 5623ecb..a97296f 100644 --- a/tests/auto/qlistview/tst_qlistview.cpp +++ b/tests/auto/qlistview/tst_qlistview.cpp @@ -130,6 +130,8 @@ private slots: void taskQTBUG_12308_wrongFlowLayout(); void taskQTBUG_21115_scrollToAndHiddenItems_data(); void taskQTBUG_21115_scrollToAndHiddenItems(); + void taskQTBUG_21804_hiddenItemsAndScrollingWithKeys_data(); + void taskQTBUG_21804_hiddenItemsAndScrollingWithKeys(); }; // Testing get/set functions @@ -2108,5 +2110,55 @@ void tst_QListView::taskQTBUG_21115_scrollToAndHiddenItems() QCOMPARE(lv.visualRect(index), firstItemRect); } +void tst_QListView::taskQTBUG_21804_hiddenItemsAndScrollingWithKeys_data() +{ + QTest::addColumn<int>("flow"); + QTest::newRow("flow TopToBottom") << static_cast<int>(QListView::TopToBottom); + QTest::newRow("flow LeftToRight") << static_cast<int>(QListView::LeftToRight); +} + +void tst_QListView::taskQTBUG_21804_hiddenItemsAndScrollingWithKeys() +{ + QFETCH(int, flow); + + // create some items to show + QStringListModel model; + QStringList list; + for (int i = 0; i < 60; i++) + list << QString::number(i); + model.setStringList(list); + + // create listview + QListView lv; + lv.setFlow(static_cast<QListView::Flow>(flow)); + lv.setModel(&model); + lv.show(); + QTest::qWaitForWindowShown(&lv); + + // hide every odd number row + for (int i = 1; i < model.rowCount(); i+=2) + lv.setRowHidden(i, true); + + // scroll forward and check that selected item is visible always + for (int i = 0; i < model.rowCount()/2; i++) { + if (flow == QListView::TopToBottom) + QTest::keyClick(&lv, Qt::Key_Down); + else + QTest::keyClick(&lv, Qt::Key_Right); + QTest::qWait(100); + QVERIFY(lv.rect().contains(lv.visualRect(lv.currentIndex()))); + } + + // scroll backward + for (int i = 0; i < model.rowCount()/2; i++) { + if (flow == QListView::TopToBottom) + QTest::keyClick(&lv, Qt::Key_Up); + else + QTest::keyClick(&lv, Qt::Key_Left); + QTest::qWait(100); + QVERIFY(lv.rect().contains(lv.visualRect(lv.currentIndex()))); + } +} + QTEST_MAIN(tst_QListView) #include "tst_qlistview.moc" |