summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorAaron Kennedy <aaron.kennedy@nokia.com>2009-09-30 01:07:07 (GMT)
committerAaron Kennedy <aaron.kennedy@nokia.com>2009-10-05 02:39:02 (GMT)
commit49527e854a9edb0a92e64264d6efac6be46cf0ed (patch)
tree2bcc8dad3c1e6c0a239eac5e3188c2ec8eada602
parentc4190288ca68eca9b84ccab67d860517a6a8e7c5 (diff)
downloadQt-49527e854a9edb0a92e64264d6efac6be46cf0ed.zip
Qt-49527e854a9edb0a92e64264d6efac6be46cf0ed.tar.gz
Qt-49527e854a9edb0a92e64264d6efac6be46cf0ed.tar.bz2
Create a property cache for synthesized metaobjects
-rw-r--r--src/declarative/qml/qml.pri6
-rw-r--r--src/declarative/qml/qmlcompileddata.cpp3
-rw-r--r--src/declarative/qml/qmlcompiler.cpp6
-rw-r--r--src/declarative/qml/qmlcompiler_p.h3
-rw-r--r--src/declarative/qml/qmldeclarativedata_p.h3
-rw-r--r--src/declarative/qml/qmlengine.cpp14
-rw-r--r--src/declarative/qml/qmlengine_p.h18
-rw-r--r--src/declarative/qml/qmlinstruction.cpp2
-rw-r--r--src/declarative/qml/qmlinstruction_p.h2
-rw-r--r--src/declarative/qml/qmlmetaproperty.cpp71
-rw-r--r--src/declarative/qml/qmlmetaproperty_p.h22
-rw-r--r--src/declarative/qml/qmlpropertycache.cpp137
-rw-r--r--src/declarative/qml/qmlpropertycache_p.h100
-rw-r--r--src/declarative/qml/qmlvme.cpp9
14 files changed, 303 insertions, 93 deletions
diff --git a/src/declarative/qml/qml.pri b/src/declarative/qml/qml.pri
index 8349e29..216adb1 100644
--- a/src/declarative/qml/qml.pri
+++ b/src/declarative/qml/qml.pri
@@ -34,7 +34,8 @@ SOURCES += qml/qmlparser.cpp \
qml/qmlxmlhttprequest.cpp \
qml/qmlsqldatabase.cpp \
qml/qmetaobjectbuilder.cpp \
- qml/qmlwatcher.cpp
+ qml/qmlwatcher.cpp \
+ qml/qmlpropertycache.cpp
HEADERS += qml/qmlparser_p.h \
qml/qmlinstruction_p.h \
@@ -86,7 +87,8 @@ HEADERS += qml/qmlparser_p.h \
qml/qmlxmlhttprequest_p.h \
qml/qmlsqldatabase_p.h \
qml/qmetaobjectbuilder_p.h \
- qml/qmlwatcher_p.h
+ qml/qmlwatcher_p.h \
+ qml/qmlpropertycache_p.h
# for qtscript debugger
contains(QT_CONFIG, scripttools):QT += scripttools
diff --git a/src/declarative/qml/qmlcompileddata.cpp b/src/declarative/qml/qmlcompileddata.cpp
index a46d893..a603d4e 100644
--- a/src/declarative/qml/qmlcompileddata.cpp
+++ b/src/declarative/qml/qmlcompileddata.cpp
@@ -160,6 +160,9 @@ QmlCompiledData::~QmlCompiledData()
types.at(ii).ref->release();
}
+ for (int ii = 0; ii < propertyCaches.count(); ++ii)
+ propertyCaches.at(ii)->release();
+
qDeleteAll(programs);
}
diff --git a/src/declarative/qml/qmlcompiler.cpp b/src/declarative/qml/qmlcompiler.cpp
index e67f79a..0b4ac20 100644
--- a/src/declarative/qml/qmlcompiler.cpp
+++ b/src/declarative/qml/qmlcompiler.cpp
@@ -647,7 +647,7 @@ void QmlCompiler::compileTree(Object *tree)
Q_ASSERT(tree->metatype);
static_cast<QMetaObject &>(output->root) = *tree->metaObject();
- if (!tree->metadata.isEmpty())
+ if (!tree->metadata.isEmpty())
QmlEnginePrivate::get(engine)->registerCompositeType(output);
}
@@ -807,7 +807,9 @@ void QmlCompiler::genObject(QmlParser::Object *obj)
meta.line = -1;
meta.storeMeta.data = output->indexForByteArray(obj->metadata);
meta.storeMeta.aliasData = output->indexForByteArray(obj->synthdata);
- meta.storeMeta.slotData = -1;
+ meta.storeMeta.propertyCache = output->propertyCaches.count();
+ // ### Surely the creation of this property cache could be more efficient
+ output->propertyCaches << QmlPropertyCache::create(engine, obj->metaObject());
output->bytecode << meta;
}
diff --git a/src/declarative/qml/qmlcompiler_p.h b/src/declarative/qml/qmlcompiler_p.h
index 447c421..677aba7 100644
--- a/src/declarative/qml/qmlcompiler_p.h
+++ b/src/declarative/qml/qmlcompiler_p.h
@@ -62,6 +62,7 @@
#include <private/qmlparser_p.h>
#include <private/qmlengine_p.h>
#include <private/qbitfield_p.h>
+#include <private/qmlpropertycache_p.h>
QT_BEGIN_NAMESPACE
@@ -99,6 +100,7 @@ public:
int index;
int type;
};
+
QAbstractDynamicMetaObject root;
QList<QString> primitives;
QList<float> floatData;
@@ -108,6 +110,7 @@ public:
QList<QmlParser::Location> locations;
QList<QmlInstruction> bytecode;
QList<QScriptProgram *> programs;
+ QList<QmlPropertyCache *> propertyCaches;
void dumpInstructions();
private:
diff --git a/src/declarative/qml/qmldeclarativedata_p.h b/src/declarative/qml/qmldeclarativedata_p.h
index ade961f..b4c87b8 100644
--- a/src/declarative/qml/qmldeclarativedata_p.h
+++ b/src/declarative/qml/qmldeclarativedata_p.h
@@ -60,6 +60,7 @@ QT_BEGIN_NAMESPACE
class QmlCompiledData;
class QmlAbstractBinding;
class QmlContext;
+class QmlPropertyCache;
class QmlDeclarativeData : public QDeclarativeData
{
public:
@@ -85,6 +86,8 @@ public:
QHash<int, QObject *> *attachedProperties;
+ QmlPropertyCache *propertyCache;
+
static QmlDeclarativeData *get(const QObject *object, bool create = false) {
QObjectPrivate *priv =
QObjectPrivate::get(const_cast<QObject *>(object));
diff --git a/src/declarative/qml/qmlengine.cpp b/src/declarative/qml/qmlengine.cpp
index 72603ed..757670b 100644
--- a/src/declarative/qml/qmlengine.cpp
+++ b/src/declarative/qml/qmlengine.cpp
@@ -41,11 +41,12 @@
#undef QT3_SUPPORT // don't want it here - it just causes bugs (which is why we removed it)
-#include <QMetaProperty>
+#include <QtCore/qmetaobject.h>
#include <private/qmlengine_p.h>
#include <private/qmlcontext_p.h>
#include <private/qobject_p.h>
#include <private/qmlcompiler_p.h>
+#include <private/qscriptdeclarativeclass_p.h>
#ifdef QT_SCRIPTTOOLS_LIB
#include <QScriptEngineDebugger>
@@ -192,6 +193,8 @@ QmlEnginePrivate::~QmlEnginePrivate()
contextClass = 0;
delete objectClass;
objectClass = 0;
+ delete objectClass2;
+ objectClass2 = 0;
delete valueTypeClass;
valueTypeClass = 0;
delete typeNameClass;
@@ -211,6 +214,9 @@ QmlEnginePrivate::~QmlEnginePrivate()
clear(parserStatus[ii]);
for(QHash<int, QmlCompiledData*>::ConstIterator iter = m_compositeTypes.constBegin(); iter != m_compositeTypes.constEnd(); ++iter)
(*iter)->release();
+ for(QHash<const QMetaObject *, QmlPropertyCache *>::Iterator iter = propertyCache.begin(); iter != propertyCache.end(); ++iter)
+ (*iter)->release();
+
}
void QmlEnginePrivate::clear(SimpleList<QmlAbstractBinding> &bvs)
@@ -236,6 +242,7 @@ void QmlEnginePrivate::init()
scriptEngine.installTranslatorFunctions();
contextClass = new QmlContextScriptClass(q);
objectClass = new QmlObjectScriptClass(q);
+ objectClass2 = new QScriptDeclarativeClass(&scriptEngine);
valueTypeClass = new QmlValueTypeScriptClass(q);
typeNameClass = new QmlTypeNameScriptClass(q);
rootContext = new QmlContext(q,true);
@@ -700,7 +707,7 @@ QObject *qmlAttachedPropertiesObjectById(int id, const QObject *object, bool cre
QmlDeclarativeData::QmlDeclarativeData(QmlContext *ctxt)
: context(ctxt), bindings(0), bindingBitsSize(0), bindingBits(0),
outerContext(0), lineNumber(0), columnNumber(0), deferredComponent(0),
- deferredIdx(0), attachedProperties(0)
+ deferredIdx(0), attachedProperties(0), propertyCache(0)
{
}
@@ -725,6 +732,9 @@ void QmlDeclarativeData::destroyed(QObject *object)
if (bindingBits)
free(bindingBits);
+ if (propertyCache)
+ propertyCache->release();
+
delete this;
}
diff --git a/src/declarative/qml/qmlengine_p.h b/src/declarative/qml/qmlengine_p.h
index 74e24d4..68019e2 100644
--- a/src/declarative/qml/qmlengine_p.h
+++ b/src/declarative/qml/qmlengine_p.h
@@ -72,6 +72,7 @@
#include <QtDeclarative/qmlexpression.h>
#include <QtScript/qscriptengine.h>
#include <private/qmlmetaproperty_p.h>
+#include <private/qmlpropertycache_p.h>
QT_BEGIN_NAMESPACE
@@ -88,6 +89,7 @@ class QScriptEngineDebugger;
class QNetworkReply;
class QNetworkAccessManager;
class QmlAbstractBinding;
+class QScriptDeclarativeClass;
class QmlEnginePrivate : public QObjectPrivate
{
@@ -149,6 +151,7 @@ public:
} resolveData;
QmlContextScriptClass *contextClass;
QmlObjectScriptClass *objectClass;
+ QScriptDeclarativeClass *objectClass2;
QmlValueTypeScriptClass *valueTypeClass;
QmlTypeNameScriptClass *typeNameClass;
// Used by DOM Core 3 API
@@ -212,10 +215,17 @@ public:
// ### Fixme
typedef QHash<QPair<const QMetaObject *, QString>, bool> FunctionCache;
FunctionCache functionCache;
- QHash<const QMetaObject *, QmlMetaObjectCache> propertyCache;
- static QmlMetaObjectCache *cache(QmlEnginePrivate *priv, QObject *obj) {
- if (!priv || !obj || QObjectPrivate::get(obj)->metaObject) return 0;
- return &priv->propertyCache[obj->metaObject()];
+ QHash<const QMetaObject *, QmlPropertyCache *> propertyCache;
+ QmlPropertyCache *cache(QObject *obj) {
+ Q_Q(QmlEngine);
+ if (!obj || QObjectPrivate::get(obj)->metaObject) return 0;
+ const QMetaObject *mo = obj->metaObject();
+ QmlPropertyCache *rv = propertyCache.value(mo);
+ if (!rv) {
+ rv = QmlPropertyCache::create(q, mo);
+ propertyCache.insert(mo, rv);
+ }
+ return rv;
}
struct Imports {
diff --git a/src/declarative/qml/qmlinstruction.cpp b/src/declarative/qml/qmlinstruction.cpp
index b71c6e3..18439f4 100644
--- a/src/declarative/qml/qmlinstruction.cpp
+++ b/src/declarative/qml/qmlinstruction.cpp
@@ -69,7 +69,7 @@ void QmlCompiledData::dump(QmlInstruction *instr, int idx)
qWarning() << idx << "\t" << line << "\t" << "CREATE_COMPONENT\t" << instr->createComponent.count;
break;
case QmlInstruction::StoreMetaObject:
- qWarning() << idx << "\t" << line << "\t" << "STORE_META\t\t" << instr->storeMeta.data << "\t" << instr->storeMeta.slotData;
+ qWarning() << idx << "\t" << line << "\t" << "STORE_META\t\t" << instr->storeMeta.data << "\t";
break;
case QmlInstruction::StoreFloat:
qWarning() << idx << "\t" << line << "\t" << "STORE_FLOAT\t\t" << instr->storeFloat.propertyIndex << "\t" << instr->storeFloat.value;
diff --git a/src/declarative/qml/qmlinstruction_p.h b/src/declarative/qml/qmlinstruction_p.h
index 2c9ceac..e62bfdf 100644
--- a/src/declarative/qml/qmlinstruction_p.h
+++ b/src/declarative/qml/qmlinstruction_p.h
@@ -175,8 +175,8 @@ public:
} create;
struct {
int data;
- int slotData;
int aliasData;
+ int propertyCache;
} storeMeta;
struct {
int value;
diff --git a/src/declarative/qml/qmlmetaproperty.cpp b/src/declarative/qml/qmlmetaproperty.cpp
index efc4a2b..f7882dc 100644
--- a/src/declarative/qml/qmlmetaproperty.cpp
+++ b/src/declarative/qml/qmlmetaproperty.cpp
@@ -58,56 +58,6 @@ Q_DECLARE_METATYPE(QList<QObject *>);
QT_BEGIN_NAMESPACE
-QmlMetaObjectCache::QmlMetaObjectCache()
-: propertyCache(0)
-{
-}
-
-void QmlMetaObjectCache::init(const QMetaObject *metaObject)
-{
- if (propertyCache || !metaObject)
- return;
-
- int propCount = metaObject->propertyCount();
-
- propertyCache = new Data[propCount];
- for (int ii = 0; ii < propCount; ++ii) {
- QMetaProperty p = metaObject->property(ii);
- propertyCache[ii].propType = p.userType();
- propertyCache[ii].coreIndex = ii;
- propertyCache[ii].name = QLatin1String(p.name());
-
- propertyNameCache.insert(propertyCache[ii].name, ii);
- }
-}
-
-QmlMetaObjectCache::~QmlMetaObjectCache()
-{
- delete [] propertyCache;
-}
-
-QmlMetaObjectCache::Data *
-QmlMetaObjectCache::property(int index, const QMetaObject *metaObject)
-{
- init(metaObject);
-
- return propertyCache + index;
-}
-
-QmlMetaObjectCache::Data *
-QmlMetaObjectCache::property(const QString &name, const QMetaObject *metaObject)
-{
- init(metaObject);
-
- QHash<QString, int>::ConstIterator iter = propertyNameCache.find(name);
-
- if (iter != propertyNameCache.end()) {
- return propertyCache + *iter;
- } else {
- return 0;
- }
-}
-
/*!
\class QmlMetaProperty
\brief The QmlMetaProperty class abstracts accessing QML properties.
@@ -258,11 +208,17 @@ void QmlMetaPropertyPrivate::initProperty(QObject *obj, const QString &name)
}
// Property
- QmlMetaObjectCache *cache = QmlEnginePrivate::cache(enginePrivate, obj);
+ QmlPropertyCache *cache = 0;
+ QmlDeclarativeData *ddata = QmlDeclarativeData::get(obj);
+ if (ddata)
+ cache = ddata->propertyCache;
+ if (!cache)
+ cache = enginePrivate?enginePrivate->cache(obj):0;
+
if (cache) {
- QmlMetaObjectCache::Data *data =
- cache->property(name, obj->metaObject());
- if (data) {
+ QmlPropertyCache::Data *data = cache->property(name);
+
+ if (data && !data->isFunction) {
type = QmlMetaProperty::Property;
propType = data->propType;
coreIdx = data->coreIndex;
@@ -272,7 +228,7 @@ void QmlMetaPropertyPrivate::initProperty(QObject *obj, const QString &name)
QMetaProperty p = QmlMetaType::property(obj, name.toUtf8().constData());
propType = p.userType();
coreIdx = p.propertyIndex();
- if (p.name())
+ if (p.name())
type = QmlMetaProperty::Property;
}
}
@@ -1186,13 +1142,12 @@ void QmlMetaProperty::restore(quint32 id, QObject *obj, QmlContext *ctxt)
} else if (d->type & Property) {
- QmlMetaObjectCache *cache = QmlEnginePrivate::cache(enginePrivate, obj);
+ QmlPropertyCache *cache = enginePrivate?enginePrivate->cache(obj):0;
d->coreIdx = id;
if (cache) {
- QmlMetaObjectCache::Data *data =
- cache->property(id, obj->metaObject());
+ QmlPropertyCache::Data *data = cache->property(id);
d->propType = data->propType;
d->name = data->name;
} else {
diff --git a/src/declarative/qml/qmlmetaproperty_p.h b/src/declarative/qml/qmlmetaproperty_p.h
index 1ccf913..0d96174 100644
--- a/src/declarative/qml/qmlmetaproperty_p.h
+++ b/src/declarative/qml/qmlmetaproperty_p.h
@@ -58,28 +58,6 @@
QT_BEGIN_NAMESPACE
-class QmlMetaObjectCache
-{
-public:
- QmlMetaObjectCache();
- ~QmlMetaObjectCache();
-
- struct Data {
- int propType;
- int coreIndex;
- QString name;
- };
-
- Data *property(const QString &, const QMetaObject *);
- Data *property(int, const QMetaObject *);
-
-private:
- void init(const QMetaObject *);
-
- Data *propertyCache;
- QHash<QString, int> propertyNameCache;
-};
-
class QmlContext;
class QmlMetaPropertyPrivate
{
diff --git a/src/declarative/qml/qmlpropertycache.cpp b/src/declarative/qml/qmlpropertycache.cpp
new file mode 100644
index 0000000..f88b3a3
--- /dev/null
+++ b/src/declarative/qml/qmlpropertycache.cpp
@@ -0,0 +1,137 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** Contact: Qt Software Information (qt-info@nokia.com)
+**
+** This file is part of the QtDeclarative module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the either Technology Preview License Agreement or the
+** Beta Release License Agreement.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain
+** additional rights. These rights are described in the Nokia Qt LGPL
+** Exception version 1.0, included in the file LGPL_EXCEPTION.txt in this
+** package.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 3.0 as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU General Public License version 3.0 requirements will be
+** met: http://www.gnu.org/copyleft/gpl.html.
+**
+** If you are unsure which license is appropriate for your use, please
+** contact the sales department at qt-sales@nokia.com.
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "qmlpropertycache_p.h"
+#include "qmlengine_p.h"
+
+QmlPropertyCache::QmlPropertyCache()
+{
+}
+
+QmlPropertyCache::~QmlPropertyCache()
+{
+ for (int ii = 0; ii < indexCache.count(); ++ii)
+ indexCache.at(ii)->release();
+
+ for (StringCache::ConstIterator iter = stringCache.begin();
+ iter != stringCache.end(); ++iter)
+ (*iter)->release();
+
+ for (IdentifierCache::ConstIterator iter = identifierCache.begin();
+ iter != identifierCache.end(); ++iter)
+ (*iter)->release();
+}
+
+// ### Optimize - check engine for the parent meta object etc.
+QmlPropertyCache *QmlPropertyCache::create(QmlEngine *engine, const QMetaObject *metaObject)
+{
+ Q_ASSERT(engine);
+ Q_ASSERT(metaObject);
+
+ QmlPropertyCache *cache = new QmlPropertyCache;
+
+ QmlEnginePrivate *enginePriv = QmlEnginePrivate::get(engine);
+
+ // ### The properties/methods should probably be spliced on a per-metaobject basis
+ int propCount = metaObject->propertyCount();
+
+ cache->indexCache.resize(propCount);
+ for (int ii = propCount - 1; ii >= 0; --ii) {
+ QMetaProperty p = metaObject->property(ii);
+ QString propName = QLatin1String(p.name());
+
+ QScriptDeclarativeClass::PersistentIdentifier<Data> *data =
+ enginePriv->objectClass2->createPersistentIdentifier<Data>(propName);
+ data->propType = p.userType();
+ data->coreIndex = ii;
+ data->name = propName;
+
+ cache->indexCache[ii] = data;
+
+ if (cache->stringCache.contains(propName))
+ continue;
+
+ cache->stringCache.insert(propName, data);
+ cache->identifierCache.insert(data->identifier, data);
+ data->addref();
+ data->addref();
+ }
+
+ int methodCount = metaObject->methodCount();
+ for (int ii = methodCount - 1; ii >= 0; --ii) {
+ QMetaMethod m = metaObject->method(ii);
+ QString methodName = QLatin1String(m.signature());
+
+ int parenIdx = methodName.indexOf(QLatin1Char('('));
+ Q_ASSERT(parenIdx != -1);
+ methodName = methodName.left(parenIdx);
+
+ if (cache->stringCache.contains(methodName))
+ continue;
+
+ QScriptDeclarativeClass::PersistentIdentifier<Data> *data =
+ enginePriv->objectClass2->createPersistentIdentifier<Data>(methodName);
+ cache->stringCache.insert(methodName, data);
+ cache->identifierCache.insert(data->identifier, data);
+ data->addref();
+ data->addref();
+
+ data->isFunction = true;
+ }
+
+ return cache;
+}
+
+QmlPropertyCache::Data *
+QmlPropertyCache::property(int index) const
+{
+ if (index < 0 || index >= indexCache.count())
+ return 0;
+
+ return indexCache.at(index);
+}
+
+QmlPropertyCache::Data *
+QmlPropertyCache::property(const QString &str) const
+{
+ return stringCache.value(str);
+}
+
diff --git a/src/declarative/qml/qmlpropertycache_p.h b/src/declarative/qml/qmlpropertycache_p.h
new file mode 100644
index 0000000..c10fafa
--- /dev/null
+++ b/src/declarative/qml/qmlpropertycache_p.h
@@ -0,0 +1,100 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** Contact: Qt Software Information (qt-info@nokia.com)
+**
+** This file is part of the QtDeclarative module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the either Technology Preview License Agreement or the
+** Beta Release License Agreement.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain
+** additional rights. These rights are described in the Nokia Qt LGPL
+** Exception version 1.0, included in the file LGPL_EXCEPTION.txt in this
+** package.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 3.0 as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU General Public License version 3.0 requirements will be
+** met: http://www.gnu.org/copyleft/gpl.html.
+**
+** If you are unsure which license is appropriate for your use, please
+** contact the sales department at qt-sales@nokia.com.
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef QMLPROPERTYCACHE_P_H
+#define QMLPROPERTYCACHE_P_H
+
+//
+// W A R N I N G
+// -------------
+//
+// This file is not part of the Qt API. It exists purely as an
+// implementation detail. This header file may change from version to
+// version without notice, or even be removed.
+//
+// We mean it.
+//
+
+#include <private/qmlrefcount_p.h>
+#include <private/qscriptdeclarativeclass_p.h>
+#include <QtCore/qvector.h>
+
+QT_BEGIN_NAMESPACE
+
+class QmlEngine;
+class QMetaProperty;
+class QmlPropertyCache : public QmlRefCount
+{
+public:
+ QmlPropertyCache();
+ virtual ~QmlPropertyCache();
+
+ struct Data : public QmlRefCount {
+ Data() : isFunction(false) {}
+
+ bool isFunction;
+ int propType;
+ int coreIndex;
+ QString name;
+ };
+
+ static QmlPropertyCache *create(QmlEngine *, const QMetaObject *);
+
+ Data *property(const QScriptDeclarativeClass::Identifier &id) const {
+ return identifierCache.value(id);
+ }
+
+ Data *property(const QString &) const;
+ Data *property(int) const;
+
+private:
+ typedef QVector<QScriptDeclarativeClass::PersistentIdentifier<Data> *> IndexCache;
+ typedef QHash<QString, QScriptDeclarativeClass::PersistentIdentifier<Data> *> StringCache;
+ typedef QHash<QScriptDeclarativeClass::Identifier, QScriptDeclarativeClass::PersistentIdentifier<Data> *> IdentifierCache;
+
+ IndexCache indexCache;
+ StringCache stringCache;
+ IdentifierCache identifierCache;
+};
+
+QT_END_NAMESPACE
+
+#endif // QMLPROPERTYCACHE_P_H
diff --git a/src/declarative/qml/qmlvme.cpp b/src/declarative/qml/qmlvme.cpp
index 44b17e6..a5d2732 100644
--- a/src/declarative/qml/qmlvme.cpp
+++ b/src/declarative/qml/qmlvme.cpp
@@ -143,6 +143,7 @@ QObject *QmlVME::run(QStack<QObject *> &stack, QmlContext *ctxt,
const QList<QmlCompiledData::CustomTypeData> &customTypeData = comp->customTypeData;
const QList<int> &intData = comp->intData;
const QList<float> &floatData = comp->floatData;
+ const QList<QmlPropertyCache *> &propertyCaches = comp->propertyCaches;
QmlEnginePrivate::SimpleList<QmlAbstractBinding> bindValues;
@@ -259,9 +260,15 @@ QObject *QmlVME::run(QStack<QObject *> &stack, QmlContext *ctxt,
const QByteArray &metadata = datas.at(instr.storeMeta.data);
QMetaObjectBuilder::fromRelocatableData(&mo, 0, metadata);
- const QmlVMEMetaData *data = (const QmlVMEMetaData *)datas.at(instr.storeMeta.aliasData).constData();
+ const QmlVMEMetaData *data =
+ (const QmlVMEMetaData *)datas.at(instr.storeMeta.aliasData).constData();
(void)new QmlVMEMetaObject(target, &mo, data, comp);
+
+ QmlDeclarativeData *ddata = QmlDeclarativeData::get(target, true);
+ if (ddata->propertyCache) ddata->propertyCache->release();
+ ddata->propertyCache = propertyCaches.at(instr.storeMeta.propertyCache);
+ ddata->propertyCache->addref();
}
break;