summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorTang Haixiang <tanghaixiang@uniontech.com>2021-04-27 17:39:48 +0800
committerQt Cherry-pick Bot <cherrypick_bot@qt-project.org>2021-05-31 04:04:00 +0000
commitbd73184395aa25b5736449b8e99c8111661bef24 (patch)
treef32b2a3774b1c928a4acfe1783bdb65661713c04
parent1a081042abda3a32efeedeba7879017eed9237c6 (diff)
Fix PageDown behavior and PageUP
When the PageDown is pressed, the current's rect cannot be used to match the item, because we don't know the size of the rect. Move the rect by the height of the viewport, and then move the rect upwards until it matches the button <= viewport's bottom of the item Fixes: QTBUG-92583 Change-Id: I210edc0e8b942984f3fc20e7752c6e1315152ea1 Reviewed-by: Volker Hilsheimer <volker.hilsheimer@qt.io> (cherry picked from commit c77840d734883c91079c942e052cbdc0994c2f01) Reviewed-by: Qt Cherry-pick Bot <cherrypick_bot@qt-project.org>
-rw-r--r--src/widgets/itemviews/qlistview.cpp53
-rw-r--r--tests/auto/widgets/itemviews/qlistview/tst_qlistview.cpp51
2 files changed, 90 insertions, 14 deletions
diff --git a/src/widgets/itemviews/qlistview.cpp b/src/widgets/itemviews/qlistview.cpp
index 59ba1ec6b6..e655b639b9 100644
--- a/src/widgets/itemviews/qlistview.cpp
+++ b/src/widgets/itemviews/qlistview.cpp
@@ -1234,13 +1234,25 @@ QModelIndex QListView::moveCursor(CursorAction cursorAction, Qt::KeyboardModifie
d->removeCurrentAndDisabled(&intersectVector, current);
}
return d->closestIndex(initialRect, intersectVector);
- case MovePageUp:
- // move current by (visibileRowCount - 1) items.
- // rect.translate(0, -rect.height()); will happen in the switch fallthrough for MoveUp.
- rect.moveTop(rect.top() - d->viewport->height() + 2 * rect.height());
- if (rect.top() < rect.height())
- rect.moveTop(rect.height());
- Q_FALLTHROUGH();
+ case MovePageUp: {
+ rect.moveTop(rect.top() - d->viewport->height() + 1 );
+ if (rect.top() < rect.height()) {
+ rect.setTop(0);
+ rect.setBottom(1);
+ }
+ QModelIndex findindex = current;
+ while (intersectVector.isEmpty()
+ || rectForIndex(findindex).top() <= (rectForIndex(current).bottom() - d->viewport->rect().height())
+ || rect.top() <= 0) {
+ rect.translate(0, 1);
+ if (rect.bottom() <= 0) {
+ return current;
+ }
+ intersectVector = d->intersectingSet(rect);
+ findindex = d->closestIndex(initialRect, intersectVector);
+ }
+ return findindex;
+ }
case MovePrevious:
case MoveUp:
while (intersectVector.isEmpty()) {
@@ -1263,13 +1275,26 @@ QModelIndex QListView::moveCursor(CursorAction cursorAction, Qt::KeyboardModifie
d->removeCurrentAndDisabled(&intersectVector, current);
}
return d->closestIndex(initialRect, intersectVector);
- case MovePageDown:
- // move current by (visibileRowCount - 1) items.
- // rect.translate(0, rect.height()); will happen in the switch fallthrough for MoveDown.
- rect.moveTop(rect.top() + d->viewport->height() - 2 * rect.height());
- if (rect.bottom() > contents.height() - rect.height())
- rect.moveBottom(contents.height() - rect.height());
- Q_FALLTHROUGH();
+ case MovePageDown: {
+ rect.moveTop(rect.top() + d->viewport->height() - 1 );
+ if (rect.bottom() > contents.height() - rect.height()){
+ rect.setTop(contents.height() - 1);
+ rect.setBottom(contents.height());
+ }
+ QModelIndex index = current;
+ // index's bottom() - current's top() always <= (d->viewport->rect().height()
+ while (intersectVector.isEmpty()
+ || rectForIndex(index).bottom() >= (d->viewport->rect().height() + rectForIndex(current).top())
+ || rect.bottom() > contents.height()) {
+ rect.translate(0, -1);
+ if (rect.top() >= contents.height()) {
+ return current;
+ }
+ intersectVector = d->intersectingSet(rect);
+ index = d->closestIndex(initialRect, intersectVector);
+ }
+ return index;
+ }
case MoveNext:
case MoveDown:
while (intersectVector.isEmpty()) {
diff --git a/tests/auto/widgets/itemviews/qlistview/tst_qlistview.cpp b/tests/auto/widgets/itemviews/qlistview/tst_qlistview.cpp
index 3768acade7..8948f02a8b 100644
--- a/tests/auto/widgets/itemviews/qlistview/tst_qlistview.cpp
+++ b/tests/auto/widgets/itemviews/qlistview/tst_qlistview.cpp
@@ -109,6 +109,7 @@ private slots:
void moveCursor();
void moveCursor2();
void moveCursor3();
+ void moveCursor4();
void indexAt();
void clicked();
void singleSelectionRemoveRow();
@@ -573,6 +574,56 @@ void tst_QListView::moveCursor3()
QCOMPARE(view.selectionModel()->currentIndex(), model.index(0, 0));
}
+void tst_QListView::moveCursor4()
+{
+ int indexCount = 100;
+ PublicListView listView;
+ QStandardItemModel model;
+ for (int i = 0; i < 100; i++)
+ {
+ QStandardItem* item = new QStandardItem(QString("item 0%0").arg(i));
+ QFont font = item->font();
+ font.setPixelSize(14);
+ item->setFont(font);
+ model.appendRow(item);
+ }
+ QFont font = model.item(0)->font();
+ font.setPixelSize(50);
+ font.setBold(true);
+ model.item(0)->setFont(font);
+ listView.setModel(&model);
+ listView.setFixedSize(200, 200);
+ listView.setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
+ listView.setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
+ listView.show();
+ listView.selectionModel()->setCurrentIndex(model.index(0, 0), QItemSelectionModel::SelectCurrent);
+
+ QModelIndex idx = listView.moveCursor(PublicListView::MovePageDown, Qt::NoModifier);
+
+ int actualIndex = 0;
+ int indexHeight = 0;
+ while (indexHeight <= listView.viewport()->height()) {
+ indexHeight += listView.visualRect(model.item(actualIndex)->index()).height();
+ actualIndex++;
+ }
+ QTRY_COMPARE(idx, model.index(actualIndex - 2, 0));
+ idx = listView.moveCursor(PublicListView::MoveUp, Qt::NoModifier);
+ QTRY_COMPARE(idx, model.index(0, 0));
+
+ listView.setCurrentIndex(model.index(indexCount - 2, 0));
+ idx = listView.moveCursor(PublicListView::MovePageDown, Qt::NoModifier);
+ QTRY_COMPARE(idx, model.index(99, 0));
+
+ listView.setCurrentIndex(model.index(3, 0));
+ actualIndex = 3;
+ indexHeight = 0;
+ while (indexHeight <= listView.viewport()->height()) {
+ indexHeight += listView.visualRect(model.item(actualIndex)->index()).height();
+ actualIndex++;
+ }
+ idx = listView.moveCursor(PublicListView::MovePageDown, Qt::NoModifier);
+ QTRY_COMPARE(idx, model.index(actualIndex - 2, 0));
+}
class QListViewShowEventListener : public QListView
{