summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDavid Faure <[email protected]>2025-06-27 13:01:58 +0200
committerDavid Faure <[email protected]>2025-06-30 17:40:07 +0200
commit729ee33a881cc4a829bacc75e323c3bedadf6f0e (patch)
tree5a48557d5236ad0f12935109b0d417919dfe32f3
parent1fed7005c5bc19a284ce394fea1d383388a5b366 (diff)
QIdentityProxyModel: call data() from subclasses in match()
The implementation of match() was only looking into the source model, without considering the fact that data() could be reimplemented in a QIdentityProxyModel subclass (a very common usage pattern for the class, part of the documentation). The simplest solution is to let the default implementation from QAbstractItemModel do matching the usual way, calling data(). Fixes: QTBUG-78013 Pick-to: 6.10 6.9 6.8 Change-Id: If984ffa5f8dbdfe9a76eaec8b82648d705cfecd4 Reviewed-by: Volker Hilsheimer <[email protected]>
-rw-r--r--src/corelib/itemmodels/qidentityproxymodel.cpp14
-rw-r--r--tests/auto/corelib/itemmodels/qidentityproxymodel/tst_qidentityproxymodel.cpp34
2 files changed, 35 insertions, 13 deletions
diff --git a/src/corelib/itemmodels/qidentityproxymodel.cpp b/src/corelib/itemmodels/qidentityproxymodel.cpp
index 1a97dd5b05d..afe4dca5071 100644
--- a/src/corelib/itemmodels/qidentityproxymodel.cpp
+++ b/src/corelib/itemmodels/qidentityproxymodel.cpp
@@ -197,19 +197,7 @@ QModelIndex QIdentityProxyModel::mapToSource(const QModelIndex& proxyIndex) cons
*/
QModelIndexList QIdentityProxyModel::match(const QModelIndex& start, int role, const QVariant& value, int hits, Qt::MatchFlags flags) const
{
- Q_D(const QIdentityProxyModel);
- Q_ASSERT(start.isValid() ? start.model() == this : true);
- if (!d->model)
- return QModelIndexList();
-
- const QModelIndexList sourceList = d->model->match(mapToSource(start), role, value, hits, flags);
- QModelIndexList::const_iterator it = sourceList.constBegin();
- const QModelIndexList::const_iterator end = sourceList.constEnd();
- QModelIndexList proxyList;
- proxyList.reserve(sourceList.size());
- for ( ; it != end; ++it)
- proxyList.append(mapFromSource(*it));
- return proxyList;
+ return QAbstractProxyModel::match(start, role, value, hits, flags);
}
/*!
diff --git a/tests/auto/corelib/itemmodels/qidentityproxymodel/tst_qidentityproxymodel.cpp b/tests/auto/corelib/itemmodels/qidentityproxymodel/tst_qidentityproxymodel.cpp
index c99242c927b..79d94c9b45c 100644
--- a/tests/auto/corelib/itemmodels/qidentityproxymodel/tst_qidentityproxymodel.cpp
+++ b/tests/auto/corelib/itemmodels/qidentityproxymodel/tst_qidentityproxymodel.cpp
@@ -67,6 +67,7 @@ private slots:
void testSetHandleLayoutChanges();
void testSetHandleDataChanges();
+ void matchCustomRole();
protected:
void verifyIdentity(QAbstractItemModel *model, const QModelIndex &parent = QModelIndex());
@@ -576,5 +577,38 @@ void tst_QIdentityProxyModel::testSetHandleDataChanges()
QVERIFY(!model.isConnected(signal));
}
+class CustomRoleProxyModel : public QIdentityProxyModel
+{
+public:
+ using QIdentityProxyModel::QIdentityProxyModel;
+
+ QVariant data(const QModelIndex &index, int role = Qt::DisplayRole) const override
+ {
+ Q_ASSERT(index.isValid());
+ if (role == Qt::UserRole)
+ return QStringLiteral("CustomUserData-%1").arg(index.row());
+ return QIdentityProxyModel::data(index, role);
+ }
+};
+
+void tst_QIdentityProxyModel::matchCustomRole()
+{
+ QStandardItemModel sourceModel;
+ for (int i = 0; i < 5; ++i)
+ sourceModel.appendRow(new QStandardItem(QString("Item %1").arg(i)));
+
+ CustomRoleProxyModel proxyModel;
+ proxyModel.setSourceModel(&sourceModel);
+
+ const QString targetValue = QStringLiteral("CustomUserData-3");
+
+ const QModelIndexList matches = proxyModel.match(proxyModel.index(0, 0), Qt::UserRole,
+ targetValue, 1, Qt::MatchExactly);
+
+ QCOMPARE(matches.size(), 1);
+ QCOMPARE(matches.first().row(), 3);
+ QCOMPARE(proxyModel.data(matches.first(), Qt::UserRole).toString(), targetValue);
+}
+
QTEST_MAIN(tst_QIdentityProxyModel)
#include "tst_qidentityproxymodel.moc"