summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--examples/qtobject/main.cpp2
-rw-r--r--examples/qtobject/qml/qtobject/index.html36
-rw-r--r--examples/qtobject/qml/qtobject/main.qml53
-rw-r--r--examples/qtobject/qml/qtobject/qtobject.js118
-rw-r--r--examples/qtobject/qtmetaobjectpublisher.cpp32
-rw-r--r--examples/qtobject/qtmetaobjectpublisher.h34
-rw-r--r--examples/qtobject/qtobject.pro5
-rw-r--r--examples/qtobject/testobject.cpp2
-rw-r--r--examples/qtobject/testobject.h2
-rw-r--r--src/MetaObjectPublisher.qml74
-rw-r--r--src/qmldir3
-rw-r--r--src/qobject.js119
-rw-r--r--src/qtmetaobjectpublisher.cpp73
-rw-r--r--src/qtmetaobjectpublisher.h74
-rw-r--r--src/qwebchannel.cpp9
-rw-r--r--src/qwebchannel_plugin.cpp3
-rw-r--r--src/resources.qrc1
-rw-r--r--src/src.pri4
-rw-r--r--src/src.pro7
-rw-r--r--src/webchannel-iframe.html1
20 files changed, 414 insertions, 238 deletions
diff --git a/examples/qtobject/main.cpp b/examples/qtobject/main.cpp
index 6165664..fe8efff 100644
--- a/examples/qtobject/main.cpp
+++ b/examples/qtobject/main.cpp
@@ -3,13 +3,11 @@
#include <QtQml>
#include "qtquick2applicationviewer.h"
-#include "qtmetaobjectpublisher.h"
#include "testobject.h"
int main(int argc, char *argv[])
{
QGuiApplication app(argc, argv);
- qmlRegisterType<QtMetaObjectPublisher>("Qt.labs", 1, 0, "QtMetaObjectPublisher");
qmlRegisterType<TestObject>("Qt.labs", 1, 0, "TestObject");
QtQuick2ApplicationViewer viewer;
diff --git a/examples/qtobject/qml/qtobject/index.html b/examples/qtobject/qml/qtobject/index.html
index d79fd7e..a24dde3 100644
--- a/examples/qtobject/qml/qtobject/index.html
+++ b/examples/qtobject/qml/qtobject/index.html
@@ -1,21 +1,39 @@
<html>
<head>
- <script>
- document.write('<script src="' + (/[?&]webChannelBaseUrl=([A-Za-z0-9\-:/]+)/.exec(location.search)[1]) + '/webchannel.js/createWebChannel"><' + '/script>');
+ <script type="text/javascript">
+ var base = (/[?&]webChannelBaseUrl=([A-Za-z0-9\-:/]+)/.exec(location.search)[1]);
+ document.write('<script src="' + base + '/webchannel.js/setupWebChannel"></script>');
+ document.write('<script src="' + base + '/qobject.js"><' + '/script>');
window.output = function(x)
{
document.querySelector("#out").innerHTML += x + "\n";
}
- </script>
- <script src="qtobject.js"></script>
- <script>
+ window.onload = function() {
+ setupWebChannel(function(webChannel) {
+ setupQObjectWebChannel(webChannel);
+ });
+ }
</script>
</head>
<body>
- <a href="#" onclick="testObject.debugMe('Debugging!', function(result) { output(result); })">invoke method</a>
- <a href="#" onclick="testObject.prop1(function(value) { output(value); })">Get property</a>
- <a href="#" onclick="testObject.prop1 = 'Different property'; testObject.prop1(function(value) { output(value); })">Set property</a>
- <a href="#" onclick="testObject.timeout.connect(function() { output('timeout'); }); testObject.startTimer(1000);">Timer</a>
+ <p>TestObject 1:
+ <a href="#" onclick="testObject1.debugMe('Debugging!', function(result) { output(result); })">invoke method</a>
+ <a href="#" onclick="testObject1.prop1(function(value) { output(value); })">Get property</a>
+ <a href="#" onclick="testObject1.prop1 = 'Different property'; testObject1.prop1(function(value) { output(value); })">Set property</a>
+ <a href="#" onclick="testObject1.timeout.connect(function() { output('timeout 1'); }); testObject1.startTimer(1000);">Timer</a>
+ </p>
+ <p>TestObject 2:
+ <a href="#" onclick="testObject2.debugMe('Debugging!', function(result) { output(result); })">invoke method</a>
+ <a href="#" onclick="testObject2.prop1(function(value) { output(value); })">Get property</a>
+ <a href="#" onclick="testObject2.prop1 = 'Different property'; testObject2.prop1(function(value) { output(value); })">Set property</a>
+ <a href="#" onclick="testObject2.timeout.connect(function() { output('timeout 2'); }); testObject2.startTimer(1000);">Timer</a>
+ </p>
+ <p>TestObject 3:
+ <a href="#" onclick="testObject3.debugMe('Debugging!', function(result) { output(result); })">invoke method</a>
+ <a href="#" onclick="testObject3.prop1(function(value) { output(value); })">Get property</a>
+ <a href="#" onclick="testObject3.prop1 = 'Different property'; testObject3.prop1(function(value) { output(value); })">Set property</a>
+ <a href="#" onclick="testObject3.timeout.connect(function() { output('timeout 3'); }); testObject3.startTimer(1000);">Timer</a>
+ </p>
<br/>
<textarea id="out" style="height:80%; width: 80%"></textarea>
</body>
diff --git a/examples/qtobject/qml/qtobject/main.qml b/examples/qtobject/qml/qtobject/main.qml
index 6ed3ad6..a4ab0c3 100644
--- a/examples/qtobject/qml/qtobject/main.qml
+++ b/examples/qtobject/qml/qtobject/main.qml
@@ -47,52 +47,45 @@ import QtWebKit 3.0
import QtWebKit.experimental 1.0
Rectangle {
- QtMetaObjectPublisher {
+ MetaObjectPublisher {
id: publisher
}
TestObject {
- id: testObject
+ id: testObject1
+ objectName: "object1"
+ }
+
+ TestObject {
+ id: testObject2
+ objectName: "object2"
+ }
+
+ TestObject {
+ id: testObject3
+ objectName: "object3"
}
WebChannel {
id: webChannel
onExecute: {
var payload = JSON.parse(requestData);
- var object = publisher.namedObject(payload.object);
- var ret;
- console.log(requestData);
- if (payload.type == "Qt.invokeMethod") {
- ret = (object[payload.method])(payload.args);
- } else if (payload.type == "Qt.connectToSignal") {
- object[payload.signal].connect(
- function(a,b,c,d,e,f,g,h,i,j) {
- broadcast("Qt.signal", JSON.stringify({object: payload.object, signal: payload.signal, args: [a,b,c,d,e,f,g,h,i,j]}));
- });
- } else if (payload.type == "Qt.getProperty") {
- ret = object[payload.property];
- } else if (payload.type == "Qt.setProperty") {
- object[payload.property] = payload.value;
- } else if (payload.type == "Qt.getObjects") {
- var objectNames = publisher.objectNames;
- for (var i = 0; i < objectNames.length; ++i) {
- var name = objectNames[i];
- var o = publisher.namedObject(name);
- addObject(name, o);
- }
+ var ret = publisher.handleRequest(payload, webChannel);
+ if (!ret) {
+ console.log("unhandled request: ", requestData);
+ } else {
+ response.send(JSON.stringify(ret));
}
-
- response.send(JSON.stringify(ret));
}
- function addObject(name, object)
+ function registerObjects(objects)
{
- publisher.addObject(name, object);
- var metaData = { name: name, data: publisher.classInfoForObject(object) };
- broadcast("Qt.addToWindowObject", JSON.stringify(metaData));
+ for (var name in objects) {
+ publisher.addObject(name, objects[name]);
+ }
}
- onBaseUrlChanged: addObject("testObject", testObject)
+ onBaseUrlChanged: registerObjects({"testObject1": testObject1, "testObject2": testObject2, "testObject3":testObject3})
}
width: 480
diff --git a/examples/qtobject/qml/qtobject/qtobject.js b/examples/qtobject/qml/qtobject/qtobject.js
deleted file mode 100644
index 0553a36..0000000
--- a/examples/qtobject/qml/qtobject/qtobject.js
+++ /dev/null
@@ -1,118 +0,0 @@
-/****************************************************************************
-**
-** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
-** All rights reserved.
-** Contact: Nokia Corporation (qt-info@nokia.com)
-**
-** This file is part of the QWebChannel module on Qt labs.
-**
-** $QT_BEGIN_LICENSE:LGPL$
-** No Commercial Usage
-** This file contains pre-release code and may not be distributed.
-** You may use this file in accordance with the terms and conditions
-** contained in the Technology Preview License Agreement accompanying
-** this package.
-**
-** GNU Lesser General Public License Usage
-** Alternatively, 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.
-**
-** If you have questions regarding the use of this file, please contact
-** Nokia at qt-info@nokia.com.
-**
-**
-**
-**
-**
-**
-**
-**
-** $QT_END_LICENSE$
-**
-****************************************************************************/
-
-window.onload = function() {
- createWebChannel(function(webChannel) {
- var allSignals = {};
- webChannel.subscribe(
- "Qt.signal",
- function(payload) {
- var signalData = JSON.parse(payload);
- var object = allSignals[signalData.object];
- var conns = (object ? object[signalData.signal] : []) || [];
- var a = payload.args;
- conns.forEach(function(callback) {
- callback.call(a);
- });
- }
- );
- webChannel.subscribe(
- "Qt.addToWindowObject",
- function(payload) {
- var addObjectData = JSON.parse(payload);
- var objectSignals = {};
- var methodsAndSignals = [];
- var object = {};
- var objectName = addObjectData.name;
- var data = addObjectData.data;
- for (var i in data.methods)
- methodsAndSignals.push(data.methods[i]);
- for (i in data.signals)
- methodsAndSignals.push(data.signals[i]);
-
- methodsAndSignals.forEach(function(method) {
- object[method] = function() {
- var args = [];
- var callback;
- for (var i = 0; i < arguments.length; ++i) {
- if (typeof arguments[i] == "function")
- callback = arguments[i];
- else
- args.push(arguments[i]);
- }
-
- webChannel.exec(JSON.stringify({type: "Qt.invokeMethod", object: objectName, method: method, args: args}), function(response) {
- if (response.length)
- (callback)(JSON.parse(response));
- });
- };
- });
-
- for (i in data.signals) {
- var signal = data.signals[i];
- object[signal].connect = function(callback) {
- objectSignals[signal] = objectSignals[signal] || [];
- webChannel.exec(JSON.stringify({type: "Qt.connectToSignal", object: objectName, signal: signal}));
- objectSignals[signal].push(callback);
- };
- }
- allSignals[objectName] = objectSignals;
-
- for (i in data.properties) {
- var prop = data.properties[i];
- object.__defineSetter__(prop, function(value) {
- webChannel.exec(JSON.stringify({type: "Qt.setProperty", object: objectName, property: prop, value: value }));
- });
- object.__defineGetter__(prop, function() {
- return (function(callback) {
- webChannel.exec(JSON.stringify({type: "Qt.getProperty", object: objectName, property: prop}), function(response) {
- callback(JSON.parse(response));
- });
- });
- });
- }
-
- window[objectName] = object;
- }
- );
- webChannel.exec(JSON.stringify({type:"Qt.getObjects"}));
- });
-};
diff --git a/examples/qtobject/qtmetaobjectpublisher.cpp b/examples/qtobject/qtmetaobjectpublisher.cpp
deleted file mode 100644
index db86145..0000000
--- a/examples/qtobject/qtmetaobjectpublisher.cpp
+++ /dev/null
@@ -1,32 +0,0 @@
-#include "qtmetaobjectpublisher.h"
-#include <QVariantMap>
-#include <QStringList>
-#include <QMetaObject>
-#include <QMetaProperty>
-
-QtMetaObjectPublisher::QtMetaObjectPublisher(QObject *parent) :
- QObject(parent)
-{
-}
-
-QVariantMap QtMetaObjectPublisher::classInfoForObject(QObject *object)
-{
- QVariantMap data;
- QStringList qtSignals, qtMethods, qtProperties;
- const QMetaObject* metaObject = object->metaObject();
- for (int i = 0; i < metaObject->propertyCount(); ++i)
- qtProperties.append(metaObject->property(i).name());
- for (int i = 0; i < metaObject->methodCount(); ++i) {
- QMetaMethod method = metaObject->method(i);
- QString signature = method.methodSignature();
- QString name = signature.left(signature.indexOf("("));
- if (method.access() == QMetaMethod::Public)
- qtMethods << signature << name;
- if (method.methodType() == QMetaMethod::Signal)
- qtSignals << signature << name;
- }
- data["signals"] = qtSignals;
- data["methods"] = qtMethods;
- data["properties"] = qtProperties;
- return data;
-}
diff --git a/examples/qtobject/qtmetaobjectpublisher.h b/examples/qtobject/qtmetaobjectpublisher.h
deleted file mode 100644
index 3262525..0000000
--- a/examples/qtobject/qtmetaobjectpublisher.h
+++ /dev/null
@@ -1,34 +0,0 @@
-#ifndef QTMETAOBJECTPUBLISHER_H
-#define QTMETAOBJECTPUBLISHER_H
-
-#include <QObject>
-#include <QVariantMap>
-#include <QPointer>
-#include <QStringList>
-
-class QtMetaObjectPublisher : public QObject
-{
- Q_OBJECT
- Q_PROPERTY(QStringList objectNames READ objectNames)
-public:
- explicit QtMetaObjectPublisher(QObject *parent = 0);
- Q_INVOKABLE QVariantMap classInfoForObject(QObject*);
- QStringList objectNames() { return objects.keys(); }
- Q_INVOKABLE QObject* namedObject(const QString& name) {
- if (!objects.contains(name))
- return 0;
- return objects[name];
- }
-
-public slots:
- void addObject(const QString& name, QObject* object)
- {
- objects[name] = object;
- }
-
-private:
- QMap<QString, QPointer<QObject> > objects;
-
-};
-
-#endif // QTMETAOBJECTPUBLISHER_H
diff --git a/examples/qtobject/qtobject.pro b/examples/qtobject/qtobject.pro
index 0be2129..b6ff512 100644
--- a/examples/qtobject/qtobject.pro
+++ b/examples/qtobject/qtobject.pro
@@ -14,12 +14,9 @@ QML_IMPORT_PATH =
# The .cpp file which was generated for your project. Feel free to hack it.
SOURCES += main.cpp \
- qtmetaobjectpublisher.cpp \
testobject.cpp
-HEADERS += \
- qtmetaobjectpublisher.h \
- testobject.h
+HEADERS += testobject.h
# Please do not modify the following two lines. Required for deployment.
include(qtquick2applicationviewer/qtquick2applicationviewer.pri)
diff --git a/examples/qtobject/testobject.cpp b/examples/qtobject/testobject.cpp
index f13c5ab..75daa8d 100644
--- a/examples/qtobject/testobject.cpp
+++ b/examples/qtobject/testobject.cpp
@@ -10,7 +10,7 @@ TestObject::TestObject(QObject *parent) :
QString TestObject::debugMe(const QString& data)
{
qWarning() << data;
- return "OK";
+ return QString("OK from %1: %2").arg(objectName()).arg(data);
}
void TestObject::setProp1(const QString& s)
diff --git a/examples/qtobject/testobject.h b/examples/qtobject/testobject.h
index 93aa227..992247d 100644
--- a/examples/qtobject/testobject.h
+++ b/examples/qtobject/testobject.h
@@ -10,7 +10,7 @@ class TestObject : public QObject
Q_PROPERTY(QString prop1 READ prop1 WRITE setProp1)
public:
explicit TestObject(QObject *parent = 0);
- QString prop1() const { return p1; }
+ QString prop1() const { return p1 + objectName(); }
void setProp1(const QString& s);
signals:
diff --git a/src/MetaObjectPublisher.qml b/src/MetaObjectPublisher.qml
new file mode 100644
index 0000000..e938a83
--- /dev/null
+++ b/src/MetaObjectPublisher.qml
@@ -0,0 +1,74 @@
+/****************************************************************************
+**
+** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the QWebChannel module on Qt labs.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, 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.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick 2.0
+
+import Qt.labs.WebChannel 1.0
+
+MetaObjectPublisherPrivate {
+ function handleRequest(payload, webChannel) {
+ var object = publisher.namedObject(payload.object);
+ var ret = false;
+ if (payload.type == "Qt.invokeMethod") {
+ ret = (object[payload.method])(payload.args);
+ } else if (payload.type == "Qt.connectToSignal") {
+ object[payload.signal].connect(
+ function(a,b,c,d,e,f,g,h,i,j) {
+ webChannel.broadcast("Qt.signal", JSON.stringify({object: payload.object, signal: payload.signal, args: [a,b,c,d,e,f,g,h,i,j]}));
+ });
+ } else if (payload.type == "Qt.getProperty") {
+ ret = object[payload.property];
+ } else if (payload.type == "Qt.setProperty") {
+ object[payload.property] = payload.value;
+ } else if (payload.type == "Qt.getObjects") {
+ var objects = {};
+ var objectNames = publisher.objectNames;
+ for (var i = 0; i < objectNames.length; ++i) {
+ var name = objectNames[i];
+ var object = publisher.namedObject(name);
+ objects[name] = publisher.classInfoForObject(object);
+ }
+ ret = objects;
+ }
+
+ return ret;
+ }
+} \ No newline at end of file
diff --git a/src/qmldir b/src/qmldir
index 38d107a..9ec75e6 100644
--- a/src/qmldir
+++ b/src/qmldir
@@ -1,2 +1,3 @@
+module Qt.labs.WebChannel
plugin qwebchannel
-
+MetaObjectPublisher 1.0 MetaObjectPublisher.qml \ No newline at end of file
diff --git a/src/qobject.js b/src/qobject.js
new file mode 100644
index 0000000..d5d7f42
--- /dev/null
+++ b/src/qobject.js
@@ -0,0 +1,119 @@
+/****************************************************************************
+**
+** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the QWebChannel module on Qt labs.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, 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.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+function QObject(name, data, webChannel) {
+ this.__id__ = name;
+ this.__objectSignals__ = {};
+
+ var methodsAndSignals = [];
+ for (var i in data.methods)
+ methodsAndSignals.push(data.methods[i]);
+ for (i in data.signals)
+ methodsAndSignals.push(data.signals[i]);
+
+ var object = this;
+
+ methodsAndSignals.forEach(function(method) {
+ object[method] = function() {
+ var args = [];
+ var callback;
+ for (var i = 0; i < arguments.length; ++i) {
+ if (typeof arguments[i] == "function")
+ callback = arguments[i];
+ else
+ args.push(arguments[i]);
+ }
+
+ webChannel.exec(JSON.stringify({"type": "Qt.invokeMethod", "object": object.__id__, "method": method, "args": args}), function(response) {
+ if (response.length)
+ (callback)(JSON.parse(response));
+ });
+ };
+ });
+
+ for (i in data.signals) {
+ var signal = data.signals[i];
+ object[signal].connect = function(callback) {
+ object.__objectSignals__[signal] = object.__objectSignals__[signal] || [];
+ webChannel.exec(JSON.stringify({"type": "Qt.connectToSignal", "object": object.__id__, "signal": signal}));
+ object.__objectSignals__[signal].push(callback);
+ };
+ }
+
+ for (i in data.properties) {
+ var prop = data.properties[i];
+ object.__defineSetter__(prop, function(value) {
+ webChannel.exec(JSON.stringify({"type": "Qt.setProperty", "object": object.__id__, "property": prop, "value": value }));
+ });
+ object.__defineGetter__(prop, function() {
+ return (function(callback) {
+ webChannel.exec(JSON.stringify({"type": "Qt.getProperty", "object": object.__id__, "property": prop}), function(response) {
+ callback(JSON.parse(response));
+ });
+ });
+ });
+ }
+}
+
+window.setupQObjectWebChannel = function(webChannel) {
+ webChannel.subscribe(
+ "Qt.signal",
+ function(payload) {
+ var signalData = JSON.parse(payload);
+ var object = window[signalData.object];
+ var conns = (object ? object.__objectSignals__[signalData.signal] : []) || [];
+ var a = payload.args;
+ conns.forEach(function(callback) {
+ callback.call(a);
+ });
+ }
+ );
+ webChannel.exec(JSON.stringify({type:"Qt.getObjects"}), function(response) {
+ if (response.length) {
+ var objects = JSON.parse(response);
+ for (var objectName in objects) {
+ var data = objects[objectName];
+ var object = new QObject(objectName, data, webChannel);
+ window[objectName] = object;
+ }
+ }
+ });
+};
diff --git a/src/qtmetaobjectpublisher.cpp b/src/qtmetaobjectpublisher.cpp
new file mode 100644
index 0000000..d136ce7
--- /dev/null
+++ b/src/qtmetaobjectpublisher.cpp
@@ -0,0 +1,73 @@
+/****************************************************************************
+**
+** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the QWebChannel module on Qt labs.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, 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.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "qtmetaobjectpublisher.h"
+#include <QVariantMap>
+#include <QStringList>
+#include <QMetaObject>
+#include <QMetaProperty>
+
+QtMetaObjectPublisher::QtMetaObjectPublisher(QObject *parent) :
+ QObject(parent)
+{
+}
+
+QVariantMap QtMetaObjectPublisher::classInfoForObject(QObject *object)
+{
+ QVariantMap data;
+ QStringList qtSignals, qtMethods, qtProperties;
+ const QMetaObject* metaObject = object->metaObject();
+ for (int i = 0; i < metaObject->propertyCount(); ++i)
+ qtProperties.append(metaObject->property(i).name());
+ for (int i = 0; i < metaObject->methodCount(); ++i) {
+ QMetaMethod method = metaObject->method(i);
+ QString signature = method.methodSignature();
+ QString name = signature.left(signature.indexOf("("));
+ if (method.access() == QMetaMethod::Public)
+ qtMethods << signature << name;
+ if (method.methodType() == QMetaMethod::Signal)
+ qtSignals << signature << name;
+ }
+ data["signals"] = qtSignals;
+ data["methods"] = qtMethods;
+ data["properties"] = qtProperties;
+ return data;
+}
diff --git a/src/qtmetaobjectpublisher.h b/src/qtmetaobjectpublisher.h
new file mode 100644
index 0000000..816338a
--- /dev/null
+++ b/src/qtmetaobjectpublisher.h
@@ -0,0 +1,74 @@
+/****************************************************************************
+**
+** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the QWebChannel module on Qt labs.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, 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.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef QTMETAOBJECTPUBLISHER_H
+#define QTMETAOBJECTPUBLISHER_H
+
+#include <QObject>
+#include <QVariantMap>
+#include <QPointer>
+#include <QStringList>
+
+class QtMetaObjectPublisher : public QObject
+{
+ Q_OBJECT
+ Q_PROPERTY(QStringList objectNames READ objectNames)
+public:
+ explicit QtMetaObjectPublisher(QObject *parent = 0);
+ Q_INVOKABLE QVariantMap classInfoForObject(QObject*);
+ QStringList objectNames() { return objects.keys(); }
+ Q_INVOKABLE QObject* namedObject(const QString& name) {
+ if (!objects.contains(name))
+ return 0;
+ return objects[name];
+ }
+public slots:
+ void addObject(const QString& name, QObject* object)
+ {
+ objects[name] = object;
+ }
+
+private:
+ QMap<QString, QPointer<QObject> > objects;
+
+};
+
+#endif // QTMETAOBJECTPUBLISHER_H
diff --git a/src/qwebchannel.cpp b/src/qwebchannel.cpp
index 6d7d62f..ee03cf8 100644
--- a/src/qwebchannel.cpp
+++ b/src/qwebchannel.cpp
@@ -311,6 +311,15 @@ void QWebChannelPrivate::handleHttpRequest(QTcpSocket *socket, const HttpRequest
socket->write("\n})();");
socket->close();
file.close();
+ } else if (type == "qobject.js") {
+ QFile file(":/qobject.js");
+ file.open(QIODevice::ReadOnly);
+ socket->write("HTTP/1.1 200 OK\r\n"
+ "Content-Type: text/javascript\r\n"
+ "\r\n");
+ socket->write(file.readAll());
+ socket->close();
+ file.close();
} else if (type == "iframe.html") {
QFile file(":/webchannel-iframe.html");
file.open(QIODevice::ReadOnly);
diff --git a/src/qwebchannel_plugin.cpp b/src/qwebchannel_plugin.cpp
index a0675d6..1c71463 100644
--- a/src/qwebchannel_plugin.cpp
+++ b/src/qwebchannel_plugin.cpp
@@ -42,12 +42,13 @@
#include <qqml.h>
#include "qwebchannel.h"
+#include "qtmetaobjectpublisher.h"
#include "qwebchannel_plugin.h"
void QWebChannelPlugin::registerTypes(const char *uri)
{
- Q_ASSERT(uri == QLatin1String("Qt.labs.WebChannel"));
qmlRegisterType<QWebChannel>(uri, 1, 0, "WebChannel");
+ qmlRegisterType<QtMetaObjectPublisher>(uri, 1, 0, "MetaObjectPublisherPrivate");
}
diff --git a/src/resources.qrc b/src/resources.qrc
index 6f81393..431c12b 100644
--- a/src/resources.qrc
+++ b/src/resources.qrc
@@ -1,6 +1,7 @@
<RCC>
<qresource prefix="/">
<file>webchannel.js</file>
+ <file>qobject.js</file>
<file>webchannel-iframe.html</file>
</qresource>
</RCC>
diff --git a/src/src.pri b/src/src.pri
index c64cc76..55ed7e3 100644
--- a/src/src.pri
+++ b/src/src.pri
@@ -1,3 +1,3 @@
QT += network
-SOURCES += $$PWD/qwebchannel.cpp
-HEADERS += $$PWD/qwebchannel.h
+SOURCES += $$PWD/qwebchannel.cpp $$PWD/qtmetaobjectpublisher.cpp
+HEADERS += $$PWD/qwebchannel.h $$PWD/qtmetaobjectpublisher.h
diff --git a/src/src.pro b/src/src.pro
index 1f940c6..1f5a62e 100644
--- a/src/src.pro
+++ b/src/src.pro
@@ -13,7 +13,6 @@ SOURCES += qwebchannel_plugin.cpp
HEADERS += qwebchannel_plugin.h
OTHER_FILES = qmldir \
- qwebchannel.js \
qtc_packaging/debian_harmattan/rules \
qtc_packaging/debian_harmattan/README \
qtc_packaging/debian_harmattan/copyright \
@@ -21,7 +20,9 @@ OTHER_FILES = qmldir \
qtc_packaging/debian_harmattan/compat \
qtc_packaging/debian_harmattan/changelog \
webchannel.js \
- webchannel-iframe.html
+ qobject.js \
+ webchannel-iframe.html \
+ MetaObjectPublisher.qml
!equals(_PRO_FILE_PWD_, $$OUT_PWD) {
copy_qmldir.target = $$OUT_PWD/qmldir
@@ -33,7 +34,7 @@ OTHER_FILES = qmldir \
target.path = $$[QT_INSTALL_QML]/$$TARGETPATH
-qmldir.files += $$PWD/qmldir
+qmldir.files += $$PWD/qmldir $$PWD/MetaObjectPublisher.qml
qmldir.path += $$[QT_INSTALL_QML]/$$TARGETPATH
INSTALLS += target qmldir
diff --git a/src/webchannel-iframe.html b/src/webchannel-iframe.html
index 1f93eac..bbaf7cd 100644
--- a/src/webchannel-iframe.html
+++ b/src/webchannel-iframe.html
@@ -24,6 +24,7 @@
window.addEventListener("message", function(event) {
var data = JSON.parse(event.data);
+ console.log("MESSAGE:", data);
function callback(r) { window.parent.postMessage(JSON.stringify({ type: "callback", id: data.id, payload: r }), "*"); }
if (data.type == "EXEC")
exec(data.payload, callback);