QtQml: Avoid double-wrapping when converting to QVariantList
Amends commit 1b89c1edca
Fixes: QTBUG-139764
Pick-to: 6.10 6.9 6.8
Change-Id: I1488527a235d74fc0352c72b9bfb69589c2f3d93
Reviewed-by: Sami Shalayel <sami.shalayel@qt.io>
This commit is contained in:
parent
398411caaf
commit
ce266fbcdd
|
@ -2516,15 +2516,29 @@ bool convertToIterable(QMetaType metaType, void *data, Source *sequence)
|
||||||
if (!QMetaType::view(metaType, data, QMetaType::fromType<QSequentialIterable>(), &iterable))
|
if (!QMetaType::view(metaType, data, QMetaType::fromType<QSequentialIterable>(), &iterable))
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
const QMetaType elementMetaType = iterable.valueMetaType();
|
// Clear the sequence before appending. There may be stale data in there.
|
||||||
|
metaType.destruct(data);
|
||||||
|
metaType.construct(data);
|
||||||
|
|
||||||
QV4::Scope scope(sequence->engine());
|
QV4::Scope scope(sequence->engine());
|
||||||
QV4::ScopedValue v(scope);
|
QV4::ScopedValue v(scope);
|
||||||
|
|
||||||
|
const QMetaType elementMetaType = iterable.valueMetaType();
|
||||||
|
QVariant element;
|
||||||
|
void *elementData = nullptr;
|
||||||
|
if (elementMetaType == QMetaType::fromType<QVariant>()) {
|
||||||
|
elementData = &element;
|
||||||
|
} else {
|
||||||
|
element = QVariant(elementMetaType);
|
||||||
|
elementData = element.data();
|
||||||
|
}
|
||||||
|
|
||||||
for (qsizetype i = 0, end = sequence->getLength(); i < end; ++i) {
|
for (qsizetype i = 0, end = sequence->getLength(); i < end; ++i) {
|
||||||
QVariant element(elementMetaType);
|
|
||||||
v = sequence->get(i);
|
v = sequence->get(i);
|
||||||
ExecutionEngine::metaTypeFromJS(v, elementMetaType, element.data());
|
ExecutionEngine::metaTypeFromJS(v, elementMetaType, elementData);
|
||||||
iterable.addValue(element, QSequentialIterable::AtEnd);
|
iterable.addValue(element, QSequentialIterable::AtEnd);
|
||||||
}
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -285,6 +285,7 @@ set(qml_files
|
||||||
script.js
|
script.js
|
||||||
script.mjs
|
script.mjs
|
||||||
sequenceToIterable.qml
|
sequenceToIterable.qml
|
||||||
|
sequenceToIterable2.qml
|
||||||
setLookupConversion.qml
|
setLookupConversion.qml
|
||||||
setLookupOriginalScope.qml
|
setLookupOriginalScope.qml
|
||||||
shadowedAsCasts.qml
|
shadowedAsCasts.qml
|
||||||
|
|
|
@ -48,6 +48,13 @@ public:
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Q_INVOKABLE QList<Entry *> getEntries() const { return m_entries; }
|
Q_INVOKABLE QList<Entry *> getEntries() const { return m_entries; }
|
||||||
|
Q_INVOKABLE QList<Entry *> convertEntries(const QVariantList &entries) const
|
||||||
|
{
|
||||||
|
QList<Entry *> converted;
|
||||||
|
for (const QVariant &entry : entries)
|
||||||
|
converted.push_back(entry.value<Entry *>());
|
||||||
|
return converted;
|
||||||
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
QList<Entry*> m_entries;
|
QList<Entry*> m_entries;
|
||||||
|
|
|
@ -0,0 +1,6 @@
|
||||||
|
import QtQml
|
||||||
|
import TestTypes
|
||||||
|
|
||||||
|
QtObject {
|
||||||
|
property list<Entry> converted: EntrySource.convertEntries(EntrySource.getEntries());
|
||||||
|
}
|
|
@ -12,6 +12,7 @@
|
||||||
#include <data/objectwithmethod.h>
|
#include <data/objectwithmethod.h>
|
||||||
#include <data/qmlusing.h>
|
#include <data/qmlusing.h>
|
||||||
#include <data/resettable.h>
|
#include <data/resettable.h>
|
||||||
|
#include <data/sequenceToIterable.h>
|
||||||
#include <data/takenumber.h>
|
#include <data/takenumber.h>
|
||||||
#include <data/weathermoduleurl.h>
|
#include <data/weathermoduleurl.h>
|
||||||
#include <data/withlength.h>
|
#include <data/withlength.h>
|
||||||
|
@ -5086,6 +5087,19 @@ void tst_QmlCppCodegen::sequenceToIterable()
|
||||||
QVERIFY(match.hasMatch());
|
QVERIFY(match.hasMatch());
|
||||||
QCOMPARE(match.captured(1), QString::number(i));
|
QCOMPARE(match.captured(1), QString::number(i));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
QQmlComponent component2(&engine, QUrl(u"qrc:/qt/qml/TestTypes/sequenceToIterable2.qml"_s));
|
||||||
|
QVERIFY2(!component2.isError(), component.errorString().toUtf8());
|
||||||
|
QScopedPointer<QObject> object2(component2.create());
|
||||||
|
QVERIFY(!object2.isNull());
|
||||||
|
|
||||||
|
QQmlListReference converted(object2.data(), "converted");
|
||||||
|
QCOMPARE(converted.count(), 10);
|
||||||
|
for (int i = 0; i < 10; ++i) {
|
||||||
|
Entry *e = qobject_cast<Entry *>(converted.at(i));
|
||||||
|
QVERIFY(e);
|
||||||
|
QCOMPARE(e->objectName(), QStringLiteral("Item %1").arg(i));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void tst_QmlCppCodegen::setLookupConversion()
|
void tst_QmlCppCodegen::setLookupConversion()
|
||||||
|
|
Loading…
Reference in New Issue