diff options
author | Kent Hansen <[email protected]> | 2011-11-23 12:09:15 +0100 |
---|---|---|
committer | Qt by Nokia <[email protected]> | 2011-11-28 07:45:43 +0100 |
commit | f892f806124ea254449ee7bba75f5629d60559a8 (patch) | |
tree | 18f1c41d2f36d1d811281a61786a3da4262853eb | |
parent | 00909a4262671c685dc4f5f004746d39fdcf29ad (diff) |
qml debugger: Create abstraction for State management
State and PropertyChanges aren't part of the core qml types. The
(general-purpose) qml debugger shouldn't have to know those types;
they are only relevant when QtQuick (2.0) has been imported.
Introduce a delegate interface that performs State processing.
Implement a delegate for QtQuick 2, and install it when the QtQuick 2
module is imported.
Change-Id: I8af1157346ca9365eb0f7b99ccb71744d17fcebc
Reviewed-by: Aurindam Jana <[email protected]>
-rw-r--r-- | src/declarative/debugger/debugger.pri | 1 | ||||
-rw-r--r-- | src/declarative/debugger/qdeclarativedebugstatesdelegate_p.h | 99 | ||||
-rw-r--r-- | src/declarative/debugger/qdeclarativeenginedebugservice.cpp | 85 | ||||
-rw-r--r-- | src/declarative/debugger/qdeclarativeenginedebugservice_p.h | 9 | ||||
-rw-r--r-- | src/declarative/qtquick2.cpp | 130 |
5 files changed, 260 insertions, 64 deletions
diff --git a/src/declarative/debugger/debugger.pri b/src/declarative/debugger/debugger.pri index 4128771492..e5508a2bb2 100644 --- a/src/declarative/debugger/debugger.pri +++ b/src/declarative/debugger/debugger.pri @@ -21,6 +21,7 @@ HEADERS += \ $$PWD/qdeclarativedebughelper_p.h \ $$PWD/qdeclarativedebugserver_p.h \ $$PWD/qdeclarativedebugserverconnection_p.h \ + $$PWD/qdeclarativedebugstatesdelegate_p.h \ $$PWD/qdeclarativeinspectorservice_p.h \ $$PWD/qdeclarativeinspectorinterface_p.h \ $$PWD/qv8debugservice_p.h \ diff --git a/src/declarative/debugger/qdeclarativedebugstatesdelegate_p.h b/src/declarative/debugger/qdeclarativedebugstatesdelegate_p.h new file mode 100644 index 0000000000..0d70aa3755 --- /dev/null +++ b/src/declarative/debugger/qdeclarativedebugstatesdelegate_p.h @@ -0,0 +1,99 @@ +/**************************************************************************** +** +** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies). +** All rights reserved. +** Contact: Nokia Corporation ([email protected]) +** +** This file is part of the QtDeclarative module of the Qt Toolkit. +** +** $QT_BEGIN_LICENSE:LGPL$ +** GNU Lesser General Public License Usage +** This file may be used under the terms of the GNU Lesser General Public +** License version 2.1 as published by the Free Software Foundation and +** appearing in the file LICENSE.LGPL included in the packaging of this +** file. Please review the following information to ensure the GNU Lesser +** General Public License version 2.1 requirements will be met: +** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. +** +** In addition, as a special exception, Nokia gives you certain additional +** rights. These rights are described in the Nokia Qt LGPL Exception +** version 1.1, included in the file LGPL_EXCEPTION.txt in this package. +** +** GNU General Public License Usage +** Alternatively, this file may be used under the terms of the GNU General +** Public License version 3.0 as published by the Free Software Foundation +** and appearing in the file LICENSE.GPL included in the packaging of this +** file. Please review the following information to ensure the GNU General +** Public License version 3.0 requirements will be met: +** http://www.gnu.org/copyleft/gpl.html. +** +** Other Usage +** Alternatively, this file may be used in accordance with the terms and +** conditions contained in a signed written agreement between you and Nokia. +** +** +** +** +** +** $QT_END_LICENSE$ +** +****************************************************************************/ + +#ifndef QDECLARATIVEDEBUGSTATESDELEGATE_P_H +#define QDECLARATIVEDEBUGSTATESDELEGATE_P_H + +// +// W A R N I N G +// ------------- +// +// This file is not part of the Qt API. It exists purely as an +// implementation detail. This header file may change from version to +// version without notice, or even be removed. +// +// We mean it. +// + +#include <private/qdeclarativeglobal_p.h> + +QT_BEGIN_HEADER + +QT_BEGIN_NAMESPACE + +QT_MODULE(Declarative) + +class QDeclarativeContext; +class QDeclarativeProperty; +class QObject; +class QString; +class QVariant; + +class QDeclarativeDebugStatesDelegate +{ +protected: + QDeclarativeDebugStatesDelegate() {} + +public: + virtual ~QDeclarativeDebugStatesDelegate() {} + + virtual void buildStatesList(QDeclarativeContext *ctxt, bool cleanList) = 0; + virtual void updateBinding(QDeclarativeContext *context, + const QDeclarativeProperty &property, + const QVariant &expression, bool isLiteralValue, + const QString &fileName, int line, + bool *inBaseState) = 0; + virtual bool setBindingForInvalidProperty(QObject *object, + const QString &propertyName, + const QVariant &expression, + bool isLiteralValue) = 0; + virtual void resetBindingForInvalidProperty(QObject *object, + const QString &propertyName) = 0; + +private: + Q_DISABLE_COPY(QDeclarativeDebugStatesDelegate) +}; + +QT_END_NAMESPACE + +QT_END_HEADER + +#endif // QDECLARATIVEDEBUGSTATESDELEGATE_P_H diff --git a/src/declarative/debugger/qdeclarativeenginedebugservice.cpp b/src/declarative/debugger/qdeclarativeenginedebugservice.cpp index 501e60096b..f831929e57 100644 --- a/src/declarative/debugger/qdeclarativeenginedebugservice.cpp +++ b/src/declarative/debugger/qdeclarativeenginedebugservice.cpp @@ -41,6 +41,7 @@ #include "qdeclarativeenginedebugservice_p.h" +#include "qdeclarativedebugstatesdelegate_p.h" #include <private/qdeclarativeboundsignal_p.h> #include <qdeclarativeengine.h> #include <private/qdeclarativemetatype_p.h> @@ -52,7 +53,6 @@ #include <private/qdeclarativevaluetype_p.h> #include <private/qdeclarativevmemetaobject_p.h> #include <private/qdeclarativeexpression_p.h> -#include <private/qdeclarativepropertychanges_p.h> #include <QtCore/qdebug.h> #include <QtCore/qmetaobject.h> @@ -68,7 +68,8 @@ QDeclarativeEngineDebugService *QDeclarativeEngineDebugService::instance() QDeclarativeEngineDebugService::QDeclarativeEngineDebugService(QObject *parent) : QDeclarativeDebugService(QLatin1String("QDeclarativeEngine"), parent), - m_watch(new QDeclarativeWatcher(this)) + m_watch(new QDeclarativeWatcher(this)), + m_statesDelegate(0) { QObject::connect(m_watch, SIGNAL(propertyChanged(int,int,QMetaProperty,QVariant)), this, SLOT(propertyChanged(int,int,QMetaProperty,QVariant))); @@ -76,6 +77,11 @@ QDeclarativeEngineDebugService::QDeclarativeEngineDebugService(QObject *parent) registerService(); } +QDeclarativeEngineDebugService::~QDeclarativeEngineDebugService() +{ + delete m_statesDelegate; +} + QDataStream &operator<<(QDataStream &ds, const QDeclarativeEngineDebugService::QDeclarativeObjectData &data) { @@ -318,33 +324,10 @@ void QDeclarativeEngineDebugService::buildObjectList(QDataStream &message, QDecl } } -void QDeclarativeEngineDebugService::buildStatesList(QDeclarativeContext *ctxt, bool cleanList=false) +void QDeclarativeEngineDebugService::buildStatesList(QDeclarativeContext *ctxt, bool cleanList) { - if (cleanList) - m_allStates.clear(); - - QDeclarativeContextPrivate *ctxtPriv = QDeclarativeContextPrivate::get(ctxt); - for (int ii = 0; ii < ctxtPriv->instances.count(); ++ii) { - buildStatesList(ctxtPriv->instances.at(ii)); - } - - QDeclarativeContextData *child = QDeclarativeContextData::get(ctxt)->childContexts; - while (child) { - buildStatesList(child->asQDeclarativeContext()); - child = child->nextChild; - } -} - -void QDeclarativeEngineDebugService::buildStatesList(QObject *obj) -{ - if (QDeclarativeState *state = qobject_cast<QDeclarativeState *>(obj)) { - m_allStates.append(state); - } - - QObjectList children = obj->children(); - for (int ii = 0; ii < children.count(); ++ii) { - buildStatesList(children.at(ii)); - } + if (m_statesDelegate) + m_statesDelegate->buildStatesList(ctxt, cleanList); } QDeclarativeEngineDebugService::QDeclarativeObjectData @@ -567,27 +550,9 @@ void QDeclarativeEngineDebugService::setBinding(int objectId, if (property.isValid()) { bool inBaseState = true; - - foreach(QWeakPointer<QDeclarativeState> statePointer, m_allStates) { - if (QDeclarativeState *state = statePointer.data()) { - // here we assume that the revert list on itself defines the base state - if (state->isStateActive() && state->containsPropertyInRevertList(object, propertyName)) { - inBaseState = false; - - QDeclarativeBinding *newBinding = 0; - if (!isLiteralValue) { - newBinding = new QDeclarativeBinding(expression.toString(), object, context); - newBinding->setTarget(property); - newBinding->setNotifyOnValueChanged(true); - newBinding->setSourceLocation(filename, line); - } - - state->changeBindingInRevertList(object, propertyName, newBinding); - - if (isLiteralValue) - state->changeValueInRevertList(object, propertyName, expression); - } - } + if (m_statesDelegate) { + m_statesDelegate->updateBinding(context, property, expression, isLiteralValue, + filename, line, &inBaseState); } if (inBaseState) { @@ -613,15 +578,11 @@ void QDeclarativeEngineDebugService::setBinding(int objectId, } else { // not a valid property - if (QDeclarativePropertyChanges *propertyChanges = qobject_cast<QDeclarativePropertyChanges *>(object)) { - if (isLiteralValue) { - propertyChanges->changeValue(propertyName, expression); - } else { - propertyChanges->changeExpression(propertyName, expression.toString()); - } - } else { + bool ok = false; + if (m_statesDelegate) + ok = m_statesDelegate->setBindingForInvalidProperty(object, propertyName, expression, isLiteralValue); + if (!ok) qWarning() << "QDeclarativeEngineDebugService::setBinding: unable to set property" << propertyName << "on object" << object; - } } } } @@ -664,9 +625,8 @@ void QDeclarativeEngineDebugService::resetBinding(int objectId, const QString &p QDeclarativeProperty property(object, propertyName, context); QDeclarativePropertyPrivate::setSignalExpression(property, 0); } else { - if (QDeclarativePropertyChanges *propertyChanges = qobject_cast<QDeclarativePropertyChanges *>(object)) { - propertyChanges->removeProperty(propertyName); - } + if (m_statesDelegate) + m_statesDelegate->resetBindingForInvalidProperty(object, propertyName); } } } @@ -751,4 +711,9 @@ void QDeclarativeEngineDebugService::objectCreated(QDeclarativeEngine *engine, Q sendMessage(reply); } +void QDeclarativeEngineDebugService::setStatesDelegate(QDeclarativeDebugStatesDelegate *delegate) +{ + m_statesDelegate = delegate; +} + QT_END_NAMESPACE diff --git a/src/declarative/debugger/qdeclarativeenginedebugservice_p.h b/src/declarative/debugger/qdeclarativeenginedebugservice_p.h index d3e5c79297..7c74c63801 100644 --- a/src/declarative/debugger/qdeclarativeenginedebugservice_p.h +++ b/src/declarative/debugger/qdeclarativeenginedebugservice_p.h @@ -57,7 +57,6 @@ #include <QtCore/qurl.h> #include <QtCore/qvariant.h> -#include <QWeakPointer> QT_BEGIN_NAMESPACE @@ -65,13 +64,14 @@ class QDeclarativeEngine; class QDeclarativeContext; class QDeclarativeWatcher; class QDataStream; -class QDeclarativeState; +class QDeclarativeDebugStatesDelegate; class QDeclarativeEngineDebugService : public QDeclarativeDebugService { Q_OBJECT public: QDeclarativeEngineDebugService(QObject * = 0); + ~QDeclarativeEngineDebugService(); struct QDeclarativeObjectData { QUrl url; @@ -98,6 +98,8 @@ public: void remEngine(QDeclarativeEngine *); void objectCreated(QDeclarativeEngine *, QObject *); + void setStatesDelegate(QDeclarativeDebugStatesDelegate *); + static QDeclarativeEngineDebugService *instance(); protected: @@ -112,7 +114,6 @@ private: void buildObjectList(QDataStream &, QDeclarativeContext *); void buildObjectDump(QDataStream &, QObject *, bool, bool); void buildStatesList(QDeclarativeContext *, bool); - void buildStatesList(QObject *obj); QDeclarativeObjectData objectData(QObject *); QDeclarativeObjectProperty propertyData(QObject *, int); QVariant valueContents(const QVariant &defaultValue) const; @@ -122,7 +123,7 @@ private: QList<QDeclarativeEngine *> m_engines; QDeclarativeWatcher *m_watch; - QList<QWeakPointer<QDeclarativeState> > m_allStates; + QDeclarativeDebugStatesDelegate *m_statesDelegate; }; Q_DECLARATIVE_PRIVATE_EXPORT QDataStream &operator<<(QDataStream &, const QDeclarativeEngineDebugService::QDeclarativeObjectData &); Q_DECLARATIVE_PRIVATE_EXPORT QDataStream &operator>>(QDataStream &, QDeclarativeEngineDebugService::QDeclarativeObjectData &); diff --git a/src/declarative/qtquick2.cpp b/src/declarative/qtquick2.cpp index 64739b3547..72e3251dd8 100644 --- a/src/declarative/qtquick2.cpp +++ b/src/declarative/qtquick2.cpp @@ -46,8 +46,133 @@ #include <private/qquickitemsmodule_p.h> #include <private/qquickparticlesmodule_p.h> +#include <private/qdeclarativeenginedebugservice_p.h> +#include <private/qdeclarativedebugstatesdelegate_p.h> +#include <private/qdeclarativebinding_p.h> +#include <private/qdeclarativecontext_p.h> +#include <private/qdeclarativepropertychanges_p.h> +#include <private/qdeclarativestate_p.h> +#include <qdeclarativeproperty.h> +#include <QtCore/QWeakPointer> + QT_BEGIN_NAMESPACE +class QDeclarativeQtQuick2DebugStatesDelegate : public QDeclarativeDebugStatesDelegate +{ +public: + QDeclarativeQtQuick2DebugStatesDelegate(); + virtual ~QDeclarativeQtQuick2DebugStatesDelegate(); + virtual void buildStatesList(QDeclarativeContext *ctxt, bool cleanList); + virtual void updateBinding(QDeclarativeContext *context, + const QDeclarativeProperty &property, + const QVariant &expression, bool isLiteralValue, + const QString &fileName, int line, + bool *isBaseState); + virtual bool setBindingForInvalidProperty(QObject *object, + const QString &propertyName, + const QVariant &expression, + bool isLiteralValue); + virtual void resetBindingForInvalidProperty(QObject *object, + const QString &propertyName); + +private: + void buildStatesList(QObject *obj); + + QList<QWeakPointer<QDeclarativeState> > m_allStates; +}; + +QDeclarativeQtQuick2DebugStatesDelegate::QDeclarativeQtQuick2DebugStatesDelegate() +{ +} + +QDeclarativeQtQuick2DebugStatesDelegate::~QDeclarativeQtQuick2DebugStatesDelegate() +{ +} + +void QDeclarativeQtQuick2DebugStatesDelegate::buildStatesList(QDeclarativeContext *ctxt, bool cleanList) +{ + if (cleanList) + m_allStates.clear(); + + QDeclarativeContextPrivate *ctxtPriv = QDeclarativeContextPrivate::get(ctxt); + for (int ii = 0; ii < ctxtPriv->instances.count(); ++ii) { + buildStatesList(ctxtPriv->instances.at(ii)); + } + + QDeclarativeContextData *child = QDeclarativeContextData::get(ctxt)->childContexts; + while (child) { + buildStatesList(child->asQDeclarativeContext()); + child = child->nextChild; + } +} + +void QDeclarativeQtQuick2DebugStatesDelegate::buildStatesList(QObject *obj) +{ + if (QDeclarativeState *state = qobject_cast<QDeclarativeState *>(obj)) { + m_allStates.append(state); + } + + QObjectList children = obj->children(); + for (int ii = 0; ii < children.count(); ++ii) { + buildStatesList(children.at(ii)); + } +} + +void QDeclarativeQtQuick2DebugStatesDelegate::updateBinding(QDeclarativeContext *context, + const QDeclarativeProperty &property, + const QVariant &expression, bool isLiteralValue, + const QString &fileName, int line, + bool *inBaseState) +{ + QObject *object = property.object(); + QString propertyName = property.name(); + foreach (QWeakPointer<QDeclarativeState> statePointer, m_allStates) { + if (QDeclarativeState *state = statePointer.data()) { + // here we assume that the revert list on itself defines the base state + if (state->isStateActive() && state->containsPropertyInRevertList(object, propertyName)) { + *inBaseState = false; + + QDeclarativeBinding *newBinding = 0; + if (!isLiteralValue) { + newBinding = new QDeclarativeBinding(expression.toString(), object, context); + newBinding->setTarget(property); + newBinding->setNotifyOnValueChanged(true); + newBinding->setSourceLocation(fileName, line); + } + + state->changeBindingInRevertList(object, propertyName, newBinding); + + if (isLiteralValue) + state->changeValueInRevertList(object, propertyName, expression); + } + } + } +} + +bool QDeclarativeQtQuick2DebugStatesDelegate::setBindingForInvalidProperty(QObject *object, + const QString &propertyName, + const QVariant &expression, + bool isLiteralValue) +{ + if (QDeclarativePropertyChanges *propertyChanges = qobject_cast<QDeclarativePropertyChanges *>(object)) { + if (isLiteralValue) + propertyChanges->changeValue(propertyName, expression); + else + propertyChanges->changeExpression(propertyName, expression.toString()); + return true; + } else { + return false; + } +} + +void QDeclarativeQtQuick2DebugStatesDelegate::resetBindingForInvalidProperty(QObject *object, const QString &propertyName) +{ + if (QDeclarativePropertyChanges *propertyChanges = qobject_cast<QDeclarativePropertyChanges *>(object)) { + propertyChanges->removeProperty(propertyName); + } +} + + void QDeclarativeQtQuick2Module::defineModule() { QDeclarativeUtilModule::defineModule(); @@ -55,6 +180,11 @@ void QDeclarativeQtQuick2Module::defineModule() QQuickItemsModule::defineModule(); QQuickParticlesModule::defineModule(); QDeclarativeValueTypeFactory::registerValueTypes(); + + if (QDeclarativeEngineDebugService::isDebuggingEnabled()) { + QDeclarativeEngineDebugService::instance()->setStatesDelegate( + new QDeclarativeQtQuick2DebugStatesDelegate); + } } QT_END_NAMESPACE |