forked from qt-creator/qt-creator
Readded the QmlJS client proxy.
This commit is contained in:
301
src/plugins/qmljsinspector/qmljsclientproxy.cpp
Normal file
301
src/plugins/qmljsinspector/qmljsclientproxy.cpp
Normal file
@@ -0,0 +1,301 @@
|
||||
#include "qmljsclientproxy.h"
|
||||
#include "qmljsdebuggerclient.h"
|
||||
|
||||
#include <utils/qtcassert.h>
|
||||
|
||||
#include <private/qdeclarativedebug_p.h>
|
||||
#include <private/qdeclarativedebugclient_p.h>
|
||||
|
||||
#include <QUrl>
|
||||
#include <QAbstractSocket>
|
||||
#include <QDebug>
|
||||
|
||||
using namespace QmlJSInspector::Internal;
|
||||
|
||||
ClientProxy *ClientProxy::m_instance = 0;
|
||||
|
||||
ClientProxy::ClientProxy(QObject *parent) :
|
||||
QObject(parent),
|
||||
m_conn(0),
|
||||
m_client(0),
|
||||
m_engineQuery(0),
|
||||
m_contextQuery(0),
|
||||
m_objectTreeQuery(0),
|
||||
m_debuggerRunControl(0)
|
||||
{
|
||||
m_instance = this;
|
||||
}
|
||||
|
||||
ClientProxy *ClientProxy::instance()
|
||||
{
|
||||
return m_instance;
|
||||
}
|
||||
|
||||
bool ClientProxy::connectToViewer(const QString &host, quint16 port)
|
||||
{
|
||||
if (m_conn && m_conn->state() != QAbstractSocket::UnconnectedState)
|
||||
return false;
|
||||
|
||||
qDebug() << Q_FUNC_INFO;
|
||||
if (m_client) {
|
||||
disconnect(m_client, SIGNAL(propertyDumpReceived(QDeclarativeDebugPropertyDump)),
|
||||
this, SIGNAL(propertyDumpReceived(QDeclarativeDebugPropertyDump)));
|
||||
disconnect(m_client, SIGNAL(selectedItemsChanged(QList<QDeclarativeDebugObjectReference>)),
|
||||
this, SIGNAL(selectedItemsChanged(QList<QDeclarativeDebugObjectReference>)));
|
||||
|
||||
emit aboutToDisconnect();
|
||||
|
||||
delete m_client; m_client = 0;
|
||||
}
|
||||
|
||||
if (m_conn) {
|
||||
m_conn->disconnectFromHost();
|
||||
delete m_conn;
|
||||
m_conn = 0;
|
||||
}
|
||||
|
||||
m_conn = new QDeclarativeDebugConnection(this);
|
||||
connect(m_conn, SIGNAL(stateChanged(QAbstractSocket::SocketState)),
|
||||
SLOT(connectionStateChanged()));
|
||||
connect(m_conn, SIGNAL(error(QAbstractSocket::SocketError)),
|
||||
SLOT(connectionError()));
|
||||
|
||||
emit connectionStatusMessage(tr("[Inspector] set to connect to debug server %1:%2").arg(host).arg(port));
|
||||
m_conn->connectToHost(host, port);
|
||||
|
||||
|
||||
// blocks until connected; if no connection is available, will fail immediately
|
||||
if (!m_conn->waitForConnected())
|
||||
return false;
|
||||
|
||||
// ### commented out as the code resulted in asserts
|
||||
// QTC_ASSERT(m_debuggerRunControl, return false);
|
||||
// Debugger::Internal::QmlEngine *engine = qobject_cast<Debugger::Internal::QmlEngine *>(m_debuggerRunControl->engine());
|
||||
// QTC_ASSERT(engine, return false);
|
||||
// (void) new DebuggerClient(m_conn, engine);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void ClientProxy::disconnectFromViewer()
|
||||
{
|
||||
m_conn->disconnectFromHost();
|
||||
emit disconnected();
|
||||
}
|
||||
|
||||
void ClientProxy::connectionError()
|
||||
{
|
||||
emit connectionStatusMessage(tr("[Inspector] error: (%1) %2", "%1=error code, %2=error message")
|
||||
.arg(m_conn->error()).arg(m_conn->errorString()));
|
||||
}
|
||||
|
||||
void ClientProxy::connectionStateChanged()
|
||||
{
|
||||
switch (m_conn->state()) {
|
||||
case QAbstractSocket::UnconnectedState:
|
||||
{
|
||||
emit connectionStatusMessage(tr("[Inspector] disconnected.\n\n"));
|
||||
|
||||
delete m_engineQuery;
|
||||
m_engineQuery = 0;
|
||||
delete m_contextQuery;
|
||||
m_contextQuery = 0;
|
||||
|
||||
if (m_objectTreeQuery) {
|
||||
delete m_objectTreeQuery;
|
||||
m_objectTreeQuery = 0;
|
||||
}
|
||||
|
||||
emit disconnected();
|
||||
|
||||
break;
|
||||
}
|
||||
case QAbstractSocket::HostLookupState:
|
||||
emit connectionStatusMessage(tr("[Inspector] resolving host..."));
|
||||
break;
|
||||
case QAbstractSocket::ConnectingState:
|
||||
emit connectionStatusMessage(tr("[Inspector] connecting to debug server..."));
|
||||
break;
|
||||
case QAbstractSocket::ConnectedState:
|
||||
{
|
||||
emit connectionStatusMessage(tr("[Inspector] connected.\n"));
|
||||
|
||||
if (!m_client) {
|
||||
qDebug() << "CREATING ENGINE";
|
||||
m_client = new QDeclarativeEngineDebug(m_conn, this);
|
||||
emit connected(m_client);
|
||||
|
||||
connect(m_client,
|
||||
SIGNAL(propertyDumpReceived(QDeclarativeDebugPropertyDump)),
|
||||
SIGNAL(propertyDumpReceived(QDeclarativeDebugPropertyDump)));
|
||||
connect(m_client,
|
||||
SIGNAL(selectedItemsChanged(QList<QDeclarativeDebugObjectReference>)),
|
||||
SIGNAL(selectedItemsChanged(QList<QDeclarativeDebugObjectReference>)));
|
||||
}
|
||||
|
||||
reloadEngines();
|
||||
|
||||
break;
|
||||
}
|
||||
case QAbstractSocket::ClosingState:
|
||||
emit connectionStatusMessage(tr("[Inspector] closing..."));
|
||||
break;
|
||||
case QAbstractSocket::BoundState:
|
||||
case QAbstractSocket::ListeningState:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
bool ClientProxy::isConnected() const
|
||||
{
|
||||
return (m_conn && m_client && m_conn->state() == QAbstractSocket::ConnectedState);
|
||||
}
|
||||
|
||||
bool ClientProxy::isUnconnected() const
|
||||
{
|
||||
return (!m_conn || m_conn->state() == QAbstractSocket::UnconnectedState);
|
||||
}
|
||||
|
||||
void ClientProxy::setSelectedItemByObjectId(int engineId, const QDeclarativeDebugObjectReference &objectRef)
|
||||
{
|
||||
qDebug() << "TODO:" << Q_FUNC_INFO;
|
||||
#if 0
|
||||
if (isConnected())
|
||||
m_client->setSelectedItemByObjectId(engineId, objectRef);
|
||||
#endif
|
||||
}
|
||||
|
||||
QList<QDeclarativeDebugObjectReference> ClientProxy::objectReferences(const QUrl &url) const
|
||||
{
|
||||
return objectReferences(url, m_rootObject);
|
||||
}
|
||||
|
||||
QList<QDeclarativeDebugObjectReference> ClientProxy::objectReferences(const QUrl &url,
|
||||
const QDeclarativeDebugObjectReference &objectRef) const
|
||||
{
|
||||
QList<QDeclarativeDebugObjectReference> result;
|
||||
if (objectRef.source().url() == url)
|
||||
result.append(objectRef);
|
||||
|
||||
foreach(const QDeclarativeDebugObjectReference &child, objectRef.children()) {
|
||||
result.append(objectReferences(url, child));
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
QDeclarativeDebugExpressionQuery *ClientProxy::setBindingForObject(int objectDebugId,
|
||||
const QString &propertyName,
|
||||
const QVariant &value,
|
||||
bool isLiteralValue)
|
||||
{
|
||||
qDebug() << "TODO:" << Q_FUNC_INFO;
|
||||
#if 0
|
||||
if (propertyName == QLatin1String("id") || objectDebugId == -1)
|
||||
return 0;
|
||||
|
||||
qDebug() << "executeBinding():" << objectDebugId << propertyName << value << "isLiteral:" << isLiteralValue;
|
||||
|
||||
return m_client->setBindingForObject(objectDebugId, propertyName, value.toString(), isLiteralValue, 0);
|
||||
#else
|
||||
return 0;
|
||||
#endif
|
||||
}
|
||||
|
||||
void ClientProxy::queryEngineContext(int id)
|
||||
{
|
||||
if (id < 0)
|
||||
return;
|
||||
|
||||
if (m_contextQuery) {
|
||||
delete m_contextQuery;
|
||||
m_contextQuery = 0;
|
||||
}
|
||||
|
||||
m_contextQuery = m_client->queryRootContexts(QDeclarativeDebugEngineReference(id), this);
|
||||
if (!m_contextQuery->isWaiting())
|
||||
contextChanged();
|
||||
else
|
||||
QObject::connect(m_contextQuery, SIGNAL(stateChanged(QDeclarativeDebugQuery::State)),
|
||||
this, SLOT(contextChanged()));
|
||||
}
|
||||
|
||||
void ClientProxy::contextChanged()
|
||||
{
|
||||
if (m_contextQuery) {
|
||||
|
||||
if (m_contextQuery->rootContext().objects().isEmpty()) {
|
||||
m_rootObject = QDeclarativeDebugObjectReference();
|
||||
emit objectTreeUpdated(m_rootObject);
|
||||
} else {
|
||||
m_rootObject = m_contextQuery->rootContext().objects().first();
|
||||
}
|
||||
|
||||
delete m_contextQuery; m_contextQuery = 0;
|
||||
|
||||
m_objectTreeQuery = m_client->queryObjectRecursive(m_rootObject, this);
|
||||
if (!m_objectTreeQuery->isWaiting()) {
|
||||
objectTreeFetched();
|
||||
} else {
|
||||
connect(m_objectTreeQuery,
|
||||
SIGNAL(stateChanged(QDeclarativeDebugQuery::State)),
|
||||
SLOT(objectTreeFetched(QDeclarativeDebugQuery::State)));
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
void ClientProxy::objectTreeFetched(QDeclarativeDebugQuery::State state)
|
||||
{
|
||||
if (state != QDeclarativeDebugQuery::Completed) {
|
||||
m_rootObject = QDeclarativeDebugObjectReference();
|
||||
return;
|
||||
}
|
||||
|
||||
m_rootObject = m_objectTreeQuery->object();
|
||||
|
||||
delete m_objectTreeQuery;
|
||||
m_objectTreeQuery = 0;
|
||||
|
||||
emit objectTreeUpdated(m_rootObject);
|
||||
}
|
||||
|
||||
void ClientProxy::reloadQmlViewer(int engineId)
|
||||
{
|
||||
qDebug() << "TODO:" << Q_FUNC_INFO;
|
||||
#if 0
|
||||
if (m_client && m_conn->isConnected()) {
|
||||
m_client->reloadQmlViewer(engineId);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
void ClientProxy::reloadEngines()
|
||||
{
|
||||
if (m_engineQuery) {
|
||||
emit connectionStatusMessage("[Inspector] Waiting for response to previous engine query");
|
||||
return;
|
||||
}
|
||||
|
||||
emit aboutToReloadEngines();
|
||||
|
||||
m_engineQuery = m_client->queryAvailableEngines(this);
|
||||
if (!m_engineQuery->isWaiting())
|
||||
updateEngineList();
|
||||
else
|
||||
QObject::connect(m_engineQuery, SIGNAL(stateChanged(QDeclarativeDebugQuery::State)),
|
||||
this, SLOT(updateEngineList()));
|
||||
}
|
||||
|
||||
QList<QDeclarativeDebugEngineReference> ClientProxy::engines() const
|
||||
{
|
||||
return m_engines;
|
||||
}
|
||||
|
||||
void ClientProxy::updateEngineList()
|
||||
{
|
||||
m_engines = m_engineQuery->engines();
|
||||
delete m_engineQuery; m_engineQuery = 0;
|
||||
|
||||
emit enginesChanged();
|
||||
}
|
||||
101
src/plugins/qmljsinspector/qmljsclientproxy.h
Normal file
101
src/plugins/qmljsinspector/qmljsclientproxy.h
Normal file
@@ -0,0 +1,101 @@
|
||||
#ifndef QMLJSCLIENTPROXY_H
|
||||
#define QMLJSCLIENTPROXY_H
|
||||
|
||||
#include "qmljsinspectorplugin.h"
|
||||
|
||||
#include <private/qdeclarativedebug_p.h>
|
||||
#include <QObject>
|
||||
|
||||
QT_FORWARD_DECLARE_CLASS(QUrl)
|
||||
QT_FORWARD_DECLARE_CLASS(QDeclarativeEngineDebug)
|
||||
QT_FORWARD_DECLARE_CLASS(QDeclarativeDebugConnection)
|
||||
QT_FORWARD_DECLARE_CLASS(QDeclarativeDebugExpressionQuery)
|
||||
QT_FORWARD_DECLARE_CLASS(QDeclarativeDebugPropertyDump)
|
||||
|
||||
namespace Debugger {
|
||||
class DebuggerRunControl;
|
||||
}
|
||||
|
||||
namespace QmlJSInspector {
|
||||
namespace Internal {
|
||||
|
||||
class QmlInspectorPlugin;
|
||||
|
||||
class ClientProxy : public QObject
|
||||
{
|
||||
Q_OBJECT
|
||||
|
||||
public:
|
||||
static ClientProxy *instance();
|
||||
QDeclarativeDebugExpressionQuery *setBindingForObject(int objectDebugId,
|
||||
const QString &propertyName,
|
||||
const QVariant &value,
|
||||
bool isLiteralValue);
|
||||
|
||||
// returns the object references for the given url.
|
||||
QList<QDeclarativeDebugObjectReference> objectReferences(const QUrl &url) const;
|
||||
|
||||
bool isConnected() const;
|
||||
bool isUnconnected() const;
|
||||
|
||||
void setSelectedItemByObjectId(int engineId, const QDeclarativeDebugObjectReference &objectRef);
|
||||
|
||||
bool connectToViewer(const QString &host, quint16 port);
|
||||
void disconnectFromViewer();
|
||||
|
||||
QList<QDeclarativeDebugEngineReference> engines() const;
|
||||
|
||||
signals:
|
||||
void objectTreeUpdated(const QDeclarativeDebugObjectReference &rootObject);
|
||||
void connectionStatusMessage(const QString &text);
|
||||
|
||||
void aboutToReloadEngines();
|
||||
void enginesChanged();
|
||||
|
||||
void propertyDumpReceived(const QDeclarativeDebugPropertyDump &propertyDump);
|
||||
void selectedItemsChanged(const QList<QDeclarativeDebugObjectReference> &selectedItems);
|
||||
|
||||
void connected(QDeclarativeEngineDebug *client);
|
||||
void aboutToDisconnect();
|
||||
void disconnected();
|
||||
|
||||
public slots:
|
||||
void queryEngineContext(int id);
|
||||
void reloadQmlViewer(int engineId);
|
||||
|
||||
private slots:
|
||||
void contextChanged();
|
||||
void connectionStateChanged();
|
||||
void connectionError();
|
||||
|
||||
void updateEngineList();
|
||||
void objectTreeFetched(QDeclarativeDebugQuery::State state = QDeclarativeDebugQuery::Completed);
|
||||
|
||||
private:
|
||||
void reloadEngines();
|
||||
QList<QDeclarativeDebugObjectReference> objectReferences(const QUrl &url, const QDeclarativeDebugObjectReference &objectRef) const;
|
||||
|
||||
private:
|
||||
explicit ClientProxy(QObject *parent = 0);
|
||||
Q_DISABLE_COPY(ClientProxy);
|
||||
|
||||
static ClientProxy *m_instance;
|
||||
|
||||
QDeclarativeDebugConnection *m_conn;
|
||||
QDeclarativeEngineDebug *m_client;
|
||||
|
||||
QDeclarativeDebugEnginesQuery *m_engineQuery;
|
||||
QDeclarativeDebugRootContextQuery *m_contextQuery;
|
||||
QDeclarativeDebugObjectQuery *m_objectTreeQuery;
|
||||
|
||||
QDeclarativeDebugObjectReference m_rootObject;
|
||||
QList<QDeclarativeDebugEngineReference> m_engines;
|
||||
|
||||
Debugger::DebuggerRunControl *m_debuggerRunControl;
|
||||
friend class QmlJSInspector::Internal::QmlInspectorPlugin;
|
||||
};
|
||||
|
||||
} // namespace Internal
|
||||
} // namespace QmlJSInspector
|
||||
|
||||
#endif // QMLJSCLIENTPROXY_H
|
||||
@@ -2,7 +2,7 @@ TEMPLATE = lib
|
||||
TARGET = QmlJSInspector
|
||||
INCLUDEPATH += .
|
||||
DEPENDPATH += .
|
||||
QT += declarative
|
||||
QT += declarative network
|
||||
|
||||
include(../../private_headers.pri)
|
||||
|
||||
@@ -13,12 +13,14 @@ qmljsdebuggerclient.h \
|
||||
qmljsinspector_global.h \
|
||||
qmljsinspectorconstants.h \
|
||||
qmljsinspectorcontext.h \
|
||||
qmljsinspectorplugin.h
|
||||
qmljsinspectorplugin.h \
|
||||
qmljsclientproxy.h
|
||||
|
||||
SOURCES += \
|
||||
qmljsdebuggerclient.cpp \
|
||||
qmljsinspectorcontext.cpp \
|
||||
qmljsinspectorplugin.cpp
|
||||
qmljsinspectorplugin.cpp \
|
||||
qmljsclientproxy.cpp
|
||||
|
||||
OTHER_FILES += QmlJSInspector.pluginspec
|
||||
RESOURCES += qmljsinspector.qrc
|
||||
|
||||
Reference in New Issue
Block a user