diff options
author | Simon Hausmann <simon.hausmann@theqtcompany.com> | 2014-11-20 10:42:34 +0100 |
---|---|---|
committer | Simon Hausmann <simon.hausmann@digia.com> | 2015-01-02 15:06:46 +0100 |
commit | 2b5fb185627f8adfb6c5b3d62990a58429bf4ea7 (patch) | |
tree | 63ae9357fbcb652b48b01a8a6de2da026fb93f40 /tests/auto/qml/qqmlvaluetypes | |
parent | 9a2701c1c3c7c805335fb2c1a1dfd1e712e4db6b (diff) |
Enable gadget wrapping for custom value types
[ChangeLog][QtQml] Custom C++ value types annotated with Q_GADGET are now fully
accessible in the QML and QJSEngine JavaScript environment.
QJSEngine::toScriptValue can be used for injection and fromScriptValue to
extraction. The QML "built-in" gadget wrappers for QPoint and the gui types are
not exposed this way, toScriptValue(point) will still return an opaque QVariant
wrapper. We could expose the core types right away, but then we would be
lacking an API to enable use of the Gui types that are registered in QtQuick.
It would be better to make the core types in qtbase gadgets and thus enable
them without the need for hooks and init functions to be called by the user.
Task-number: QTBUG-29769
Change-Id: I8179cd599bdc1209ff61cfdbdda419cb400296bb
Reviewed-by: Lars Knoll <lars.knoll@digia.com>
Diffstat (limited to 'tests/auto/qml/qqmlvaluetypes')
-rw-r--r-- | tests/auto/qml/qqmlvaluetypes/data/customvaluetype.qml | 8 | ||||
-rw-r--r-- | tests/auto/qml/qqmlvaluetypes/qqmlvaluetypes.pro | 3 | ||||
-rw-r--r-- | tests/auto/qml/qqmlvaluetypes/tst_qqmlvaluetypes.cpp | 83 |
3 files changed, 94 insertions, 0 deletions
diff --git a/tests/auto/qml/qqmlvaluetypes/data/customvaluetype.qml b/tests/auto/qml/qqmlvaluetypes/data/customvaluetype.qml new file mode 100644 index 0000000000..7ae73475c3 --- /dev/null +++ b/tests/auto/qml/qqmlvaluetypes/data/customvaluetype.qml @@ -0,0 +1,8 @@ +import QtQuick 2.0 +import Test 1.0 + +TypeWithCustomValueType { + desk { + monitorCount: 3 + } +} diff --git a/tests/auto/qml/qqmlvaluetypes/qqmlvaluetypes.pro b/tests/auto/qml/qqmlvaluetypes/qqmlvaluetypes.pro index e318966e56..e36be45f41 100644 --- a/tests/auto/qml/qqmlvaluetypes/qqmlvaluetypes.pro +++ b/tests/auto/qml/qqmlvaluetypes/qqmlvaluetypes.pro @@ -15,3 +15,6 @@ CONFIG += parallel_test QT += core-private gui-private qml-private quick-private gui testlib DEFINES += QT_DISABLE_DEPRECATED_BEFORE=0 + +DISTFILES += \ + data/customvaluetype.qml diff --git a/tests/auto/qml/qqmlvaluetypes/tst_qqmlvaluetypes.cpp b/tests/auto/qml/qqmlvaluetypes/tst_qqmlvaluetypes.cpp index e3703eac00..f07a34b2f2 100644 --- a/tests/auto/qml/qqmlvaluetypes/tst_qqmlvaluetypes.cpp +++ b/tests/auto/qml/qqmlvaluetypes/tst_qqmlvaluetypes.cpp @@ -88,6 +88,8 @@ private slots: void initializeByWrite(); void groupedInterceptors(); void groupedInterceptors_data(); + void customValueType(); + void customValueTypeInQml(); private: QQmlEngine engine; @@ -1422,6 +1424,87 @@ void tst_qqmlvaluetypes::groupedInterceptors() delete object; } +struct MyDesk +{ + Q_PROPERTY(int monitorCount MEMBER monitorCount) + Q_GADGET +public: + MyDesk() : monitorCount(1) {} + + int monitorCount; +}; + +bool operator==(const MyDesk &lhs, const MyDesk &rhs) +{ return lhs.monitorCount == rhs.monitorCount; } +bool operator!=(const MyDesk &lhs, const MyDesk &rhs) +{ return lhs.monitorCount != rhs.monitorCount; } + +Q_DECLARE_METATYPE(MyDesk) + +struct MyOffice +{ + Q_PROPERTY(int chairs MEMBER m_chairs) + Q_PROPERTY(MyDesk desk READ desk WRITE setDesk) + Q_GADGET +public: + MyOffice() : m_chairs(0) {} + + MyDesk desk() const { return m_desk; } + void setDesk(const MyDesk &d) { m_desk = d; } + + int m_chairs; + MyDesk m_desk; +}; + +Q_DECLARE_METATYPE(MyOffice) + +void tst_qqmlvaluetypes::customValueType() +{ + QJSEngine engine; + + MyOffice cppOffice; + cppOffice.m_chairs = 2; + + QJSValue office = engine.toScriptValue(cppOffice); + QCOMPARE(office.property("chairs").toInt(), 2); + office.setProperty("chairs", 1); + QCOMPARE(office.property("chairs").toInt(), 1); + QCOMPARE(cppOffice.m_chairs, 2); + + QJSValue jsDesk = office.property("desk"); + QCOMPARE(jsDesk.property("monitorCount").toInt(), 1); + jsDesk.setProperty("monitorCount", 2); + QCOMPARE(jsDesk.property("monitorCount").toInt(), 2); + + QCOMPARE(cppOffice.desk().monitorCount, 1); + + office.setProperty("desk", jsDesk); + cppOffice = engine.fromScriptValue<MyOffice>(office); + QCOMPARE(cppOffice.m_chairs, 1); + QCOMPARE(cppOffice.desk().monitorCount, 2); +} + +class TypeWithCustomValueType : public QObject +{ + Q_OBJECT + Q_PROPERTY(MyDesk desk MEMBER m_desk) +public: + + MyDesk m_desk; +}; + +void tst_qqmlvaluetypes::customValueTypeInQml() +{ + qmlRegisterType<TypeWithCustomValueType>("Test", 1, 0, "TypeWithCustomValueType"); + QQmlComponent component(&engine, testFileUrl("customvaluetype.qml")); + QScopedPointer<QObject> object(component.create()); + QVERIFY(!object.isNull()); + + TypeWithCustomValueType *t = qobject_cast<TypeWithCustomValueType*>(object.data()); + Q_ASSERT(t); + QCOMPARE(t->m_desk.monitorCount, 3); +} + QTEST_MAIN(tst_qqmlvaluetypes) #include "tst_qqmlvaluetypes.moc" |