Uploaded image for project: 'Qt'
  1. Qt
  2. QTBUG-58580

QTableView is slow when receiving a dataChanged where topLeft != bottomRight

    XMLWordPrintable

Details

    • Bug
    • Resolution: Done
    • P3: Somewhat important
    • None
    • 5.6.0, 5.7.0, 5.7.1, 5.8.0
    • Widgets: Itemviews
    • None
    • 8de62d34321cd827e60b0a7b6e7434070de301ae (qt/qtbase/dev)

    Description

      If the topLeft index and bottomRight index received by the dataChanged slot in QAbstractItemView do not match then entire view is repainted rather than just the changed cells, if they do match only one the changed cell is repainted.

      qabstractitemview.cpp
      void QAbstractItemView::dataChanged(const QModelIndex &topLeft, const QModelIndex &bottomRight, const QVector<int> &roles)
      {
      ...
          if (topLeft == bottomRight && topLeft.isValid()) {
      
      ...
      
              if (isVisible() && !d->delayedPendingLayout) {
                  // otherwise the items will be update later anyway
                  update(topLeft);
              }
          } else {
      
      ...
      
              if (isVisible() && !d->delayedPendingLayout)
                  d->viewport->update();
          }
      }
      

      With a model containing around 200 rows and 50 columns, receiving approximately 10 updates a second where multiple adjacent columns on the same row were changing I was seeing a CPU load of 50%, when the QTableView was open, by changing the model to emit individual dataChanged calls even when all items are adjacent this load dropped to 5%.

      Subclassing QTableView and implementing the following override also had the same effect.

      void MyTableView::dataChanged(const QModelIndex &topLeft, const QModelIndex &bottomRight, const QVector<int> &roles)
      {
          for(int row=topLeft.row(); row <= bottomRight.row(); ++row)
          {
              for(int column=topLeft.column(); column <= bottomRight.column(); ++column)
              {
                  QModelIndex index = topLeft.sibling(row, column);
                  QTableView::dataChanged(index, index, roles);
              }
          }
      }
      

      This issue should impact QListView and QTreeView as well.

      Attachments

        For Gerrit Dashboard: QTBUG-58580
        # Subject Branch Project Status CR V

        Activity

          People

            qt.team.quick.subscriptions Qt Quick and Widgets Team
            jtjbrady Jonathan Brady
            Votes:
            2 Vote for this issue
            Watchers:
            7 Start watching this issue

            Dates

              Created:
              Updated:
              Resolved:

              Gerrit Reviews

                There are no open Gerrit changes