diff options
author | Tarja Sundqvist <tarja.sundqvist@qt.io> | 2023-04-24 16:43:14 +0300 |
---|---|---|
committer | Tarja Sundqvist <tarja.sundqvist@qt.io> | 2023-04-24 16:43:14 +0300 |
commit | 29400a683f96867133b28299c0d0bd6bcf40df35 (patch) | |
tree | b616dfb91ce111d61a34a67b28069561306575da /src/gui/accessible/qaccessible.cpp | |
parent | 42e4ae042a4c86e58bcb8b6d2d59ba4a988285b4 (diff) | |
parent | 9c60c8b122e5eb74fe74e11b929c30aa19ec0dd3 (diff) |
Merge remote-tracking branch 'origin/tqtc/lts-5.15.10' into tqtc/lts-5.15-opensourcev5.15.10-lts-lgpl
Change-Id: Ic1bb4240ca70a8a361fa0267476707446579221d
Diffstat (limited to 'src/gui/accessible/qaccessible.cpp')
-rw-r--r-- | src/gui/accessible/qaccessible.cpp | 29 |
1 files changed, 25 insertions, 4 deletions
diff --git a/src/gui/accessible/qaccessible.cpp b/src/gui/accessible/qaccessible.cpp index d0d46942fb..32d0e6ca91 100644 --- a/src/gui/accessible/qaccessible.cpp +++ b/src/gui/accessible/qaccessible.cpp @@ -54,6 +54,7 @@ #include <QtCore/qdebug.h> #include <QtCore/qloggingcategory.h> #include <QtCore/qmetaobject.h> +#include <QtCore/private/qmetaobject_p.h> #include <QtCore/qhash.h> #include <private/qfactoryloader_p.h> @@ -680,6 +681,25 @@ QAccessibleInterface *QAccessible::queryAccessibleInterface(QObject *object) // Create a QAccessibleInterface for the object class. Start by the most // derived class and walk up the class hierarchy. const QMetaObject *mo = object->metaObject(); + const auto *objectPriv = QObjectPrivate::get(object); + /* + We do not want to cache each and every QML metaobject (Button_QMLTYPE_124, + Button_QMLTYPE_125, etc.). Those dynamic metaobjects shouldn't have an + accessible interface in any case. Instead, we start the whole checking + with the first non-dynamic meta-object. To avoid potential regressions + in other areas of Qt that also use dynamic metaobjects, we only do this + for objects that are QML-related (approximated by checking whether they + have ddata set). + */ + const bool qmlRelated = !objectPriv->isDeletingChildren && + objectPriv->declarativeData; + while (qmlRelated && mo) { + auto mop = QMetaObjectPrivate::get(mo); + if (!mop || !(mop->flags & DynamicMetaObject)) + break; + + mo = mo->superClass(); + }; while (mo) { const QString cn = QLatin1String(mo->className()); @@ -695,14 +715,15 @@ QAccessibleInterface *QAccessible::queryAccessibleInterface(QObject *object) // Find a QAccessiblePlugin (factory) for the class name. If there's // no entry in the cache try to create it using the plugin loader. if (!qAccessiblePlugins()->contains(cn)) { + QAccessiblePlugin *factory = nullptr; // 0 means "no plugin found". This is cached as well. const int index = loader()->indexOf(cn); - if (index != -1) { - QAccessiblePlugin *factory = qobject_cast<QAccessiblePlugin *>(loader()->instance(index)); - qAccessiblePlugins()->insert(cn, factory); - } + if (index != -1) + factory = qobject_cast<QAccessiblePlugin *>(loader()->instance(index)); + qAccessiblePlugins()->insert(cn, factory); } // At this point the cache should contain a valid factory pointer or 0: + Q_ASSERT(qAccessiblePlugins()->contains(cn)); QAccessiblePlugin *factory = qAccessiblePlugins()->value(cn); if (factory) { QAccessibleInterface *result = factory->create(cn, object); |