1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
|
// Copyright (C) 2024 The Qt Company Ltd.
// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only
#include "qv4qmetaobjectwrapper_p.h"
#include <private/qqmlobjectorgadget_p.h>
#include <private/qv4jscall_p.h>
#include <private/qv4qobjectwrapper_p.h>
QT_BEGIN_NAMESPACE
using namespace Qt::StringLiterals;
namespace QV4 {
void Heap::QMetaObjectWrapper::init(const QMetaObject *metaObject)
{
FunctionObject::init();
m_metaObject = metaObject;
}
void Heap::QMetaObjectWrapper::destroy()
{
delete[] m_constructors;
FunctionObject::destroy();
}
ReturnedValue QMetaObjectWrapper::create(ExecutionEngine *engine, const QMetaObject* metaObject) {
Scope scope(engine);
Scoped<QMetaObjectWrapper> mo(scope, engine->memoryManager->allocate<QMetaObjectWrapper>(metaObject)->asReturnedValue());
mo->init(engine);
return mo->asReturnedValue();
}
void QMetaObjectWrapper::init(ExecutionEngine *) {
const QMetaObject &mo = *d()->metaObject();
for (int i = 0; i < mo.enumeratorCount(); i++) {
QMetaEnum Enum = mo.enumerator(i);
for (int k = 0; k < Enum.keyCount(); k++) {
const char* key = Enum.key(k);
const int value = Enum.value(k);
defineReadonlyProperty(QLatin1String(key), Value::fromInt32(value));
}
}
}
ReturnedValue QMetaObjectWrapper::virtualCallAsConstructor(const FunctionObject *f, const Value *argv, int argc, const Value *)
{
Q_ASSERT(f->as<QMetaObjectWrapper>());
return construct(static_cast<const QMetaObjectWrapper*>(f)->d(), argv, argc);
}
ReturnedValue QMetaObjectWrapper::constructInternal(
const QMetaObject *mo, const QQmlPropertyData *constructors, Heap::FunctionObject *d,
const Value *argv, int argc)
{
ExecutionEngine *v4 = d->internalClass->engine;
if (!constructors) {
return v4->throwTypeError(QLatin1String(mo->className())
+ QLatin1String(" has no invokable constructor"));
}
Scope scope(v4);
ScopedObject object(scope);
JSCallData cData(nullptr, argv, argc);
CallData *callData = cData.callData(scope);
const QQmlObjectOrGadget objectOrGadget(mo);
const auto callType = [](QMetaType metaType) {
return metaType.flags() & QMetaType::PointerToQObject
? QMetaObject::CreateInstance
: QMetaObject::ConstructInPlace;
};
const int constructorCount = mo->constructorCount();
if (constructorCount == 1) {
object = QObjectMethod::callPrecise(
objectOrGadget, constructors[0], v4, callData,
callType(constructors[0].propType()));
} else if (const QQmlPropertyData *ctor = QObjectMethod::resolveOverloaded(
objectOrGadget, constructors, constructorCount, v4, callData)) {
object = QObjectMethod::callPrecise(
objectOrGadget, *ctor, v4, callData, callType(ctor->propType()));
}
if (object) {
Scoped<FunctionObject> functionObject(scope, d);
object->defineDefaultProperty(v4->id_constructor(), functionObject);
object->setPrototypeOf(functionObject);
}
return object.asReturnedValue();
}
bool QMetaObjectWrapper::virtualIsEqualTo(Managed *a, Managed *b)
{
const QMetaObjectWrapper *aMetaObject = a->as<QMetaObjectWrapper>();
Q_ASSERT(aMetaObject);
const QMetaObjectWrapper *bMetaObject = b->as<QMetaObjectWrapper>();
return bMetaObject && aMetaObject->metaObject() == bMetaObject->metaObject();
}
DEFINE_OBJECT_VTABLE(QMetaObjectWrapper);
} // namespace QV4
QT_END_NAMESPACE
|