diff options
author | Aleksandar Stojiljkovic <aleksandar.stojiljkovic@mapbox.com> | 2019-07-26 09:17:46 +0300 |
---|---|---|
committer | Aleksandar Stojiljkovic <aleksandar.stojiljkovic@mapbox.com> | 2019-08-05 18:59:43 +0300 |
commit | b12889539e9e92a48360e536d11abf95b6513690 (patch) | |
tree | d7ceda98b40bd4d29c83f37042aeb5d55aa05a61 /src/mbgl/util/tile_cover.cpp | |
parent | 8103a2b028358b747fe0f2d6cce2e32ca1424680 (diff) | |
download | qtlocation-mapboxgl-b12889539e9e92a48360e536d11abf95b6513690.tar.gz |
Tiles LOD: load and render based on zoom when displayed
Fixes #9037
Diffstat (limited to 'src/mbgl/util/tile_cover.cpp')
-rw-r--r-- | src/mbgl/util/tile_cover.cpp | 53 |
1 files changed, 53 insertions, 0 deletions
diff --git a/src/mbgl/util/tile_cover.cpp b/src/mbgl/util/tile_cover.cpp index 5189b79f26..11e1a97f4c 100644 --- a/src/mbgl/util/tile_cover.cpp +++ b/src/mbgl/util/tile_cover.cpp @@ -173,6 +173,59 @@ std::vector<UnwrappedTileID> tileCover(const TransformState& state, int32_t z) { z); } +std::vector<UnwrappedTileID> tileCoverWithLOD(const TransformState& state, int32_t z, int32_t minZ) { + assert(state.valid()); + + const double w = state.getSize().width; + const double h = state.getSize().height; + + const auto offset = state.getCenterOffset(); + constexpr double zoomDiff = 1.0; + constexpr double coefLOD[] = { + 0.55 * zoomDiff / (zoomDiff + 1), + 0.55 * (zoomDiff + 1) / (zoomDiff + 2), + 0.55 * (zoomDiff + 2) / (zoomDiff + 3) + }; + // Tangens of field of view above center. + const double tanFov = (h * 0.5 + offset.y) / (1.5 * h); + + std::vector<UnwrappedTileID> result; + double top = 0.0; + double bottom = 0.0; + + for (size_t i = 0; top < h && i <= std::extent<decltype(coefLOD)>::value; i++, z--) { + if (z == minZ || i == std::extent<decltype(coefLOD)>::value) { + top = h; // final pass, get all to the top. + } else { + const double treshold = state.getPitch() ? : (h * 0.5 + offset.y); + top = std::min(h, treshold ); + top = state.getPitch() + ? std::min(h, h * 0.5 - offset.y + h * coefLOD[i] / (tanFov * std::tan(state.getPitch()))) + : h; + } + std::vector<UnwrappedTileID> cover = tileCover( + TileCoordinate::fromScreenCoordinate(state, z, { 0, top }).p, + TileCoordinate::fromScreenCoordinate(state, z, { w, top }).p, + TileCoordinate::fromScreenCoordinate(state, z, { w, bottom }).p, + TileCoordinate::fromScreenCoordinate(state, z, { 0, bottom }).p, + TileCoordinate::fromScreenCoordinate(state, z, { w/2, h/2 }).p, + z); + bottom = top; + if (i == 0) { + if (top == h) { + return cover; + } + std::swap(result, cover); + continue; + } + result.insert( + result.end(), + std::make_move_iterator(cover.begin()), + std::make_move_iterator(cover.end())); + } + return result; +} + std::vector<UnwrappedTileID> tileCover(const Geometry<double>& geometry, int32_t z) { std::vector<UnwrappedTileID> result; TileCover tc(geometry, z, true); |