Don't unnecessarily construct QMetaPropertys
[profile/ivi/qtdeclarative.git] / src / declarative / qml / qdeclarativeparser_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 QDECLARATIVEPARSER_P_H
43 #define QDECLARATIVEPARSER_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 "qdeclarative.h"
57
58 #include <QtCore/qbytearray.h>
59 #include <QtCore/qlist.h>
60 #include <QtCore/qurl.h>
61 #include <QtCore/qstring.h>
62 #include <QtCore/qstringlist.h>
63
64 #include <private/qobject_p.h>
65 #include <private/qdeclarativerefcount_p.h>
66 #include <private/qdeclarativeglobal_p.h>
67 #include <private/qdeclarativepool_p.h>
68 #include <private/qfieldlist_p.h>
69 #include <private/qdeclarativepropertycache_p.h>
70
71 QT_BEGIN_HEADER
72
73 QT_BEGIN_NAMESPACE
74
75 QT_MODULE(Declarative)
76
77 class QDeclarativePropertyCache;
78 namespace QDeclarativeJS { namespace AST { class Node; class StringLiteral; } }
79 namespace QDeclarativeCompilerTypes { class BindingReference; class ComponentCompileState; }
80
81 /*
82     XXX
83
84     These types are created (and owned) by the QDeclarativeScriptParser and consumed by the 
85     QDeclarativeCompiler.  During the compilation phase the compiler will update some of
86     the fields for its own use.
87
88     The types are part of the generic sounding "QDeclarativeParser" namespace for legacy 
89     reasons (there used to be more in this namespace) and will be cleaned up and
90     migrated into a more appropriate location eventually.
91 */
92 namespace QDeclarativeParser
93 {
94     struct Location 
95     {
96         Location() : line(-1), column(-1) {}
97         int line;
98         int column;
99
100         inline bool operator<(const Location &other) {
101             return line < other.line || 
102                    (line == other.line && column < other.column);
103         }
104     };
105
106     struct LocationRange
107     {
108         LocationRange() : offset(0), length(0) {}
109         quint32 offset;
110         quint32 length;
111     };
112
113     struct LocationSpan
114     {
115         Location start;
116         Location end;
117         LocationRange range;
118
119         bool operator<(LocationSpan &o) const {
120             return (start.line < o.start.line) ||
121                    (start.line == o.start.line && start.column < o.start.column);
122         }
123     };
124
125     class Object;
126     class Property;
127     class Q_DECLARATIVE_EXPORT Variant 
128     {
129     public:
130         enum Type {
131             Invalid,
132             Boolean,
133             Number,
134             String,
135             Script
136         };
137
138         Variant();
139         Variant(const Variant &);
140         explicit Variant(bool);
141         explicit Variant(double, const QStringRef &asWritten = QStringRef());
142         explicit Variant(QDeclarativeJS::AST::StringLiteral *);
143         explicit Variant(const QStringRef &asWritten, QDeclarativeJS::AST::Node *);
144         Variant &operator=(const Variant &);
145
146         Type type() const;
147
148         bool isBoolean() const { return type() == Boolean; }
149         bool isNumber() const { return type() == Number; }
150         bool isString() const { return type() == String; }
151         bool isScript() const { return type() == Script; }
152         bool isStringList() const;
153
154         bool asBoolean() const;
155         QString asString() const;
156         double asNumber() const;
157         QString asScript() const;
158         QDeclarativeJS::AST::Node *asAST() const;
159         QStringList asStringList() const;
160
161     private:
162         Type t;
163         union {
164             bool b;
165             double d;
166             QDeclarativeJS::AST::StringLiteral *l;
167             QDeclarativeJS::AST::Node *n;
168         };
169         QStringRef asWritten;
170     };
171
172     class Value : public QDeclarativePool::POD
173     {
174     public:
175         Value();
176
177         enum Type {
178             // The type of this value assignment is not yet known
179             Unknown,
180             // This is used as a literal property assignment
181             Literal,
182             // This is used as a property binding assignment
183             PropertyBinding,
184             // This is used as a QDeclarativePropertyValueSource assignment
185             ValueSource,
186             // This is used as a QDeclarativePropertyValueInterceptor assignment
187             ValueInterceptor,
188             // This is used as a property QObject assignment
189             CreatedObject,
190             // This is used as a signal object assignment
191             SignalObject,
192             // This is used as a signal expression assignment
193             SignalExpression,
194             // This is used as an id assignment only
195             Id
196         };
197         Type type;
198
199         // ### Temporary (for id only)
200         QString primitive() const { return value.isString() ? value.asString() : value.asScript(); }
201
202         // Primitive value
203         Variant value;
204         // Object value
205         Object *object;
206
207         LocationSpan location;
208
209         // Used by compiler
210         QDeclarativeCompilerTypes::BindingReference *bindingReference;
211         int signalExpressionContextStack;
212
213         // Used in Property::ValueList lists
214         Value *nextValue;
215     };
216
217     class Property : public QDeclarativePool::POD
218     {
219     public:
220         Property();
221
222         // The Object to which this property is attached
223         Object *parent;
224
225         Object *getValue(const LocationSpan &);
226         void addValue(Value *v);
227         void addOnValue(Value *v);
228
229         // The QVariant::Type of the property, or 0 (QVariant::Invalid) if 
230         // unknown.
231         int type;
232         // The metaobject index of this property, or -1 if unknown.
233         int index;
234         // The core data in the case of a regular property.  
235         // XXX This has to be a value now as the synthCache may change during
236         // compilation which invalidates pointers.  We should fix this.
237         QDeclarativePropertyCache::Data core;
238
239         // Returns true if this is an empty property - both value and values
240         // are unset.
241         bool isEmpty() const;
242
243         typedef QFieldList<Value, &Value::nextValue> ValueList;
244         // The list of values assigned to this property.  Content in values
245         // and value are mutually exclusive
246         ValueList values;
247         // The list of values assigned to this property using the "on" syntax
248         ValueList onValues;
249         // The accessed property.  This is used to represent dot properties.
250         // Content in value and values are mutually exclusive.
251         Object *value;
252         // The property name
253         QStringRef name() const { return _name; }
254         void setName(const QString &n) { _name = QStringRef(pool()->NewString(n)); }
255         // True if this property was accessed as the default property.  
256         bool isDefault;
257         // True if the setting of this property will be deferred.  Set by the
258         // QDeclarativeCompiler
259         bool isDeferred;
260         // True if this property is a value-type pseudo-property
261         bool isValueTypeSubProperty;
262         // True if this property is a property alias.  Set by the 
263         // QDeclarativeCompiler
264         bool isAlias;
265
266         // Used for scriptStringProperties
267         int scriptStringScope;
268
269         LocationSpan location;
270         LocationRange listValueRange;
271
272         // Used in Object::MainPropertyList
273         Property *nextMainProperty;
274
275         // Used in Object::PropertyList lists
276         Property *nextProperty;
277
278     private:
279         friend class Object;
280         QStringRef _name;
281     };
282
283     class Object : public QDeclarativePool::Class
284     {
285     public:
286         Object();
287         virtual ~Object(); 
288
289         // Type of the object.  The integer is an index into the 
290         // QDeclarativeCompiledData::types array, or -1 if the object is a property
291         // group.
292         int type;
293
294         // The fully-qualified name of this type
295         QByteArray typeName;
296         // The id assigned to the object (if any).  Set by the QDeclarativeCompiler
297         QString id;
298         // The id index assigned to the object (if any).  Set by the QDeclarativeCompiler
299         int idIndex;
300         // Custom parsed data
301         QByteArray custom;
302         // Bit mask of the properties assigned bindings
303         QByteArray bindingBitmask; 
304         void setBindingBit(int);
305         // Returns the metaobject for this type, or 0 if not available.  
306         // Internally selectd between the metatype and extObject variables
307         const QMetaObject *metaObject() const;
308
309         // The compile time metaobject for this type
310         const QMetaObject *metatype;
311         // The synthesized metaobject, if QML added signals or properties to
312         // this type.  Otherwise null
313         QAbstractDynamicMetaObject extObject;
314         QByteArray metadata; // Generated by compiler
315         QByteArray synthdata; // Generated by compiler
316         QDeclarativePropertyCache *synthCache; // Generated by compiler
317
318         Property *getDefaultProperty();
319         // name ptr must be guarenteed to remain valid
320         Property *getProperty(const QStringRef &name, bool create=true);
321         Property *getProperty(const QString &name, bool create=true);
322
323         Property *defaultProperty;
324
325         typedef QFieldList<Property, &Property::nextMainProperty> MainPropertyList;
326         MainPropertyList properties;
327
328         // Output of the compilation phase (these properties continue to exist
329         // in either the defaultProperty or properties members too)
330         void addValueProperty(Property *);
331         void addSignalProperty(Property *);
332         void addAttachedProperty(Property *);
333         void addGroupedProperty(Property *);
334         void addValueTypeProperty(Property *);
335         void addScriptStringProperty(Property *);
336
337         typedef QFieldList<Property, &Property::nextProperty> PropertyList;
338         PropertyList valueProperties;
339         PropertyList signalProperties;
340         PropertyList attachedProperties;
341         PropertyList groupedProperties;
342         PropertyList valueTypeProperties;
343         PropertyList scriptStringProperties;
344
345         // Script blocks that were nested under this object
346         struct ScriptBlock {
347             enum Pragma { 
348                 None   = 0x00000000,
349                 Shared = 0x00000001
350             };
351             Q_DECLARE_FLAGS(Pragmas, Pragma)
352
353             QString code;
354             QString file;
355             Pragmas pragmas;
356         };
357
358         // The bytes to cast instances by to get to the QDeclarativeParserStatus 
359         // interface.  -1 indicates the type doesn't support this interface.
360         // Set by the QDeclarativeCompiler.
361         int parserStatusCast;
362
363         LocationSpan location;
364
365         struct DynamicProperty {
366             DynamicProperty();
367             DynamicProperty(const DynamicProperty &);
368
369             enum Type { Variant, Int, Bool, Real, String, Url, Color, Time, Date, DateTime, Alias, Custom, CustomList };
370
371             bool isDefaultProperty;
372             Type type;
373             QByteArray customType;
374             QByteArray name;
375             QDeclarativeParser::Property *defaultValue;
376             LocationSpan location;
377         };
378         struct DynamicSignal {
379             DynamicSignal();
380             DynamicSignal(const DynamicSignal &);
381
382             QByteArray name;
383             QList<QByteArray> parameterTypes;
384             QList<QByteArray> parameterNames;
385         };
386         struct DynamicSlot {
387             DynamicSlot();
388             DynamicSlot(const DynamicSlot &);
389
390             QByteArray name;
391             QString body;
392             QList<QByteArray> parameterNames;
393             LocationSpan location;
394         };
395
396         // The list of dynamic properties
397         QList<DynamicProperty> dynamicProperties;
398         // The list of dynamic signals
399         QList<DynamicSignal> dynamicSignals;
400         // The list of dynamic slots
401         QList<DynamicSlot> dynamicSlots;
402
403         // Used by compiler
404         QDeclarativeCompilerTypes::ComponentCompileState *componentCompileState;
405
406         // Used by ComponentCompileState::AliasingObjectsList
407         Object *nextAliasingObject;
408         // Used by ComponentComppileState::IdList
409         Object *nextIdObject;
410     };
411
412 }
413
414 Q_DECLARE_OPERATORS_FOR_FLAGS(QDeclarativeParser::Object::ScriptBlock::Pragmas);
415
416 QT_END_NAMESPACE
417
418 Q_DECLARE_METATYPE(QDeclarativeParser::Variant)
419
420 QT_END_HEADER
421
422 #endif // QDECLARATIVEPARSER_P_H