int Test::qt_metacall(QMetaObject::Call call, int id, void **args) { id = QObject::qt_metacall(call, id, args); if (id < 0 || !d->meta) return id; if (call == QMetaObject::InvokeMetaMethod) { int metaIndex = id + d->meta->methodOffset(); QMetaMethod method = d->meta->method(metaIndex); if (!method.isValid()) { qWarning() << "invoked invalid method with id" << id; return -1; } QVariantList vargs; for (int i = 0; i < method.parameterCount(); ++i) vargs.append(QVariant(method.parameterType(i), args[1 + i])); QString catchedName = d->slotId2Name.value(metaIndex); void *_a[] = { 0, const_cast<void*>(reinterpret_cast<const void*>(&catchedName)), const_cast<void*>(reinterpret_cast<const void*>(&vargs)) }; QMetaObject::activate(this, metaObject(), d->catchedSignalId, _a); } return -1; }
void Test::activateSignal(const QString &signal, const QVariantList &args) { int metaIndex = d->signalName2Id.value(signal, -1); if (metaIndex == -1) { qWarning() << "dynamic signal" << signal << "doesn't exist"; return; } QMetaMethod sig = d->meta->method(metaIndex); if (sig.parameterCount() != args.count()) { qWarning() << "dynamic signal has" << sig.parameterCount() << "args" << args.count() << "provided"; return; } QVariantList argsCopy = args; void * _a[11] = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}; for (int i = 0; i < sig.parameterCount(); ++i) { if (!argsCopy[i].convert(sig.parameterType(i))) { qWarning() << "dynamic signal" << signal << "wrong parameter" << i; return; } _a[i + 1] = argsCopy[i].data(); } QMetaObject::activate(this, d->meta, metaIndex - d->meta->methodOffset(), _a); }
QVector<int> metaMethodParamTypeIds(QMetaMethod m) { QVector<int> ret; int maxCnt = m.parameterCount(); for (int i = 0; i < maxCnt; i++) { ret.push_back(m.parameterType(i)); } return ret; }
Method Nuria::ObjectWrapperResourcePrivate::createMetaMethod (QMetaMethod method) { Method m; QList< QByteArray > names = method.parameterNames (); for (int i = 0, count = names.length (); i < count; ++i) { m.names.append (QString::fromLatin1 (names.at (i))); m.types.append (method.parameterType (i)); } // Done return m; }
void tst_QQmlMetaObject::method() { QFETCH(QString, testFile); QFETCH(QString, signature); QFETCH(QMetaMethod::MethodType, methodType); QFETCH(int, returnType); QFETCH(QString, returnTypeName); QFETCH(QList<int>, parameterTypes); QFETCH(QList<QByteArray>, parameterTypeNames); QFETCH(QList<QByteArray>, parameterNames); QCOMPARE(parameterTypes.size(), parameterTypeNames.size()); QCOMPARE(parameterTypeNames.size(), parameterNames.size()); QQmlEngine engine; QQmlComponent component(&engine, testFileUrl(testFile)); QObject *object = component.create(); QVERIFY(object != 0); const QMetaObject *mo = object->metaObject(); QVERIFY(mo->superClass() != 0); QVERIFY(QByteArray(mo->className()).contains("_QML_")); QCOMPARE(mo->methodOffset(), mo->superClass()->methodCount()); QCOMPARE(mo->methodCount(), mo->superClass()->methodCount() + 1); QMetaMethod method = mo->method(mo->methodOffset()); QCOMPARE(method.methodType(), methodType); QCOMPARE(QString::fromUtf8(method.methodSignature().constData()), signature); QCOMPARE(method.access(), QMetaMethod::Public); QString computedName = signature.left(signature.indexOf('(')); QCOMPARE(QString::fromUtf8(method.name()), computedName); QCOMPARE(method.parameterCount(), parameterTypes.size()); for (int i = 0; i < parameterTypes.size(); ++i) QCOMPARE(method.parameterType(i), parameterTypes.at(i)); QCOMPARE(method.parameterTypes(), parameterTypeNames); QCOMPARE(method.tag(), ""); QCOMPARE(QString::fromUtf8(method.typeName()), returnTypeName); QCOMPARE(method.returnType(), returnType); delete object; }
void QFSignalProxy::bind(QObject *source, int signalIdx, QQmlEngine* engine, QFDispatcher* dispatcher) { const int memberOffset = QObject::staticMetaObject.methodCount(); QMetaMethod method = source->metaObject()->method(signalIdx); parameterTypes = QVector<int>(method.parameterCount()); parameterNames = QVector<QString>(method.parameterCount()); type = method.name(); m_engine = engine; m_dispatcher = dispatcher; for (int i = 0 ; i < method.parameterCount() ; i++) { parameterTypes[i] = method.parameterType(i); parameterNames[i] = QString(method.parameterNames().at(i)); } if (!QMetaObject::connect(source, signalIdx, this, memberOffset, Qt::AutoConnection, 0)) { qWarning() << "Failed to bind signal"; } }
int DynamicQObject::qt_metacall(QMetaObject::Call call, int id, void **arguments) { printf("%d\n", call); // Call default handlers in QObject first id = QObject::qt_metacall(call, id, arguments); if (id == -1 || call != QMetaObject::InvokeMetaMethod) return id; #if 0 Q_ASSERT(id < callbacks.count()); Callback *callback = callbacks[id]; int methodId = findSignalId(callback->signal); // Convert parameters HandleScope scope; const QMetaObject *meta = obj->metaObject(); QMetaMethod method = meta->method(methodId); int argc = method.parameterCount(); Handle<Value> *argv = new Handle<Value>[argc]; for (int i = 0; i < method.parameterCount(); ++i) { int type = method.parameterType(i); // Convert argv[i] = Utils::QDataToV8(type, arguments[i + 1]); } // Invoke MakeCallback(callback->handler, callback->handler, argc, argv); // Release delete [] argv; #endif return -1; }
void tst_QMetaMethod::method() { QFETCH(QByteArray, signature); QFETCH(int, returnType); QFETCH(QByteArray, returnTypeName); QFETCH(QList<int>, parameterTypes); QFETCH(QList<QByteArray>, parameterTypeNames); QFETCH(QList<QByteArray>, parameterNames); QFETCH(QMetaMethod::MethodType, methodType); QFETCH(QMetaMethod::Access, access); QVERIFY(parameterTypes.size() == parameterTypeNames.size()); QVERIFY(parameterTypes.size() == parameterNames.size()); const QMetaObject *mo = &MethodTestObject::staticMetaObject; int index = (methodType == QMetaMethod::Constructor) ? mo->indexOfConstructor(signature) : mo->indexOfMethod(signature); QVERIFY(index != -1); QMetaMethod method = (methodType == QMetaMethod::Constructor) ? mo->constructor(index) : mo->method(index); QVERIFY(method.isValid()); QCOMPARE(method.methodType(), methodType); QCOMPARE(method.access(), access); QVERIFY(!method.methodSignature().isEmpty()); if (method.methodSignature() != signature) { // QMetaMethod should always produce a semantically equivalent signature int signatureIndex = (methodType == QMetaMethod::Constructor) ? mo->indexOfConstructor(method.methodSignature()) : mo->indexOfMethod(method.methodSignature()); QCOMPARE(signatureIndex, index); } QByteArray computedName = signature.left(signature.indexOf('(')); QCOMPARE(method.name(), computedName); QCOMPARE(method.tag(), ""); QCOMPARE(method.returnType(), returnType); QVERIFY(method.typeName() != 0); if (QByteArray(method.typeName()) != returnTypeName) { // QMetaMethod should always produce a semantically equivalent typename QCOMPARE(QMetaType::type(method.typeName()), QMetaType::type(returnTypeName)); } if (method.parameterTypes() != parameterTypeNames) { // QMetaMethod should always produce semantically equivalent typenames QList<QByteArray> actualTypeNames = method.parameterTypes(); QCOMPARE(actualTypeNames.size(), parameterTypeNames.size()); for (int i = 0; i < parameterTypeNames.size(); ++i) { QCOMPARE(QMetaType::type(actualTypeNames.at(i)), QMetaType::type(parameterTypeNames.at(i))); } } QCOMPARE(method.parameterNames(), parameterNames); QCOMPARE(method.parameterCount(), parameterTypes.size()); for (int i = 0; i < parameterTypes.size(); ++i) QCOMPARE(method.parameterType(i), parameterTypes.at(i)); { QVector<int> actualParameterTypes(parameterTypes.size()); method.getParameterTypes(actualParameterTypes.data()); for (int i = 0; i < parameterTypes.size(); ++i) QCOMPARE(actualParameterTypes.at(i), parameterTypes.at(i)); } // Bogus indexes QCOMPARE(method.parameterType(-1), 0); QCOMPARE(method.parameterType(parameterTypes.size()), 0); }