Use V4 binding for non-final properties where possible
[profile/ivi/qtdeclarative.git] / tests / auto / qml / qqmlecmascript / testtypes.cpp
1 /****************************************************************************
2 **
3 ** Copyright (C) 2012 Nokia Corporation and/or its subsidiary(-ies).
4 ** Contact: http://www.qt-project.org/
5 **
6 ** This file is part of the test suite of the Qt Toolkit.
7 **
8 ** $QT_BEGIN_LICENSE:LGPL$
9 ** GNU Lesser General Public License Usage
10 ** This file may be used under the terms of the GNU Lesser General Public
11 ** License version 2.1 as published by the Free Software Foundation and
12 ** appearing in the file LICENSE.LGPL included in the packaging of this
13 ** file. Please review the following information to ensure the GNU Lesser
14 ** General Public License version 2.1 requirements will be met:
15 ** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
16 **
17 ** In addition, as a special exception, Nokia gives you certain additional
18 ** rights. These rights are described in the Nokia Qt LGPL Exception
19 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
20 **
21 ** GNU General Public License Usage
22 ** Alternatively, this file may be used under the terms of the GNU General
23 ** Public License version 3.0 as published by the Free Software Foundation
24 ** and appearing in the file LICENSE.GPL included in the packaging of this
25 ** file. Please review the following information to ensure the GNU General
26 ** Public License version 3.0 requirements will be met:
27 ** http://www.gnu.org/copyleft/gpl.html.
28 **
29 ** Other Usage
30 ** Alternatively, this file may be used in accordance with the terms and
31 ** conditions contained in a signed written agreement between you and Nokia.
32 **
33 **
34 **
35 **
36 **
37 **
38 ** $QT_END_LICENSE$
39 **
40 ****************************************************************************/
41 #include "testtypes.h"
42 #ifndef QT_NO_WIDGETS
43 # include <QWidget>
44 # include <QPlainTextEdit>
45 #endif
46 #include <QQmlEngine>
47 #include <QJSEngine>
48 #include <QThread>
49
50 class BaseExtensionObject : public QObject
51 {
52     Q_OBJECT
53     Q_PROPERTY(int baseExtendedProperty READ extendedProperty WRITE setExtendedProperty NOTIFY extendedPropertyChanged)
54 public:
55     BaseExtensionObject(QObject *parent) : QObject(parent), m_value(0) {}
56
57     int extendedProperty() const { return m_value; }
58     void setExtendedProperty(int v) { m_value = v; emit extendedPropertyChanged(); }
59
60 signals:
61     void extendedPropertyChanged();
62 private:
63     int m_value;
64 };
65
66 class ExtensionObject : public QObject
67 {
68     Q_OBJECT
69     Q_PROPERTY(int extendedProperty READ extendedProperty WRITE setExtendedProperty NOTIFY extendedPropertyChanged)
70 public:
71     ExtensionObject(QObject *parent) : QObject(parent), m_value(0) {}
72
73     int extendedProperty() const { return m_value; }
74     void setExtendedProperty(int v) { m_value = v; emit extendedPropertyChanged(); }
75
76 signals:
77     void extendedPropertyChanged();
78 private:
79     int m_value;
80 };
81
82 class DefaultPropertyExtensionObject : public QObject
83 {
84     Q_OBJECT
85     Q_CLASSINFO("DefaultProperty", "firstProperty")
86 public:
87     DefaultPropertyExtensionObject(QObject *parent) : QObject(parent) {}
88 };
89
90 class QWidgetDeclarativeUI : public QObject
91 {
92     Q_OBJECT
93
94     Q_PROPERTY(int width READ width WRITE setWidth NOTIFY widthChanged)
95
96 signals:
97     void widthChanged();
98
99 public:
100     QWidgetDeclarativeUI(QObject *other) : QObject(other) { }
101
102 public:
103     int width() const { return 0; }
104     void setWidth(int) { }
105 };
106
107 void MyQmlObject::v8function(QQmlV8Function *)
108 {
109     const char *error = "Exception thrown from within QObject slot";
110     v8::ThrowException(v8::Exception::Error(v8::String::New(error)));
111 }
112
113 static QJSValue script_api(QQmlEngine *engine, QJSEngine *scriptEngine)
114 {
115     Q_UNUSED(engine)
116
117     static int testProperty = 13;
118     QJSValue v = scriptEngine->newObject();
119     v.setProperty("scriptTestProperty", testProperty++);
120     return v;
121 }
122
123 static QJSValue readonly_script_api(QQmlEngine *engine, QJSEngine *scriptEngine)
124 {
125     Q_UNUSED(engine)
126
127     static int testProperty = 42;
128     QJSValue v = scriptEngine->newObject();
129     v.setProperty("scriptTestProperty", testProperty++);
130
131     // now freeze it so that it's read-only
132     QJSValue freezeFunction = scriptEngine->evaluate("(function(obj) { return Object.freeze(obj); })");
133     v = freezeFunction.call(QJSValueList() << v);
134
135     return v;
136 }
137
138 static QObject *qobject_api(QQmlEngine *engine, QJSEngine *scriptEngine)
139 {
140     Q_UNUSED(engine)
141     Q_UNUSED(scriptEngine)
142
143     testQObjectApi *o = new testQObjectApi();
144     o->setQObjectTestProperty(20);
145     o->setQObjectTestWritableProperty(50);
146     o->setQObjectTestWritableFinalProperty(10);
147     return o;
148 }
149
150 static QObject *qobject_api_engine_parent(QQmlEngine *engine, QJSEngine *scriptEngine)
151 {
152     Q_UNUSED(scriptEngine)
153
154     static int testProperty = 26;
155     testQObjectApi *o = new testQObjectApi(engine);
156     o->setQObjectTestProperty(testProperty++);
157     return o;
158 }
159
160 static QObject *fallback_bindings_object(QQmlEngine *engine, QJSEngine *scriptEngine)
161 {
162     Q_UNUSED(engine)
163     Q_UNUSED(scriptEngine)
164
165     return new FallbackBindingsObject();
166 }
167
168 static QObject *fallback_bindings_derived(QQmlEngine *engine, QJSEngine *scriptEngine)
169 {
170     Q_UNUSED(engine)
171     Q_UNUSED(scriptEngine)
172
173     return new FallbackBindingsDerived();
174 }
175
176 class MyWorkerObjectThread : public QThread
177 {
178 public:
179     MyWorkerObjectThread(MyWorkerObject *o) : QThread(o), o(o) { start(); }
180
181     virtual void run() {
182         emit o->done(QLatin1String("good"));
183     }
184
185     MyWorkerObject *o;
186 };
187
188 void MyWorkerObject::doIt()
189 {
190     new MyWorkerObjectThread(this);
191 }
192
193 void registerTypes()
194 {
195     qmlRegisterType<MyQmlObject>("Qt.test", 1,0, "MyQmlObjectAlias");
196     qmlRegisterType<MyQmlObject>("Qt.test", 1,0, "MyQmlObject");
197     qmlRegisterType<MyDeferredObject>("Qt.test", 1,0, "MyDeferredObject");
198     qmlRegisterType<MyQmlContainer>("Qt.test", 1,0, "MyQmlContainer");
199     qmlRegisterExtendedType<MyBaseExtendedObject, BaseExtensionObject>("Qt.test", 1,0, "MyBaseExtendedObject");
200     qmlRegisterExtendedType<MyExtendedObject, ExtensionObject>("Qt.test", 1,0, "MyExtendedObject");
201     qmlRegisterType<MyTypeObject>("Qt.test", 1,0, "MyTypeObject");
202     qmlRegisterType<MyDerivedObject>("Qt.test", 1,0, "MyDerivedObject");
203     qmlRegisterType<NumberAssignment>("Qt.test", 1,0, "NumberAssignment");
204     qmlRegisterExtendedType<DefaultPropertyExtendedObject, DefaultPropertyExtensionObject>("Qt.test", 1,0, "DefaultPropertyExtendedObject");
205     qmlRegisterType<OverrideDefaultPropertyObject>("Qt.test", 1,0, "OverrideDefaultPropertyObject");
206     qmlRegisterType<MyRevisionedClass>("Qt.test",1,0,"MyRevisionedClass");
207     qmlRegisterType<MyDeleteObject>("Qt.test", 1,0, "MyDeleteObject");
208     qmlRegisterType<MyRevisionedClass,1>("Qt.test",1,1,"MyRevisionedClass");
209     qmlRegisterType<MyWorkerObject>("Qt.test", 1,0, "MyWorkerObject");
210
211     // test scarce resource property binding post-evaluation optimisation
212     // and for testing memory usage in property var circular reference test
213     qmlRegisterType<ScarceResourceObject>("Qt.test", 1,0, "MyScarceResourceObject");
214
215     // Register the uncreatable base class
216     qmlRegisterRevision<MyRevisionedBaseClassRegistered,1>("Qt.test",1,1);
217     // MyRevisionedSubclass 1.0 uses MyRevisionedClass revision 0
218     qmlRegisterType<MyRevisionedSubclass>("Qt.test",1,0,"MyRevisionedSubclass");
219     // MyRevisionedSubclass 1.1 uses MyRevisionedClass revision 1
220     qmlRegisterType<MyRevisionedSubclass,1>("Qt.test",1,1,"MyRevisionedSubclass");
221
222 #ifndef QT_NO_WIDGETS
223     qmlRegisterExtendedType<QWidget,QWidgetDeclarativeUI>("Qt.test",1,0,"QWidget");
224     qmlRegisterType<QPlainTextEdit>("Qt.test",1,0,"QPlainTextEdit");
225 #endif
226
227     qRegisterMetaType<MyQmlObject::MyType>("MyQmlObject::MyType");
228
229     qmlRegisterModuleApi("Qt.test",1,0,script_api);                             // register (script) module API for an existing uri which contains elements
230     qmlRegisterModuleApi<testQObjectApi>("Qt.test",1,0,qobject_api);            // register (qobject) for an existing uri for which another module API was previously regd.  Should replace!
231     qmlRegisterModuleApi("Qt.test.scriptApi",1,0,script_api);                   // register (script) module API for a uri which doesn't contain elements
232     qmlRegisterModuleApi("Qt.test.scriptApi",2,0,readonly_script_api);          // register (script) module API for a uri which doesn't contain elements - will be made read-only
233     qmlRegisterModuleApi<testQObjectApi>("Qt.test.qobjectApi",1,0,qobject_api); // register (qobject) module API for a uri which doesn't contain elements
234     qmlRegisterModuleApi<testQObjectApi>("Qt.test.qobjectApi",1,3,qobject_api); // register (qobject) module API for a uri which doesn't contain elements, minor version set
235     qmlRegisterModuleApi<testQObjectApi>("Qt.test.qobjectApi",2,0,qobject_api); // register (qobject) module API for a uri which doesn't contain elements, major version set
236     qmlRegisterModuleApi<testQObjectApi>("Qt.test.qobjectApiParented",1,0,qobject_api_engine_parent); // register (parented qobject) module API for a uri which doesn't contain elements
237
238     qRegisterMetaType<MyQmlObject::MyEnum2>("MyEnum2");
239     qRegisterMetaType<Qt::MouseButtons>("Qt::MouseButtons");
240
241     qmlRegisterType<CircularReferenceObject>("Qt.test", 1, 0, "CircularReferenceObject");
242     qmlRegisterType<CircularReferenceHandle>("Qt.test", 1, 0, "CircularReferenceHandle");
243
244     qmlRegisterType<MyDynamicCreationDestructionObject>("Qt.test", 1, 0, "MyDynamicCreationDestructionObject");
245     qmlRegisterType<WriteCounter>("Qt.test", 1, 0, "WriteCounter");
246
247     qmlRegisterType<MySequenceConversionObject>("Qt.test", 1, 0, "MySequenceConversionObject");
248
249     qmlRegisterType<MyUnregisteredEnumTypeObject>("Qt.test", 1, 0, "MyUnregisteredEnumTypeObject");
250
251     qmlRegisterModuleApi<FallbackBindingsObject>("Qt.test.fallbackBindingsObject", 1, 0, fallback_bindings_object);
252     qmlRegisterModuleApi<FallbackBindingsObject>("Qt.test.fallbackBindingsDerived", 1, 0, fallback_bindings_derived);
253
254     qmlRegisterType<FallbackBindingsTypeObject>("Qt.test.fallbackBindingsObject", 1, 0, "FallbackBindingsType");
255     qmlRegisterType<FallbackBindingsTypeDerived>("Qt.test.fallbackBindingsDerived", 1, 0, "FallbackBindingsType");
256 }
257
258 #include "testtypes.moc"