From 4e75cb56f37ac2ff22fbc562c85daeb8599753a9 Mon Sep 17 00:00:00 2001 From: Christopher Ham Date: Wed, 16 Feb 2011 11:48:02 +1000 Subject: GridView and ListView bug fixes ListView and GridView check before accessing an empty model. Fixed issue with undefined header. Current index initialised properly when dynamically creating ListModel items with javascript. Change-Id: I121c0626db6eb7ccaab689dfc750e0d03773d90f Task-number: QTBUG-15877 Reviewed-by: Joona Petrell --- .../graphicsitems/qdeclarativegridview.cpp | 57 +++++++++++----------- .../graphicsitems/qdeclarativelistview.cpp | 16 +++--- .../tst_qdeclarativegridview.cpp | 2 + .../tst_qdeclarativelistview.cpp | 2 +- 4 files changed, 40 insertions(+), 37 deletions(-) diff --git a/src/declarative/graphicsitems/qdeclarativegridview.cpp b/src/declarative/graphicsitems/qdeclarativegridview.cpp index 39fa8e8..2eeadf4 100644 --- a/src/declarative/graphicsitems/qdeclarativegridview.cpp +++ b/src/declarative/graphicsitems/qdeclarativegridview.cpp @@ -73,22 +73,22 @@ public: if (view->flow() == QDeclarativeGridView::LeftToRight) { rowPos = item->y(); } else { - if (view->layoutDirection() == Qt::LeftToRight) - rowPos = item->x(); - else + if (view->layoutDirection() == Qt::RightToLeft) rowPos = -view->cellWidth()-item->x(); + else + rowPos = item->x(); } return rowPos; } qreal colPos() const { qreal colPos = 0; if (view->flow() == QDeclarativeGridView::LeftToRight) { - if (view->layoutDirection() == Qt::LeftToRight) { - colPos = item->x(); - } else { + if (view->layoutDirection() == Qt::RightToLeft) { int colSize = view->cellWidth(); int columns = view->width()/colSize; colPos = colSize * (columns-1) - item->x(); + } else { + colPos = item->x(); } } else { colPos = item->y(); @@ -101,25 +101,25 @@ public: if (view->flow() == QDeclarativeGridView::LeftToRight) { return item->y() + view->cellHeight() - 1; } else { - if (view->layoutDirection() == Qt::LeftToRight) - return item->x() + view->cellWidth() - 1; - else + if (view->layoutDirection() == Qt::RightToLeft) return -item->x() - 1; + else + return item->x() + view->cellWidth() - 1; } } void setPosition(qreal col, qreal row) { - if (view->layoutDirection() == Qt::LeftToRight) { - if (view->flow() == QDeclarativeGridView::LeftToRight) - item->setPos(QPointF(col, row)); - else - item->setPos(QPointF(row, col)); - } else { + if (view->layoutDirection() == Qt::RightToLeft) { if (view->flow() == QDeclarativeGridView::LeftToRight) { int columns = view->width()/view->cellWidth(); item->setPos(QPointF((view->cellWidth() * (columns-1) - col), row)); } else { item->setPos(QPointF(-view->cellWidth()-row, col)); } + } else { + if (view->flow() == QDeclarativeGridView::LeftToRight) + item->setPos(QPointF(col, row)); + else + item->setPos(QPointF(row, col)); } } @@ -697,7 +697,7 @@ void QDeclarativeGridViewPrivate::layout() qreal rowPos = visibleItems.first()->rowPos(); qreal colPos = visibleItems.first()->colPos(); int col = visibleIndex % columns; - if (colPos != col * colSize() || isRightToLeftTopToBottom()) { + if (colPos != col * colSize()) { colPos = col * colSize(); visibleItems.first()->setPosition(colPos, rowPos); } @@ -747,7 +747,7 @@ void QDeclarativeGridViewPrivate::updateUnrequestedPositions() if (isRightToLeftTopToBottom()) item->setPos(QPointF(-rowPosAt(*it)-item->width(), colPosAt(*it))); else - item->setPos(QPointF(rowPosAt(*it), (columns-1)*colSize()-colPosAt(*it))); + item->setPos(QPointF(rowPosAt(*it), colPosAt(*it))); } } } @@ -1032,7 +1032,9 @@ void QDeclarativeGridViewPrivate::fixup(AxisData &data, qreal minExtent, qreal m qreal bottomPos = qMax(bottomItem->rowPos() - highlightEnd, -minExtent); pos = qAbs(data.move + topPos) < qAbs(data.move + bottomPos) ? topPos : bottomPos; } else if (topItem) { - qreal headerPos = isRightToLeftTopToBottom() ? header->rowPos() + cellWidth - headerSize() : header->rowPos(); + qreal headerPos = 0; + if (header) + headerPos = isRightToLeftTopToBottom() ? header->rowPos() + cellWidth - headerSize() : header->rowPos(); if (topItem->index == 0 && header && tempPosition+highlightStart < headerPos+headerSize()/2) { pos = isRightToLeftTopToBottom() ? - headerPos + highlightStart - size() : headerPos - highlightStart; } else { @@ -2191,9 +2193,6 @@ qreal QDeclarativeGridView::maxXExtent() const if (d->flow == QDeclarativeGridView::LeftToRight) return QDeclarativeFlickable::maxXExtent(); qreal extent; - if (!d->model || !d->model->count()) { - extent = 0; - } qreal highlightStart; qreal highlightEnd; qreal lastItemPosition; @@ -2204,9 +2203,12 @@ qreal QDeclarativeGridView::maxXExtent() const } else { highlightStart = d->highlightRangeStart; highlightEnd = d->highlightRangeEnd; - lastItemPosition = d->rowPosAt(d->model->count()-1); + if (d->model && d->model->count()) + lastItemPosition = d->rowPosAt(d->model->count()-1); } - if (d->haveHighlightRange && d->highlightRange == StrictlyEnforceRange) { + if (!d->model || !d->model->count()) { + extent = 0; + } else if (d->haveHighlightRange && d->highlightRange == StrictlyEnforceRange) { extent = -(lastItemPosition - highlightStart); if (highlightEnd != highlightStart) extent = d->isRightToLeftTopToBottom() @@ -2725,7 +2727,7 @@ void QDeclarativeGridView::itemsInserted(int modelIndex, int count) modelIndex = d->visibleIndex; } - qreal tempPos = d->isRightToLeftTopToBottom() ? -d->position()-d->size() : d->position(); + qreal tempPos = d->isRightToLeftTopToBottom() ? -d->position()-d->size()+d->width()+1 : d->position(); int to = d->buffer+tempPos+d->size()-1; int colPos = 0; int rowPos = 0; @@ -2744,10 +2746,7 @@ void QDeclarativeGridView::itemsInserted(int modelIndex, int count) } } } else if (d->itemCount == 0 && d->header) { - if (d->flow == QDeclarativeGridView::LeftToRight) - rowPos = d->headerSize(); - else - colPos = d->headerSize(); + rowPos = d->headerSize(); } // Update the indexes of the following visible items. @@ -2804,6 +2803,8 @@ void QDeclarativeGridView::itemsInserted(int modelIndex, int count) d->updateCurrent(0); } emit currentIndexChanged(); + } else if (d->itemCount == 0 && d->currentIndex == -1) { + setCurrentIndex(0); } // everything is in order now - emit add() signal diff --git a/src/declarative/graphicsitems/qdeclarativelistview.cpp b/src/declarative/graphicsitems/qdeclarativelistview.cpp index 6749657..486cec8 100644 --- a/src/declarative/graphicsitems/qdeclarativelistview.cpp +++ b/src/declarative/graphicsitems/qdeclarativelistview.cpp @@ -329,6 +329,7 @@ public: else idx = visibleItems.at(idx)->index; int count = modelIndex - idx - 1; + return (*(--visibleItems.constEnd()))->endPosition() + spacing + count * (averageSize + spacing) + 1; } } @@ -1316,10 +1317,8 @@ void QDeclarativeListViewPrivate::flick(AxisData &data, qreal minExtent, qreal m if (velocity > 0) { if (data.move.value() < minExtent) { if (snapMode == QDeclarativeListView::SnapOneItem) { - if (FxListItem *item = isRightToLeft() ? nextVisibleItem() : firstVisibleItem()) { + if (FxListItem *item = isRightToLeft() ? nextVisibleItem() : firstVisibleItem()) maxDistance = qAbs(item->position() + dataValue); -// qDebug() << "maxDist" << maxDistance << item->position() << dataValue; - } } else { maxDistance = qAbs(minExtent - data.move.value()); } @@ -1329,10 +1328,8 @@ void QDeclarativeListViewPrivate::flick(AxisData &data, qreal minExtent, qreal m } else { if (data.move.value() > maxExtent) { if (snapMode == QDeclarativeListView::SnapOneItem) { - if (FxListItem *item = isRightToLeft() ? firstVisibleItem() : nextVisibleItem()) { + if (FxListItem *item = isRightToLeft() ? firstVisibleItem() : nextVisibleItem()) maxDistance = qAbs(item->position() + dataValue); -// qDebug() << "maxDist2" << maxDistance << item->position() << dataValue; - } } else { maxDistance = qAbs(maxExtent - data.move.value()); } @@ -2595,7 +2592,8 @@ qreal QDeclarativeListView::minXExtent() const qreal highlightEnd; qreal endPositionFirstItem; if (d->isRightToLeft()) { - endPositionFirstItem = d->positionAt(d->model->count()-1); + if (d->model && d->model->count()) + endPositionFirstItem = d->positionAt(d->model->count()-1); highlightStart = d->highlightRangeStartValid ? d->highlightRangeStart - (d->lastPosition()-endPositionFirstItem) : d->size() - (d->lastPosition()-endPositionFirstItem); @@ -2635,7 +2633,8 @@ qreal QDeclarativeListView::maxXExtent() const } else { highlightStart = d->highlightRangeStart; highlightEnd = d->highlightRangeEnd; - lastItemPosition = d->positionAt(d->model->count()-1); + if (d->model && d->model->count()) + lastItemPosition = d->positionAt(d->model->count()-1); } if (!d->model || !d->model->count()) { d->maxExtent = 0; @@ -3058,6 +3057,7 @@ void QDeclarativeListView::itemsInserted(int modelIndex, int count) qreal tempPos = d->isRightToLeft() ? -d->position()-d->size() : d->position(); int index = d->visibleItems.count() ? d->mapFromModel(modelIndex) : 0; + if (index < 0) { int i = d->visibleItems.count() - 1; while (i > 0 && d->visibleItems.at(i)->index == -1) diff --git a/tests/auto/declarative/qdeclarativegridview/tst_qdeclarativegridview.cpp b/tests/auto/declarative/qdeclarativegridview/tst_qdeclarativegridview.cpp index 188fd6e..4fcaed6 100644 --- a/tests/auto/declarative/qdeclarativegridview/tst_qdeclarativegridview.cpp +++ b/tests/auto/declarative/qdeclarativegridview/tst_qdeclarativegridview.cpp @@ -1317,6 +1317,7 @@ void tst_QDeclarativeGridView::snapping() QDeclarativeContext *ctxt = canvas->rootContext(); ctxt->setContextProperty("testModel", &model); ctxt->setContextProperty("testTopToBottom", QVariant(false)); + ctxt->setContextProperty("testRightToLeft", QVariant(false)); canvas->setSource(QUrl::fromLocalFile(SRCDIR "/data/gridview1.qml")); qApp->processEvents(); @@ -1343,6 +1344,7 @@ void tst_QDeclarativeGridView::snapping() QCOMPARE(gridview->contentY(), 120.); delete canvas; + } void tst_QDeclarativeGridView::positionViewAtIndex_rightToLeft() diff --git a/tests/auto/declarative/qdeclarativelistview/tst_qdeclarativelistview.cpp b/tests/auto/declarative/qdeclarativelistview/tst_qdeclarativelistview.cpp index 26219fe..02c8dad 100644 --- a/tests/auto/declarative/qdeclarativelistview/tst_qdeclarativelistview.cpp +++ b/tests/auto/declarative/qdeclarativelistview/tst_qdeclarativelistview.cpp @@ -2332,7 +2332,7 @@ void tst_QDeclarativeListView::rightToLeft() item = findItem(contentItem, "item3"); QTRY_VERIFY(item); - QTRY_COMPARE(item->x(), -600.0); + QTRY_COMPARE(item->x(), -540.0); text = findItem(contentItem, "text3"); QTRY_VERIFY(text); -- cgit v0.12