ListModel data from JSON without .append() loop
-
wrote on 15 Jun 2021, 12:58 last edited by
Dear all,
im getting JSON data from XMLHttpRequest(), and the data are huge.
lets say 10000 rows (each if its own array) which I have to add into ListModel.so far im using:
// Populate Model function populateRecordsGrouped() { console.log("start " + new Date().getTime()); var array_records = httpRequest(); // this gives me array from JSON from XMLHttpRequest(), i guess no need to specify for (var ix = 0; ix < array_records.length; ++ix) { myModelGrouped.append({"serialNumber": "", "material": array_records[ix]['material'], "batch": array_records[ix]['batch'], "amount": array_records[ix]['amount'], "location": array_records[ix]['location']}); } console.log("end " + new Date().getTime()); }
so is there better/faster way than looping?
I have noticed this link:
https://blog.felgo.com/cross-platform-app-development/avoid-cpp-models-qt
which is using AppListView instead, where they just simply asset all data at once like:// on app start: fetch data from REST api Component.onCompleted: { HttpRequest.get("https://jsonplaceholder.typicode.com/todos") .timeout(5000) .then(function(res) { dataFetched(res.body) }) .catch(function(err) { console.err("Fetch failed:"+err) }); } // dataFetched gets called on success of http request function dataFetched(jsonData) { listView.model = jsonData // set retrieved json data as model for list } // list page NavigationStack { Page { title: "Todo List" AppListView { id: listView anchors.fill: parent delegate: SimpleRow { text: modelData.title } } } }
so is there something I could use for ListModel the same/similar way?
cause looping thought 10.000 records (each its own array) takes roughly 8 seconds :( -
Dear all,
im getting JSON data from XMLHttpRequest(), and the data are huge.
lets say 10000 rows (each if its own array) which I have to add into ListModel.so far im using:
// Populate Model function populateRecordsGrouped() { console.log("start " + new Date().getTime()); var array_records = httpRequest(); // this gives me array from JSON from XMLHttpRequest(), i guess no need to specify for (var ix = 0; ix < array_records.length; ++ix) { myModelGrouped.append({"serialNumber": "", "material": array_records[ix]['material'], "batch": array_records[ix]['batch'], "amount": array_records[ix]['amount'], "location": array_records[ix]['location']}); } console.log("end " + new Date().getTime()); }
so is there better/faster way than looping?
I have noticed this link:
https://blog.felgo.com/cross-platform-app-development/avoid-cpp-models-qt
which is using AppListView instead, where they just simply asset all data at once like:// on app start: fetch data from REST api Component.onCompleted: { HttpRequest.get("https://jsonplaceholder.typicode.com/todos") .timeout(5000) .then(function(res) { dataFetched(res.body) }) .catch(function(err) { console.err("Fetch failed:"+err) }); } // dataFetched gets called on success of http request function dataFetched(jsonData) { listView.model = jsonData // set retrieved json data as model for list } // list page NavigationStack { Page { title: "Todo List" AppListView { id: listView anchors.fill: parent delegate: SimpleRow { text: modelData.title } } } }
so is there something I could use for ListModel the same/similar way?
cause looping thought 10.000 records (each its own array) takes roughly 8 seconds :(wrote on 17 Jun 2021, 21:47 last edited by jeremy_kIs the intention to support updating the model in place? If not, a json array can be directly used as a model.
property var jsonModel: JSON.parse('[ {"data": "one", "data2": "1"}, {"data": "two", "data2": "2"} ]') ListView { id: view anchors.fill: parent model: jsonModel delegate: Text { text: modelData.data + ":" + modelData.data2 } }
If the model does need to be updated in place, and using C++ instead of javascript isn't an option, the threaded ListModel example demonstrates using WorkerScript to avoid blocking the UI thread.
-
If the model needs to be updated (even if not), I would advise to use https://github.com/benlau/qsyncable and its
JsonListModel
. It's aQAbstractListModel
under the hood that calculates the diff between the new and old model and only emit the necessary signals (dataChanged, rowInserted/Removed), no complete model reset and delegate deletion/recreation.
1/3