summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChris Loer <chris.loer@gmail.com>2017-11-03 11:23:14 -0700
committerChris Loer <chris.loer@mapbox.com>2017-11-06 11:54:27 -0800
commit3b3009014fff3704a4d836dc4617cd603e6f40ee (patch)
treed9103eb291cb86eafae76cee56944a5546c92d7d
parentb28fc5d71133f46bc79c8918796a3375286eb161 (diff)
downloadqtlocation-mapboxgl-3b3009014fff3704a4d836dc4617cd603e6f40ee.tar.gz
Switch to "one-phase" tile loading:
- Don't render tiles that don't have a symbol layer - Remove unused tiles/bucket from the cross tile symbol index - Clear cached "crossTileIDs" from symbol buckets that are removed from the symbol index
-rw-r--r--src/mbgl/renderer/tile_pyramid.cpp9
-rw-r--r--src/mbgl/text/cross_tile_symbol_index.cpp29
-rw-r--r--src/mbgl/tile/geometry_tile.cpp17
-rw-r--r--src/mbgl/tile/geometry_tile.hpp2
-rw-r--r--src/mbgl/tile/tile.hpp2
5 files changed, 48 insertions, 11 deletions
diff --git a/src/mbgl/renderer/tile_pyramid.cpp b/src/mbgl/renderer/tile_pyramid.cpp
index 4acc67daa8..fae16c9ce6 100644
--- a/src/mbgl/renderer/tile_pyramid.cpp
+++ b/src/mbgl/renderer/tile_pyramid.cpp
@@ -119,6 +119,7 @@ void TilePyramid::update(const std::vector<Immutable<style::Layer::Impl>>& layer
// use because they're still loading. In addition to that, we also need to retain all tiles that
// we're actively using, e.g. as a replacement for tile that aren't loaded yet.
std::set<OverscaledTileID> retain;
+ std::set<UnwrappedTileID> rendered;
auto retainTileFn = [&](Tile& tile, TileNecessity necessity) -> void {
if (retain.emplace(tile.id).second) {
@@ -149,6 +150,7 @@ void TilePyramid::update(const std::vector<Immutable<style::Layer::Impl>>& layer
};
auto renderTileFn = [&](const UnwrappedTileID& tileID, Tile& tile) {
renderTiles.emplace_back(tileID, tile);
+ rendered.emplace(tileID);
};
renderTiles.clear();
@@ -176,6 +178,13 @@ void TilePyramid::update(const std::vector<Immutable<style::Layer::Impl>>& layer
auto tilesIt = tiles.begin();
auto retainIt = retain.begin();
while (tilesIt != tiles.end()) {
+ auto renderedIt = rendered.find(tilesIt->first.toUnwrapped());
+ if (renderedIt == rendered.end()) {
+ // Since this tile isn't in the render set, crossTileIDs won't be kept
+ // updated by CrossTileSymbolIndex. We need to reset the stored crossTileIDs
+ // so they're not reused if/when this tile is re-added to the render set
+ tilesIt->second->resetCrossTileIDs();
+ }
if (retainIt == retain.end() || tilesIt->first < *retainIt) {
if (!needsRelayout) {
tilesIt->second->setNecessity(TileNecessity::Optional);
diff --git a/src/mbgl/text/cross_tile_symbol_index.cpp b/src/mbgl/text/cross_tile_symbol_index.cpp
index 13771fcd9b..8655e45804 100644
--- a/src/mbgl/text/cross_tile_symbol_index.cpp
+++ b/src/mbgl/text/cross_tile_symbol_index.cpp
@@ -7,7 +7,7 @@
namespace mbgl {
-TileLayerIndex::TileLayerIndex(OverscaledTileID coord_, std::vector<SymbolInstance>& symbolInstances, uint32_t bucketInstanceId_)
+TileLayerIndex::TileLayerIndex(OverscaledTileID coord_, std::vector<SymbolInstance>& symbolInstances, uint32_t bucketInstanceId_)
: coord(coord_), bucketInstanceId(bucketInstanceId_) {
for (SymbolInstance& symbolInstance : symbolInstances) {
indexedSymbolInstances[symbolInstance.key].emplace_back(symbolInstance.crossTileID, getScaledCoordinates(symbolInstance, coord));
@@ -28,11 +28,16 @@ void TileLayerIndex::findMatches(std::vector<SymbolInstance>& symbolInstances, c
float tolerance = coord.canonical.z < newCoord.canonical.z ? 1 : std::pow(2, coord.canonical.z - newCoord.canonical.z);
for (auto& symbolInstance : symbolInstances) {
- // already has a match, skip
- if (symbolInstance.crossTileID) continue;
+ if (symbolInstance.crossTileID) {
+ // already has a match, skip
+ continue;
+ }
auto it = indexedSymbolInstances.find(symbolInstance.key);
- if (it == indexedSymbolInstances.end()) continue;
+ if (it == indexedSymbolInstances.end()) {
+ // No symbol with this key in this bucket
+ continue;
+ }
auto scaledSymbolCoord = getScaledCoordinates(symbolInstance, newCoord);
@@ -72,7 +77,9 @@ void CrossTileSymbolLayerIndex::addBucket(const OverscaledTileID& coord, SymbolB
auto zoomIndexes = indexes.find(z);
if (zoomIndexes != indexes.end()) {
for (auto& childIndex : zoomIndexes->second) {
- if (!childIndex.second.coord.isChildOf(coord)) continue;
+ if (!childIndex.second.coord.isChildOf(coord)) {
+ continue;
+ }
childIndex.second.findMatches(bucket.symbolInstances, coord);
}
}
@@ -110,8 +117,7 @@ bool CrossTileSymbolLayerIndex::removeStaleBuckets(const std::unordered_set<uint
bool tilesChanged = false;
for (auto& zoomIndexes : indexes) {
for (auto it = zoomIndexes.second.begin(); it != zoomIndexes.second.end();) {
- // TODO remove false condition when pyramid flickering is fixed
- if (false && !currentIDs.count(it->second.bucketInstanceId)) {
+ if (!currentIDs.count(it->second.bucketInstanceId)) {
it = zoomIndexes.second.erase(it);
tilesChanged = true;
} else {
@@ -140,12 +146,17 @@ bool CrossTileSymbolIndex::addLayer(RenderSymbolLayer& symbolLayer) {
assert(dynamic_cast<SymbolBucket*>(bucket));
SymbolBucket& symbolBucket = *reinterpret_cast<SymbolBucket*>(bucket);
- if (!symbolBucket.bucketInstanceId) symbolBucketsChanged = true;
+ if (!symbolBucket.bucketInstanceId) {
+ symbolBucketsChanged = true;
+ }
layerIndex.addBucket(renderTile.tile.id, symbolBucket);
currentBucketIDs.insert(symbolBucket.bucketInstanceId);
}
- if (layerIndex.removeStaleBuckets(currentBucketIDs)) symbolBucketsChanged = true;
+ if (layerIndex.removeStaleBuckets(currentBucketIDs)) {
+ symbolBucketsChanged = true;
+ }
return symbolBucketsChanged;
}
} // namespace mbgl
+
diff --git a/src/mbgl/tile/geometry_tile.cpp b/src/mbgl/tile/geometry_tile.cpp
index e1a5c272f9..02f1e53093 100644
--- a/src/mbgl/tile/geometry_tile.cpp
+++ b/src/mbgl/tile/geometry_tile.cpp
@@ -125,8 +125,9 @@ void GeometryTile::setShowCollisionBoxes(const bool showCollisionBoxes_) {
}
void GeometryTile::onLayout(LayoutResult result, const uint64_t resultCorrelationID) {
- loaded = true;
- renderable = true;
+ // Don't mark ourselves loaded or renderable until the first successful placement
+ // TODO: Ideally we'd render this tile without symbols as long as this tile wasn't
+ // replacing a tile at a different zoom that _did_ have symbols.
(void)resultCorrelationID;
nonSymbolBuckets = std::move(result.nonSymbolBuckets);
featureIndex = std::move(result.featureIndex);
@@ -281,4 +282,16 @@ void GeometryTile::querySourceFeatures(
}
}
+void GeometryTile::resetCrossTileIDs() {
+ for (auto& bucket : symbolBuckets) {
+ SymbolBucket* symbolBucket = dynamic_cast<SymbolBucket*>(bucket.second.get());
+ if (symbolBucket && symbolBucket->bucketInstanceId) {
+ symbolBucket->bucketInstanceId = 0;
+ for (auto& symbolInstance : symbolBucket->symbolInstances) {
+ symbolInstance.crossTileID = 0;
+ }
+ }
+ }
+}
+
} // namespace mbgl
diff --git a/src/mbgl/tile/geometry_tile.hpp b/src/mbgl/tile/geometry_tile.hpp
index 80f2f8c6d7..3f4b36984b 100644
--- a/src/mbgl/tile/geometry_tile.hpp
+++ b/src/mbgl/tile/geometry_tile.hpp
@@ -96,6 +96,8 @@ public:
void onError(std::exception_ptr, uint64_t correlationID);
+ void resetCrossTileIDs() override;
+
protected:
const GeometryTileData* getData() {
return data.get();
diff --git a/src/mbgl/tile/tile.hpp b/src/mbgl/tile/tile.hpp
index 0aa2a1bcad..6c163c93bb 100644
--- a/src/mbgl/tile/tile.hpp
+++ b/src/mbgl/tile/tile.hpp
@@ -95,6 +95,8 @@ public:
bool isComplete() const {
return loaded && !pending;
}
+
+ virtual void resetCrossTileIDs() {};
void dumpDebugLogs() const;