From: Lars Knoll Date: Mon, 27 Jan 2014 13:58:52 +0000 (+0100) Subject: Make the Ref classes not template based X-Git-Tag: upstream/5.2.90+alpha~251 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=39d7e330e64c2132828a040497a5b7326202b5b9;p=platform%2Fupstream%2Fqtdeclarative.git Make the Ref classes not template based Move to a class hierarchy that mirrors the main classes. This will allow moving functionality over into the Ref classes, as the current Managed classes become mainly something that holds the data. This is required to make objects movable by the GC. Change-Id: I4ca88ab0e5d8c88c8dc56d51937990500a33e0d9 Reviewed-by: Simon Hausmann --- diff --git a/src/imports/localstorage/plugin.cpp b/src/imports/localstorage/plugin.cpp index c5e6db4..7a7649c 100644 --- a/src/imports/localstorage/plugin.cpp +++ b/src/imports/localstorage/plugin.cpp @@ -131,6 +131,7 @@ public: bool forwardOnly; // type == Rows }; +DEFINE_REF(QQmlSqlDatabaseWrapper, Object); DEFINE_OBJECT_VTABLE(QQmlSqlDatabaseWrapper); static ReturnedValue qmlsqldatabase_version(CallContext *ctx) @@ -206,7 +207,7 @@ static QString qmlsqldatabase_databaseFile(const QString& connectionName, QV8Eng return qmlsqldatabase_databasesPath(engine) + QDir::separator() + connectionName; } -static ReturnedValue qmlsqldatabase_rows_index(QV4::ManagedRef r, ExecutionEngine *v4, quint32 index, bool *hasProperty = 0) +static ReturnedValue qmlsqldatabase_rows_index(QQmlSqlDatabaseWrapperRef r, ExecutionEngine *v4, quint32 index, bool *hasProperty = 0) { Scope scope(v4); QV8Engine *v8 = v4->v8Engine; diff --git a/src/qml/jsruntime/qv4debugging.cpp b/src/qml/jsruntime/qv4debugging.cpp index 32d8c1f..9ab1622 100644 --- a/src/qml/jsruntime/qv4debugging.cpp +++ b/src/qml/jsruntime/qv4debugging.cpp @@ -179,7 +179,7 @@ void Debugger::resume(Speed speed) return; if (!m_returnedValue.isUndefined()) - m_returnedValue = Primitive::undefinedValue(); + m_returnedValue = Encode::undefined(); clearTemporaryBreakPoints(); if (speed == StepOver) diff --git a/src/qml/jsruntime/qv4engine.cpp b/src/qml/jsruntime/qv4engine.cpp index 6de40f4..16bacbf 100644 --- a/src/qml/jsruntime/qv4engine.cpp +++ b/src/qml/jsruntime/qv4engine.cpp @@ -560,7 +560,7 @@ Returned *ExecutionEngine::newRegExpObject(const QString &pattern, return newRegExpObject(re, global); } -Returned *ExecutionEngine::newRegExpObject(ManagedRef re, bool global) +Returned *ExecutionEngine::newRegExpObject(RegExpRef re, bool global) { RegExpObject *object = new (memoryManager) RegExpObject(this, re, global); return object->asReturned(); diff --git a/src/qml/jsruntime/qv4engine_p.h b/src/qml/jsruntime/qv4engine_p.h index 4fbef14..63c57b8 100644 --- a/src/qml/jsruntime/qv4engine_p.h +++ b/src/qml/jsruntime/qv4engine_p.h @@ -317,7 +317,7 @@ public: Returned *newDateObject(const QDateTime &dt); Returned *newRegExpObject(const QString &pattern, int flags); - Returned *newRegExpObject(ManagedRef re, bool global); + Returned *newRegExpObject(RegExpRef re, bool global); Returned *newRegExpObject(const QRegExp &re); Returned *newErrorObject(const ValueRef value); diff --git a/src/qml/jsruntime/qv4functionobject_p.h b/src/qml/jsruntime/qv4functionobject_p.h index d1fc56a..af4ec02 100644 --- a/src/qml/jsruntime/qv4functionobject_p.h +++ b/src/qml/jsruntime/qv4functionobject_p.h @@ -155,6 +155,8 @@ inline FunctionObject *value_cast(const Value &v) { return v.asFunctionObject(); } +DEFINE_REF(FunctionObject, Object); + struct FunctionCtor: FunctionObject { V4_OBJECT diff --git a/src/qml/jsruntime/qv4global_p.h b/src/qml/jsruntime/qv4global_p.h index d3764d0..746513c 100644 --- a/src/qml/jsruntime/qv4global_p.h +++ b/src/qml/jsruntime/qv4global_p.h @@ -156,11 +156,12 @@ template struct Returned; typedef Returned ReturnedString; typedef Returned ReturnedObject; typedef Returned ReturnedFunctionObject; -template struct ManagedRef; -typedef ManagedRef StringRef; -typedef ManagedRef ObjectRef; -typedef ManagedRef ArrayObjectRef; -typedef ManagedRef FunctionObjectRef; +struct ManagedRef; +struct StringRef; +struct ObjectRef; +struct ArrayObjectRef; +struct FunctionObjectRef; +struct RegExpRef; struct PersistentValuePrivate; class PersistentValue; diff --git a/src/qml/jsruntime/qv4managed_p.h b/src/qml/jsruntime/qv4managed_p.h index ed4637e..8c6f2da 100644 --- a/src/qml/jsruntime/qv4managed_p.h +++ b/src/qml/jsruntime/qv4managed_p.h @@ -353,80 +353,6 @@ private: friend struct ObjectIterator; }; -template -struct ManagedRef { - // Important: Do NOT add a copy constructor to this class or any derived class - // adding a copy constructor actually changes the calling convention, ie. - // is not even binary compatible. Adding it would break assumptions made - // in the jit'ed code. - ManagedRef(const ScopedValue); - ManagedRef(const Scoped &v); - ManagedRef(TypedValue &v) { ptr = &v; } - ManagedRef(Value &v) { - ptr = value_cast(v) ? &v : 0; - } - static ManagedRef fromValuePointer(Value *s) { - ManagedRef r(s); - if (sizeof(void *) == 8) - r.ptr->val = 0; - else - *r.ptr = Value::fromManaged(0); - return r; - } - - ManagedRef &operator=(T *t) - { - if (sizeof(void *) == 4) - ptr->tag = Value::Managed_Type; - ptr->m = t; - return *this; - } - ManagedRef &operator=(Returned *t) { - if (sizeof(void *) == 4) - ptr->tag = Value::Managed_Type; - ptr->m = t->getPointer(); - return *this; - } - - operator const T *() const { - return ptr ? static_cast(ptr->managed()) : 0; - } - const T *operator->() const { - return static_cast(ptr->managed()); - } - - operator T *() { - return ptr ? static_cast(ptr->managed()) : 0; - } - T *operator->() { - return static_cast(ptr->managed()); - } - - T *getPointer() const { - return static_cast(ptr->managed()); - } - ReturnedValue asReturnedValue() const { return ptr ? ptr->val : Primitive::undefinedValue().asReturnedValue(); } - operator Returned *() const { return ptr ? Returned::create(getPointer()) : 0; } - - bool operator==(const ManagedRef &other) { - if (ptr == other.ptr) - return true; - return ptr && other.ptr && ptr->m == other.ptr->m; - } - bool operator!=(const ManagedRef &other) { - return !operator==(other); - } - bool operator!() const { return !ptr || !ptr->managed(); } - - static ManagedRef null() { return ManagedRef((Value *)0); } - bool isNull() const { return !ptr; } -protected: - ManagedRef(Value *v) { - ptr = v; - } - Value *ptr; -}; - template<> inline Managed *value_cast(const Value &v) { @@ -456,6 +382,68 @@ inline FunctionObject *managed_cast(Managed *m) } +Value *extractValuePointer(const ScopedValue &); +template +Value *extractValuePointer(const Scoped &); + +#define DEFINE_REF_METHODS(Class, Base) \ + Class##Ref(const QV4::ScopedValue &v) \ + { QV4::Value *val = extractValuePointer(v); ptr = QV4::value_cast(*val) ? val : 0; } \ + Class##Ref(const QV4::Scoped &v) { ptr = extractValuePointer(v); } \ + Class##Ref(QV4::TypedValue &v) { ptr = &v; } \ + Class##Ref(QV4::Value &v) { ptr = QV4::value_cast(v) ? &v : 0; } \ + Class##Ref &operator=(Class *t) { \ + if (sizeof(void *) == 4) \ + ptr->tag = QV4::Value::Managed_Type; \ + ptr->m = t; \ + return *this; \ + } \ + Class##Ref &operator=(QV4::Returned *t) { \ + if (sizeof(void *) == 4) \ + ptr->tag = QV4::Value::Managed_Type; \ + ptr->m = t->getPointer(); \ + return *this; \ + } \ + operator const Class *() const { return ptr ? static_cast(ptr->managed()) : 0; } \ + const Class *operator->() const { return static_cast(ptr->managed()); } \ + operator Class *() { return ptr ? static_cast(ptr->managed()) : 0; } \ + Class *operator->() { return static_cast(ptr->managed()); } \ + Class *getPointer() const { return static_cast(ptr->managed()); } \ + operator QV4::Returned *() const { return ptr ? QV4::Returned::create(getPointer()) : 0; } \ + static Class##Ref null() { Class##Ref c; c.ptr = 0; return c; } \ +protected: \ + Class##Ref() {} \ +public: \ + +#define DEFINE_REF(Class, Base) \ +struct Class##Ref : public Base##Ref \ +{ DEFINE_REF_METHODS(Class, Base) } \ + + +struct ManagedRef { + // Important: Do NOT add a copy constructor to this class or any derived class + // adding a copy constructor actually changes the calling convention, ie. + // is not even binary compatible. Adding it would break assumptions made + // in the jit'ed code. + DEFINE_REF_METHODS(Managed, Managed); + + bool operator==(const ManagedRef &other) { + if (ptr == other.ptr) + return true; + return ptr && other.ptr && ptr->m == other.ptr->m; + } + bool operator!=(const ManagedRef &other) { + return !operator==(other); + } + bool operator!() const { return !ptr || !ptr->managed(); } + + bool isNull() const { return !ptr; } + ReturnedValue asReturnedValue() const { return ptr ? ptr->val : Primitive::undefinedValue().asReturnedValue(); } + +public: + Value *ptr; +}; + } diff --git a/src/qml/jsruntime/qv4object_p.h b/src/qml/jsruntime/qv4object_p.h index 3a4cb3d..e3361ae 100644 --- a/src/qml/jsruntime/qv4object_p.h +++ b/src/qml/jsruntime/qv4object_p.h @@ -422,6 +422,23 @@ inline ReturnedValue value_convert(ExecutionEngine *e, const Value &v) return v.toObject(e->currentContext())->asReturnedValue(); } +struct ObjectRef : public ManagedRef +{ + DEFINE_REF_METHODS(Object, Managed) + + static ObjectRef fromValuePointer(Value *s) { + ObjectRef r; + r.ptr = s; + if (sizeof(void *) == 8) + r.ptr->val = 0; + else + *r.ptr = Value::fromManaged(0); + return r; + } +}; + +DEFINE_REF(ArrayObject, Object); + } QT_END_NAMESPACE diff --git a/src/qml/jsruntime/qv4objectiterator.cpp b/src/qml/jsruntime/qv4objectiterator.cpp index 707bea0..e5f693c 100644 --- a/src/qml/jsruntime/qv4objectiterator.cpp +++ b/src/qml/jsruntime/qv4objectiterator.cpp @@ -46,18 +46,18 @@ using namespace QV4; -ObjectIterator::ObjectIterator(ObjectRef scratch1, ObjectRef scratch2, const ObjectRef o, uint flags) - : object(scratch1) - , current(scratch2) +ObjectIterator::ObjectIterator(Value *scratch1, Value *scratch2, const ObjectRef o, uint flags) + : object(ObjectRef::fromValuePointer(scratch1)) + , current(ObjectRef::fromValuePointer(scratch2)) , arrayNode(0) , arrayIndex(0) , memberIndex(0) , flags(flags) { - object = o; - current = o; + object = o.getPointer(); + current = o.getPointer(); - if (object && object->asArgumentsObject()) { + if (!!object && object->asArgumentsObject()) { Scope scope(object->engine()); Scoped (scope, object->asReturnedValue())->fullyCreate(); } @@ -74,7 +74,7 @@ ObjectIterator::ObjectIterator(Scope &scope, const ObjectRef o, uint flags) object = o; current = o; - if (object && object->asArgumentsObject()) { + if (!!object && object->asArgumentsObject()) { Scope scope(object->engine()); Scoped (scope, object->asReturnedValue())->fullyCreate(); } @@ -103,7 +103,7 @@ void ObjectIterator::next(StringRef name, uint *index, Property *pd, PropertyAtt Object *o = object; bool shadowed = false; while (o != current) { - if ((name && o->hasOwnProperty(name)) || + if ((!!name && o->hasOwnProperty(name)) || (*index != UINT_MAX && o->hasOwnProperty(*index))) { shadowed = true; break; diff --git a/src/qml/jsruntime/qv4objectiterator_p.h b/src/qml/jsruntime/qv4objectiterator_p.h index dafd269..c87f284 100644 --- a/src/qml/jsruntime/qv4objectiterator_p.h +++ b/src/qml/jsruntime/qv4objectiterator_p.h @@ -74,7 +74,7 @@ struct Q_QML_EXPORT ObjectIterator uint memberIndex; uint flags; - ObjectIterator(ObjectRef scratch1, ObjectRef scratch2, const ObjectRef o, uint flags); + ObjectIterator(Value *scratch1, Value *scratch2, const ObjectRef o, uint flags); ObjectIterator(Scope &scope, const ObjectRef o, uint flags); void next(StringRef name, uint *index, Property *pd, PropertyAttributes *attributes = 0); ReturnedValue nextPropertyName(ValueRef value); @@ -87,7 +87,7 @@ struct ForEachIteratorObject: Object { Q_MANAGED_TYPE(ForeachIteratorObject) ObjectIterator it; ForEachIteratorObject(ExecutionContext *ctx, const ObjectRef o) - : Object(ctx->engine), it(ObjectRef::fromValuePointer(workArea), ObjectRef::fromValuePointer(workArea + 1), + : Object(ctx->engine), it(workArea, workArea + 1, o, ObjectIterator::EnumerableOnly|ObjectIterator::WithProtoChain) { setVTable(staticVTable()); } diff --git a/src/qml/jsruntime/qv4persistent_p.h b/src/qml/jsruntime/qv4persistent_p.h index 34cf9ba..21f37f3 100644 --- a/src/qml/jsruntime/qv4persistent_p.h +++ b/src/qml/jsruntime/qv4persistent_p.h @@ -84,14 +84,13 @@ public: PersistentValue(ReturnedValue val); template PersistentValue(Returned *obj); - template - PersistentValue(const ManagedRef obj); + PersistentValue(const ManagedRef obj); PersistentValue &operator=(const ValueRef other); + PersistentValue &operator=(const ScopedValue &other); PersistentValue &operator =(ReturnedValue other); template PersistentValue &operator=(Returned *obj); - template - PersistentValue &operator=(const ManagedRef obj); + PersistentValue &operator=(const ManagedRef obj); ~PersistentValue(); ReturnedValue value() const { diff --git a/src/qml/jsruntime/qv4qobjectwrapper.cpp b/src/qml/jsruntime/qv4qobjectwrapper.cpp index 4645efc..9bc01d1 100644 --- a/src/qml/jsruntime/qv4qobjectwrapper.cpp +++ b/src/qml/jsruntime/qv4qobjectwrapper.cpp @@ -1702,7 +1702,8 @@ QV4::ReturnedValue CallArgument::toValue(QV8Engine *engine) } else if (type == -1 || type == qMetaTypeId()) { QVariant value = *qvariantPtr; QV4::ScopedValue rv(scope, engine->fromVariant(value)); - if (QV4::ManagedRef qobjectWrapper = rv) { + QV4::QObjectWrapperRef qobjectWrapper = rv; + if (!!qobjectWrapper) { if (QObject *object = qobjectWrapper->object()) QQmlData::get(object, true)->setImplicitDestructible(); } diff --git a/src/qml/jsruntime/qv4qobjectwrapper_p.h b/src/qml/jsruntime/qv4qobjectwrapper_p.h index 38003eb..ca38c5b 100644 --- a/src/qml/jsruntime/qv4qobjectwrapper_p.h +++ b/src/qml/jsruntime/qv4qobjectwrapper_p.h @@ -200,6 +200,8 @@ private Q_SLOTS: void removeDestroyedObject(QObject*); }; +DEFINE_REF(QObjectWrapper, Object); + } QT_END_NAMESPACE diff --git a/src/qml/jsruntime/qv4regexpobject.cpp b/src/qml/jsruntime/qv4regexpobject.cpp index 35ba9bc..74c8a2d 100644 --- a/src/qml/jsruntime/qv4regexpobject.cpp +++ b/src/qml/jsruntime/qv4regexpobject.cpp @@ -80,7 +80,7 @@ RegExpObject::RegExpObject(InternalClass *ic) init(ic->engine); } -RegExpObject::RegExpObject(ExecutionEngine *engine, ManagedRef value, bool global) +RegExpObject::RegExpObject(ExecutionEngine *engine, RegExpRef value, bool global) : Object(engine->regExpClass) , value(value) , global(global) diff --git a/src/qml/jsruntime/qv4regexpobject_p.h b/src/qml/jsruntime/qv4regexpobject_p.h index ce3d017..1b40874 100644 --- a/src/qml/jsruntime/qv4regexpobject_p.h +++ b/src/qml/jsruntime/qv4regexpobject_p.h @@ -84,7 +84,7 @@ struct RegExpObject: Object { Property *lastIndexProperty(ExecutionContext *ctx); bool global; - RegExpObject(ExecutionEngine *engine, ManagedRef value, bool global); + RegExpObject(ExecutionEngine *engine, RegExpRef value, bool global); RegExpObject(ExecutionEngine *engine, const QRegExp &re); ~RegExpObject() {} @@ -101,6 +101,7 @@ protected: static void markObjects(Managed *that, ExecutionEngine *e); }; +DEFINE_REF(RegExp, Object); struct RegExpCtor: FunctionObject { diff --git a/src/qml/jsruntime/qv4scopedvalue_p.h b/src/qml/jsruntime/qv4scopedvalue_p.h index 9b9f062..5d471ab 100644 --- a/src/qml/jsruntime/qv4scopedvalue_p.h +++ b/src/qml/jsruntime/qv4scopedvalue_p.h @@ -379,9 +379,9 @@ struct ScopedCallData { }; -typedef ManagedRef StringRef; -typedef ManagedRef ObjectRef; -typedef ManagedRef FunctionObjectRef; +struct StringRef; +struct ObjectRef; +struct FunctionObjectRef; template inline Scoped::Scoped(const Scope &scope, const ValueRef &v) @@ -485,12 +485,12 @@ inline TypedValue &TypedValue::operator=(Returned *t) return *this; } -template -inline TypedValue &TypedValue::operator =(const ManagedRef &v) -{ - val = v.asReturnedValue(); - return *this; -} +//template +//inline TypedValue &TypedValue::operator =(const ManagedRef &v) +//{ +// val = v.asReturnedValue(); +// return *this; +//} template inline TypedValue &TypedValue::operator=(const TypedValue &t) @@ -517,9 +517,8 @@ PersistentValue::PersistentValue(Returned *obj) { } -template -inline PersistentValue::PersistentValue(const ManagedRef obj) - : d(new PersistentValuePrivate(*obj.ptr)) +inline PersistentValue::PersistentValue(const ManagedRef obj) + : d(new PersistentValuePrivate(obj.asReturnedValue())) { } @@ -529,12 +528,15 @@ inline PersistentValue &PersistentValue::operator=(Returned *obj) return operator=(QV4::Value::fromManaged(obj->getPointer()).asReturnedValue()); } -template -inline PersistentValue &PersistentValue::operator=(const ManagedRef obj) +inline PersistentValue &PersistentValue::operator=(const ManagedRef obj) { - return operator=(*obj.ptr); + return operator=(obj.asReturnedValue()); } +inline PersistentValue &PersistentValue::operator=(const ScopedValue &other) +{ + return operator=(other.asReturnedValue()); +} template inline WeakValue::WeakValue(Returned *obj) @@ -572,16 +574,16 @@ inline ValueRef &ValueRef::operator=(const ScopedValue &o) } -template -ManagedRef::ManagedRef(const ScopedValue v) +inline Value *extractValuePointer(const ScopedValue &v) { - ptr = value_cast(*v.ptr) ? v.ptr : 0; + return v.ptr; } template -ManagedRef::ManagedRef(const Scoped &v) - : ptr(v.ptr) -{} +Value *extractValuePointer(const Scoped &v) +{ + return v.ptr; +} struct ScopedProperty { diff --git a/src/qml/jsruntime/qv4script.cpp b/src/qml/jsruntime/qv4script.cpp index c50b025..7d94195 100644 --- a/src/qml/jsruntime/qv4script.cpp +++ b/src/qml/jsruntime/qv4script.cpp @@ -168,7 +168,7 @@ Script::Script(ExecutionEngine *v4, ObjectRef qml, CompiledData::CompilationUnit Q_ASSERT(vmFunction); Scope valueScope(v4); ScopedValue holder(valueScope, new (v4->memoryManager) CompilationUnitHolder(v4, compilationUnit)); - compilationUnitHolder = holder; + compilationUnitHolder = holder.asReturnedValue(); } else vmFunction = 0; } @@ -236,7 +236,7 @@ void Script::parse() QV4::CompiledData::CompilationUnit *compilationUnit = isel->compile(); vmFunction = compilationUnit->linkToEngine(v4); ScopedValue holder(valueScope, new (v4->memoryManager) CompilationUnitHolder(v4, compilationUnit)); - compilationUnitHolder = holder; + compilationUnitHolder = holder.asReturnedValue(); } if (!vmFunction) { diff --git a/src/qml/jsruntime/qv4string_p.h b/src/qml/jsruntime/qv4string_p.h index c981472..ade64d1 100644 --- a/src/qml/jsruntime/qv4string_p.h +++ b/src/qml/jsruntime/qv4string_p.h @@ -187,6 +187,8 @@ inline ReturnedValue value_convert(ExecutionEngine *e, const Value &v) return v.toString(e)->asReturnedValue(); } +DEFINE_REF(String, Managed); + } QT_END_NAMESPACE diff --git a/src/qml/jsruntime/qv4value_p.h b/src/qml/jsruntime/qv4value_p.h index 2aefcc4..27c81d5 100644 --- a/src/qml/jsruntime/qv4value_p.h +++ b/src/qml/jsruntime/qv4value_p.h @@ -433,7 +433,7 @@ struct TypedValue : public Value } TypedValue &operator =(T *t); TypedValue &operator =(const Scoped &v); - TypedValue &operator =(const ManagedRef &v); +// TypedValue &operator =(const ManagedRef &v); TypedValue &operator =(Returned *t); TypedValue &operator =(const TypedValue &t); diff --git a/src/qml/jsruntime/qv4variantobject_p.h b/src/qml/jsruntime/qv4variantobject_p.h index 6c4a365..656608d 100644 --- a/src/qml/jsruntime/qv4variantobject_p.h +++ b/src/qml/jsruntime/qv4variantobject_p.h @@ -82,6 +82,8 @@ public: static bool isEqualTo(Managed *m, Managed *other); }; +DEFINE_REF(VariantObject, Object); + struct VariantPrototype : VariantObject { public: diff --git a/src/qml/qml/qqmlvmemetaobject.cpp b/src/qml/qml/qqmlvmemetaobject.cpp index 48893c1..f9cb956 100644 --- a/src/qml/qml/qqmlvmemetaobject.cpp +++ b/src/qml/qml/qqmlvmemetaobject.cpp @@ -1086,7 +1086,8 @@ void QQmlVMEMetaObject::writeProperty(int id, const QVariant &value) // And, if the new value is a scarce resource, we need to ensure that it does not get // automatically released by the engine until no other references to it exist. QV4::ScopedValue newv(scope, QQmlEnginePrivate::get(ctxt->engine)->v8engine()->fromVariant(value)); - if (QV4::ManagedRef v = newv) + QV4::VariantObjectRef v = newv; + if (!!v) v->addVmePropertyReference(); // Write the value and emit change signal as appropriate. diff --git a/src/quick/items/context2d/qquickcontext2d.cpp b/src/quick/items/context2d/qquickcontext2d.cpp index 120397c..9851983 100644 --- a/src/quick/items/context2d/qquickcontext2d.cpp +++ b/src/quick/items/context2d/qquickcontext2d.cpp @@ -921,6 +921,8 @@ struct QQuickJSContext2DImageData : public QV4::Object QV4::Value pixelData; }; +DEFINE_REF(QQuickJSContext2DImageData, QV4::Object); + DEFINE_OBJECT_VTABLE(QQuickJSContext2DImageData); static QV4::ReturnedValue qt_create_image_data(qreal w, qreal h, QV8Engine* engine, const QImage& image) @@ -2112,7 +2114,8 @@ QV4::ReturnedValue QQuickJSContext2D::method_set_path(QV4::CallContext *ctx) QV4::ScopedValue value(scope, ctx->argument(0)); r->context->beginPath(); - if (QV4::ManagedRef qobjectWrapper = value) { + QV4::QObjectWrapperRef qobjectWrapper = value; + if (!!qobjectWrapper) { if (QQuickPath *path = qobject_cast(qobjectWrapper->object())) r->context->m_path = path->path(); } else { @@ -2983,7 +2986,8 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_drawImage(QV4::CallContext pixmap = r->context->createPixmap(url); } else if (arg->isObject()) { - if (QV4::ManagedRef qobjectWrapper = arg) { + QV4::QObjectWrapperRef qobjectWrapper = arg; + if (!!qobjectWrapper) { if (QQuickImage *imageItem = qobject_cast(qobjectWrapper->object())) { pixmap = r->context->createPixmap(imageItem->source()); } else if (QQuickCanvasItem *canvas = qobject_cast(qobjectWrapper->object())) { @@ -2993,19 +2997,22 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_drawImage(QV4::CallContext } else { V4THROW_DOM(DOMEXCEPTION_TYPE_MISMATCH_ERR, "drawImage(), type mismatch"); } - } else if (QV4::ManagedRef imageData = arg) { - QV4::Scoped pix(scope, imageData->pixelData.as()); - if (pix && !pix->image.isNull()) { - pixmap.take(new QQuickCanvasPixmap(pix->image)); + } else { + QQuickJSContext2DImageDataRef imageData = arg; + if (!!imageData) { + QV4::Scoped pix(scope, imageData->pixelData.as()); + if (pix && !pix->image.isNull()) { + pixmap.take(new QQuickCanvasPixmap(pix->image)); + } else { + V4THROW_DOM(DOMEXCEPTION_TYPE_MISMATCH_ERR, "drawImage(), type mismatch"); + } } else { - V4THROW_DOM(DOMEXCEPTION_TYPE_MISMATCH_ERR, "drawImage(), type mismatch"); + QUrl url(arg->toQStringNoThrow()); + if (url.isValid()) + pixmap = r->context->createPixmap(url); + else + V4THROW_DOM(DOMEXCEPTION_TYPE_MISMATCH_ERR, "drawImage(), type mismatch"); } - } else { - QUrl url(arg->toQStringNoThrow()); - if (url.isValid()) - pixmap = r->context->createPixmap(url); - else - V4THROW_DOM(DOMEXCEPTION_TYPE_MISMATCH_ERR, "drawImage(), type mismatch"); } } else { V4THROW_DOM(DOMEXCEPTION_TYPE_MISMATCH_ERR, "drawImage(), type mismatch"); @@ -3263,7 +3270,8 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_createImageData(QV4::CallC if (ctx->callData->argc == 1) { QV4::ScopedValue arg0(scope, ctx->callData->args[0]); - if (QV4::ManagedRef imgData = arg0) { + QQuickJSContext2DImageDataRef imgData = arg0; + if (!!imgData) { QV4::Scoped pa(scope, imgData->pixelData.as()); if (pa) { qreal w = pa->image.width(); @@ -3340,7 +3348,7 @@ QV4::ReturnedValue QQuickJSContext2DPrototype::method_putImageData(QV4::CallCont if (!qIsFinite(dx) || !qIsFinite(dy)) V4THROW_DOM(DOMEXCEPTION_NOT_SUPPORTED_ERR, "putImageData() : Invalid arguments"); - QV4::ManagedRef imageData = arg0; + QQuickJSContext2DImageDataRef imageData = arg0; if (!imageData) return ctx->callData->thisObject.asReturnedValue();