Merge branch 'master' into v8
[profile/ivi/qtdeclarative.git] / src / declarative / qml / qdeclarativeengine_p.h
1 /****************************************************************************
2 **
3 ** Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
4 ** All rights reserved.
5 ** Contact: Nokia Corporation (qt-info@nokia.com)
6 **
7 ** This file is part of the QtDeclarative module of the Qt Toolkit.
8 **
9 ** $QT_BEGIN_LICENSE:LGPL$
10 ** GNU Lesser General Public License Usage
11 ** This file may be used under the terms of the GNU Lesser General Public
12 ** License version 2.1 as published by the Free Software Foundation and
13 ** appearing in the file LICENSE.LGPL included in the packaging of this
14 ** file. Please review the following information to ensure the GNU Lesser
15 ** General Public License version 2.1 requirements will be met:
16 ** http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
17 **
18 ** In addition, as a special exception, Nokia gives you certain additional
19 ** rights. These rights are described in the Nokia Qt LGPL Exception
20 ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
21 **
22 ** GNU General Public License Usage
23 ** Alternatively, this file may be used under the terms of the GNU General
24 ** Public License version 3.0 as published by the Free Software Foundation
25 ** and appearing in the file LICENSE.GPL included in the packaging of this
26 ** file. Please review the following information to ensure the GNU General
27 ** Public License version 3.0 requirements will be met:
28 ** http://www.gnu.org/copyleft/gpl.html.
29 **
30 ** Other Usage
31 ** Alternatively, this file may be used in accordance with the terms and
32 ** conditions contained in a signed written agreement between you and Nokia.
33 **
34 **
35 **
36 **
37 **
38 ** $QT_END_LICENSE$
39 **
40 ****************************************************************************/
41
42 #ifndef QDECLARATIVEENGINE_P_H
43 #define QDECLARATIVEENGINE_P_H
44
45 //
46 //  W A R N I N G
47 //  -------------
48 //
49 // This file is not part of the Qt API.  It exists purely as an
50 // implementation detail.  This header file may change from version to
51 // version without notice, or even be removed.
52 //
53 // We mean it.
54 //
55
56 #include "qdeclarativeengine.h"
57
58 #include "private/qdeclarativetypeloader_p.h"
59 #include "private/qdeclarativeimport_p.h"
60 #include "private/qpodvector_p.h"
61 #include "qdeclarative.h"
62 #include "private/qdeclarativevaluetype_p.h"
63 #include "qdeclarativecontext.h"
64 #include "private/qdeclarativecontext_p.h"
65 #include "qdeclarativeexpression.h"
66 #include "qdeclarativeimageprovider.h"
67 #include "private/qdeclarativeproperty_p.h"
68 #include "private/qdeclarativepropertycache_p.h"
69 #include "private/qdeclarativemetatype_p.h"
70 #include "private/qdeclarativedirparser_p.h"
71 #include "private/qintrusivelist_p.h"
72
73 #include <QtScript/QScriptValue>
74 #include <QtScript/QScriptString>
75 #include <QtCore/qstring.h>
76 #include <QtCore/qlist.h>
77 #include <QtCore/qpair.h>
78 #include <QtCore/qstack.h>
79 #include <QtCore/qmutex.h>
80 #include <QtScript/qscriptengine.h>
81
82 #include <private/qobject_p.h>
83
84 #include <private/qv8engine_p.h>
85
86 QT_BEGIN_NAMESPACE
87
88 class QDeclarativeContext;
89 class QDeclarativeEngine;
90 class QDeclarativeContextPrivate;
91 class QDeclarativeExpression;
92 class QDeclarativeImportDatabase;
93 class ScarceResourceData;
94 class QScriptEngineDebugger;
95 class QNetworkReply;
96 class QNetworkAccessManager;
97 class QDeclarativeNetworkAccessManagerFactory;
98 class QDeclarativeAbstractBinding;
99 class QScriptDeclarativeClass;
100 class QDeclarativeTypeNameCache;
101 class QDeclarativeComponentAttached;
102 class QDeclarativeCleanup;
103 class QDeclarativeDelayedError;
104 class QDeclarativeWorkerScriptEngine;
105 class QDir;
106 class QSGTexture;
107 class QSGContext;
108
109 class QDeclarativeScriptEngine : public QScriptEngine
110 {
111 public:
112     QDeclarativeScriptEngine(QDeclarativeEnginePrivate *priv);
113     virtual ~QDeclarativeScriptEngine();
114
115     static QDeclarativeScriptEngine *get(QScriptEngine* e) { return static_cast<QDeclarativeScriptEngine*>(e); }
116
117     QDeclarativeEnginePrivate *p;
118
119     QUrl baseUrl;
120
121     virtual QNetworkAccessManager *networkAccessManager();
122 };
123
124 class Q_AUTOTEST_EXPORT QDeclarativeEnginePrivate : public QObjectPrivate
125 {
126     Q_DECLARE_PUBLIC(QDeclarativeEngine)
127 public:
128     QDeclarativeEnginePrivate(QDeclarativeEngine *);
129     ~QDeclarativeEnginePrivate();
130
131     void init();
132
133     struct CapturedProperty {
134         CapturedProperty(QObject *o, int c, int n)
135             : object(o), coreIndex(c), notifier(0), notifyIndex(n) {}
136         CapturedProperty(QDeclarativeNotifier *n)
137             : object(0), coreIndex(-1), notifier(n), notifyIndex(-1) {}
138
139         QObject *object;
140         int coreIndex;
141         QDeclarativeNotifier *notifier;
142         int notifyIndex;
143     };
144     bool captureProperties;
145     QPODVector<CapturedProperty> capturedProperties;
146
147     QDeclarativeContext *rootContext;
148     bool isDebugging;
149
150     bool outputWarningsToStdErr;
151
152     QDeclarativeContextData *sharedContext;
153     QObject *sharedScope;
154
155     // Registered cleanup handlers
156     QDeclarativeCleanup *cleanup;
157
158     // Bindings that have had errors during startup
159     QDeclarativeDelayedError *erroredBindings;
160     int inProgressCreations;
161
162     // V8 Engine
163     QV8Engine v8engine;
164
165     QDeclarativeScriptEngine scriptEngine;
166
167     QDeclarativeWorkerScriptEngine *getWorkerScriptEngine();
168     QDeclarativeWorkerScriptEngine *workerScriptEngine;
169
170     QUrl baseUrl;
171
172     template<class T>
173     struct SimpleList {
174         SimpleList()
175             : count(0), values(0) {}
176         SimpleList(int r)
177             : count(0), values(new T*[r]) {}
178
179         int count;
180         T **values;
181
182         void append(T *v) {
183             values[count++] = v;
184         }
185
186         T *at(int idx) const {
187             return values[idx];
188         }
189
190         void clear() {
191             delete [] values;
192         }
193     };
194
195     static void clear(SimpleList<QDeclarativeAbstractBinding> &);
196     static void clear(SimpleList<QDeclarativeParserStatus> &);
197
198     QList<SimpleList<QDeclarativeAbstractBinding> > bindValues;
199     QList<SimpleList<QDeclarativeParserStatus> > parserStatus;
200     QList<QPair<QDeclarativeGuard<QObject>,int> > finalizedParserStatus;
201     QDeclarativeComponentAttached *componentAttached;
202
203     void registerFinalizedParserStatusObject(QObject *obj, int index) {
204         finalizedParserStatus.append(qMakePair(QDeclarativeGuard<QObject>(obj), index));
205     }
206
207     bool inBeginCreate;
208
209     QNetworkAccessManager *createNetworkAccessManager(QObject *parent) const;
210     QNetworkAccessManager *getNetworkAccessManager() const;
211     mutable QNetworkAccessManager *networkAccessManager;
212     mutable QDeclarativeNetworkAccessManagerFactory *networkAccessManagerFactory;
213
214     QHash<QString,QSharedPointer<QDeclarativeImageProvider> > imageProviders;
215     QDeclarativeImageProvider::ImageType getImageProviderType(const QUrl &url);
216     QSGTexture *getTextureFromProvider(const QUrl &url, QSize *size, const QSize& req_size);
217     QImage getImageFromProvider(const QUrl &url, QSize *size, const QSize& req_size);
218     QPixmap getPixmapFromProvider(const QUrl &url, QSize *size, const QSize& req_size);
219
220     // Scarce resources are "exceptionally high cost" QVariant types where allowing the
221     // normal JavaScript GC to clean them up is likely to lead to out-of-memory or other
222     // out-of-resource situations.  When such a resource is passed into JavaScript we
223     // add it to the scarceResources list and it is destroyed when we return from the
224     // JavaScript execution that created it.  The user can prevent this behavior by
225     // calling preserve() on the object which removes it from this scarceResource list.
226     class ScarceResourceData {
227     public:
228         ScarceResourceData(const QVariant &data) : data(data) {}
229         QVariant data;
230         QIntrusiveListNode node;
231     };
232     QIntrusiveList<ScarceResourceData, &ScarceResourceData::node> scarceResources;
233     int scarceResourcesRefCount;
234     void referenceScarceResources();
235     void dereferenceScarceResources();
236
237     mutable QMutex mutex;
238
239     QDeclarativeTypeLoader typeLoader;
240     QDeclarativeImportDatabase importDatabase;
241
242     QString offlineStoragePath;
243
244     mutable quint32 uniqueId;
245     quint32 getUniqueId() const {
246         return uniqueId++;
247     }
248
249     QDeclarativeValueTypeFactory valueTypes;
250
251     QHash<QDeclarativeMetaType::ModuleApi, QDeclarativeMetaType::ModuleApiInstance *> moduleApiInstances;
252
253     QHash<const QMetaObject *, QDeclarativePropertyCache *> propertyCache;
254     QHash<QPair<QDeclarativeType *, int>, QDeclarativePropertyCache *> typePropertyCache;
255     inline QDeclarativePropertyCache *cache(QObject *obj);
256     inline QDeclarativePropertyCache *cache(const QMetaObject *);
257     inline QDeclarativePropertyCache *cache(QDeclarativeType *, int, QDeclarativeError &error);
258     QDeclarativePropertyCache *createCache(const QMetaObject *);
259     QDeclarativePropertyCache *createCache(QDeclarativeType *, int, QDeclarativeError &error);
260
261     void registerCompositeType(QDeclarativeCompiledData *);
262
263     bool isQObject(int);
264     QObject *toQObject(const QVariant &, bool *ok = 0) const;
265     QDeclarativeMetaType::TypeCategory typeCategory(int) const;
266     bool isList(int) const;
267     int listType(int) const;
268     const QMetaObject *rawMetaObjectForType(int) const;
269     const QMetaObject *metaObjectForType(int) const;
270     QHash<int, int> m_qmlLists;
271     QHash<int, QDeclarativeCompiledData *> m_compositeTypes;
272
273     void sendQuit();
274     void warning(const QDeclarativeError &);
275     void warning(const QList<QDeclarativeError> &);
276     static void warning(QDeclarativeEngine *, const QDeclarativeError &);
277     static void warning(QDeclarativeEngine *, const QList<QDeclarativeError> &);
278     static void warning(QDeclarativeEnginePrivate *, const QDeclarativeError &);
279     static void warning(QDeclarativeEnginePrivate *, const QList<QDeclarativeError> &);
280
281     static QScriptEngine *getScriptEngine(QDeclarativeEngine *e) { return &e->d_func()->scriptEngine; }
282     static QDeclarativeEngine *getEngine(QScriptEngine *e) { return static_cast<QDeclarativeScriptEngine*>(e)->p->q_func(); }
283     static QDeclarativeEnginePrivate *get(QDeclarativeEngine *e) { return e->d_func(); }
284     static QDeclarativeEnginePrivate *get(QDeclarativeContext *c) { return (c && c->engine()) ? QDeclarativeEnginePrivate::get(c->engine()) : 0; }
285     static QDeclarativeEnginePrivate *get(QDeclarativeContextData *c) { return (c && c->engine) ? QDeclarativeEnginePrivate::get(c->engine) : 0; }
286     static QDeclarativeEnginePrivate *get(QScriptEngine *e) { return static_cast<QDeclarativeScriptEngine*>(e)->p; }
287     static QDeclarativeEngine *get(QDeclarativeEnginePrivate *p) { return p->q_func(); }
288
289     static QString urlToLocalFileOrQrc(const QUrl& url);
290
291     static void defineModule();
292
293     static bool qml_debugging_enabled;
294
295     QSGContext *sgContext;
296 };
297
298 /*!
299 Returns a QDeclarativePropertyCache for \a obj if one is available.
300
301 If \a obj is null, being deleted or contains a dynamic meta object 0
302 is returned.
303
304 The returned cache is not referenced, so if it is to be stored, call addref().
305 */
306 QDeclarativePropertyCache *QDeclarativeEnginePrivate::cache(QObject *obj)
307 {
308     if (!obj || QObjectPrivate::get(obj)->metaObject || QObjectPrivate::get(obj)->wasDeleted)
309         return 0;
310
311     const QMetaObject *mo = obj->metaObject();
312     QDeclarativePropertyCache *rv = propertyCache.value(mo);
313     if (!rv) rv = createCache(mo);
314     return rv;
315 }
316
317 /*!
318 Returns a QDeclarativePropertyCache for \a metaObject.
319
320 As the cache is persisted for the life of the engine, \a metaObject must be
321 a static "compile time" meta-object, or a meta-object that is otherwise known to
322 exist for the lifetime of the QDeclarativeEngine.
323
324 The returned cache is not referenced, so if it is to be stored, call addref().
325 */
326 QDeclarativePropertyCache *QDeclarativeEnginePrivate::cache(const QMetaObject *metaObject)
327 {
328     Q_ASSERT(metaObject);
329
330     QDeclarativePropertyCache *rv = propertyCache.value(metaObject);
331     if (!rv) rv = createCache(metaObject);
332     return rv;
333 }
334
335 /*!
336 Returns a QDeclarativePropertyCache for \a type with \a minorVersion.
337
338 The returned cache is not referenced, so if it is to be stored, call addref().
339 */
340 QDeclarativePropertyCache *QDeclarativeEnginePrivate::cache(QDeclarativeType *type, int minorVersion, QDeclarativeError &error)
341 {
342     Q_ASSERT(type);
343
344     if (minorVersion == -1 || !type->containsRevisionedAttributes())
345         return cache(type->metaObject());
346
347     QDeclarativePropertyCache *rv = typePropertyCache.value(qMakePair(type, minorVersion));
348     if (!rv) rv = createCache(type, minorVersion, error);
349     return rv;
350 }
351
352 QT_END_NAMESPACE
353
354 #endif // QDECLARATIVEENGINE_P_H