From 3a61da32e485621c9afbd453d22cbe1f6c25479e Mon Sep 17 00:00:00 2001 From: Simon Hausmann Date: Mon, 4 Nov 2013 02:48:16 +0100 Subject: [PATCH] Ensure the this object is set correctly to the scope object in binding expressions This is a regression from 5.1 Change-Id: I61ad372a02d937c195dad74bd9fcb8fd4410d97a Reviewed-by: Lars Knoll --- src/qml/jsruntime/qv4qobjectwrapper.cpp | 2 -- src/qml/qml/qqmlbinding.cpp | 10 ---------- src/qml/qml/qqmlbinding_p.h | 8 -------- src/qml/qml/qqmljavascriptexpression.cpp | 4 ++-- src/qml/qml/qqmljavascriptexpression_p.h | 13 ------------- src/qml/qml/qqmlvaluetypewrapper.cpp | 2 -- tests/auto/qml/qqmlecmascript/data/thisObject.qml | 10 ++++++++++ tests/auto/qml/qqmlecmascript/tst_qqmlecmascript.cpp | 10 ++++++++++ 8 files changed, 22 insertions(+), 37 deletions(-) create mode 100644 tests/auto/qml/qqmlecmascript/data/thisObject.qml diff --git a/src/qml/jsruntime/qv4qobjectwrapper.cpp b/src/qml/jsruntime/qv4qobjectwrapper.cpp index d5aa9f4..4537b6c 100644 --- a/src/qml/jsruntime/qv4qobjectwrapper.cpp +++ b/src/qml/jsruntime/qv4qobjectwrapper.cpp @@ -477,8 +477,6 @@ void QObjectWrapper::setProperty(QObject *object, ExecutionContext *ctx, QQmlPro newBinding = new QQmlBinding(value, object, callingQmlContext, frame.source, qmlSourceCoordinate(frame.line), qmlSourceCoordinate(frame.column)); newBinding->setTarget(object, *property, callingQmlContext); - newBinding->setEvaluateFlags(newBinding->evaluateFlags() | - QQmlBinding::RequiresThisObject); } } diff --git a/src/qml/qml/qqmlbinding.cpp b/src/qml/qml/qqmlbinding.cpp index a388178..557267d 100644 --- a/src/qml/qml/qqmlbinding.cpp +++ b/src/qml/qml/qqmlbinding.cpp @@ -194,16 +194,6 @@ QQmlBinding::~QQmlBinding() { } -void QQmlBinding::setEvaluateFlags(EvaluateFlags flags) -{ - setRequiresThisObject(flags & RequiresThisObject); -} - -QQmlBinding::EvaluateFlags QQmlBinding::evaluateFlags() const -{ - return requiresThisObject()?RequiresThisObject:None; -} - void QQmlBinding::setNotifyOnValueChanged(bool v) { QQmlJavaScriptExpression::setNotifyOnValueChanged(v); diff --git a/src/qml/qml/qqmlbinding_p.h b/src/qml/qml/qqmlbinding_p.h index e872482..9dd63a6 100644 --- a/src/qml/qml/qqmlbinding_p.h +++ b/src/qml/qml/qqmlbinding_p.h @@ -76,9 +76,6 @@ class Q_QML_PRIVATE_EXPORT QQmlBinding : public QQmlJavaScriptExpression, public QQmlAbstractBinding { public: - enum EvaluateFlag { None = 0x00, RequiresThisObject = 0x01 }; - Q_DECLARE_FLAGS(EvaluateFlags, EvaluateFlag) - QQmlBinding(const QString &, QObject *, QQmlContext *); QQmlBinding(const QQmlScriptString &, QObject *, QQmlContext *); QQmlBinding(const QString &, QObject *, QQmlContextData *); @@ -91,9 +88,6 @@ public: void setTarget(QObject *, const QQmlPropertyData &, QQmlContextData *); QQmlProperty property() const; - void setEvaluateFlags(EvaluateFlags flags); - EvaluateFlags evaluateFlags() const; - void setNotifyOnValueChanged(bool); // Inherited from QQmlAbstractExpression @@ -177,8 +171,6 @@ void QQmlBinding::setEnabledFlag(bool v) m_ctxt.setFlag2Value(v); } -Q_DECLARE_OPERATORS_FOR_FLAGS(QQmlBinding::EvaluateFlags) - QT_END_NAMESPACE Q_DECLARE_METATYPE(QQmlBinding*) diff --git a/src/qml/qml/qqmljavascriptexpression.cpp b/src/qml/qml/qqmljavascriptexpression.cpp index 53b7504..3fd0003 100644 --- a/src/qml/qml/qqmljavascriptexpression.cpp +++ b/src/qml/qml/qqmljavascriptexpression.cpp @@ -156,8 +156,8 @@ QV4::ReturnedValue QQmlJavaScriptExpression::evaluate(QQmlContextData *context, QV4::Scope scope(v4); QV4::ScopedValue result(scope, QV4::Primitive::undefinedValue()); QV4::ExecutionContext *ctx = v4->current; - callData->thisObject = ep->v8engine()->global(); - if (scopeObject() && requiresThisObject()) { + callData->thisObject = v4->globalObject; + if (scopeObject()) { QV4::ScopedValue value(scope, QV4::QObjectWrapper::wrap(ctx->engine, scopeObject())); if (value->isObject()) callData->thisObject = value; diff --git a/src/qml/qml/qqmljavascriptexpression_p.h b/src/qml/qml/qqmljavascriptexpression_p.h index 4435704..7d65f1c 100644 --- a/src/qml/qml/qqmljavascriptexpression_p.h +++ b/src/qml/qml/qqmljavascriptexpression_p.h @@ -117,8 +117,6 @@ public: QV4::ReturnedValue evaluate(QQmlContextData *, const QV4::ValueRef function, bool *isUndefined); QV4::ReturnedValue evaluate(QQmlContextData *, const QV4::ValueRef function, QV4::CallData *callData, bool *isUndefined); - inline bool requiresThisObject() const; - inline void setRequiresThisObject(bool v); inline bool notifyOnValueChanged() const; void setNotifyOnValueChanged(bool v); @@ -183,7 +181,6 @@ private: QPointerValuePair m_vtable; // We store some flag bits in the following flag pointers. - // m_scopeObject:flag1 - requiresThisObject // activeGuards:flag1 - notifyOnValueChanged // activeGuards:flag2 - useSharedContext QBiPointer m_scopeObject; @@ -215,16 +212,6 @@ bool QQmlJavaScriptExpression::DeleteWatcher::wasDeleted() const return *_w == 0; } -bool QQmlJavaScriptExpression::requiresThisObject() const -{ - return m_scopeObject.flag(); -} - -void QQmlJavaScriptExpression::setRequiresThisObject(bool v) -{ - m_scopeObject.setFlagValue(v); -} - bool QQmlJavaScriptExpression::notifyOnValueChanged() const { return activeGuards.flag(); diff --git a/src/qml/qml/qqmlvaluetypewrapper.cpp b/src/qml/qml/qqmlvaluetypewrapper.cpp index 6c9f90c..d6f35f1 100644 --- a/src/qml/qml/qqmlvaluetypewrapper.cpp +++ b/src/qml/qml/qqmlvaluetypewrapper.cpp @@ -385,8 +385,6 @@ void QmlValueTypeWrapper::put(Managed *m, const StringRef name, const ValueRef v newBinding = new QQmlBinding(value, reference->object, context, frame.source, qmlSourceCoordinate(frame.line), qmlSourceCoordinate(frame.column)); newBinding->setTarget(reference->object, cacheData, context); - newBinding->setEvaluateFlags(newBinding->evaluateFlags() | - QQmlBinding::RequiresThisObject); } QQmlAbstractBinding *oldBinding = diff --git a/tests/auto/qml/qqmlecmascript/data/thisObject.qml b/tests/auto/qml/qqmlecmascript/data/thisObject.qml new file mode 100644 index 0000000..c93d030 --- /dev/null +++ b/tests/auto/qml/qqmlecmascript/data/thisObject.qml @@ -0,0 +1,10 @@ +import QtQml 2.0 +QtObject { + property int value: 1 + property QtObject subObject: QtObject { + property int value: 2 + property int test: { + return this.value; + } + } +} diff --git a/tests/auto/qml/qqmlecmascript/tst_qqmlecmascript.cpp b/tests/auto/qml/qqmlecmascript/tst_qqmlecmascript.cpp index b1cf8c9..f464114 100644 --- a/tests/auto/qml/qqmlecmascript/tst_qqmlecmascript.cpp +++ b/tests/auto/qml/qqmlecmascript/tst_qqmlecmascript.cpp @@ -307,6 +307,7 @@ private slots: void numberParsing(); void stringParsing(); void qtbug_32801(); + void thisObject(); private: // static void propertyVarWeakRefCallback(v8::Persistent object, void* parameter); @@ -7311,6 +7312,15 @@ void tst_qqmlecmascript::qtbug_32801() QVERIFY(QMetaObject::invokeMethod(obj.data(), "emitTestSignal")); } +void tst_qqmlecmascript::thisObject() +{ + QQmlComponent component(&engine, testFileUrl("thisObject.qml")); + QObject *object = component.create(); + QVERIFY(object); + QCOMPARE(qvariant_cast(object->property("subObject"))->property("test").toInt(), 2); + delete object; +} + QTEST_MAIN(tst_qqmlecmascript) #include "tst_qqmlecmascript.moc" -- 2.7.4