aboutsummaryrefslogtreecommitdiffstats
path: root/src/qml/common
diff options
context:
space:
mode:
authorSami Shalayel <sami.shalayel@qt.io>2023-08-10 09:45:37 +0200
committerSami Shalayel <sami.shalayel@qt.io>2023-08-15 12:13:31 +0000
commita1ce0596e517e84913b14ab23422137c95b8c785 (patch)
treea7a012aa8a0d260c6f464c6b5dc722806697fa4c /src/qml/common
parent8d6f9e716d1c3fdd05ac14612583359313b9dc6e (diff)
Replace signal name manipulations with QQmlSignalNames
Remove custom implementations found in qqmljs* and use the static helper methods from qqmlsignalnames_p.h instead. This sometimes requires to move some code around to avoid bugs with property that do not have letters in their name. Add a warning in the JS implementation of the SignalSpy.qml that the used heuristic might fail on certain signal names. Add tests in in tst_qqmllanguage to see if the property change handlers work correctly for weird names. Change-Id: I4dc73c34df7f77f529511fa04ab5fcc5385b59fc Reviewed-by: Qt CI Bot <qt_ci_bot@qt-project.org> Reviewed-by: Fabian Kosmale <fabian.kosmale@qt.io>
Diffstat (limited to 'src/qml/common')
-rw-r--r--src/qml/common/qqmlsignalnames.cpp38
-rw-r--r--src/qml/common/qqmlsignalnames_p.h1
2 files changed, 29 insertions, 10 deletions
diff --git a/src/qml/common/qqmlsignalnames.cpp b/src/qml/common/qqmlsignalnames.cpp
index 5d46531dfb..96c4ee5ad7 100644
--- a/src/qml/common/qqmlsignalnames.cpp
+++ b/src/qml/common/qqmlsignalnames.cpp
@@ -14,10 +14,10 @@ using namespace Qt::Literals;
static std::optional<qsizetype> firstLetterIdx(QStringView name, qsizetype removePrefix = 0,
qsizetype removeSuffix = 0)
{
- auto result = std::find_if(std::next(name.cbegin(), removePrefix),
- std::prev(name.cend(), removeSuffix),
+ auto end = std::prev(name.cend(), removeSuffix);
+ auto result = std::find_if(std::next(name.cbegin(), removePrefix), end,
[](const QChar &c) { return c.isLetter(); });
- if (result != name.cend())
+ if (result != end)
return std::distance(name.begin(), result);
return {};
@@ -157,23 +157,41 @@ QString QQmlSignalNames::signalNameToHandlerName(QAnyStringView signal)
return handlerName;
}
-/*!
-\internal
-Returns a signal name from \a handlerName string.
-*/
-std::optional<QString> QQmlSignalNames::handlerNameToSignalName(QStringView handler)
+enum HandlerType { ChangedHandler, Handler };
+
+static std::optional<QString> handlerNameToSignalNameHelper(QStringView handler, HandlerType type)
{
- if (!isHandlerName(handler))
+ if (!QQmlSignalNames::isHandlerName(handler))
return {};
QString signalName = handler.sliced(strlen("on")).toString();
if (signalName.isEmpty())
return {};
- changeCaseOfFirstLetter(signalName, ToLower);
+ changeCaseOfFirstLetter(signalName, ToLower, 0, type == ChangedHandler ? strlen("Changed") : 0);
return signalName;
}
+/*!
+\internal
+Returns a signal name from \a handlerName string. Do not use it on changed handlers, see
+changedHandlerNameToSignalName for that!
+*/
+std::optional<QString> QQmlSignalNames::handlerNameToSignalName(QStringView handler)
+{
+ return handlerNameToSignalNameHelper(handler, Handler);
+}
+
+/*!
+\internal
+Returns a signal name from \a changedHandlerName string. Makes sure not to lowercase the 'C' from
+Changed.
+*/
+std::optional<QString> QQmlSignalNames::changedHandlerNameToSignalName(QStringView handler)
+{
+ return handlerNameToSignalNameHelper(handler, ChangedHandler);
+}
+
bool QQmlSignalNames::isChangedSignalName(QStringView signalName)
{
const qsizetype smallestAllowedSize = strlen("XChanged");
diff --git a/src/qml/common/qqmlsignalnames_p.h b/src/qml/common/qqmlsignalnames_p.h
index f777e89812..753f2ca97a 100644
--- a/src/qml/common/qqmlsignalnames_p.h
+++ b/src/qml/common/qqmlsignalnames_p.h
@@ -42,6 +42,7 @@ public:
static std::optional<QByteArray> changedHandlerNameToPropertyName(QUtf8StringView handler);
static std::optional<QString> handlerNameToSignalName(QStringView handler);
+ static std::optional<QString> changedHandlerNameToSignalName(QStringView changedHandler);
static bool isChangedHandlerName(QStringView signalName);
static bool isChangedSignalName(QStringView signalName);