diff options
Diffstat (limited to 'src/quick/items/qquicktableview.cpp')
| -rw-r--r-- | src/quick/items/qquicktableview.cpp | 94 |
1 files changed, 54 insertions, 40 deletions
diff --git a/src/quick/items/qquicktableview.cpp b/src/quick/items/qquicktableview.cpp index 390d246170..1b564df125 100644 --- a/src/quick/items/qquicktableview.cpp +++ b/src/quick/items/qquicktableview.cpp @@ -1011,32 +1011,26 @@ \qmlmethod real QtQuick::TableView::implicitColumnWidth(int column) \since 6.2 - Returns the implicit width of the given \a column. If the - column is not loaded (and therefore not visible), the return value - will be \c -1. + Returns the implicit width of the given \a column. This is the largest + \l implicitWidth found among the currently \l{isRowLoaded()}{loaded} + delegate items inside that column. - The implicit width of a column is the largest implicitWidth - found among the currently loaded delegate items inside that column. - Widths returned by the \l columnWidthProvider will not be taken - into account. + If the \a column is not loaded (and therefore not visible), the return value is \c -1. - \sa columnWidthProvider, columnWidth(), isColumnLoaded(), {Row heights and column widths} + \sa columnWidth(), isRowLoaded(), {Row heights and column widths} */ /*! \qmlmethod real QtQuick::TableView::implicitRowHeight(int row) \since 6.2 - Returns the implicit height of the given \a row. If the - row is not loaded (and therefore not visible), the return value - will be \c -1. + Returns the implicit height of the given \a row. This is the largest + \l implicitHeight found among the currently \l{isColumnLoaded()}{loaded} + delegate items inside that row. - The implicit height of a row is the largest implicitHeight - found among the currently loaded delegate items inside that row. - Heights returned by the \l rowHeightProvider will not be taken - into account. + If the \a row is not loaded (and therefore not visible), the return value is \c -1. - \sa rowHeightProvider, rowHeight(), isRowLoaded(), {Row heights and column widths} + \sa rowHeight(), isColumnLoaded(), {Row heights and column widths} */ /*! @@ -1202,13 +1196,15 @@ Convenience function for doing: \code - modelIndex(cell.y, cell.x) + index(cell.y, cell.x) \endcode A cell is simply a \l point that combines row and column into a single type. \note \c {point.x} will map to the column, and \c {point.y} will map to the row. + + \sa index() */ /*! @@ -2155,11 +2151,13 @@ void QQuickTableViewPrivate::updateExtents() const int nextTopRow = nextVisibleEdgeIndexAroundLoadedTable(Qt::TopEdge); const int nextBottomRow = nextVisibleEdgeIndexAroundLoadedTable(Qt::BottomEdge); + QPointF prevOrigin = origin; + QSizeF prevEndExtent = endExtent; + if (syncHorizontally) { const auto syncView_d = syncView->d_func(); origin.rx() = syncView_d->origin.x(); endExtent.rwidth() = syncView_d->endExtent.width(); - hData.markExtentsDirty(); } else if (nextLeftColumn == kEdgeIndexAtEnd) { // There are no more columns to load on the left side of the table. // In that case, we ensure that the origin match the beginning of the table. @@ -2176,7 +2174,6 @@ void QQuickTableViewPrivate::updateExtents() } } origin.rx() = loadedTableOuterRect.left(); - hData.markExtentsDirty(); } else if (loadedTableOuterRect.left() <= origin.x() + cellSpacing.width()) { // The table rect is at the origin, or outside, but we still have more // visible columns to the left. So we try to guesstimate how much space @@ -2186,7 +2183,6 @@ void QQuickTableViewPrivate::updateExtents() const qreal remainingSpacing = columnsRemaining * cellSpacing.width(); const qreal estimatedRemainingWidth = remainingColumnWidths + remainingSpacing; origin.rx() = loadedTableOuterRect.left() - estimatedRemainingWidth; - hData.markExtentsDirty(); } else if (nextRightColumn == kEdgeIndexAtEnd) { // There are no more columns to load on the right side of the table. // In that case, we ensure that the end of the content view match the end of the table. @@ -2204,7 +2200,6 @@ void QQuickTableViewPrivate::updateExtents() } } endExtent.rwidth() = loadedTableOuterRect.right() - q->contentWidth(); - hData.markExtentsDirty(); } else if (loadedTableOuterRect.right() >= q->contentWidth() + endExtent.width() - cellSpacing.width()) { // The right-most column is outside the end of the content view, and we // still have more visible columns in the model. This can happen if the application @@ -2215,14 +2210,12 @@ void QQuickTableViewPrivate::updateExtents() const qreal estimatedRemainingWidth = remainingColumnWidths + remainingSpacing; const qreal pixelsOutsideContentWidth = loadedTableOuterRect.right() - q->contentWidth(); endExtent.rwidth() = pixelsOutsideContentWidth + estimatedRemainingWidth; - hData.markExtentsDirty(); } if (syncVertically) { const auto syncView_d = syncView->d_func(); origin.ry() = syncView_d->origin.y(); endExtent.rheight() = syncView_d->endExtent.height(); - vData.markExtentsDirty(); } else if (nextTopRow == kEdgeIndexAtEnd) { // There are no more rows to load on the top side of the table. // In that case, we ensure that the origin match the beginning of the table. @@ -2239,7 +2232,6 @@ void QQuickTableViewPrivate::updateExtents() } } origin.ry() = loadedTableOuterRect.top(); - vData.markExtentsDirty(); } else if (loadedTableOuterRect.top() <= origin.y() + cellSpacing.height()) { // The table rect is at the origin, or outside, but we still have more // visible rows at the top. So we try to guesstimate how much space @@ -2249,7 +2241,6 @@ void QQuickTableViewPrivate::updateExtents() const qreal remainingSpacing = rowsRemaining * cellSpacing.height(); const qreal estimatedRemainingHeight = remainingRowHeights + remainingSpacing; origin.ry() = loadedTableOuterRect.top() - estimatedRemainingHeight; - vData.markExtentsDirty(); } else if (nextBottomRow == kEdgeIndexAtEnd) { // There are no more rows to load on the bottom side of the table. // In that case, we ensure that the end of the content view match the end of the table. @@ -2267,7 +2258,6 @@ void QQuickTableViewPrivate::updateExtents() } } endExtent.rheight() = loadedTableOuterRect.bottom() - q->contentHeight(); - vData.markExtentsDirty(); } else if (loadedTableOuterRect.bottom() >= q->contentHeight() + endExtent.height() - cellSpacing.height()) { // The bottom-most row is outside the end of the content view, and we // still have more visible rows in the model. This can happen if the application @@ -2278,7 +2268,6 @@ void QQuickTableViewPrivate::updateExtents() const qreal estimatedRemainingHeight = remainingRowHeigts + remainingSpacing; const qreal pixelsOutsideContentHeight = loadedTableOuterRect.bottom() - q->contentHeight(); endExtent.rheight() = pixelsOutsideContentHeight + estimatedRemainingHeight; - vData.markExtentsDirty(); } if (tableMovedHorizontally || tableMovedVertically) { @@ -2299,12 +2288,23 @@ void QQuickTableViewPrivate::updateExtents() } } - if (hData.minExtentDirty || vData.minExtentDirty) { - qCDebug(lcTableViewDelegateLifecycle) << "move origin and endExtent to:" << origin << endExtent; + if (prevOrigin != origin || prevEndExtent != endExtent) { + if (prevOrigin != origin) + qCDebug(lcTableViewDelegateLifecycle) << "move origin to:" << origin; + if (prevEndExtent != endExtent) + qCDebug(lcTableViewDelegateLifecycle) << "move endExtent to:" << endExtent; // updateBeginningEnd() will let the new extents take effect. This will also change the // visualArea of the flickable, which again will cause any attached scrollbars to adjust // the position of the handle. Note the latter will cause the viewport to move once more. + hData.markExtentsDirty(); + vData.markExtentsDirty(); updateBeginningEnd(); + if (!q->isMoving()) { + // When we adjust the extents, the viewport can sometimes be left suspended in an + // overshooted state. It will bounce back again once the user clicks inside the + // viewport. But this comes across as a bug, so returnToBounds explicitly. + q->returnToBounds(); + } } } @@ -4318,11 +4318,18 @@ void QQuickTableViewPrivate::syncSyncView() q->setRightMargin(syncView->rightMargin()); updateContentWidth(); - if (syncView->leftColumn() != q->leftColumn()) { - // The left column is no longer the same as the left - // column in syncView. This requires a rebuild. - scheduledRebuildOptions |= QQuickTableViewPrivate::RebuildOption::CalculateNewTopLeftColumn; - scheduledRebuildOptions.setFlag(RebuildOption::ViewportOnly); + if (scheduledRebuildOptions & RebuildOption::LayoutOnly) { + if (syncView->leftColumn() != q->leftColumn() + || syncView->d_func()->loadedTableOuterRect.left() != loadedTableOuterRect.left()) { + // The left column is no longer the same, or at the same pos, as the left column in + // syncView. This can happen if syncView did a relayout that caused its left column + // to be resized so small that it ended up outside the viewport. It can also happen + // if the syncView loaded and unloaded columns after the relayout. We therefore need + // to sync our own left column and pos to be the same, which we do by rebuilding the + // whole viewport instead of just doing a plain LayoutOnly. + scheduledRebuildOptions |= QQuickTableViewPrivate::RebuildOption::CalculateNewTopLeftColumn; + scheduledRebuildOptions.setFlag(RebuildOption::ViewportOnly); + } } } @@ -4333,11 +4340,18 @@ void QQuickTableViewPrivate::syncSyncView() q->setBottomMargin(syncView->bottomMargin()); updateContentHeight(); - if (syncView->topRow() != q->topRow()) { - // The top row is no longer the same as the top - // row in syncView. This requires a rebuild. - scheduledRebuildOptions |= QQuickTableViewPrivate::RebuildOption::CalculateNewTopLeftRow; - scheduledRebuildOptions.setFlag(RebuildOption::ViewportOnly); + if (scheduledRebuildOptions & RebuildOption::LayoutOnly) { + if (syncView->topRow() != q->topRow() + || syncView->d_func()->loadedTableOuterRect.top() != loadedTableOuterRect.top()) { + // The top row is no longer the same, or at the same pos, as the top row in + // syncView. This can happen if syncView did a relayout that caused its top row + // to be resized so small that it ended up outside the viewport. It can also happen + // if the syncView loaded and unloaded rows after the relayout. We therefore need + // to sync our own top row and pos to be the same, which we do by rebuilding the + // whole viewport instead of just doing a plain LayoutOnly. + scheduledRebuildOptions |= QQuickTableViewPrivate::RebuildOption::CalculateNewTopLeftRow; + scheduledRebuildOptions.setFlag(RebuildOption::ViewportOnly); + } } } @@ -4724,7 +4738,7 @@ void QQuickTableViewPrivate::syncViewportRect() auto syncChild_d = syncChild->d_func(); if (syncChild_d->syncHorizontally) w = qMax(w, syncChild->width()); - if (syncChild_d->syncHorizontally) + if (syncChild_d->syncVertically) h = qMax(h, syncChild->height()); } |
