#include "mapview.h" #include "mapview_tile_cache_p.h" #include "mapview_tile_downloader_p.h" MapViewTileDownloader::MapViewTileDownloader(MapView * p): QThread() { qRegisterMetaType(); parent = p; start(); } MapViewTileDownloader::~MapViewTileDownloader() { requestInterruption(); cond.wakeAll(); wait(); if (provider) provider->deleteLater(); } bool MapViewTileDownloader::queueTile(MapViewTypes::TileIndex index, bool force) { // auto hash = tile.hash(); bool ret = false; cond_mutex.lock(); if ((!queue.contains(index) && !in_progress.contains(index.hash())) || force) { queue.enqueue(index); cond.wakeOne(); ret = true; } cond_mutex.unlock(); return ret; } void MapViewTileDownloader::queueTiles(QList indeces) { cond_mutex.lock(); queue << indeces; cond.wakeOne(); cond_mutex.unlock(); } void MapViewTileDownloader::clearQueue() { cond_mutex.lock(); queue.clear(); cond_mutex.unlock(); } void MapViewTileDownloader::setTileProvider(MapViewTileProviderBase * p) { if (provider) { disconnect(provider, &MapViewTileProviderBase::tileReady, this, &MapViewTileDownloader::tileReady); disconnect(provider, &MapViewTileProviderBase::parametersChanged, this, &MapViewTileDownloader::parametersChanged); provider->deleteLater(); } provider = p; if (provider) { connect(provider, &MapViewTileProviderBase::tileReady, this, &MapViewTileDownloader::tileReady); connect(provider, &MapViewTileProviderBase::parametersChanged, this, &MapViewTileDownloader::parametersChanged); } parent->cache->tileProviderChanged(); } void MapViewTileDownloader::requestTile(MapViewTypes::TileIndex index) { if (!provider) return; provider->requestTile(index); } void MapViewTileDownloader::tileReady(MapViewTypes::TileIndex index, QPixmap pm) { if (!pm.isNull()) parent->cache->tileDownloaded(index, pm); cond_mutex.lock(); in_progress.remove(index.hash()); cond_mutex.unlock(); emit tileDone(); } void MapViewTileDownloader::parametersChanged() { parent->cache->tileProviderChanged(); } void MapViewTileDownloader::run() { while (!isInterruptionRequested()) { cond_mutex.lock(); if (queue.isEmpty()) cond.wait(&cond_mutex); else { auto t = queue.dequeue(); in_progress.insert(t.hash()); QMetaObject::invokeMethod(parent, [this, t]() { requestTile(t); }, Qt::QueuedConnection); } cond_mutex.unlock(); } }