MapView scale less detailed levels on current level feature

This commit is contained in:
2023-01-20 23:28:08 +03:00
parent c166c040b0
commit 4b8a7a4779
5 changed files with 47 additions and 8 deletions

View File

@@ -66,6 +66,7 @@ QPointF MapView::center() const {
void MapView::setCenter(QPointF c) { void MapView::setCenter(QPointF c) {
center_ = OSM::geo2xy(c); center_ = OSM::geo2xy(c);
checkCenter();
updateViewRect(); updateViewRect();
drawBackground(); drawBackground();
} }
@@ -100,6 +101,7 @@ void MapView::mouseMoveEvent(QMouseEvent * e) {
if (is_pan) { if (is_pan) {
double mins = qMin(width(), height()); double mins = qMin(width(), height());
center_ -= QPointF(e->pos() - press_point) / scale_ / mins; center_ -= QPointF(e->pos() - press_point) / scale_ / mins;
checkCenter();
press_point = e->pos(); press_point = e->pos();
updateViewRect(); updateViewRect();
drawBackground(); drawBackground();
@@ -133,7 +135,7 @@ void MapView::paintEvent(QPaintEvent *) {
void MapView::resizeEvent(QResizeEvent *) { void MapView::resizeEvent(QResizeEvent *) {
cache->setMinimumCacheSize((width() + tileSize) * (height() + tileSize) * 4); cache->setMinimumCacheSize((width() + tileSize) * (height() + tileSize) * 4 * 3);
checkZoom(); checkZoom();
updateZoomLevel(); updateZoomLevel();
updateViewRect(); updateViewRect();
@@ -158,9 +160,10 @@ void MapView::drawBackground() {
for (int iy = sy; iy < ey; ++iy) { for (int iy = sy; iy < ey; ++iy) {
QRectF r((ix)*ts, (iy)*ts, ts, ts); QRectF r((ix)*ts, (iy)*ts, ts, ts);
r.translate(-offset); r.translate(-offset);
auto tile = cache->getTile((OSM::TileIndex){zoom_level, ix, iy}); QRectF px_rct(QPointF(), QSizeF(tileSize, tileSize));
auto tile = cache->getTile((OSM::TileIndex){zoom_level, ix, iy}, px_rct);
if (!tile.isEmpty()) { if (!tile.isEmpty()) {
p.drawPixmap(r, tile.pixmap, QRectF(tile.pixmap.rect())); p.drawPixmap(r, tile.pixmap, px_rct);
} else { } else {
p.fillRect(r, brush_tr); p.fillRect(r, brush_tr);
} }
@@ -212,6 +215,14 @@ void MapView::checkZoom() {
} }
void MapView::checkCenter() {
if (center_.x() < 0.) center_.setX(0.);
if (center_.x() > 1.) center_.setX(1.);
if (center_.y() < 0.) center_.setY(0.);
if (center_.y() > 1.) center_.setY(1.);
}
void MapView::zoomLevelChanged(int new_level) { void MapView::zoomLevelChanged(int new_level) {
zoom_level = qBound(0, new_level, max_level); zoom_level = qBound(0, new_level, max_level);
// qDebug() << "level changed" << new_level << zoom_level; // qDebug() << "level changed" << new_level << zoom_level;
@@ -296,7 +307,8 @@ void MapView::zoom(double factor, QPoint anchor) {
checkZoom(); checkZoom();
QPointF new_center = mapToNorm(anchor); QPointF new_center = mapToNorm(anchor);
center_ += prev_center - new_center; center_ += prev_center - new_center;
view_rect.translate(prev_center - new_center); checkCenter();
view_rect.moveCenter(center_);
updateZoomLevel(); updateZoomLevel();
drawBackground(); drawBackground();
} }
@@ -312,6 +324,7 @@ void MapView::zoomTo(double level) {
void MapView::centerTo(QPointF coord) { void MapView::centerTo(QPointF coord) {
center_ = OSM::geo2xy(coord); center_ = OSM::geo2xy(coord);
checkCenter();
updateViewRect(); updateViewRect();
drawBackground(); drawBackground();
} }

View File

@@ -64,6 +64,7 @@ private:
void drawBackground(); void drawBackground();
void drawItems(QPainter & p); void drawItems(QPainter & p);
void checkZoom(); void checkZoom();
void checkCenter();
void zoomLevelChanged(int new_level); void zoomLevelChanged(int new_level);
void updateZoomLevel(); void updateZoomLevel();
void updateViewRect(); void updateViewRect();

View File

@@ -32,7 +32,32 @@ void OSMTileCache::tileDownloaded(OSM::TileIndex index, const QPixmap & pixmap)
} }
OSM::TilePixmap OSMTileCache::getTile(OSM::TileIndex index) { OSM::TilePixmap OSMTileCache::getTile(OSM::TileIndex index, QRectF & rect_src) {
OSM::TilePixmap ret = getTileFromCache(index);
if (ret.isEmpty()) {
parent->downloader->queueTile(index);
QVector<QPointF> offsets;
while (index.z >= 0) {
index.z--;
offsets << QPointF(index.x % 2, index.y % 2);
index.x /= 2;
index.y /= 2;
ret = getTileFromCache(index);
if (!ret.isEmpty()) {
for (int i = offsets.size() - 1; i >= 0; --i) {
rect_src.setSize(rect_src.size() / 2.);
rect_src.translate(offsets[i].x() * rect_src.width(), offsets[i].y() * rect_src.height());
}
return ret;
}
}
} else
rect_src = ret.pixmap.rect();
return ret;
}
OSM::TilePixmap OSMTileCache::getTileFromCache(OSM::TileIndex index) {
OSM::TilePixmap ret; OSM::TilePixmap ret;
ret.index = index; ret.index = index;
auto * tile = tile_cache[index.hash()]; auto * tile = tile_cache[index.hash()];
@@ -51,7 +76,6 @@ OSM::TilePixmap OSMTileCache::getTile(OSM::TileIndex index) {
return ret; return ret;
} }
} }
parent->downloader->queueTile(index);
} }
return ret; return ret;
} }

View File

@@ -48,9 +48,10 @@ public:
} }
void tileDownloaded(OSM::TileIndex index, const QPixmap & pixmap); void tileDownloaded(OSM::TileIndex index, const QPixmap & pixmap);
OSM::TilePixmap getTile(OSM::TileIndex index); OSM::TilePixmap getTile(OSM::TileIndex index, QRectF & rect_src);
private: private:
OSM::TilePixmap getTileFromCache(OSM::TileIndex index);
void updateCacheSize(); void updateCacheSize();
void saveTile(OSM::TilePixmap * tile); void saveTile(OSM::TilePixmap * tile);
void writeToDisk(const OSM::TilePixmap & tile); void writeToDisk(const OSM::TilePixmap & tile);

View File

@@ -67,6 +67,6 @@ int main(int argc, char * argv[]) {
w.addItem(it); w.addItem(it);
w.addItem(ell);*/ w.addItem(ell);*/
w.centerTo({55.583055, 37.580008}); w.centerTo({55.583055, 37.580008});
w.zoomTo(17); w.zoomTo(2);
return a.exec(); return a.exec();
} }