From 66f8b97f5ea4a8d196f908fae78d2b68cfab32cf Mon Sep 17 00:00:00 2001 From: Ulf Hermann Date: Tue, 12 Dec 2017 14:35:13 +0100 Subject: QQmlEngineDebugService: Actually call value types' toString() method QML value types generally are Q_GADGETs, but the userType we see there is the wrapped class's type, which doesn't have to be a gadget. So, the toString() method was rarely called, and a model index would still crash the debug service. Change-Id: I63778953eb9d2fc60113c11057da3047fc75a9bd Reviewed-by: Simon Hausmann --- .../qmldbg_debugger/qqmlenginedebugservice.cpp | 19 +++++++++++++++---- 1 file changed, 15 insertions(+), 4 deletions(-) (limited to 'src/plugins/qmltooling') diff --git a/src/plugins/qmltooling/qmldbg_debugger/qqmlenginedebugservice.cpp b/src/plugins/qmltooling/qmldbg_debugger/qqmlenginedebugservice.cpp index d2cf7dc57f..cbce99956d 100644 --- a/src/plugins/qmltooling/qmldbg_debugger/qqmlenginedebugservice.cpp +++ b/src/plugins/qmltooling/qmldbg_debugger/qqmlenginedebugservice.cpp @@ -209,19 +209,30 @@ QVariant QQmlEngineDebugServiceImpl::valueContents(QVariant value) const } if (QQmlValueTypeFactory::isValueType(userType)) { + switch (userType) { + case QMetaType::QRect: + case QMetaType::QRectF: + case QMetaType::QPoint: + case QMetaType::QPointF: + case QMetaType::QFont: + // Don't call the toString() method on those. The stream operators are better. + return value; + default: + break; + } + const QMetaObject *mo = QQmlValueTypeFactory::metaObjectForMetaType(userType); if (mo) { - int toStringIndex = mo->indexOfMethod("toString"); + int toStringIndex = mo->indexOfMethod("toString()"); if (toStringIndex != -1) { QMetaMethod mm = mo->method(toStringIndex); - QMetaType info(userType); QString s; - if (info.flags() & QMetaType::IsGadget - && mm.invokeOnGadget(value.data(), Q_RETURN_ARG(QString, s))) + if (mm.invokeOnGadget(value.data(), Q_RETURN_ARG(QString, s))) return s; } } + // We expect all QML value types to either have a toString() method or stream operators return value; } -- cgit v1.2.3 From 228790f27a4cb8f4f307693fb1c9f13a96eddfaa Mon Sep 17 00:00:00 2001 From: Ulf Hermann Date: Mon, 15 Jan 2018 12:28:09 +0100 Subject: QQmlProfilerService: Only send "Complete" if no more engines are running Also, make sure to report all engine's events when stopping one. Otherwise the timestamps will reset when reporting multiple engines in a row (such as when stopping the application). Task-number: QTBUG-65767 Change-Id: I0a6a9170069318dd5b8a7422cb7e248c87d5adce Reviewed-by: Michael Brasser --- .../qmldbg_profiler/qqmlprofilerservice.cpp | 32 ++++++++++++++-------- 1 file changed, 20 insertions(+), 12 deletions(-) (limited to 'src/plugins/qmltooling') diff --git a/src/plugins/qmltooling/qmldbg_profiler/qqmlprofilerservice.cpp b/src/plugins/qmltooling/qmldbg_profiler/qqmlprofilerservice.cpp index 4176ede40e..affd2a417e 100644 --- a/src/plugins/qmltooling/qmldbg_profiler/qqmlprofilerservice.cpp +++ b/src/plugins/qmltooling/qmldbg_profiler/qqmlprofilerservice.cpp @@ -296,10 +296,11 @@ void QQmlProfilerServiceImpl::stopProfiling(QJSEngine *engine) for (QMultiHash::iterator i(m_engineProfilers.begin()); i != m_engineProfilers.end(); ++i) { if (i.value()->isRunning()) { + m_startTimes.insert(-1, i.value()); if (engine == 0 || i.key() == engine) { - m_startTimes.insert(-1, i.value()); stopping << i.value(); } else { + reporting << i.value(); stillRunning = true; } } @@ -368,25 +369,32 @@ void QQmlProfilerServiceImpl::sendMessages() } } + bool stillRunning = false; + for (const QQmlAbstractProfilerAdapter *profiler : qAsConst(m_engineProfilers)) { + if (profiler->isRunning()) { + stillRunning = true; + break; + } + } + if (m_waitingForStop) { - //indicate completion + // EndTrace can be sent multiple times, as it's engine specific. messages << traceEnd.data(); - QQmlDebugPacket ds; - ds << (qint64)-1 << (int)Complete; - messages << ds.data(); - m_waitingForStop = false; + if (!stillRunning) { + // Complete is only sent once, when no engines are running anymore. + QQmlDebugPacket ds; + ds << (qint64)-1 << (int)Complete; + messages << ds.data(); + m_waitingForStop = false; + } } emit messagesToClient(name(), messages); // Restart flushing if any profilers are still running - for (const QQmlAbstractProfilerAdapter *profiler : qAsConst(m_engineProfilers)) { - if (profiler->isRunning()) { - emit startFlushTimer(); - break; - } - } + if (stillRunning) + emit startFlushTimer(); } void QQmlProfilerServiceImpl::stateAboutToBeChanged(QQmlDebugService::State newState) -- cgit v1.2.3 From de3605a53db7fb3119615ffe5e8485ebe985e5db Mon Sep 17 00:00:00 2001 From: Ulf Hermann Date: Tue, 16 Jan 2018 17:02:44 +0100 Subject: QQmlEngineDebugService: Use native stream operators for QSize and QSizeF Those are better than toString() as they preserve the actual value. Change-Id: If156b800e48ae9f51f519dadcb75dff4148fc8cb Reviewed-by: Simon Hausmann --- src/plugins/qmltooling/qmldbg_debugger/qqmlenginedebugservice.cpp | 2 ++ 1 file changed, 2 insertions(+) (limited to 'src/plugins/qmltooling') diff --git a/src/plugins/qmltooling/qmldbg_debugger/qqmlenginedebugservice.cpp b/src/plugins/qmltooling/qmldbg_debugger/qqmlenginedebugservice.cpp index cbce99956d..d2934ba034 100644 --- a/src/plugins/qmltooling/qmldbg_debugger/qqmlenginedebugservice.cpp +++ b/src/plugins/qmltooling/qmldbg_debugger/qqmlenginedebugservice.cpp @@ -214,6 +214,8 @@ QVariant QQmlEngineDebugServiceImpl::valueContents(QVariant value) const case QMetaType::QRectF: case QMetaType::QPoint: case QMetaType::QPointF: + case QMetaType::QSize: + case QMetaType::QSizeF: case QMetaType::QFont: // Don't call the toString() method on those. The stream operators are better. return value; -- cgit v1.2.3