summaryrefslogtreecommitdiffstats
path: root/src/declarative/qml
diff options
context:
space:
mode:
Diffstat (limited to 'src/declarative/qml')
-rw-r--r--src/declarative/qml/qmlcompiler.cpp17
-rw-r--r--src/declarative/qml/qmlcompiler_p.h2
-rw-r--r--src/declarative/qml/qmlinstruction.cpp2
-rw-r--r--src/declarative/qml/qmlinstruction_p.h1
-rw-r--r--src/declarative/qml/qmlvme.cpp2
-rw-r--r--src/declarative/qml/qmlvmemetaobject.cpp132
-rw-r--r--src/declarative/qml/qmlvmemetaobject_p.h6
7 files changed, 106 insertions, 56 deletions
diff --git a/src/declarative/qml/qmlcompiler.cpp b/src/declarative/qml/qmlcompiler.cpp
index b8f3921..d4003ab 100644
--- a/src/declarative/qml/qmlcompiler.cpp
+++ b/src/declarative/qml/qmlcompiler.cpp
@@ -545,7 +545,7 @@ bool QmlCompiler::compileObject(Object *obj, int ctxt)
create.create.type = obj->type;
output->bytecode << create;
- COMPILE_CHECK(compileDynamicPropertiesAndSignals(obj));
+ COMPILE_CHECK(compileDynamicMeta(obj));
if (obj->type != -1) {
if (output->types.at(obj->type).component) {
@@ -1212,10 +1212,12 @@ bool QmlCompiler::compilePropertyLiteralAssignment(QmlParser::Property *prop,
return true;
}
-bool QmlCompiler::compileDynamicPropertiesAndSignals(QmlParser::Object *obj)
+bool QmlCompiler::compileDynamicMeta(QmlParser::Object *obj)
{
// ### FIXME - Check that there is only one default property etc.
- if (obj->dynamicProperties.isEmpty() && obj->dynamicSignals.isEmpty())
+ if (obj->dynamicProperties.isEmpty() &&
+ obj->dynamicSignals.isEmpty() &&
+ obj->dynamicSlots.isEmpty())
return true;
QMetaObjectBuilder builder;
@@ -1263,6 +1265,14 @@ bool QmlCompiler::compileDynamicPropertiesAndSignals(QmlParser::Object *obj)
builder.addSignal(s.name + "()");
}
+ int slotStart = obj->dynamicSlots.isEmpty()?-1:output->primitives.count();
+
+ for (int ii = 0; ii < obj->dynamicSlots.count(); ++ii) {
+ const Object::DynamicSlot &s = obj->dynamicSlots.at(ii);
+ builder.addSlot(s.name + "()");
+ output->primitives << s.body;
+ }
+
if (obj->metatype)
builder.setSuperClass(obj->metatype);
@@ -1272,6 +1282,7 @@ bool QmlCompiler::compileDynamicPropertiesAndSignals(QmlParser::Object *obj)
QmlInstruction store;
store.type = QmlInstruction::StoreMetaObject;
store.storeMeta.data = output->mos.count() - 1;
+ store.storeMeta.slotData = slotStart;
store.line = obj->line;
output->bytecode << store;
diff --git a/src/declarative/qml/qmlcompiler_p.h b/src/declarative/qml/qmlcompiler_p.h
index 4acdcfa..e2b8388 100644
--- a/src/declarative/qml/qmlcompiler_p.h
+++ b/src/declarative/qml/qmlcompiler_p.h
@@ -163,7 +163,7 @@ private:
QmlParser::Value *value,
int ctxt);
- bool compileDynamicPropertiesAndSignals(QmlParser::Object *obj);
+ bool compileDynamicMeta(QmlParser::Object *obj);
void compileBinding(const QString &, QmlParser::Property *prop,
int ctxt, const QMetaObject *, qint64);
diff --git a/src/declarative/qml/qmlinstruction.cpp b/src/declarative/qml/qmlinstruction.cpp
index 52677c2..0617913 100644
--- a/src/declarative/qml/qmlinstruction.cpp
+++ b/src/declarative/qml/qmlinstruction.cpp
@@ -68,7 +68,7 @@ void QmlCompiledComponent::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;
+ qWarning() << idx << "\t" << line << "\t" << "STORE_META\t\t" << instr->storeMeta.data << "\t" << instr->storeMeta.slotData;
break;
case QmlInstruction::StoreReal:
qWarning() << idx << "\t" << line << "\t" << "STORE_REAL\t\t" << instr->storeReal.propertyIndex << "\t" << instr->storeReal.value;
diff --git a/src/declarative/qml/qmlinstruction_p.h b/src/declarative/qml/qmlinstruction_p.h
index 462f9e4..01bdfdd 100644
--- a/src/declarative/qml/qmlinstruction_p.h
+++ b/src/declarative/qml/qmlinstruction_p.h
@@ -177,6 +177,7 @@ public:
} create;
struct {
int data;
+ int slotData;
} storeMeta;
struct {
int value;
diff --git a/src/declarative/qml/qmlvme.cpp b/src/declarative/qml/qmlvme.cpp
index ad3d1d5..ee7a881 100644
--- a/src/declarative/qml/qmlvme.cpp
+++ b/src/declarative/qml/qmlvme.cpp
@@ -320,7 +320,7 @@ QObject *QmlVME::run(QmlContext *ctxt, QmlCompiledComponent *comp, int start, in
QFxCompilerTimer<QFxCompiler::InstrStoreMetaObject> cc;
#endif
QObject *target = stack.top();
- new QmlVMEMetaObject(target, mos.at(instr.storeMeta.data), comp);
+ new QmlVMEMetaObject(target, mos.at(instr.storeMeta.data), &comp->primitives, instr.storeMeta.slotData, comp);
}
break;
diff --git a/src/declarative/qml/qmlvmemetaobject.cpp b/src/declarative/qml/qmlvmemetaobject.cpp
index f7d2635..58708cf 100644
--- a/src/declarative/qml/qmlvmemetaobject.cpp
+++ b/src/declarative/qml/qmlvmemetaobject.cpp
@@ -44,13 +44,18 @@
#include <private/qmlrefcount_p.h>
#include <QColor>
#include <QDate>
+#include <QtCore/qlist.h>
+#include <QtCore/qdebug.h>
+#include <qmlexpression.h>
QT_BEGIN_NAMESPACE
QmlVMEMetaObject::QmlVMEMetaObject(QObject *obj,
- const QMetaObject *other,
- QmlRefCount *rc)
-: object(obj), ref(rc)
+ const QMetaObject *other,
+ QList<QString> *strData,
+ int slotData,
+ QmlRefCount *rc)
+: object(obj), ref(rc), slotData(strData), slotDataIdx(slotData)
{
if (ref)
ref->addref();
@@ -64,6 +69,7 @@ QmlVMEMetaObject::QmlVMEMetaObject(QObject *obj,
data = new QVariant[propertyCount() - baseProp];
vTypes.resize(propertyCount() - baseProp);
+ // ### Optimize
for (int ii = baseProp; ii < propertyCount(); ++ii) {
QMetaProperty prop = property(ii);
if ((int)prop.type() != -1) {
@@ -72,6 +78,23 @@ QmlVMEMetaObject::QmlVMEMetaObject(QObject *obj,
vTypes.setBit(ii - baseProp, true);
}
}
+
+ baseSlot = -1;
+ slotCount = 0;
+ for (int ii = baseSig; ii < methodCount(); ++ii) {
+ QMetaMethod m = method(ii);
+ if (m.methodType() == QMetaMethod::Slot) {
+ if (baseSlot == -1)
+ baseSlot = ii;
+ } else {
+ if (baseSlot != -1) {
+ slotCount = ii - baseSlot;
+ break;
+ }
+ }
+ }
+ if(baseSlot != -1 && !slotCount)
+ slotCount = methodCount() - baseSlot;
}
QmlVMEMetaObject::~QmlVMEMetaObject()
@@ -83,58 +106,69 @@ QmlVMEMetaObject::~QmlVMEMetaObject()
int QmlVMEMetaObject::metaCall(QMetaObject::Call c, int id, void **a)
{
- if (id >= baseProp) {
- int propId = id - baseProp;
- bool needActivate = false;
+ if(c == QMetaObject::ReadProperty || c == QMetaObject::WriteProperty) {
+ if (id >= baseProp) {
+ int propId = id - baseProp;
+ bool needActivate = false;
- if (vTypes.testBit(propId)) {
- if (c == QMetaObject::ReadProperty) {
- *reinterpret_cast<QVariant *>(a[0]) = data[propId];
- } else if (c == QMetaObject::WriteProperty) {
- needActivate =
- (data[propId] != *reinterpret_cast<QVariant *>(a[0]));
- data[propId] = *reinterpret_cast<QVariant *>(a[0]);
- }
- } else {
- if (c == QMetaObject::ReadProperty) {
- switch(data[propId].type()) {
- case QVariant::Int:
- *reinterpret_cast<int *>(a[0]) = data[propId].toInt();
- break;
- case QVariant::Bool:
- *reinterpret_cast<bool *>(a[0]) = data[propId].toBool();
- break;
- case QVariant::Double:
- *reinterpret_cast<double *>(a[0]) = data[propId].toDouble();
- break;
- case QVariant::String:
- *reinterpret_cast<QString *>(a[0]) = data[propId].toString();
- break;
- case QVariant::Color:
- *reinterpret_cast<QColor *>(a[0]) = data[propId].value<QColor>();
- break;
- case QVariant::Date:
- *reinterpret_cast<QDate *>(a[0]) = data[propId].toDate();
- break;
- default:
- qFatal("Unknown type");
- break;
+ if (vTypes.testBit(propId)) {
+ if (c == QMetaObject::ReadProperty) {
+ *reinterpret_cast<QVariant *>(a[0]) = data[propId];
+ } else if (c == QMetaObject::WriteProperty) {
+ needActivate =
+ (data[propId] != *reinterpret_cast<QVariant *>(a[0]));
+ data[propId] = *reinterpret_cast<QVariant *>(a[0]);
}
- } else if (c == QMetaObject::WriteProperty) {
+ } else {
+ if (c == QMetaObject::ReadProperty) {
+ switch(data[propId].type()) {
+ case QVariant::Int:
+ *reinterpret_cast<int *>(a[0]) = data[propId].toInt();
+ break;
+ case QVariant::Bool:
+ *reinterpret_cast<bool *>(a[0]) = data[propId].toBool();
+ break;
+ case QVariant::Double:
+ *reinterpret_cast<double *>(a[0]) = data[propId].toDouble();
+ break;
+ case QVariant::String:
+ *reinterpret_cast<QString *>(a[0]) = data[propId].toString();
+ break;
+ case QVariant::Color:
+ *reinterpret_cast<QColor *>(a[0]) = data[propId].value<QColor>();
+ break;
+ case QVariant::Date:
+ *reinterpret_cast<QDate *>(a[0]) = data[propId].toDate();
+ break;
+ default:
+ qFatal("Unknown type");
+ break;
+ }
+ } else if (c == QMetaObject::WriteProperty) {
- QVariant value = QVariant((QVariant::Type)data[propId].type(), a[0]);
- needActivate = (data[propId] != value);
- data[propId] = value;
+ QVariant value = QVariant((QVariant::Type)data[propId].type(), a[0]);
+ needActivate = (data[propId] != value);
+ data[propId] = value;
+ }
}
- }
- if (c == QMetaObject::WriteProperty && needActivate) {
- activate(object, baseSig + propId, 0);
- }
+ if (c == QMetaObject::WriteProperty && needActivate) {
+ activate(object, baseSig + propId, 0);
+ }
- return id;
- } else {
- return object->qt_metacall(c, id, a);
+ return id;
+ }
+ } else if(c == QMetaObject::InvokeMetaMethod) {
+ if(id >= baseSlot && id < (baseSlot + slotCount)) {
+ int idx = id - baseSlot + slotDataIdx;
+ QmlContext *ctxt = qmlContext(object);
+ QmlExpression expr(ctxt, slotData->at(idx), object);
+ expr.setTrackChange(false);
+ expr.value();
+ return id;
+ }
}
+
+ return object->qt_metacall(c, id, a);
}
QT_END_NAMESPACE
diff --git a/src/declarative/qml/qmlvmemetaobject_p.h b/src/declarative/qml/qmlvmemetaobject_p.h
index 3fb1c46..d8ed242 100644
--- a/src/declarative/qml/qmlvmemetaobject_p.h
+++ b/src/declarative/qml/qmlvmemetaobject_p.h
@@ -52,7 +52,7 @@ class QmlRefCount;
class QmlVMEMetaObject : public QAbstractDynamicMetaObject
{
public:
- QmlVMEMetaObject(QObject *, const QMetaObject *, QmlRefCount * = 0);
+ QmlVMEMetaObject(QObject *, const QMetaObject *, QList<QString> *, int slotData, QmlRefCount * = 0);
~QmlVMEMetaObject();
protected:
@@ -63,8 +63,12 @@ private:
QmlRefCount *ref;
int baseProp;
int baseSig;
+ int baseSlot;
+ int slotCount;
QVariant *data;
QBitArray vTypes;
+ QList<QString> *slotData;
+ int slotDataIdx;
};
QT_END_NAMESPACE