Details
-
Bug
-
Resolution: Done
-
P2: Important
-
5.12
-
-
dbc811e164019b5f9ce371cb7b49d695644f6a90 (qt/qtdeclarative/5.12)
Description
In the following example, a delegate model uses a QQmlListProperty as a source model. The DelegateModel is used by a ListView. In this case, a change in the QQmlListProperty leads to a Segmentation Fault during the call of the the following line:
// qqmldelegatemodel.cpp line 592
QQmlDelegateModelItem *cacheItem = QQmlDelegateModelItem::dataForObject(object);
The error does not occur when list view does not use the delegate model or if the DelegateModel does not use the underlying QQmlListProperty.
Also, by avoiding the DelegateModel all together and having the ListView accessing the QQmlListProperty model directly, also does not crash.
Down here there is the QML part of the example, in the attached ZIP file, you can find the whole project and additionally the backtrace caused by the Segmentation Fault.
The QQmlListProperty model of RandomObjectsProvider contains a very simple elements of a QObjects derivative with random content.
The changes in the model are caused by the objectsProvider.createNewElements() call. This method is triggered every 300ms
// QML is shaped as follows import QtQuick.Window 2.2 import QtQuick 2.6 import QtQuick.Controls 2.0 import QtQuick.Layouts 1.3 import QtQml.Models 2.11 import example 1.0 Window { visible: true width: 640 height: 480 title: qsTr("Hello World") ListView { anchors.fill: parent model: delegateModel } DelegateModel { id: delegateModel model: objectsProvider.randomObjects delegate: delegate filterOnGroup: "visible" groups: [ DelegateModelGroup { id: visibleGroup name: "visible" includeByDefault: false } ] items.onChanged: { Qt.callLater(update) // very similar backtrace with `update();` } function update() { if(items.count>0) items.addGroups(0, items.count, ["visible"]); } } Component { id: delegate Rectangle { anchors.left: parent.left anchors.right: parent.right height: 30 Text { text: "Data: " + (!modelData ? name : modelData.name) } } } Timer { id: changeModelTimer property int count: 0 interval: 300 onTriggered: { count++; console.log("Round", count); objectsProvider.createNewElements(); console.log("Number of elements", objectsProvider.count()); if(count>=100) { Qt.quit() } } repeat: true } Component.onCompleted: { objectsProvider.createNewElements(); changeModelTimer.start(); } RandomObjectsProvider { id: objectsProvider } }