diff options
author | Alan Alpert <alan.alpert@nokia.com> | 2009-07-23 05:30:46 (GMT) |
---|---|---|
committer | Alan Alpert <alan.alpert@nokia.com> | 2009-07-23 05:30:46 (GMT) |
commit | dc68651b60b552e010735903e45328f8ebf18f69 (patch) | |
tree | 25e625dfc003de83559d61018abac811ffa208da /src/declarative/qml/qmlengine.cpp | |
parent | 1d1b32453519eb952438c734e21ae5ddf09e4966 (diff) | |
parent | 5f648e669235e0c6a11b6d25688c6dbd9bb58106 (diff) | |
download | Qt-dc68651b60b552e010735903e45328f8ebf18f69.zip Qt-dc68651b60b552e010735903e45328f8ebf18f69.tar.gz Qt-dc68651b60b552e010735903e45328f8ebf18f69.tar.bz2 |
Merge branch 'kinetic-declarativeui' of git@scm.dev.nokia.troll.no:qt/kinetic into kinetic-declarativeui
Diffstat (limited to 'src/declarative/qml/qmlengine.cpp')
-rw-r--r-- | src/declarative/qml/qmlengine.cpp | 143 |
1 files changed, 125 insertions, 18 deletions
diff --git a/src/declarative/qml/qmlengine.cpp b/src/declarative/qml/qmlengine.cpp index c4b3c0d..6549e5c 100644 --- a/src/declarative/qml/qmlengine.cpp +++ b/src/declarative/qml/qmlengine.cpp @@ -149,6 +149,7 @@ void QmlEnginePrivate::init() scriptEngine.installTranslatorFunctions(); contextClass = new QmlContextScriptClass(q); objectClass = new QmlObjectScriptClass(q); + valueTypeClass = new QmlValueTypeScriptClass(q); rootContext = new QmlContext(q,true); #ifdef QT_SCRIPTTOOLS_LIB if (qmlDebugger()){ @@ -190,7 +191,7 @@ Q_GLOBAL_STATIC(FunctionCache, functionCache); QScriptClass::QueryFlags QmlEnginePrivate::queryObject(const QString &propName, - uint *id, QObject *obj) + uint *id, QObject *obj) { QScriptClass::QueryFlags rv = 0; @@ -224,8 +225,15 @@ QmlEnginePrivate::queryObject(const QString &propName, return rv; } +struct QmlValueTypeReference { + QmlValueType *type; + QGuard<QObject> object; + int property; +}; +Q_DECLARE_METATYPE(QmlValueTypeReference); + QScriptValue QmlEnginePrivate::propertyObject(const QScriptString &propName, - QObject *obj, uint id) + QObject *obj, uint id) { if (id == QmlScriptClass::FunctionId) { QScriptValue sobj = scriptEngine.newQObject(obj); @@ -237,10 +245,20 @@ QScriptValue QmlEnginePrivate::propertyObject(const QScriptString &propName, if (!prop.isValid()) return QScriptValue(); - QVariant var = prop.read(); if (prop.needsChangedNotifier()) capturedProperties << CapturedProperty(prop); - QObject *varobj = QmlMetaType::toQObject(var); + + int propType = prop.propertyType(); + if (propType < QVariant::UserType && valueTypes[propType]) { + QmlValueTypeReference ref; + ref.type = valueTypes[propType]; + ref.object = obj; + ref.property = prop.coreIndex(); + return scriptEngine.newObject(valueTypeClass, scriptEngine.newVariant(QVariant::fromValue(ref))); + } + + QVariant var = prop.read(); + QObject *varobj = (propType < QVariant::UserType)?0:QmlMetaType::toQObject(var); if (!varobj) varobj = qvariant_cast<QObject *>(var); if (varobj) { @@ -681,6 +699,32 @@ QmlScriptClass::QmlScriptClass(QmlEngine *bindengine) { } +QVariant QmlScriptClass::toVariant(QmlEngine *engine, const QScriptValue &val) +{ + QmlEnginePrivate *ep = + static_cast<QmlEnginePrivate *>(QObjectPrivate::get(engine)); + + QScriptClass *sc = val.scriptClass(); + if (!sc) { + return val.toVariant(); + } else if (sc == ep->contextClass) { + return QVariant(); + } else if (sc == ep->objectClass) { + return QVariant::fromValue(val.data().toQObject()); + } else if (sc == ep->valueTypeClass) { + QmlValueTypeReference ref = + qvariant_cast<QmlValueTypeReference>(val.data().toVariant()); + + if (!ref.object) + return QVariant(); + + QMetaProperty p = ref.object->metaObject()->property(ref.property); + return p.read(ref.object); + } + + return QVariant(); +} + ///////////////////////////////////////////////////////////// /* The QmlContextScriptClass handles property access for a QmlContext @@ -807,19 +851,88 @@ void QmlContextScriptClass::setProperty(QScriptValue &object, QmlMetaProperty prop; prop.restore(id, obj); - QVariant v; - QObject *data = value.data().toQObject(); - if (data) { - v = QVariant::fromValue(data); - } else { - v = value.toVariant(); - } + QVariant v = QmlScriptClass::toVariant(engine, value); prop.write(v); scriptEngine->currentContext()->setActivationObject(oldact); } ///////////////////////////////////////////////////////////// +QmlValueTypeScriptClass::QmlValueTypeScriptClass(QmlEngine *bindEngine) +: QmlScriptClass(bindEngine) +{ +} + +QmlValueTypeScriptClass::~QmlValueTypeScriptClass() +{ +} + +QmlValueTypeScriptClass::QueryFlags +QmlValueTypeScriptClass::queryProperty(const QScriptValue &object, + const QScriptString &name, + QueryFlags flags, uint *id) +{ + QmlValueTypeReference ref = + qvariant_cast<QmlValueTypeReference>(object.data().toVariant()); + + if (!ref.object) + return 0; + + QByteArray propName = name.toString().toUtf8(); + + int idx = ref.type->metaObject()->indexOfProperty(propName.constData()); + if (idx == -1) + return 0; + *id = idx; + + QMetaProperty prop = ref.object->metaObject()->property(idx); + + QmlValueTypeScriptClass::QueryFlags rv = + QmlValueTypeScriptClass::HandlesReadAccess; + if (prop.isWritable()) + rv |= QmlValueTypeScriptClass::HandlesWriteAccess; + + return rv; +} + +QScriptValue QmlValueTypeScriptClass::property(const QScriptValue &object, + const QScriptString &name, + uint id) +{ + QmlValueTypeReference ref = + qvariant_cast<QmlValueTypeReference>(object.data().toVariant()); + + if (!ref.object) + return QScriptValue(); + + ref.type->read(ref.object, ref.property); + + QMetaProperty p = ref.type->metaObject()->property(id); + QVariant rv = p.read(ref.type); + + return static_cast<QmlEnginePrivate *>(QObjectPrivate::get(engine))->scriptEngine.newVariant(rv); +} + +void QmlValueTypeScriptClass::setProperty(QScriptValue &object, + const QScriptString &name, + uint id, + const QScriptValue &value) +{ + QmlValueTypeReference ref = + qvariant_cast<QmlValueTypeReference>(object.data().toVariant()); + + if (!ref.object) + return; + + QVariant v = QmlScriptClass::toVariant(engine, value); + + ref.type->read(ref.object, ref.property); + QMetaProperty p = ref.type->metaObject()->property(id); + p.write(ref.type, v); + ref.type->write(ref.object, ref.property); +} + +///////////////////////////////////////////////////////////// /* The QmlObjectScriptClass handles property access for QObjects via QtScript. It is also used to provide a more useful API in @@ -916,13 +1029,7 @@ void QmlObjectScriptClass::setProperty(QScriptValue &object, QmlMetaProperty prop; prop.restore(id, obj); - QVariant v; - QObject *data = value.data().toQObject(); - if (data) { - v = QVariant::fromValue(data); - } else { - v = value.toVariant(); - } + QVariant v = QmlScriptClass::toVariant(engine, value); prop.write(v); scriptEngine->currentContext()->setActivationObject(oldact); |