Browse Source

qt: update getItemsForIndexes in NetworkDeviceModel to support asynchronous callbacks

pull/199/head
Ahmed Sobhy 6 months ago
committed by Steve Lhomme
parent
commit
043460f1f4
  1. 79
      modules/gui/qt/network/networkdevicemodel.cpp
  2. 5
      modules/gui/qt/network/networkdevicemodel.hpp

79
modules/gui/qt/network/networkdevicemodel.cpp

@ -18,6 +18,8 @@
#include <unordered_set>
#include <QTimer>
#include <QJSValue>
#include <QQmlEngine>
#include "maininterface/mainctx.hpp"
@ -599,48 +601,63 @@ bool NetworkDeviceModel::addAndPlay(const QModelIndexList& itemIdList)
}
/* Q_INVOKABLE */
QVariantList NetworkDeviceModel::getItemsForIndexes(const QModelIndexList & indexes) const
void NetworkDeviceModel::getItemsForIndexes(const QModelIndexList & indexes, QJSValue callback)
{
Q_D(const NetworkDeviceModel);
QVariantList items;
bool allInCache = true;
for (const QModelIndex & modelIndex : indexes)
{
const NetworkDeviceItem* item = d->getItemForRow(modelIndex.row());
if (!item)
{
allInCache = false;
break;
}
if (!callback.isCallable())
return;
items.append(QVariant::fromValue(SharedInputItem(item->getInputItem().get(), true)));
}
getItemsForIndexes(indexes, [this, callback](const QVariantList& items) mutable {
auto engine = qjsEngine(this);
if (engine)
callback.call({engine->toScriptValue(items)});
});
}
if (allInCache)
return items;
void NetworkDeviceModel::getItemsForIndexes(const QModelIndexList & indexes, std::function<void(const QVariantList&)> callback)
{
Q_D(NetworkDeviceModel);
// Sometimes if there are many items selected, some are not in cache so we need to rebuild the list
items.clear();
std::vector<NetworkDeviceItemPtr> modelData = d->getModelData(d->m_searchPattern);
if (!callback)
return;
auto sortFunc = d->getSortFunction();
if (sortFunc)
std::sort(modelData.begin(), modelData.end(), sortFunc);
if (indexes.isEmpty())
{
callback(QVariantList());
return;
}
int maxIndex = 0;
for (const QModelIndex & modelIndex : indexes)
{
int index = modelIndex.row();
if (modelIndex.row() > maxIndex)
maxIndex = modelIndex.row();
}
if (index < 0 || index >= static_cast<int>(modelData.size()))
continue;
// check if we have loaded all items we need
unsigned int loaded = getLoadedCount();
unsigned int maximum = getMaximumCount();
unsigned int needed = static_cast<unsigned int>(maxIndex) + 1;
const NetworkDeviceItemPtr& item = modelData[index];
if (!item)
continue;
if (loaded >= needed || loaded >= maximum)
{
QVariantList items;
for (const QModelIndex & modelIndex : indexes)
{
const NetworkDeviceItem* item = d->getItemForRow(modelIndex.row());
if (!item)
continue;
items.append(QVariant::fromValue(SharedInputItem(item->getInputItem().get(), true)));
}
items.append(QVariant::fromValue(SharedInputItem(item->getInputItem().get(), true)));
callback(items);
return;
}
return items;
// item() internally calls refer() to trigger cache loading for all items till the max index
d->item(maxIndex);
connect(this, &NetworkDeviceModel::dataChanged, this, [this, indexes, callback]() {
getItemsForIndexes(indexes, callback);
}, Qt::SingleShotConnection);
}

5
modules/gui/qt/network/networkdevicemodel.hpp

@ -25,9 +25,11 @@
#include "networkbasemodel.hpp"
#include <memory>
#include <functional>
Q_MOC_INCLUDE("maininterface/mainctx.hpp")
class QJSValue;
class MainCtx;
class NetworkDeviceModelPrivate;
@ -83,7 +85,8 @@ public:
Q_INVOKABLE bool addAndPlay(const QVariantList& itemIdList);
Q_INVOKABLE bool addAndPlay(const QModelIndexList& itemIdList);
Q_INVOKABLE QVariantList getItemsForIndexes(const QModelIndexList & indexes) const;
Q_INVOKABLE void getItemsForIndexes(const QModelIndexList & indexes, QJSValue callback);
void getItemsForIndexes(const QModelIndexList & indexes, std::function<void(const QVariantList&)> callback);
signals:
void ctxChanged();

Loading…
Cancel
Save