1 #include <mbgl/annotation/shape_annotation_impl.hpp>
2 #include <mbgl/annotation/annotation_tile.hpp>
3 #include <mbgl/annotation/annotation_manager.hpp>
4 #include <mbgl/tile/tile_id.hpp>
5 #include <mbgl/math/wrap.hpp>
6 #include <mbgl/math/clamp.hpp>
7 #include <mbgl/util/string.hpp>
8 #include <mbgl/util/constants.hpp>
9 #include <mbgl/util/geometry.hpp>
10 
11 namespace mbgl {
12 
13 using namespace style;
14 namespace geojsonvt = mapbox::geojsonvt;
15 
ShapeAnnotationImpl(const AnnotationID id_)16 ShapeAnnotationImpl::ShapeAnnotationImpl(const AnnotationID id_)
17     : id(id_),
18       layerID(AnnotationManager::ShapeLayerID + util::toString(id)) {
19 }
20 
updateTileData(const CanonicalTileID & tileID,AnnotationTileData & data)21 void ShapeAnnotationImpl::updateTileData(const CanonicalTileID& tileID, AnnotationTileData& data) {
22     static const double baseTolerance = 4;
23 
24     if (!shapeTiler) {
25         mapbox::geometry::feature_collection<double> features;
26         features.emplace_back(ShapeAnnotationGeometry::visit(geometry(), [] (auto&& geom) {
27             return Feature { std::move(geom) };
28         }));
29         mapbox::geojsonvt::Options options;
30         // The annotation source is currently hard coded to maxzoom 16, so we're topping out at z16
31         // here as well.
32         options.maxZoom = 16;
33         options.buffer = 255u;
34         options.extent = util::EXTENT;
35         options.tolerance = baseTolerance;
36         shapeTiler = std::make_unique<mapbox::geojsonvt::GeoJSONVT>(features, options);
37     }
38 
39     const auto& shapeTile = shapeTiler->getTile(tileID.z, tileID.x, tileID.y);
40     if (shapeTile.features.empty())
41         return;
42 
43     auto layer = data.addLayer(layerID);
44 
45     ToGeometryCollection toGeometryCollection;
46     ToFeatureType toFeatureType;
47     for (const auto& shapeFeature : shapeTile.features) {
48         FeatureType featureType = apply_visitor(toFeatureType, shapeFeature.geometry);
49         GeometryCollection renderGeometry = apply_visitor(toGeometryCollection, shapeFeature.geometry);
50 
51         assert(featureType != FeatureType::Unknown);
52 
53         // https://github.com/mapbox/geojson-vt-cpp/issues/44
54         if (featureType == FeatureType::Polygon) {
55             renderGeometry = fixupPolygons(renderGeometry);
56         }
57 
58         layer->addFeature(id, featureType, renderGeometry);
59     }
60 }
61 
62 } // namespace mbgl
63