Skip to content
This repository has been archived by the owner on Aug 8, 2023. It is now read-only.

Commit

Permalink
[core] avoid symbol flickering when longitude is wrapped
Browse files Browse the repository at this point in the history
  • Loading branch information
ansis committed May 17, 2018
1 parent 4ceb687 commit f14a757
Show file tree
Hide file tree
Showing 4 changed files with 42 additions and 6 deletions.
11 changes: 8 additions & 3 deletions include/mbgl/tile/tile_id.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -58,10 +58,11 @@ class OverscaledTileID {
uint32_t overscaleFactor() const;
OverscaledTileID scaledTo(uint8_t z) const;
UnwrappedTileID toUnwrapped() const;
OverscaledTileID unwrapTo(int16_t wrap);

const uint8_t overscaledZ;
const int16_t wrap;
const CanonicalTileID canonical;
uint8_t overscaledZ;
int16_t wrap;
CanonicalTileID canonical;
};

::std::ostream& operator<<(::std::ostream& os, const OverscaledTileID& rhs);
Expand Down Expand Up @@ -191,6 +192,10 @@ inline UnwrappedTileID OverscaledTileID::toUnwrapped() const {
return { wrap, canonical };
}

inline OverscaledTileID OverscaledTileID::unwrapTo(int16_t newWrap) {
return { overscaledZ, newWrap, canonical };
}

inline UnwrappedTileID::UnwrappedTileID(uint8_t z_, int64_t x_, int64_t y_)
: wrap((x_ < 0 ? x_ - (1ll << z_) + 1 : x_) / (1ll << z_)),
canonical(
Expand Down
3 changes: 2 additions & 1 deletion src/mbgl/renderer/renderer_impl.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -380,7 +380,8 @@ void Renderer::Impl::render(const UpdateParameters& updateParameters) {
}
for (auto it = order.rbegin(); it != order.rend(); ++it) {
if (it->layer.is<RenderSymbolLayer>()) {
if (crossTileSymbolIndex.addLayer(*it->layer.as<RenderSymbolLayer>())) symbolBucketsChanged = true;
const float lng = parameters.state.getLatLng().longitude();
if (crossTileSymbolIndex.addLayer(*it->layer.as<RenderSymbolLayer>(), lng)) symbolBucketsChanged = true;
}
}

Expand Down
30 changes: 29 additions & 1 deletion src/mbgl/text/cross_tile_symbol_index.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,32 @@ void TileLayerIndex::findMatches(std::vector<SymbolInstance>& symbolInstances, c
CrossTileSymbolLayerIndex::CrossTileSymbolLayerIndex() {
}

/*
* Sometimes when a user pans across the antimeridian the longitude value gets wrapped.
* To prevent labels from flashing out and in we adjust the tileID values in the indexes
* so that they match the new wrapped version of the map.
*/
void CrossTileSymbolLayerIndex::handleWrapJump(float newLng) {

const int wrapDelta = ::round((newLng - lng) / 360);
if (wrapDelta != 0) {
std::map<uint8_t, std::map<OverscaledTileID,TileLayerIndex>> newIndexes;
for (auto& zoomIndex : indexes) {
std::map<OverscaledTileID,TileLayerIndex> newZoomIndex;
for (auto& index : zoomIndex.second) {
// change the tileID's wrap and it to a new index
index.second.coord = index.second.coord.unwrapTo(index.second.coord.wrap + wrapDelta);
newZoomIndex.emplace(index.second.coord, std::move(index.second));
}
newIndexes.emplace(zoomIndex.first, std::move(newZoomIndex));
}

indexes = std::move(newIndexes);
}

lng = newLng;
}

bool CrossTileSymbolLayerIndex::addBucket(const OverscaledTileID& tileID, SymbolBucket& bucket, uint32_t& maxCrossTileID) {
const auto& thisZoomIndexes = indexes[tileID.overscaledZ];
auto previousIndex = thisZoomIndexes.find(tileID);
Expand Down Expand Up @@ -138,13 +164,15 @@ bool CrossTileSymbolLayerIndex::removeStaleBuckets(const std::unordered_set<uint

CrossTileSymbolIndex::CrossTileSymbolIndex() {}

bool CrossTileSymbolIndex::addLayer(RenderSymbolLayer& symbolLayer) {
bool CrossTileSymbolIndex::addLayer(RenderSymbolLayer& symbolLayer, float lng) {

auto& layerIndex = layerIndexes[symbolLayer.getID()];

bool symbolBucketsChanged = false;
std::unordered_set<uint32_t> currentBucketIDs;

layerIndex.handleWrapJump(lng);

for (RenderTile& renderTile : symbolLayer.renderTiles) {
if (!renderTile.tile.isRenderable()) {
continue;
Expand Down
4 changes: 3 additions & 1 deletion src/mbgl/text/cross_tile_symbol_index.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -45,18 +45,20 @@ class CrossTileSymbolLayerIndex {
CrossTileSymbolLayerIndex();
bool addBucket(const OverscaledTileID&, SymbolBucket&, uint32_t& maxCrossTileID);
bool removeStaleBuckets(const std::unordered_set<uint32_t>& currentIDs);
void handleWrapJump(float newLng);
private:
void removeBucketCrossTileIDs(uint8_t zoom, const TileLayerIndex& removedBucket);

std::map<uint8_t, std::map<OverscaledTileID,TileLayerIndex>> indexes;
std::map<uint8_t, std::set<uint32_t>> usedCrossTileIDs;
float lng = 0;
};

class CrossTileSymbolIndex {
public:
CrossTileSymbolIndex();

bool addLayer(RenderSymbolLayer&);
bool addLayer(RenderSymbolLayer&, float lng);
void pruneUnusedLayers(const std::set<std::string>&);

void reset();
Expand Down

0 comments on commit f14a757

Please sign in to comment.