From b1f7d1380cef500dba25586c0b6e95550e986343 Mon Sep 17 00:00:00 2001 From: Cathy Park Date: Thu, 19 Aug 2021 15:40:27 +0900 Subject: qqmllistmodel: Fix QObjects setting indestructible It makes a QObject indestructable only if its ownership is determined. This fixes an issue where a QObject created by createObject() in QML becomes indestructable once it is appended to a ListModel. Fixes: QTBUG-95895 Change-Id: I30647298977d7901dab938626e8f94b9910c21e3 Reviewed-by: Ulf Hermann Reviewed-by: Jaeyoon Jung Reviewed-by: Andrei Golubev (cherry picked from commit 69e07c55ad9b49b7643ffddfedc9a558983272ad) Reviewed-by: Qt Cherry-pick Bot --- .../auto/qml/qqmllistmodel/data/destroyObject.qml | 23 +++++++++++++++++++ tests/auto/qml/qqmllistmodel/data/dummyItem.qml | 5 +++++ tests/auto/qml/qqmllistmodel/tst_qqmllistmodel.cpp | 26 ++++++++++++++++++++++ 3 files changed, 54 insertions(+) create mode 100644 tests/auto/qml/qqmllistmodel/data/destroyObject.qml create mode 100644 tests/auto/qml/qqmllistmodel/data/dummyItem.qml (limited to 'tests') diff --git a/tests/auto/qml/qqmllistmodel/data/destroyObject.qml b/tests/auto/qml/qqmllistmodel/data/destroyObject.qml new file mode 100644 index 0000000000..e6b3f33bb9 --- /dev/null +++ b/tests/auto/qml/qqmllistmodel/data/destroyObject.qml @@ -0,0 +1,23 @@ +import QtQml + +QtObject { + id: root + property ListModel projects: ListModel {} + property var object + + Component.onCompleted: { + var comp= Qt.createComponent("dummyItem.qml"); + object = comp.createObject(root, {}); + projects.append({"obj": object}); + } + + function destroy() { + try { + object.destroy(); + } catch(e) { + console.warn(e); + return false; + } + return true; + } +} diff --git a/tests/auto/qml/qqmllistmodel/data/dummyItem.qml b/tests/auto/qml/qqmllistmodel/data/dummyItem.qml new file mode 100644 index 0000000000..c9939efcdf --- /dev/null +++ b/tests/auto/qml/qqmllistmodel/data/dummyItem.qml @@ -0,0 +1,5 @@ +import QtQml + +QtObject { + property var random: null +} diff --git a/tests/auto/qml/qqmllistmodel/tst_qqmllistmodel.cpp b/tests/auto/qml/qqmllistmodel/tst_qqmllistmodel.cpp index a9b6ec03a4..7f94180274 100644 --- a/tests/auto/qml/qqmllistmodel/tst_qqmllistmodel.cpp +++ b/tests/auto/qml/qqmllistmodel/tst_qqmllistmodel.cpp @@ -136,6 +136,7 @@ private slots: void destroyObject(); void emptyStringNotUndefined(); void listElementWithTemplateString(); + void destroyComponentObject(); }; bool tst_qqmllistmodel::compareVariantList(const QVariantList &testList, QVariant object) @@ -1856,6 +1857,31 @@ void tst_qqmllistmodel::listElementWithTemplateString() QVERIFY(!root.isNull()); } +//QTBUG-95895 +void tst_qqmllistmodel::destroyComponentObject() +{ + QQmlEngine eng; + QQmlComponent component(&eng, testFileUrl("destroyObject.qml")); + QVERIFY(!component.isError()); + QScopedPointer obj(component.create()); + QVERIFY(!obj.isNull()); + QQmlListModel *list = qvariant_cast(obj->property("projects")); + QVERIFY(list != nullptr); + QCOMPARE(list->count(), 1); + QPointer created(qvariant_cast(obj->property("object"))); + QVERIFY(!created.isNull()); + QCOMPARE(list->get(0).property("obj").toQObject(), created.data()); + QVariant retVal; + QMetaObject::invokeMethod(obj.data(), + "destroy", + Qt::DirectConnection, + Q_RETURN_ARG(QVariant, retVal)); + QVERIFY(retVal.toBool()); + QTRY_VERIFY(created.isNull()); + QTRY_VERIFY(list->get(0).property("obj").isUndefined()); + QCOMPARE(list->count(), 1); +} + QTEST_MAIN(tst_qqmllistmodel) #include "tst_qqmllistmodel.moc" -- cgit v1.2.3