1 | /**************************************************************************** |
2 | ** |
3 | ** Copyright (C) 2014 Digia Plc and/or its subsidiary(-ies). |
4 | ** Contact: http://www.qt-project.org/legal |
5 | ** |
6 | ** This file is part of the QtDeclarative module of the Qt Toolkit. |
7 | ** |
8 | ** $QT_BEGIN_LICENSE:LGPL$ |
9 | ** Commercial License Usage |
10 | ** Licensees holding valid commercial Qt licenses may use this file in |
11 | ** accordance with the commercial license agreement provided with the |
12 | ** Software or, alternatively, in accordance with the terms contained in |
13 | ** a written agreement between you and Digia. For licensing terms and |
14 | ** conditions see http://qt.digia.com/licensing. For further information |
15 | ** use the contact form at http://qt.digia.com/contact-us. |
16 | ** |
17 | ** GNU Lesser General Public License Usage |
18 | ** Alternatively, this file may be used under the terms of the GNU Lesser |
19 | ** General Public License version 2.1 as published by the Free Software |
20 | ** Foundation and appearing in the file LICENSE.LGPL included in the |
21 | ** packaging of this file. Please review the following information to |
22 | ** ensure the GNU Lesser General Public License version 2.1 requirements |
23 | ** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html. |
24 | ** |
25 | ** In addition, as a special exception, Digia gives you certain additional |
26 | ** rights. These rights are described in the Digia Qt LGPL Exception |
27 | ** version 1.1, included in the file LGPL_EXCEPTION.txt in this package. |
28 | ** |
29 | ** GNU General Public License Usage |
30 | ** Alternatively, this file may be used under the terms of the GNU |
31 | ** General Public License version 3.0 as published by the Free Software |
32 | ** Foundation and appearing in the file LICENSE.GPL included in the |
33 | ** packaging of this file. Please review the following information to |
34 | ** ensure the GNU General Public License version 3.0 requirements will be |
35 | ** met: http://www.gnu.org/copyleft/gpl.html. |
36 | ** |
37 | ** |
38 | ** $QT_END_LICENSE$ |
39 | ** |
40 | ****************************************************************************/ |
41 | |
42 | #include <QtDeclarative/qdeclarativeprivate.h> |
43 | #include "private/qdeclarativemetatype_p.h" |
44 | |
45 | #include "private/qdeclarativeproxymetaobject_p.h" |
46 | #include "private/qdeclarativecustomparser_p.h" |
47 | #include "private/qdeclarativeguard_p.h" |
48 | #include "private/qdeclarativeengine_p.h" |
49 | #include "private/qdeclarativeitemsmodule_p.h" |
50 | #include "private/qdeclarativeutilmodule_p.h" |
51 | |
52 | #include <QtCore/qdebug.h> |
53 | #include <QtCore/qstringlist.h> |
54 | #include <QtCore/qmetaobject.h> |
55 | #include <QtCore/qbitarray.h> |
56 | #include <QtCore/qreadwritelock.h> |
57 | #include <qfileinfo.h> |
58 | #include <qdir.h> |
59 | #include <qmetatype.h> |
60 | #include <qobjectdefs.h> |
61 | #include <qdatetime.h> |
62 | #include <qbytearray.h> |
63 | #include <qreadwritelock.h> |
64 | #include <qstring.h> |
65 | #include <qstringlist.h> |
66 | #include <qvector.h> |
67 | #include <qlocale.h> |
68 | #include <QtCore/qcryptographichash.h> |
69 | #include <QtScript/qscriptvalue.h> |
70 | |
71 | #include <ctype.h> |
72 | |
73 | #ifdef QT_BOOTSTRAPPED |
74 | # ifndef QT_NO_GEOM_VARIANT |
75 | # define QT_NO_GEOM_VARIANT |
76 | # endif |
77 | #else |
78 | # include <qbitarray.h> |
79 | # include <qurl.h> |
80 | # include <qvariant.h> |
81 | #endif |
82 | |
83 | #ifndef QT_NO_GEOM_VARIANT |
84 | # include <qsize.h> |
85 | # include <qpoint.h> |
86 | # include <qrect.h> |
87 | # include <qline.h> |
88 | # include <qvector3d.h> |
89 | #endif |
90 | #define NS(x) QT_PREPEND_NAMESPACE(x) |
91 | |
92 | QT_BEGIN_NAMESPACE |
93 | |
94 | struct QDeclarativeMetaTypeData |
95 | { |
96 | ~QDeclarativeMetaTypeData(); |
97 | QList<QDeclarativeType *> types; |
98 | typedef QHash<int, QDeclarativeType *> Ids; |
99 | Ids idToType; |
100 | typedef QHash<QByteArray, QDeclarativeType *> Names; |
101 | Names nameToType; |
102 | typedef QHash<const QMetaObject *, QDeclarativeType *> MetaObjects; |
103 | MetaObjects metaObjectToType; |
104 | typedef QHash<int, QDeclarativeMetaType::StringConverter> StringConverters; |
105 | StringConverters stringConverters; |
106 | |
107 | struct ModuleInfo { |
108 | ModuleInfo(int major, int minor) |
109 | : vmajor_min(major), vminor_min(minor), vmajor_max(major), vminor_max(minor) {} |
110 | ModuleInfo(int major_min, int minor_min, int major_max, int minor_max) |
111 | : vmajor_min(major_min), vminor_min(minor_min), vmajor_max(major_max), vminor_max(minor_max) {} |
112 | int vmajor_min, vminor_min; |
113 | int vmajor_max, vminor_max; |
114 | }; |
115 | typedef QHash<QByteArray, ModuleInfo> ModuleInfoHash; |
116 | ModuleInfoHash modules; |
117 | |
118 | QBitArray objects; |
119 | QBitArray interfaces; |
120 | QBitArray lists; |
121 | |
122 | QList<QDeclarativePrivate::AutoParentFunction> parentFunctions; |
123 | }; |
124 | Q_GLOBAL_STATIC(QDeclarativeMetaTypeData, metaTypeData) |
125 | Q_GLOBAL_STATIC(QReadWriteLock, metaTypeDataLock) |
126 | |
127 | struct QDeclarativeRegisteredComponentData |
128 | { |
129 | QMap<QByteArray, QDeclarativeDirComponents*> registeredComponents; |
130 | }; |
131 | |
132 | Q_GLOBAL_STATIC(QDeclarativeRegisteredComponentData, registeredComponentData) |
133 | Q_GLOBAL_STATIC(QReadWriteLock, registeredComponentDataLock) |
134 | |
135 | QDeclarativeMetaTypeData::~QDeclarativeMetaTypeData() |
136 | { |
137 | for (int i = 0; i < types.count(); ++i) |
138 | delete types.at(i); |
139 | } |
140 | |
141 | class QDeclarativeTypePrivate |
142 | { |
143 | public: |
144 | QDeclarativeTypePrivate(); |
145 | |
146 | void init() const; |
147 | |
148 | bool m_isInterface : 1; |
149 | const char *m_iid; |
150 | QByteArray m_module; |
151 | QByteArray m_name; |
152 | int m_version_maj; |
153 | int m_version_min; |
154 | int m_typeId; int m_listId; |
155 | int m_revision; |
156 | mutable bool m_containsRevisionedAttributes; |
157 | mutable QDeclarativeType *m_superType; |
158 | |
159 | int m_allocationSize; |
160 | void (*m_newFunc)(void *); |
161 | QString m_noCreationReason; |
162 | |
163 | const QMetaObject *m_baseMetaObject; |
164 | QDeclarativeAttachedPropertiesFunc m_attachedPropertiesFunc; |
165 | const QMetaObject *m_attachedPropertiesType; |
166 | int m_attachedPropertiesId; |
167 | int m_parserStatusCast; |
168 | int m_propertyValueSourceCast; |
169 | int m_propertyValueInterceptorCast; |
170 | QObject *(*m_extFunc)(QObject *); |
171 | const QMetaObject *m_extMetaObject; |
172 | int m_index; |
173 | QDeclarativeCustomParser *m_customParser; |
174 | mutable volatile bool m_isSetup:1; |
175 | mutable bool m_haveSuperType : 1; |
176 | mutable QList<QDeclarativeProxyMetaObject::ProxyData> m_metaObjects; |
177 | |
178 | static QHash<const QMetaObject *, int> m_attachedPropertyIds; |
179 | }; |
180 | |
181 | QHash<const QMetaObject *, int> QDeclarativeTypePrivate::m_attachedPropertyIds; |
182 | |
183 | QDeclarativeTypePrivate::QDeclarativeTypePrivate() |
184 | : m_isInterface(false), m_iid(0), m_typeId(0), m_listId(0), m_revision(0), m_containsRevisionedAttributes(false), |
185 | m_superType(0), m_allocationSize(0), m_newFunc(0), m_baseMetaObject(0), m_attachedPropertiesFunc(0), |
186 | m_attachedPropertiesType(0), m_parserStatusCast(-1), m_propertyValueSourceCast(-1), |
187 | m_propertyValueInterceptorCast(-1), m_extFunc(0), m_extMetaObject(0), m_index(-1), m_customParser(0), |
188 | m_isSetup(false), m_haveSuperType(false) |
189 | { |
190 | } |
191 | |
192 | |
193 | QDeclarativeType::QDeclarativeType(int index, const QDeclarativePrivate::RegisterInterface &interface) |
194 | : d(new QDeclarativeTypePrivate) |
195 | { |
196 | d->m_isInterface = true; |
197 | d->m_iid = interface.iid; |
198 | d->m_typeId = interface.typeId; |
199 | d->m_listId = interface.listId; |
200 | d->m_newFunc = 0; |
201 | d->m_index = index; |
202 | d->m_isSetup = true; |
203 | d->m_version_maj = 0; |
204 | d->m_version_min = 0; |
205 | } |
206 | |
207 | QDeclarativeType::QDeclarativeType(int index, const QDeclarativePrivate::RegisterType &type) |
208 | : d(new QDeclarativeTypePrivate) |
209 | { |
210 | QByteArray name = type.uri; |
211 | if (type.uri) name += '/'; |
212 | name += type.elementName; |
213 | |
214 | d->m_module = type.uri; |
215 | d->m_name = name; |
216 | d->m_version_maj = type.versionMajor; |
217 | d->m_version_min = type.versionMinor; |
218 | if (type.version >= 1) // revisions added in version 1 |
219 | d->m_revision = type.revision; |
220 | d->m_typeId = type.typeId; |
221 | d->m_listId = type.listId; |
222 | d->m_allocationSize = type.objectSize; |
223 | d->m_newFunc = type.create; |
224 | d->m_noCreationReason = type.noCreationReason; |
225 | d->m_baseMetaObject = type.metaObject; |
226 | d->m_attachedPropertiesFunc = type.attachedPropertiesFunction; |
227 | d->m_attachedPropertiesType = type.attachedPropertiesMetaObject; |
228 | if (d->m_attachedPropertiesType) { |
229 | QHash<const QMetaObject *, int>::Iterator iter = d->m_attachedPropertyIds.find(d->m_baseMetaObject); |
230 | if (iter == d->m_attachedPropertyIds.end()) |
231 | iter = d->m_attachedPropertyIds.insert(d->m_baseMetaObject, index); |
232 | d->m_attachedPropertiesId = *iter; |
233 | } else { |
234 | d->m_attachedPropertiesId = -1; |
235 | } |
236 | d->m_parserStatusCast = type.parserStatusCast; |
237 | d->m_propertyValueSourceCast = type.valueSourceCast; |
238 | d->m_propertyValueInterceptorCast = type.valueInterceptorCast; |
239 | d->m_extFunc = type.extensionObjectCreate; |
240 | d->m_index = index; |
241 | d->m_customParser = type.customParser; |
242 | |
243 | if (type.extensionMetaObject) |
244 | d->m_extMetaObject = type.extensionMetaObject; |
245 | } |
246 | |
247 | QDeclarativeType::~QDeclarativeType() |
248 | { |
249 | delete d->m_customParser; |
250 | delete d; |
251 | } |
252 | |
253 | QByteArray QDeclarativeType::module() const |
254 | { |
255 | return d->m_module; |
256 | } |
257 | |
258 | int QDeclarativeType::majorVersion() const |
259 | { |
260 | return d->m_version_maj; |
261 | } |
262 | |
263 | int QDeclarativeType::minorVersion() const |
264 | { |
265 | return d->m_version_min; |
266 | } |
267 | |
268 | bool QDeclarativeType::availableInVersion(int vmajor, int vminor) const |
269 | { |
270 | return vmajor > d->m_version_maj || (vmajor == d->m_version_maj && vminor >= d->m_version_min); |
271 | } |
272 | |
273 | bool QDeclarativeType::availableInVersion(const QByteArray &module, int vmajor, int vminor) const |
274 | { |
275 | return module == d->m_module && (vmajor > d->m_version_maj || (vmajor == d->m_version_maj && vminor >= d->m_version_min)); |
276 | } |
277 | |
278 | // returns the nearest _registered_ super class |
279 | QDeclarativeType *QDeclarativeType::superType() const |
280 | { |
281 | if (!d->m_haveSuperType) { |
282 | const QMetaObject *mo = d->m_baseMetaObject->superClass(); |
283 | while (mo && !d->m_superType) { |
284 | d->m_superType = QDeclarativeMetaType::qmlType(mo, d->m_module, d->m_version_maj, d->m_version_min); |
285 | mo = mo->superClass(); |
286 | } |
287 | d->m_haveSuperType = true; |
288 | } |
289 | |
290 | return d->m_superType; |
291 | } |
292 | |
293 | static void clone(QMetaObjectBuilder &builder, const QMetaObject *mo, |
294 | const QMetaObject *ignoreStart, const QMetaObject *ignoreEnd) |
295 | { |
296 | // Clone Q_CLASSINFO |
297 | for (int ii = mo->classInfoOffset(); ii < mo->classInfoCount(); ++ii) { |
298 | QMetaClassInfo info = mo->classInfo(ii); |
299 | |
300 | int otherIndex = ignoreEnd->indexOfClassInfo(info.name()); |
301 | if (otherIndex >= ignoreStart->classInfoOffset() + ignoreStart->classInfoCount()) { |
302 | // Skip |
303 | } else { |
304 | builder.addClassInfo(info.name(), info.value()); |
305 | } |
306 | } |
307 | |
308 | // Clone Q_PROPERTY |
309 | for (int ii = mo->propertyOffset(); ii < mo->propertyCount(); ++ii) { |
310 | QMetaProperty property = mo->property(ii); |
311 | |
312 | int otherIndex = ignoreEnd->indexOfProperty(property.name()); |
313 | if (otherIndex >= ignoreStart->propertyOffset() + ignoreStart->propertyCount()) { |
314 | builder.addProperty(QByteArray("__qml_ignore__" ) + property.name(), QByteArray("void" )); |
315 | // Skip |
316 | } else { |
317 | builder.addProperty(property); |
318 | } |
319 | } |
320 | |
321 | // Clone Q_METHODS |
322 | for (int ii = mo->methodOffset(); ii < mo->methodCount(); ++ii) { |
323 | QMetaMethod method = mo->method(ii); |
324 | |
325 | // More complex - need to search name |
326 | QByteArray name = method.signature(); |
327 | int parenIdx = name.indexOf('('); |
328 | if (parenIdx != -1) name = name.left(parenIdx); |
329 | |
330 | |
331 | bool found = false; |
332 | |
333 | for (int ii = ignoreStart->methodOffset() + ignoreStart->methodCount(); |
334 | !found && ii < ignoreEnd->methodOffset() + ignoreEnd->methodCount(); |
335 | ++ii) { |
336 | |
337 | QMetaMethod other = ignoreEnd->method(ii); |
338 | QByteArray othername = other.signature(); |
339 | int parenIdx = othername.indexOf('('); |
340 | if (parenIdx != -1) othername = othername.left(parenIdx); |
341 | |
342 | found = name == othername; |
343 | } |
344 | |
345 | QMetaMethodBuilder m = builder.addMethod(method); |
346 | if (found) // SKIP |
347 | m.setAccess(QMetaMethod::Private); |
348 | } |
349 | |
350 | // Clone Q_ENUMS |
351 | for (int ii = mo->enumeratorOffset(); ii < mo->enumeratorCount(); ++ii) { |
352 | QMetaEnum enumerator = mo->enumerator(ii); |
353 | |
354 | int otherIndex = ignoreEnd->indexOfEnumerator(enumerator.name()); |
355 | if (otherIndex >= ignoreStart->enumeratorOffset() + ignoreStart->enumeratorCount()) { |
356 | // Skip |
357 | } else { |
358 | builder.addEnumerator(enumerator); |
359 | } |
360 | } |
361 | } |
362 | |
363 | void QDeclarativeTypePrivate::init() const |
364 | { |
365 | if (m_isSetup) return; |
366 | |
367 | QWriteLocker lock(metaTypeDataLock()); |
368 | if (m_isSetup) |
369 | return; |
370 | |
371 | // Setup extended meta object |
372 | // XXX - very inefficient |
373 | const QMetaObject *mo = m_baseMetaObject; |
374 | if (m_extFunc) { |
375 | QMetaObject *mmo = new QMetaObject; |
376 | *mmo = *m_extMetaObject; |
377 | mmo->d.superdata = mo; |
378 | QDeclarativeProxyMetaObject::ProxyData data = { mmo, m_extFunc, 0, 0 }; |
379 | m_metaObjects << data; |
380 | } |
381 | |
382 | mo = mo->d.superdata; |
383 | while(mo) { |
384 | QDeclarativeType *t = metaTypeData()->metaObjectToType.value(mo); |
385 | if (t) { |
386 | if (t->d->m_extFunc) { |
387 | QMetaObjectBuilder builder; |
388 | clone(builder, t->d->m_extMetaObject, t->d->m_baseMetaObject, m_baseMetaObject); |
389 | QMetaObject *mmo = builder.toMetaObject(); |
390 | mmo->d.superdata = m_baseMetaObject; |
391 | if (!m_metaObjects.isEmpty()) |
392 | m_metaObjects.last().metaObject->d.superdata = mmo; |
393 | QDeclarativeProxyMetaObject::ProxyData data = { mmo, t->d->m_extFunc, 0, 0 }; |
394 | m_metaObjects << data; |
395 | } |
396 | } |
397 | mo = mo->d.superdata; |
398 | } |
399 | |
400 | for (int ii = 0; ii < m_metaObjects.count(); ++ii) { |
401 | m_metaObjects[ii].propertyOffset = |
402 | m_metaObjects.at(ii).metaObject->propertyOffset(); |
403 | m_metaObjects[ii].methodOffset = |
404 | m_metaObjects.at(ii).metaObject->methodOffset(); |
405 | } |
406 | |
407 | // Check for revisioned details |
408 | { |
409 | const QMetaObject *mo = 0; |
410 | if (m_metaObjects.isEmpty()) |
411 | mo = m_baseMetaObject; |
412 | else |
413 | mo = m_metaObjects.first().metaObject; |
414 | |
415 | for (int ii = 0; !m_containsRevisionedAttributes && ii < mo->propertyCount(); ++ii) { |
416 | if (mo->property(ii).revision() != 0) |
417 | m_containsRevisionedAttributes = true; |
418 | } |
419 | |
420 | for (int ii = 0; !m_containsRevisionedAttributes && ii < mo->methodCount(); ++ii) { |
421 | if (mo->method(ii).revision() != 0) |
422 | m_containsRevisionedAttributes = true; |
423 | } |
424 | } |
425 | |
426 | m_isSetup = true; |
427 | lock.unlock(); |
428 | } |
429 | |
430 | QByteArray QDeclarativeType::typeName() const |
431 | { |
432 | if (d->m_baseMetaObject) |
433 | return d->m_baseMetaObject->className(); |
434 | else |
435 | return QByteArray(); |
436 | } |
437 | |
438 | QByteArray QDeclarativeType::qmlTypeName() const |
439 | { |
440 | return d->m_name; |
441 | } |
442 | |
443 | QObject *QDeclarativeType::create() const |
444 | { |
445 | d->init(); |
446 | |
447 | QObject *rv = (QObject *)operator new(d->m_allocationSize); |
448 | d->m_newFunc(rv); |
449 | |
450 | if (rv && !d->m_metaObjects.isEmpty()) |
451 | (void)new QDeclarativeProxyMetaObject(rv, &d->m_metaObjects); |
452 | |
453 | return rv; |
454 | } |
455 | |
456 | void QDeclarativeType::create(QObject **out, void **memory, size_t additionalMemory) const |
457 | { |
458 | d->init(); |
459 | |
460 | QObject *rv = (QObject *)operator new(d->m_allocationSize + additionalMemory); |
461 | d->m_newFunc(rv); |
462 | |
463 | if (rv && !d->m_metaObjects.isEmpty()) |
464 | (void)new QDeclarativeProxyMetaObject(rv, &d->m_metaObjects); |
465 | |
466 | *out = rv; |
467 | *memory = ((char *)rv) + d->m_allocationSize; |
468 | } |
469 | |
470 | QDeclarativeCustomParser *QDeclarativeType::customParser() const |
471 | { |
472 | return d->m_customParser; |
473 | } |
474 | |
475 | QDeclarativeType::CreateFunc QDeclarativeType::createFunction() const |
476 | { |
477 | return d->m_newFunc; |
478 | } |
479 | |
480 | QString QDeclarativeType::noCreationReason() const |
481 | { |
482 | return d->m_noCreationReason; |
483 | } |
484 | |
485 | int QDeclarativeType::createSize() const |
486 | { |
487 | return d->m_allocationSize; |
488 | } |
489 | |
490 | bool QDeclarativeType::isCreatable() const |
491 | { |
492 | return d->m_newFunc != 0; |
493 | } |
494 | |
495 | bool QDeclarativeType::isExtendedType() const |
496 | { |
497 | d->init(); |
498 | |
499 | return !d->m_metaObjects.isEmpty(); |
500 | } |
501 | |
502 | bool QDeclarativeType::isInterface() const |
503 | { |
504 | return d->m_isInterface; |
505 | } |
506 | |
507 | int QDeclarativeType::typeId() const |
508 | { |
509 | return d->m_typeId; |
510 | } |
511 | |
512 | int QDeclarativeType::qListTypeId() const |
513 | { |
514 | return d->m_listId; |
515 | } |
516 | |
517 | const QMetaObject *QDeclarativeType::metaObject() const |
518 | { |
519 | d->init(); |
520 | |
521 | if (d->m_metaObjects.isEmpty()) |
522 | return d->m_baseMetaObject; |
523 | else |
524 | return d->m_metaObjects.first().metaObject; |
525 | |
526 | } |
527 | |
528 | const QMetaObject *QDeclarativeType::baseMetaObject() const |
529 | { |
530 | return d->m_baseMetaObject; |
531 | } |
532 | |
533 | bool QDeclarativeType::containsRevisionedAttributes() const |
534 | { |
535 | d->init(); |
536 | |
537 | return d->m_containsRevisionedAttributes; |
538 | } |
539 | |
540 | int QDeclarativeType::metaObjectRevision() const |
541 | { |
542 | return d->m_revision; |
543 | } |
544 | |
545 | QDeclarativeAttachedPropertiesFunc QDeclarativeType::attachedPropertiesFunction() const |
546 | { |
547 | return d->m_attachedPropertiesFunc; |
548 | } |
549 | |
550 | const QMetaObject *QDeclarativeType::attachedPropertiesType() const |
551 | { |
552 | return d->m_attachedPropertiesType; |
553 | } |
554 | |
555 | /* |
556 | This is the id passed to qmlAttachedPropertiesById(). This is different from the index |
557 | for the case that a single class is registered under two or more names (eg. Item in |
558 | Qt 4.7 and QtQuick 1.0). |
559 | */ |
560 | int QDeclarativeType::attachedPropertiesId() const |
561 | { |
562 | return d->m_attachedPropertiesId; |
563 | } |
564 | |
565 | int QDeclarativeType::parserStatusCast() const |
566 | { |
567 | return d->m_parserStatusCast; |
568 | } |
569 | |
570 | int QDeclarativeType::propertyValueSourceCast() const |
571 | { |
572 | return d->m_propertyValueSourceCast; |
573 | } |
574 | |
575 | int QDeclarativeType::propertyValueInterceptorCast() const |
576 | { |
577 | return d->m_propertyValueInterceptorCast; |
578 | } |
579 | |
580 | const char *QDeclarativeType::interfaceIId() const |
581 | { |
582 | return d->m_iid; |
583 | } |
584 | |
585 | int QDeclarativeType::index() const |
586 | { |
587 | return d->m_index; |
588 | } |
589 | |
590 | int registerAutoParentFunction(QDeclarativePrivate::RegisterAutoParent &autoparent) |
591 | { |
592 | QWriteLocker lock(metaTypeDataLock()); |
593 | QDeclarativeMetaTypeData *data = metaTypeData(); |
594 | |
595 | data->parentFunctions.append(autoparent.function); |
596 | |
597 | return data->parentFunctions.count() - 1; |
598 | } |
599 | |
600 | int registerInterface(const QDeclarativePrivate::RegisterInterface &interface) |
601 | { |
602 | if (interface.version > 0) |
603 | qFatal("qmlRegisterType(): Cannot mix incompatible QML versions." ); |
604 | |
605 | QWriteLocker lock(metaTypeDataLock()); |
606 | QDeclarativeMetaTypeData *data = metaTypeData(); |
607 | |
608 | int index = data->types.count(); |
609 | |
610 | QDeclarativeType *type = new QDeclarativeType(index, interface); |
611 | |
612 | data->types.append(type); |
613 | data->idToType.insert(type->typeId(), type); |
614 | data->idToType.insert(type->qListTypeId(), type); |
615 | // XXX No insertMulti, so no multi-version interfaces? |
616 | if (!type->qmlTypeName().isEmpty()) |
617 | data->nameToType.insert(type->qmlTypeName(), type); |
618 | |
619 | if (data->interfaces.size() <= interface.typeId) |
620 | data->interfaces.resize(interface.typeId + 16); |
621 | if (data->lists.size() <= interface.listId) |
622 | data->lists.resize(interface.listId + 16); |
623 | data->interfaces.setBit(interface.typeId, true); |
624 | data->lists.setBit(interface.listId, true); |
625 | |
626 | return index; |
627 | } |
628 | |
629 | int registerType(const QDeclarativePrivate::RegisterType &type) |
630 | { |
631 | if (type.elementName) { |
632 | for (int ii = 0; type.elementName[ii]; ++ii) { |
633 | if (!isalnum(type.elementName[ii])) { |
634 | qWarning("qmlRegisterType(): Invalid QML element name \"%s\"" , type.elementName); |
635 | return -1; |
636 | } |
637 | } |
638 | } |
639 | |
640 | QWriteLocker lock(metaTypeDataLock()); |
641 | QDeclarativeMetaTypeData *data = metaTypeData(); |
642 | int index = data->types.count(); |
643 | |
644 | QDeclarativeType *dtype = new QDeclarativeType(index, type); |
645 | |
646 | data->types.append(dtype); |
647 | data->idToType.insert(dtype->typeId(), dtype); |
648 | if (dtype->qListTypeId()) data->idToType.insert(dtype->qListTypeId(), dtype); |
649 | |
650 | if (!dtype->qmlTypeName().isEmpty()) |
651 | data->nameToType.insertMulti(dtype->qmlTypeName(), dtype); |
652 | |
653 | data->metaObjectToType.insertMulti(dtype->baseMetaObject(), dtype); |
654 | |
655 | if (data->objects.size() <= type.typeId) |
656 | data->objects.resize(type.typeId + 16); |
657 | if (data->lists.size() <= type.listId) |
658 | data->lists.resize(type.listId + 16); |
659 | data->objects.setBit(type.typeId, true); |
660 | if (type.listId) data->lists.setBit(type.listId, true); |
661 | |
662 | if (type.uri) { |
663 | QByteArray mod(type.uri); |
664 | QDeclarativeMetaTypeData::ModuleInfoHash::Iterator it = data->modules.find(mod); |
665 | if (it == data->modules.end()) { |
666 | // New module |
667 | data->modules.insert(mod, QDeclarativeMetaTypeData::ModuleInfo(type.versionMajor,type.versionMinor)); |
668 | } else if ((*it).vmajor_max < type.versionMajor || ((*it).vmajor_max == type.versionMajor && (*it).vminor_max < type.versionMinor)) { |
669 | // Newer module |
670 | data->modules.insert(mod, QDeclarativeMetaTypeData::ModuleInfo((*it).vmajor_min, (*it).vminor_min, type.versionMajor, type.versionMinor)); |
671 | } else if ((*it).vmajor_min > type.versionMajor || ((*it).vmajor_min == type.versionMajor && (*it).vminor_min > type.versionMinor)) { |
672 | // Older module |
673 | data->modules.insert(mod, QDeclarativeMetaTypeData::ModuleInfo(type.versionMajor, type.versionMinor, (*it).vmajor_min, (*it).vminor_min)); |
674 | } |
675 | } |
676 | |
677 | return index; |
678 | } |
679 | |
680 | int registerComponent(const QDeclarativePrivate::RegisterComponent& data) |
681 | { |
682 | if (data.typeName) { |
683 | for (int ii = 0; data.typeName[ii]; ++ii) { |
684 | if (!isalnum(data.typeName[ii])) { |
685 | qWarning("qmlRegisterType(): Invalid QML type name \"%s\"" , data.typeName); |
686 | return 0; |
687 | } |
688 | } |
689 | } else { |
690 | qWarning("qmlRegisterType(): No QML type name for \"%s\"" , data.url.toString().toLatin1().constData()); |
691 | return 0; |
692 | } |
693 | |
694 | QWriteLocker lock(registeredComponentDataLock()); |
695 | QString path; |
696 | // Relative paths are relative to application working directory |
697 | if (data.url.isRelative() || data.url.scheme() == QLatin1String("file" )) // Workaround QTBUG-11929 |
698 | path = QUrl::fromLocalFile(QDir::currentPath()+QLatin1String("/" )).resolved(data.url).toString(); |
699 | else |
700 | path = data.url.toString(); |
701 | QDeclarativeRegisteredComponentData *d = registeredComponentData(); |
702 | QDeclarativeDirParser::Component comp( |
703 | QString::fromUtf8(data.typeName), |
704 | path, |
705 | data.majorVersion, |
706 | data.minorVersion |
707 | ); |
708 | |
709 | QDeclarativeDirComponents* comps = d->registeredComponents.value(QByteArray(data.uri), 0); |
710 | if (!comps) |
711 | d->registeredComponents.insert(QByteArray(data.uri), comps = new QDeclarativeDirComponents); |
712 | |
713 | // Types added later should take precedence, like registerType |
714 | comps->prepend(comp); |
715 | |
716 | return 1; |
717 | } |
718 | |
719 | /* |
720 | This method is "over generalized" to allow us to (potentially) register more types of things in |
721 | the future without adding exported symbols. |
722 | */ |
723 | int QDeclarativePrivate::qmlregister(RegistrationType type, void *data) |
724 | { |
725 | if (type == TypeRegistration) { |
726 | return registerType(*reinterpret_cast<RegisterType *>(data)); |
727 | } else if (type == InterfaceRegistration) { |
728 | return registerInterface(*reinterpret_cast<RegisterInterface *>(data)); |
729 | } else if (type == AutoParentRegistration) { |
730 | return registerAutoParentFunction(*reinterpret_cast<RegisterAutoParent *>(data)); |
731 | } else if (type == ComponentRegistration) { |
732 | return registerComponent(*reinterpret_cast<RegisterComponent *>(data)); |
733 | } |
734 | return -1; |
735 | } |
736 | |
737 | /* |
738 | Have any types been registered for \a module with at least versionMajor.versionMinor, and types |
739 | for \a module with at most versionMajor.versionMinor. |
740 | |
741 | So if only 4.7 and 4.9 have been registered, 4.7,4.8, and 4.9 are valid, but not 4.6 nor 4.10. |
742 | |
743 | Passing -1 for both \a versionMajor \a versionMinor will return true if any version is installed. |
744 | */ |
745 | bool QDeclarativeMetaType::isModule(const QByteArray &module, int versionMajor, int versionMinor) |
746 | { |
747 | #ifndef QT_NO_IMPORT_QT47_QML |
748 | // "import Qt 4.7" should have died off, but unfortunately, it was in a |
749 | // major release. We don't register 4.7 types by default, as it's a |
750 | // performance penalty. Instead, register them on-demand. |
751 | if (strcmp(module.constData(), "Qt" ) == 0 && versionMajor == 4 && versionMinor == 7) { |
752 | static bool qt47Registered = false; |
753 | if (!qt47Registered) { |
754 | qWarning() << Q_FUNC_INFO << "Qt 4.7 import detected; please note that Qt 4.7 is directly reusable as QtQuick 1.x with no code changes. Continuing, but startup time will be slower." ; |
755 | qt47Registered = true; |
756 | QDeclarativeEnginePrivate::defineModuleCompat(); |
757 | QDeclarativeItemModule::defineModuleCompat(); |
758 | QDeclarativeValueTypeFactory::registerValueTypesCompat(); |
759 | QDeclarativeUtilModule::defineModuleCompat(); |
760 | } |
761 | } |
762 | #endif |
763 | |
764 | QDeclarativeMetaTypeData *data = metaTypeData(); |
765 | QDeclarativeMetaTypeData::ModuleInfoHash::Iterator it = data->modules.find(module); |
766 | return it != data->modules.end() |
767 | && ((versionMajor<0 && versionMinor<0) || |
768 | (((*it).vmajor_max > versionMajor || |
769 | ((*it).vmajor_max == versionMajor && (*it).vminor_max >= versionMinor)) |
770 | && ((*it).vmajor_min < versionMajor || |
771 | ((*it).vmajor_min == versionMajor && (*it).vminor_min <= versionMinor)))); |
772 | } |
773 | |
774 | QList<QDeclarativePrivate::AutoParentFunction> QDeclarativeMetaType::parentFunctions() |
775 | { |
776 | QReadLocker lock(metaTypeDataLock()); |
777 | QDeclarativeMetaTypeData *data = metaTypeData(); |
778 | return data->parentFunctions; |
779 | } |
780 | |
781 | QObject *QDeclarativeMetaType::toQObject(const QVariant &v, bool *ok) |
782 | { |
783 | if (!isQObject(v.userType())) { |
784 | if (ok) *ok = false; |
785 | return 0; |
786 | } |
787 | |
788 | if (ok) *ok = true; |
789 | |
790 | return *(QObject **)v.constData(); |
791 | } |
792 | |
793 | bool QDeclarativeMetaType::isQObject(int userType) |
794 | { |
795 | if (userType == QMetaType::QObjectStar) |
796 | return true; |
797 | |
798 | QReadLocker lock(metaTypeDataLock()); |
799 | QDeclarativeMetaTypeData *data = metaTypeData(); |
800 | return userType >= 0 && userType < data->objects.size() && data->objects.testBit(userType); |
801 | } |
802 | |
803 | /* |
804 | Returns the item type for a list of type \a id. |
805 | */ |
806 | int QDeclarativeMetaType::listType(int id) |
807 | { |
808 | QReadLocker lock(metaTypeDataLock()); |
809 | QDeclarativeMetaTypeData *data = metaTypeData(); |
810 | QDeclarativeType *type = data->idToType.value(id); |
811 | if (type && type->qListTypeId() == id) |
812 | return type->typeId(); |
813 | else |
814 | return 0; |
815 | } |
816 | |
817 | int QDeclarativeMetaType::attachedPropertiesFuncId(const QMetaObject *mo) |
818 | { |
819 | QReadLocker lock(metaTypeDataLock()); |
820 | QDeclarativeMetaTypeData *data = metaTypeData(); |
821 | |
822 | QDeclarativeType *type = data->metaObjectToType.value(mo); |
823 | if (type && type->attachedPropertiesFunction()) |
824 | return type->attachedPropertiesId(); |
825 | else |
826 | return -1; |
827 | } |
828 | |
829 | QDeclarativeAttachedPropertiesFunc QDeclarativeMetaType::attachedPropertiesFuncById(int id) |
830 | { |
831 | if (id < 0) |
832 | return 0; |
833 | QReadLocker lock(metaTypeDataLock()); |
834 | QDeclarativeMetaTypeData *data = metaTypeData(); |
835 | return data->types.at(id)->attachedPropertiesFunction(); |
836 | } |
837 | |
838 | QMetaProperty QDeclarativeMetaType::defaultProperty(const QMetaObject *metaObject) |
839 | { |
840 | int idx = metaObject->indexOfClassInfo("DefaultProperty" ); |
841 | if (-1 == idx) |
842 | return QMetaProperty(); |
843 | |
844 | QMetaClassInfo info = metaObject->classInfo(idx); |
845 | if (!info.value()) |
846 | return QMetaProperty(); |
847 | |
848 | idx = metaObject->indexOfProperty(info.value()); |
849 | if (-1 == idx) |
850 | return QMetaProperty(); |
851 | |
852 | return metaObject->property(idx); |
853 | } |
854 | |
855 | QMetaProperty QDeclarativeMetaType::defaultProperty(QObject *obj) |
856 | { |
857 | if (!obj) |
858 | return QMetaProperty(); |
859 | |
860 | const QMetaObject *metaObject = obj->metaObject(); |
861 | return defaultProperty(metaObject); |
862 | } |
863 | |
864 | QMetaMethod QDeclarativeMetaType::defaultMethod(const QMetaObject *metaObject) |
865 | { |
866 | int idx = metaObject->indexOfClassInfo("DefaultMethod" ); |
867 | if (-1 == idx) |
868 | return QMetaMethod(); |
869 | |
870 | QMetaClassInfo info = metaObject->classInfo(idx); |
871 | if (!info.value()) |
872 | return QMetaMethod(); |
873 | |
874 | idx = metaObject->indexOfMethod(info.value()); |
875 | if (-1 == idx) |
876 | return QMetaMethod(); |
877 | |
878 | return metaObject->method(idx); |
879 | } |
880 | |
881 | QMetaMethod QDeclarativeMetaType::defaultMethod(QObject *obj) |
882 | { |
883 | if (!obj) |
884 | return QMetaMethod(); |
885 | |
886 | const QMetaObject *metaObject = obj->metaObject(); |
887 | return defaultMethod(metaObject); |
888 | } |
889 | |
890 | QDeclarativeMetaType::TypeCategory QDeclarativeMetaType::typeCategory(int userType) |
891 | { |
892 | if (userType < 0) |
893 | return Unknown; |
894 | if (userType == QMetaType::QObjectStar) |
895 | return Object; |
896 | |
897 | QReadLocker lock(metaTypeDataLock()); |
898 | QDeclarativeMetaTypeData *data = metaTypeData(); |
899 | if (userType < data->objects.size() && data->objects.testBit(userType)) |
900 | return Object; |
901 | else if (userType < data->lists.size() && data->lists.testBit(userType)) |
902 | return List; |
903 | else |
904 | return Unknown; |
905 | } |
906 | |
907 | bool QDeclarativeMetaType::isInterface(int userType) |
908 | { |
909 | QReadLocker lock(metaTypeDataLock()); |
910 | QDeclarativeMetaTypeData *data = metaTypeData(); |
911 | return userType >= 0 && userType < data->interfaces.size() && data->interfaces.testBit(userType); |
912 | } |
913 | |
914 | const char *QDeclarativeMetaType::interfaceIId(int userType) |
915 | { |
916 | QReadLocker lock(metaTypeDataLock()); |
917 | QDeclarativeMetaTypeData *data = metaTypeData(); |
918 | QDeclarativeType *type = data->idToType.value(userType); |
919 | lock.unlock(); |
920 | if (type && type->isInterface() && type->typeId() == userType) |
921 | return type->interfaceIId(); |
922 | else |
923 | return 0; |
924 | } |
925 | |
926 | bool QDeclarativeMetaType::isList(int userType) |
927 | { |
928 | QReadLocker lock(metaTypeDataLock()); |
929 | QDeclarativeMetaTypeData *data = metaTypeData(); |
930 | return userType >= 0 && userType < data->lists.size() && data->lists.testBit(userType); |
931 | } |
932 | |
933 | /*! |
934 | A custom string convertor allows you to specify a function pointer that |
935 | returns a variant of \a type. For example, if you have written your own icon |
936 | class that you want to support as an object property assignable in QML: |
937 | |
938 | \code |
939 | int type = qRegisterMetaType<SuperIcon>("SuperIcon"); |
940 | QML::addCustomStringConvertor(type, &SuperIcon::pixmapFromString); |
941 | \endcode |
942 | |
943 | The function pointer must be of the form: |
944 | \code |
945 | QVariant (*StringConverter)(const QString &); |
946 | \endcode |
947 | */ |
948 | void QDeclarativeMetaType::registerCustomStringConverter(int type, StringConverter converter) |
949 | { |
950 | QWriteLocker lock(metaTypeDataLock()); |
951 | |
952 | QDeclarativeMetaTypeData *data = metaTypeData(); |
953 | if (data->stringConverters.contains(type)) |
954 | return; |
955 | data->stringConverters.insert(type, converter); |
956 | } |
957 | |
958 | /*! |
959 | Return the custom string converter for \a type, previously installed through |
960 | registerCustomStringConverter() |
961 | */ |
962 | QDeclarativeMetaType::StringConverter QDeclarativeMetaType::customStringConverter(int type) |
963 | { |
964 | QReadLocker lock(metaTypeDataLock()); |
965 | |
966 | QDeclarativeMetaTypeData *data = metaTypeData(); |
967 | return data->stringConverters.value(type); |
968 | } |
969 | |
970 | /*! |
971 | Returns the type (if any) of URI-qualified named \a name in version specified |
972 | by \a version_major and \a version_minor. |
973 | */ |
974 | QDeclarativeType *QDeclarativeMetaType::qmlType(const QByteArray &name, int version_major, int version_minor) |
975 | { |
976 | QReadLocker lock(metaTypeDataLock()); |
977 | QDeclarativeMetaTypeData *data = metaTypeData(); |
978 | |
979 | QList<QDeclarativeType*> types = data->nameToType.values(name); |
980 | foreach (QDeclarativeType *t, types) { |
981 | // XXX version_major<0 just a kludge for QDeclarativePropertyPrivate::initProperty |
982 | if (version_major<0 || t->availableInVersion(version_major,version_minor)) |
983 | return t; |
984 | } |
985 | return 0; |
986 | } |
987 | |
988 | /*! |
989 | Returns the type (if any) that corresponds to the \a metaObject. Returns null if no |
990 | type is registered. |
991 | */ |
992 | QDeclarativeType *QDeclarativeMetaType::qmlType(const QMetaObject *metaObject) |
993 | { |
994 | QReadLocker lock(metaTypeDataLock()); |
995 | QDeclarativeMetaTypeData *data = metaTypeData(); |
996 | |
997 | return data->metaObjectToType.value(metaObject); |
998 | } |
999 | |
1000 | /*! |
1001 | Returns the type (if any) that corresponds to the \a metaObject in version specified |
1002 | by \a version_major and \a version_minor in module specified by \a uri. Returns null if no |
1003 | type is registered. |
1004 | */ |
1005 | QDeclarativeType *QDeclarativeMetaType::qmlType(const QMetaObject *metaObject, const QByteArray &module, int version_major, int version_minor) |
1006 | { |
1007 | QReadLocker lock(metaTypeDataLock()); |
1008 | QDeclarativeMetaTypeData *data = metaTypeData(); |
1009 | |
1010 | QDeclarativeMetaTypeData::MetaObjects::const_iterator it = data->metaObjectToType.find(metaObject); |
1011 | while (it != data->metaObjectToType.end() && it.key() == metaObject) { |
1012 | QDeclarativeType *t = *it; |
1013 | if (version_major < 0 || t->availableInVersion(module, version_major,version_minor)) |
1014 | return t; |
1015 | ++it; |
1016 | } |
1017 | |
1018 | return 0; |
1019 | } |
1020 | |
1021 | /*! |
1022 | Returns the type (if any) that corresponds to the QVariant::Type \a userType. |
1023 | Returns null if no type is registered. |
1024 | */ |
1025 | QDeclarativeType *QDeclarativeMetaType::qmlType(int userType) |
1026 | { |
1027 | QReadLocker lock(metaTypeDataLock()); |
1028 | QDeclarativeMetaTypeData *data = metaTypeData(); |
1029 | |
1030 | QDeclarativeType *type = data->idToType.value(userType); |
1031 | if (type && type->typeId() == userType) |
1032 | return type; |
1033 | else |
1034 | return 0; |
1035 | } |
1036 | |
1037 | /*! |
1038 | Returns the component(s) that have been registered for the module specified by \a uri and the version specified |
1039 | by \a version_major and \a version_minor. Returns an empty list if no such components were registered. |
1040 | */ |
1041 | QDeclarativeDirComponents QDeclarativeMetaType::qmlComponents(const QByteArray &module, int version_major, int version_minor) |
1042 | { |
1043 | QReadLocker lock(registeredComponentDataLock()); |
1044 | QDeclarativeRegisteredComponentData *data = registeredComponentData(); |
1045 | |
1046 | QDeclarativeDirComponents* comps = data->registeredComponents.value(module, 0); |
1047 | if (!comps) |
1048 | return QDeclarativeDirComponents(); |
1049 | QDeclarativeDirComponents ret = *comps; |
1050 | for (int i = ret.count() - 1; i >= 0; i--) { |
1051 | QDeclarativeDirParser::Component &c = ret[i]; |
1052 | if (version_major >= 0 && (c.majorVersion != version_major || c.minorVersion > version_minor)) |
1053 | ret.removeAt(i); |
1054 | } |
1055 | |
1056 | return ret; |
1057 | } |
1058 | |
1059 | |
1060 | /*! |
1061 | Returns the list of registered QML type names. |
1062 | */ |
1063 | QList<QByteArray> QDeclarativeMetaType::qmlTypeNames() |
1064 | { |
1065 | QReadLocker lock(metaTypeDataLock()); |
1066 | QDeclarativeMetaTypeData *data = metaTypeData(); |
1067 | |
1068 | return data->nameToType.keys(); |
1069 | } |
1070 | |
1071 | /*! |
1072 | Returns the list of registered QML types. |
1073 | */ |
1074 | QList<QDeclarativeType*> QDeclarativeMetaType::qmlTypes() |
1075 | { |
1076 | QReadLocker lock(metaTypeDataLock()); |
1077 | QDeclarativeMetaTypeData *data = metaTypeData(); |
1078 | |
1079 | return data->nameToType.values(); |
1080 | } |
1081 | |
1082 | QT_END_NAMESPACE |
1083 | |
1084 | #include <QtGui/qfont.h> |
1085 | #include <QtGui/qpixmap.h> |
1086 | #include <QtGui/qbrush.h> |
1087 | #include <QtGui/qcolor.h> |
1088 | #include <QtGui/qpalette.h> |
1089 | #include <QtGui/qicon.h> |
1090 | #include <QtGui/qimage.h> |
1091 | #include <QtGui/qpolygon.h> |
1092 | #include <QtGui/qregion.h> |
1093 | #include <QtGui/qbitmap.h> |
1094 | #include <QtGui/qcursor.h> |
1095 | #include <QtGui/qsizepolicy.h> |
1096 | #include <QtGui/qkeysequence.h> |
1097 | #include <QtGui/qpen.h> |
1098 | |
1099 | //#include <QtGui/qtextlength.h> |
1100 | #include <QtGui/qtextformat.h> |
1101 | #include <QtGui/qmatrix.h> |
1102 | #include <QtGui/qtransform.h> |
1103 | #include <QtGui/qmatrix4x4.h> |
1104 | #include <QtGui/qvector2d.h> |
1105 | #include <QtGui/qvector3d.h> |
1106 | #include <QtGui/qvector4d.h> |
1107 | #include <QtGui/qquaternion.h> |
1108 | |
1109 | Q_DECLARE_METATYPE(QScriptValue); |
1110 | |
1111 | QT_BEGIN_NAMESPACE |
1112 | |
1113 | bool QDeclarativeMetaType::canCopy(int type) |
1114 | { |
1115 | switch(type) { |
1116 | case QMetaType::VoidStar: |
1117 | case QMetaType::QObjectStar: |
1118 | case QMetaType::QWidgetStar: |
1119 | case QMetaType::Long: |
1120 | case QMetaType::Int: |
1121 | case QMetaType::Short: |
1122 | case QMetaType::Char: |
1123 | case QMetaType::ULong: |
1124 | case QMetaType::UInt: |
1125 | case QMetaType::LongLong: |
1126 | case QMetaType::ULongLong: |
1127 | case QMetaType::UShort: |
1128 | case QMetaType::UChar: |
1129 | case QMetaType::Bool: |
1130 | case QMetaType::Float: |
1131 | case QMetaType::Double: |
1132 | case QMetaType::QChar: |
1133 | case QMetaType::QVariantMap: |
1134 | case QMetaType::QVariantHash: |
1135 | case QMetaType::QVariantList: |
1136 | case QMetaType::QByteArray: |
1137 | case QMetaType::QString: |
1138 | case QMetaType::QStringList: |
1139 | case QMetaType::QBitArray: |
1140 | case QMetaType::QDate: |
1141 | case QMetaType::QTime: |
1142 | case QMetaType::QDateTime: |
1143 | case QMetaType::QUrl: |
1144 | case QMetaType::QLocale: |
1145 | case QMetaType::QRect: |
1146 | case QMetaType::QRectF: |
1147 | case QMetaType::QSize: |
1148 | case QMetaType::QSizeF: |
1149 | case QMetaType::QLine: |
1150 | case QMetaType::QLineF: |
1151 | case QMetaType::QPoint: |
1152 | case QMetaType::QPointF: |
1153 | case QMetaType::QVector3D: |
1154 | #ifndef QT_NO_REGEXP |
1155 | case QMetaType::QRegExp: |
1156 | #endif |
1157 | case QMetaType::Void: |
1158 | #ifdef QT3_SUPPORT |
1159 | case QMetaType::QColorGroup: |
1160 | #endif |
1161 | case QMetaType::QFont: |
1162 | case QMetaType::QPixmap: |
1163 | case QMetaType::QBrush: |
1164 | case QMetaType::QColor: |
1165 | case QMetaType::QPalette: |
1166 | case QMetaType::QIcon: |
1167 | case QMetaType::QImage: |
1168 | case QMetaType::QPolygon: |
1169 | case QMetaType::QRegion: |
1170 | case QMetaType::QBitmap: |
1171 | #ifndef QT_NO_CURSOR |
1172 | case QMetaType::QCursor: |
1173 | #endif |
1174 | case QMetaType::QSizePolicy: |
1175 | case QMetaType::QKeySequence: |
1176 | case QMetaType::QPen: |
1177 | case QMetaType::QTextLength: |
1178 | case QMetaType::QTextFormat: |
1179 | case QMetaType::QMatrix: |
1180 | case QMetaType::QTransform: |
1181 | case QMetaType::QMatrix4x4: |
1182 | case QMetaType::QVector2D: |
1183 | case QMetaType::QVector4D: |
1184 | case QMetaType::QQuaternion: |
1185 | return true; |
1186 | |
1187 | default: |
1188 | if (type == qMetaTypeId<QVariant>() || |
1189 | type == qMetaTypeId<QScriptValue>() || |
1190 | typeCategory(type) != Unknown) { |
1191 | return true; |
1192 | } |
1193 | break; |
1194 | } |
1195 | |
1196 | return false; |
1197 | } |
1198 | |
1199 | /*! |
1200 | Copies \a copy into \a data, assuming they both are of type \a type. If |
1201 | \a copy is zero, a default type is copied. Returns true if the copy was |
1202 | successful and false if not. |
1203 | |
1204 | \note This should move into QMetaType once complete |
1205 | |
1206 | */ |
1207 | bool QDeclarativeMetaType::copy(int type, void *data, const void *copy) |
1208 | { |
1209 | if (copy) { |
1210 | switch(type) { |
1211 | case QMetaType::VoidStar: |
1212 | case QMetaType::QObjectStar: |
1213 | case QMetaType::QWidgetStar: |
1214 | *static_cast<void **>(data) = *static_cast<void* const *>(copy); |
1215 | return true; |
1216 | case QMetaType::Long: |
1217 | *static_cast<long *>(data) = *static_cast<const long*>(copy); |
1218 | return true; |
1219 | case QMetaType::Int: |
1220 | *static_cast<int *>(data) = *static_cast<const int*>(copy); |
1221 | return true; |
1222 | case QMetaType::Short: |
1223 | *static_cast<short *>(data) = *static_cast<const short*>(copy); |
1224 | return true; |
1225 | case QMetaType::Char: |
1226 | *static_cast<char *>(data) = *static_cast<const char*>(copy); |
1227 | return true; |
1228 | case QMetaType::ULong: |
1229 | *static_cast<ulong *>(data) = *static_cast<const ulong*>(copy); |
1230 | return true; |
1231 | case QMetaType::UInt: |
1232 | *static_cast<uint *>(data) = *static_cast<const uint*>(copy); |
1233 | return true; |
1234 | case QMetaType::LongLong: |
1235 | *static_cast<qlonglong *>(data) = *static_cast<const qlonglong*>(copy); |
1236 | return true; |
1237 | case QMetaType::ULongLong: |
1238 | *static_cast<qulonglong *>(data) = *static_cast<const qulonglong*>(copy); |
1239 | return true; |
1240 | case QMetaType::UShort: |
1241 | *static_cast<ushort *>(data) = *static_cast<const ushort*>(copy); |
1242 | return true; |
1243 | case QMetaType::UChar: |
1244 | *static_cast<uchar *>(data) = *static_cast<const uchar*>(copy); |
1245 | return true; |
1246 | case QMetaType::Bool: |
1247 | *static_cast<bool *>(data) = *static_cast<const bool*>(copy); |
1248 | return true; |
1249 | case QMetaType::Float: |
1250 | *static_cast<float *>(data) = *static_cast<const float*>(copy); |
1251 | return true; |
1252 | case QMetaType::Double: |
1253 | *static_cast<double *>(data) = *static_cast<const double*>(copy); |
1254 | return true; |
1255 | case QMetaType::QChar: |
1256 | *static_cast<NS(QChar) *>(data) = *static_cast<const NS(QChar)*>(copy); |
1257 | return true; |
1258 | case QMetaType::QVariantMap: |
1259 | *static_cast<NS(QVariantMap) *>(data) = *static_cast<const NS(QVariantMap)*>(copy); |
1260 | return true; |
1261 | case QMetaType::QVariantHash: |
1262 | *static_cast<NS(QVariantHash) *>(data) = *static_cast<const NS(QVariantHash)*>(copy); |
1263 | return true; |
1264 | case QMetaType::QVariantList: |
1265 | *static_cast<NS(QVariantList) *>(data) = *static_cast<const NS(QVariantList)*>(copy); |
1266 | return true; |
1267 | case QMetaType::QByteArray: |
1268 | *static_cast<NS(QByteArray) *>(data) = *static_cast<const NS(QByteArray)*>(copy); |
1269 | return true; |
1270 | case QMetaType::QString: |
1271 | *static_cast<NS(QString) *>(data) = *static_cast<const NS(QString)*>(copy); |
1272 | return true; |
1273 | case QMetaType::QStringList: |
1274 | *static_cast<NS(QStringList) *>(data) = *static_cast<const NS(QStringList)*>(copy); |
1275 | return true; |
1276 | case QMetaType::QBitArray: |
1277 | *static_cast<NS(QBitArray) *>(data) = *static_cast<const NS(QBitArray)*>(copy); |
1278 | return true; |
1279 | case QMetaType::QDate: |
1280 | *static_cast<NS(QDate) *>(data) = *static_cast<const NS(QDate)*>(copy); |
1281 | return true; |
1282 | case QMetaType::QTime: |
1283 | *static_cast<NS(QTime) *>(data) = *static_cast<const NS(QTime)*>(copy); |
1284 | return true; |
1285 | case QMetaType::QDateTime: |
1286 | *static_cast<NS(QDateTime) *>(data) = *static_cast<const NS(QDateTime)*>(copy); |
1287 | return true; |
1288 | case QMetaType::QUrl: |
1289 | *static_cast<NS(QUrl) *>(data) = *static_cast<const NS(QUrl)*>(copy); |
1290 | return true; |
1291 | case QMetaType::QLocale: |
1292 | *static_cast<NS(QLocale) *>(data) = *static_cast<const NS(QLocale)*>(copy); |
1293 | return true; |
1294 | case QMetaType::QRect: |
1295 | *static_cast<NS(QRect) *>(data) = *static_cast<const NS(QRect)*>(copy); |
1296 | return true; |
1297 | case QMetaType::QRectF: |
1298 | *static_cast<NS(QRectF) *>(data) = *static_cast<const NS(QRectF)*>(copy); |
1299 | return true; |
1300 | case QMetaType::QSize: |
1301 | *static_cast<NS(QSize) *>(data) = *static_cast<const NS(QSize)*>(copy); |
1302 | return true; |
1303 | case QMetaType::QSizeF: |
1304 | *static_cast<NS(QSizeF) *>(data) = *static_cast<const NS(QSizeF)*>(copy); |
1305 | return true; |
1306 | case QMetaType::QLine: |
1307 | *static_cast<NS(QLine) *>(data) = *static_cast<const NS(QLine)*>(copy); |
1308 | return true; |
1309 | case QMetaType::QLineF: |
1310 | *static_cast<NS(QLineF) *>(data) = *static_cast<const NS(QLineF)*>(copy); |
1311 | return true; |
1312 | case QMetaType::QPoint: |
1313 | *static_cast<NS(QPoint) *>(data) = *static_cast<const NS(QPoint)*>(copy); |
1314 | return true; |
1315 | case QMetaType::QPointF: |
1316 | *static_cast<NS(QPointF) *>(data) = *static_cast<const NS(QPointF)*>(copy); |
1317 | return true; |
1318 | case QMetaType::QVector3D: |
1319 | *static_cast<NS(QVector3D) *>(data) = *static_cast<const NS(QVector3D)*>(copy); |
1320 | return true; |
1321 | #ifndef QT_NO_REGEXP |
1322 | case QMetaType::QRegExp: |
1323 | *static_cast<NS(QRegExp) *>(data) = *static_cast<const NS(QRegExp)*>(copy); |
1324 | return true; |
1325 | #endif |
1326 | case QMetaType::Void: |
1327 | return true; |
1328 | |
1329 | |
1330 | #ifdef QT3_SUPPORT |
1331 | case QMetaType::QColorGroup: |
1332 | *static_cast<NS(QColorGroup) *>(data) = *static_cast<const NS(QColorGroup)*>(copy); |
1333 | return true; |
1334 | #endif |
1335 | |
1336 | case QMetaType::QFont: |
1337 | *static_cast<NS(QFont) *>(data) = *static_cast<const NS(QFont)*>(copy); |
1338 | return true; |
1339 | case QMetaType::QPixmap: |
1340 | *static_cast<NS(QPixmap) *>(data) = *static_cast<const NS(QPixmap)*>(copy); |
1341 | return true; |
1342 | case QMetaType::QBrush: |
1343 | *static_cast<NS(QBrush) *>(data) = *static_cast<const NS(QBrush)*>(copy); |
1344 | return true; |
1345 | case QMetaType::QColor: |
1346 | *static_cast<NS(QColor) *>(data) = *static_cast<const NS(QColor)*>(copy); |
1347 | return true; |
1348 | case QMetaType::QPalette: |
1349 | *static_cast<NS(QPalette) *>(data) = *static_cast<const NS(QPalette)*>(copy); |
1350 | return true; |
1351 | case QMetaType::QIcon: |
1352 | *static_cast<NS(QIcon) *>(data) = *static_cast<const NS(QIcon)*>(copy); |
1353 | return true; |
1354 | case QMetaType::QImage: |
1355 | *static_cast<NS(QImage) *>(data) = *static_cast<const NS(QImage)*>(copy); |
1356 | return true; |
1357 | case QMetaType::QPolygon: |
1358 | *static_cast<NS(QPolygon) *>(data) = *static_cast<const NS(QPolygon)*>(copy); |
1359 | return true; |
1360 | case QMetaType::QRegion: |
1361 | *static_cast<NS(QRegion) *>(data) = *static_cast<const NS(QRegion)*>(copy); |
1362 | return true; |
1363 | case QMetaType::QBitmap: |
1364 | *static_cast<NS(QBitmap) *>(data) = *static_cast<const NS(QBitmap)*>(copy); |
1365 | return true; |
1366 | #ifndef QT_NO_CURSOR |
1367 | case QMetaType::QCursor: |
1368 | *static_cast<NS(QCursor) *>(data) = *static_cast<const NS(QCursor)*>(copy); |
1369 | return true; |
1370 | #endif |
1371 | case QMetaType::QSizePolicy: |
1372 | *static_cast<NS(QSizePolicy) *>(data) = *static_cast<const NS(QSizePolicy)*>(copy); |
1373 | return true; |
1374 | case QMetaType::QKeySequence: |
1375 | *static_cast<NS(QKeySequence) *>(data) = *static_cast<const NS(QKeySequence)*>(copy); |
1376 | return true; |
1377 | case QMetaType::QPen: |
1378 | *static_cast<NS(QPen) *>(data) = *static_cast<const NS(QPen)*>(copy); |
1379 | return true; |
1380 | case QMetaType::QTextLength: |
1381 | *static_cast<NS(QTextLength) *>(data) = *static_cast<const NS(QTextLength)*>(copy); |
1382 | return true; |
1383 | case QMetaType::QTextFormat: |
1384 | *static_cast<NS(QTextFormat) *>(data) = *static_cast<const NS(QTextFormat)*>(copy); |
1385 | return true; |
1386 | case QMetaType::QMatrix: |
1387 | *static_cast<NS(QMatrix) *>(data) = *static_cast<const NS(QMatrix)*>(copy); |
1388 | return true; |
1389 | case QMetaType::QTransform: |
1390 | *static_cast<NS(QTransform) *>(data) = *static_cast<const NS(QTransform)*>(copy); |
1391 | return true; |
1392 | case QMetaType::QMatrix4x4: |
1393 | *static_cast<NS(QMatrix4x4) *>(data) = *static_cast<const NS(QMatrix4x4)*>(copy); |
1394 | return true; |
1395 | case QMetaType::QVector2D: |
1396 | *static_cast<NS(QVector2D) *>(data) = *static_cast<const NS(QVector2D)*>(copy); |
1397 | return true; |
1398 | case QMetaType::QVector4D: |
1399 | *static_cast<NS(QVector4D) *>(data) = *static_cast<const NS(QVector4D)*>(copy); |
1400 | return true; |
1401 | case QMetaType::QQuaternion: |
1402 | *static_cast<NS(QQuaternion) *>(data) = *static_cast<const NS(QQuaternion)*>(copy); |
1403 | return true; |
1404 | |
1405 | default: |
1406 | if (type == qMetaTypeId<QVariant>()) { |
1407 | *static_cast<NS(QVariant) *>(data) = *static_cast<const NS(QVariant)*>(copy); |
1408 | return true; |
1409 | } else if (type == qMetaTypeId<QScriptValue>()) { |
1410 | *static_cast<NS(QScriptValue) *>(data) = *static_cast<const NS(QScriptValue)*>(copy); |
1411 | return true; |
1412 | } else if (typeCategory(type) != Unknown) { |
1413 | *static_cast<void **>(data) = *static_cast<void* const *>(copy); |
1414 | return true; |
1415 | } |
1416 | break; |
1417 | } |
1418 | } else { |
1419 | switch(type) { |
1420 | case QMetaType::VoidStar: |
1421 | case QMetaType::QObjectStar: |
1422 | case QMetaType::QWidgetStar: |
1423 | *static_cast<void **>(data) = 0; |
1424 | return true; |
1425 | case QMetaType::Long: |
1426 | *static_cast<long *>(data) = long(0); |
1427 | return true; |
1428 | case QMetaType::Int: |
1429 | *static_cast<int *>(data) = int(0); |
1430 | return true; |
1431 | case QMetaType::Short: |
1432 | *static_cast<short *>(data) = short(0); |
1433 | return true; |
1434 | case QMetaType::Char: |
1435 | *static_cast<char *>(data) = char(0); |
1436 | return true; |
1437 | case QMetaType::ULong: |
1438 | *static_cast<ulong *>(data) = ulong(0); |
1439 | return true; |
1440 | case QMetaType::UInt: |
1441 | *static_cast<uint *>(data) = uint(0); |
1442 | return true; |
1443 | case QMetaType::LongLong: |
1444 | *static_cast<qlonglong *>(data) = qlonglong(0); |
1445 | return true; |
1446 | case QMetaType::ULongLong: |
1447 | *static_cast<qulonglong *>(data) = qulonglong(0); |
1448 | return true; |
1449 | case QMetaType::UShort: |
1450 | *static_cast<ushort *>(data) = ushort(0); |
1451 | return true; |
1452 | case QMetaType::UChar: |
1453 | *static_cast<uchar *>(data) = uchar(0); |
1454 | return true; |
1455 | case QMetaType::Bool: |
1456 | *static_cast<bool *>(data) = bool(false); |
1457 | return true; |
1458 | case QMetaType::Float: |
1459 | *static_cast<float *>(data) = float(0); |
1460 | return true; |
1461 | case QMetaType::Double: |
1462 | *static_cast<double *>(data) = double(0); |
1463 | return true; |
1464 | case QMetaType::QChar: |
1465 | *static_cast<NS(QChar) *>(data) = NS(QChar)(); |
1466 | return true; |
1467 | case QMetaType::QVariantMap: |
1468 | *static_cast<NS(QVariantMap) *>(data) = NS(QVariantMap)(); |
1469 | return true; |
1470 | case QMetaType::QVariantHash: |
1471 | *static_cast<NS(QVariantHash) *>(data) = NS(QVariantHash)(); |
1472 | return true; |
1473 | case QMetaType::QVariantList: |
1474 | *static_cast<NS(QVariantList) *>(data) = NS(QVariantList)(); |
1475 | return true; |
1476 | case QMetaType::QByteArray: |
1477 | *static_cast<NS(QByteArray) *>(data) = NS(QByteArray)(); |
1478 | return true; |
1479 | case QMetaType::QString: |
1480 | *static_cast<NS(QString) *>(data) = NS(QString)(); |
1481 | return true; |
1482 | case QMetaType::QStringList: |
1483 | *static_cast<NS(QStringList) *>(data) = NS(QStringList)(); |
1484 | return true; |
1485 | case QMetaType::QBitArray: |
1486 | *static_cast<NS(QBitArray) *>(data) = NS(QBitArray)(); |
1487 | return true; |
1488 | case QMetaType::QDate: |
1489 | *static_cast<NS(QDate) *>(data) = NS(QDate)(); |
1490 | return true; |
1491 | case QMetaType::QTime: |
1492 | *static_cast<NS(QTime) *>(data) = NS(QTime)(); |
1493 | return true; |
1494 | case QMetaType::QDateTime: |
1495 | *static_cast<NS(QDateTime) *>(data) = NS(QDateTime)(); |
1496 | return true; |
1497 | case QMetaType::QUrl: |
1498 | *static_cast<NS(QUrl) *>(data) = NS(QUrl)(); |
1499 | return true; |
1500 | case QMetaType::QLocale: |
1501 | *static_cast<NS(QLocale) *>(data) = NS(QLocale)(); |
1502 | return true; |
1503 | case QMetaType::QRect: |
1504 | *static_cast<NS(QRect) *>(data) = NS(QRect)(); |
1505 | return true; |
1506 | case QMetaType::QRectF: |
1507 | *static_cast<NS(QRectF) *>(data) = NS(QRectF)(); |
1508 | return true; |
1509 | case QMetaType::QSize: |
1510 | *static_cast<NS(QSize) *>(data) = NS(QSize)(); |
1511 | return true; |
1512 | case QMetaType::QSizeF: |
1513 | *static_cast<NS(QSizeF) *>(data) = NS(QSizeF)(); |
1514 | return true; |
1515 | case QMetaType::QLine: |
1516 | *static_cast<NS(QLine) *>(data) = NS(QLine)(); |
1517 | return true; |
1518 | case QMetaType::QLineF: |
1519 | *static_cast<NS(QLineF) *>(data) = NS(QLineF)(); |
1520 | return true; |
1521 | case QMetaType::QPoint: |
1522 | *static_cast<NS(QPoint) *>(data) = NS(QPoint)(); |
1523 | return true; |
1524 | case QMetaType::QPointF: |
1525 | *static_cast<NS(QPointF) *>(data) = NS(QPointF)(); |
1526 | return true; |
1527 | case QMetaType::QVector3D: |
1528 | *static_cast<NS(QVector3D) *>(data) = NS(QVector3D)(); |
1529 | return true; |
1530 | #ifndef QT_NO_REGEXP |
1531 | case QMetaType::QRegExp: |
1532 | *static_cast<NS(QRegExp) *>(data) = NS(QRegExp)(); |
1533 | return true; |
1534 | #endif |
1535 | case QMetaType::Void: |
1536 | return true; |
1537 | |
1538 | #ifdef QT3_SUPPORT |
1539 | case QMetaType::QColorGroup: |
1540 | *static_cast<NS(QColorGroup) *>(data) = NS(QColorGroup)(); |
1541 | return true; |
1542 | #endif |
1543 | |
1544 | case QMetaType::QFont: |
1545 | *static_cast<NS(QFont) *>(data) = NS(QFont)(); |
1546 | return true; |
1547 | case QMetaType::QPixmap: |
1548 | *static_cast<NS(QPixmap) *>(data) = NS(QPixmap)(); |
1549 | return true; |
1550 | case QMetaType::QBrush: |
1551 | *static_cast<NS(QBrush) *>(data) = NS(QBrush)(); |
1552 | return true; |
1553 | case QMetaType::QColor: |
1554 | *static_cast<NS(QColor) *>(data) = NS(QColor)(); |
1555 | return true; |
1556 | case QMetaType::QPalette: |
1557 | *static_cast<NS(QPalette) *>(data) = NS(QPalette)(); |
1558 | return true; |
1559 | case QMetaType::QIcon: |
1560 | *static_cast<NS(QIcon) *>(data) = NS(QIcon)(); |
1561 | return true; |
1562 | case QMetaType::QImage: |
1563 | *static_cast<NS(QImage) *>(data) = NS(QImage)(); |
1564 | return true; |
1565 | case QMetaType::QPolygon: |
1566 | *static_cast<NS(QPolygon) *>(data) = NS(QPolygon)(); |
1567 | return true; |
1568 | case QMetaType::QRegion: |
1569 | *static_cast<NS(QRegion) *>(data) = NS(QRegion)(); |
1570 | return true; |
1571 | case QMetaType::QBitmap: |
1572 | *static_cast<NS(QBitmap) *>(data) = NS(QBitmap)(); |
1573 | return true; |
1574 | #ifndef QT_NO_CURSOR |
1575 | case QMetaType::QCursor: |
1576 | *static_cast<NS(QCursor) *>(data) = NS(QCursor)(); |
1577 | return true; |
1578 | #endif |
1579 | case QMetaType::QSizePolicy: |
1580 | *static_cast<NS(QSizePolicy) *>(data) = NS(QSizePolicy)(); |
1581 | return true; |
1582 | case QMetaType::QKeySequence: |
1583 | *static_cast<NS(QKeySequence) *>(data) = NS(QKeySequence)(); |
1584 | return true; |
1585 | case QMetaType::QPen: |
1586 | *static_cast<NS(QPen) *>(data) = NS(QPen)(); |
1587 | return true; |
1588 | case QMetaType::QTextLength: |
1589 | *static_cast<NS(QTextLength) *>(data) = NS(QTextLength)(); |
1590 | return true; |
1591 | case QMetaType::QTextFormat: |
1592 | *static_cast<NS(QTextFormat) *>(data) = NS(QTextFormat)(); |
1593 | return true; |
1594 | case QMetaType::QMatrix: |
1595 | *static_cast<NS(QMatrix) *>(data) = NS(QMatrix)(); |
1596 | return true; |
1597 | case QMetaType::QTransform: |
1598 | *static_cast<NS(QTransform) *>(data) = NS(QTransform)(); |
1599 | return true; |
1600 | case QMetaType::QMatrix4x4: |
1601 | *static_cast<NS(QMatrix4x4) *>(data) = NS(QMatrix4x4)(); |
1602 | return true; |
1603 | case QMetaType::QVector2D: |
1604 | *static_cast<NS(QVector2D) *>(data) = NS(QVector2D)(); |
1605 | return true; |
1606 | case QMetaType::QVector4D: |
1607 | *static_cast<NS(QVector4D) *>(data) = NS(QVector4D)(); |
1608 | return true; |
1609 | case QMetaType::QQuaternion: |
1610 | *static_cast<NS(QQuaternion) *>(data) = NS(QQuaternion)(); |
1611 | return true; |
1612 | default: |
1613 | if (type == qMetaTypeId<QVariant>()) { |
1614 | *static_cast<NS(QVariant) *>(data) = NS(QVariant)(); |
1615 | return true; |
1616 | } else if (type == qMetaTypeId<QScriptValue>()) { |
1617 | *static_cast<NS(QScriptValue) *>(data) = NS(QScriptValue)(); |
1618 | return true; |
1619 | } else if (typeCategory(type) != Unknown) { |
1620 | *static_cast<void **>(data) = 0; |
1621 | return true; |
1622 | } |
1623 | break; |
1624 | } |
1625 | } |
1626 | |
1627 | return false; |
1628 | } |
1629 | |
1630 | QT_END_NAMESPACE |
1631 | |