diff options
author | John Firebaugh <john.firebaugh@gmail.com> | 2016-05-31 17:34:11 -0700 |
---|---|---|
committer | John Firebaugh <john.firebaugh@gmail.com> | 2016-06-01 17:37:01 -0700 |
commit | 0fba70d5a8465499b0dce900e5aa74f7189e4594 (patch) | |
tree | 7902b9bd29d25de0de6d116fc3245b1b269477f4 | |
parent | cfd6757ecc9bd4d9b1f4c5266d19da48c529f58b (diff) | |
download | qtlocation-mapboxgl-0fba70d5a8465499b0dce900e5aa74f7189e4594.tar.gz |
[all] Rationalize annotation API
32 files changed, 459 insertions, 543 deletions
diff --git a/include/mbgl/annotation/annotation.hpp b/include/mbgl/annotation/annotation.hpp index 52916549c9..3b2b7f3ade 100644 --- a/include/mbgl/annotation/annotation.hpp +++ b/include/mbgl/annotation/annotation.hpp @@ -1,11 +1,52 @@ #pragma once +#include <mbgl/style/types.hpp> + +#include <mbgl/util/geometry.hpp> +#include <mbgl/util/variant.hpp> + #include <cstdint> #include <vector> +#include <string> namespace mbgl { using AnnotationID = uint32_t; using AnnotationIDs = std::vector<AnnotationID>; +class SymbolAnnotation { +public: + Geometry<double> geometry; + std::string icon; +}; + +class LineAnnotation { +public: + Geometry<double> geometry; + float opacity = 1; + float width = 1; + Color color = {{ 0, 0, 0, 1 }}; +}; + +class FillAnnotation { +public: + Geometry<double> geometry; + float opacity = 1; + Color color = {{ 0, 0, 0, 1 }}; + Color outlineColor = {{ 0, 0, 0, -1 }}; +}; + +// An annotation whose type and properties are sourced from a style layer. +class StyleSourcedAnnotation { +public: + Geometry<double> geometry; + std::string layerID; +}; + +using Annotation = variant< + SymbolAnnotation, + LineAnnotation, + FillAnnotation, + StyleSourcedAnnotation>; + } // namespace mbgl diff --git a/include/mbgl/annotation/point_annotation.hpp b/include/mbgl/annotation/point_annotation.hpp deleted file mode 100644 index c9236c3c04..0000000000 --- a/include/mbgl/annotation/point_annotation.hpp +++ /dev/null @@ -1,18 +0,0 @@ -#pragma once - -#include <mbgl/util/geo.hpp> - -#include <string> - -namespace mbgl { - -class PointAnnotation { -public: - PointAnnotation(const LatLng& position_, const std::string& icon_ = "") - : position(position_.wrapped()), icon(icon_) {} - - const LatLng position; - const std::string icon; -}; - -} // namespace mbgl diff --git a/include/mbgl/annotation/shape_annotation.hpp b/include/mbgl/annotation/shape_annotation.hpp deleted file mode 100644 index 7dca1ec134..0000000000 --- a/include/mbgl/annotation/shape_annotation.hpp +++ /dev/null @@ -1,37 +0,0 @@ -#pragma once - -#include <mbgl/annotation/annotation.hpp> -#include <mbgl/style/types.hpp> - -#include <mbgl/util/geometry.hpp> -#include <mbgl/util/variant.hpp> - -namespace mbgl { - -struct FillAnnotationProperties { - float opacity = 1; - Color color = {{ 0, 0, 0, 1 }}; - Color outlineColor = {{ 0, 0, 0, -1 }}; -}; - -struct LineAnnotationProperties { - float opacity = 1; - float width = 1; - Color color = {{ 0, 0, 0, 1 }}; -}; - -class ShapeAnnotation { -public: - using Properties = variant< - FillAnnotationProperties, // creates a fill annotation - LineAnnotationProperties, // creates a line annotation - std::string>; // creates an annotation whose type and properties are sourced from a style layer - - ShapeAnnotation(const Geometry<double>& geometry_, const Properties& properties_) - : geometry(geometry_), properties(properties_) {} - - const Geometry<double> geometry; - const Properties properties; -}; - -} // namespace mbgl diff --git a/include/mbgl/map/map.hpp b/include/mbgl/map/map.hpp index f074a5ae54..a728e2dd62 100644 --- a/include/mbgl/map/map.hpp +++ b/include/mbgl/map/map.hpp @@ -23,8 +23,6 @@ namespace mbgl { class FileSource; class View; class SpriteImage; -class PointAnnotation; -class ShapeAnnotation; struct CameraOptions; struct AnimationOptions; @@ -142,16 +140,9 @@ public: void removeAnnotationIcon(const std::string&); double getTopOffsetPixelsForAnnotationIcon(const std::string&); - AnnotationID addPointAnnotation(const PointAnnotation&); - AnnotationIDs addPointAnnotations(const std::vector<PointAnnotation>&); - - AnnotationID addShapeAnnotation(const ShapeAnnotation&); - AnnotationIDs addShapeAnnotations(const std::vector<ShapeAnnotation>&); - - void updatePointAnnotation(AnnotationID, const PointAnnotation&); - + AnnotationID addAnnotation(const Annotation&); + void updateAnnotation(AnnotationID, const Annotation&); void removeAnnotation(AnnotationID); - void removeAnnotations(const AnnotationIDs&); AnnotationIDs getPointAnnotationsInBounds(const LatLngBounds&); diff --git a/include/mbgl/platform/default/glfw_view.hpp b/include/mbgl/platform/default/glfw_view.hpp index b3b6116ad7..b1204ce96d 100644 --- a/include/mbgl/platform/default/glfw_view.hpp +++ b/include/mbgl/platform/default/glfw_view.hpp @@ -44,7 +44,6 @@ public: void report(float duration); private: - mbgl::LatLng makeRandomLatLng() const; mbgl::Point<double> makeRandomPoint() const; static std::shared_ptr<const mbgl::SpriteImage> makeSpriteImage(int width, int height, float pixelRatio); diff --git a/src/mbgl/util/geometry.hpp b/include/mbgl/util/geometry.hpp index 6b9c332bf2..6b9c332bf2 100644 --- a/src/mbgl/util/geometry.hpp +++ b/include/mbgl/util/geometry.hpp diff --git a/platform/android/src/jni.cpp b/platform/android/src/jni.cpp index 4c3f77e9da..ed2563cf7b 100755 --- a/platform/android/src/jni.cpp +++ b/platform/android/src/jni.cpp @@ -13,8 +13,7 @@ #include <mbgl/map/map.hpp> #include <mbgl/map/camera.hpp> -#include <mbgl/annotation/point_annotation.hpp> -#include <mbgl/annotation/shape_annotation.hpp> +#include <mbgl/annotation/annotation.hpp> #include <mbgl/sprite/sprite_image.hpp> #include <mbgl/platform/event.hpp> #include <mbgl/platform/log.hpp> @@ -681,8 +680,10 @@ void nativeUpdateMarker(JNIEnv *env, jni::jobject* obj, jlong nativeMapViewPtr, jdouble latitude = jni::GetField<jdouble>(*env, position, *latLngLatitudeId); jdouble longitude = jni::GetField<jdouble>(*env, position, *latLngLongitudeId); - // Because Java only has int, not unsigned int, we need to bump the annotation id up to a long. - nativeMapView->getMap().updatePointAnnotation(markerId, mbgl::PointAnnotation(mbgl::LatLng(latitude, longitude), iconId)); + nativeMapView->getMap().updateAnnotation(markerId, mbgl::SymbolAnnotation { + mbgl::Point<double>(longitude, latitude), + iconId + }); } jni::jarray<jlong>* nativeAddMarkers(JNIEnv *env, jni::jobject* obj, jlong nativeMapViewPtr, jni::jarray<jni::jobject>* jarray) { @@ -693,30 +694,30 @@ jni::jarray<jlong>* nativeAddMarkers(JNIEnv *env, jni::jobject* obj, jlong nativ NullCheck(*env, jarray); std::size_t len = jni::GetArrayLength(*env, *jarray); - std::vector<mbgl::PointAnnotation> markers; - markers.reserve(len); + std::vector<mbgl::AnnotationID> ids; + ids.reserve(len); for (std::size_t i = 0; i < len; i++) { jni::jobject* marker = jni::GetObjectArrayElement(*env, *jarray, i); jni::jobject* position = jni::GetField<jni::jobject*>(*env, marker, *markerPositionId); jni::jobject* icon = jni::GetField<jni::jobject*>(*env, marker, *markerIconId); - jni::DeleteLocalRef(*env, marker); - jni::jstring* jid = reinterpret_cast<jni::jstring*>(jni::GetField<jni::jobject*>(*env, icon, *iconIdId)); - jni::DeleteLocalRef(*env, icon); - - std::string id = std_string_from_jstring(env, jid); - jni::DeleteLocalRef(*env, jid); jdouble latitude = jni::GetField<jdouble>(*env, position, *latLngLatitudeId); jdouble longitude = jni::GetField<jdouble>(*env, position, *latLngLongitudeId); - jni::DeleteLocalRef(*env, position); - markers.emplace_back(mbgl::PointAnnotation(mbgl::LatLng(latitude, longitude), id)); + ids.push_back(nativeMapView->getMap().addAnnotation(mbgl::SymbolAnnotation { + mbgl::Point<double>(longitude, latitude), + std_string_from_jstring(env, jid) + })); + + jni::DeleteLocalRef(*env, position); + jni::DeleteLocalRef(*env, jid); + jni::DeleteLocalRef(*env, icon); + jni::DeleteLocalRef(*env, marker); } - std::vector<uint32_t> pointAnnotationIDs = nativeMapView->getMap().addPointAnnotations(markers); - return std_vector_uint_to_jobject(env, pointAnnotationIDs); + return std_vector_uint_to_jobject(env, ids); } static mbgl::Color toColor(jint color) { @@ -762,24 +763,23 @@ jni::jarray<jlong>* nativeAddPolylines(JNIEnv *env, jni::jobject* obj, jlong nat NullCheck(*env, jarray); std::size_t len = jni::GetArrayLength(*env, *jarray); - std::vector<mbgl::ShapeAnnotation> shapes; - shapes.reserve(len); + std::vector<mbgl::AnnotationID> ids; + ids.reserve(len); for (std::size_t i = 0; i < len; i++) { jni::jobject* polyline = jni::GetObjectArrayElement(*env, *jarray, i); - - mbgl::LineAnnotationProperties lineProperties; - lineProperties.opacity = jni::GetField<jfloat>(*env, polyline, *polylineAlphaId); - lineProperties.color = toColor(jni::GetField<jint>(*env, polyline, *polylineColorId)); - lineProperties.width = jni::GetField<jfloat>(*env, polyline, *polylineWidthId); - jni::jobject* points = jni::GetField<jni::jobject*>(*env, polyline, *polylinePointsId); - shapes.emplace_back(toGeometry<mbgl::LineString<double>>(env, points), lineProperties); + + mbgl::LineAnnotation annotation { toGeometry<mbgl::LineString<double>>(env, points) }; + annotation.opacity = jni::GetField<jfloat>(*env, polyline, *polylineAlphaId); + annotation.color = toColor(jni::GetField<jint>(*env, polyline, *polylineColorId)); + annotation.width = jni::GetField<jfloat>(*env, polyline, *polylineWidthId); + ids.push_back(nativeMapView->getMap().addAnnotation(annotation)); jni::DeleteLocalRef(*env, polyline); } - return std_vector_uint_to_jobject(env, nativeMapView->getMap().addShapeAnnotations(shapes)); + return std_vector_uint_to_jobject(env, ids); } jni::jarray<jlong>* nativeAddPolygons(JNIEnv *env, jni::jobject* obj, jlong nativeMapViewPtr, jni::jarray<jni::jobject>* jarray) { @@ -790,24 +790,23 @@ jni::jarray<jlong>* nativeAddPolygons(JNIEnv *env, jni::jobject* obj, jlong nati NullCheck(*env, jarray); std::size_t len = jni::GetArrayLength(*env, *jarray); - std::vector<mbgl::ShapeAnnotation> shapes; - shapes.reserve(len); + std::vector<mbgl::AnnotationID> ids; + ids.reserve(len); for (std::size_t i = 0; i < len; i++) { jni::jobject* polygon = jni::GetObjectArrayElement(*env, *jarray, i); - - mbgl::FillAnnotationProperties fillProperties; - fillProperties.opacity = jni::GetField<jfloat>(*env, polygon, *polygonAlphaId); - fillProperties.outlineColor = toColor(jni::GetField<jint>(*env, polygon, *polygonStrokeColorId)); - fillProperties.color = toColor(jni::GetField<jint>(*env, polygon, *polygonFillColorId)); - jni::jobject* points = jni::GetField<jni::jobject*>(*env, polygon, *polygonPointsId); - shapes.emplace_back(mbgl::Polygon<double> { toGeometry<mbgl::LinearRing<double>>(env, points) }, fillProperties); + + mbgl::FillAnnotation annotation { mbgl::Polygon<double> { toGeometry<mbgl::LinearRing<double>>(env, points) } }; + annotation.opacity = jni::GetField<jfloat>(*env, polygon, *polygonAlphaId); + annotation.outlineColor = toColor(jni::GetField<jint>(*env, polygon, *polygonStrokeColorId)); + annotation.color = toColor(jni::GetField<jint>(*env, polygon, *polygonFillColorId)); + ids.push_back(nativeMapView->getMap().addAnnotation(annotation)); jni::DeleteLocalRef(*env, polygon); } - return std_vector_uint_to_jobject(env, nativeMapView->getMap().addShapeAnnotations(shapes)); + return std_vector_uint_to_jobject(env, ids); } void nativeRemoveAnnotations(JNIEnv *env, jni::jobject* obj, jlong nativeMapViewPtr, jni::jarray<jlong>* jarray) { @@ -817,20 +816,14 @@ void nativeRemoveAnnotations(JNIEnv *env, jni::jobject* obj, jlong nativeMapView NullCheck(*env, jarray); std::size_t len = jni::GetArrayLength(*env, *jarray); - - std::vector<uint32_t> ids; - ids.reserve(len); - auto elements = jni::GetArrayElements(*env, *jarray); jlong* jids = std::get<0>(elements).get(); for (std::size_t i = 0; i < len; i++) { if(jids[i] == -1L) continue; - ids.push_back(static_cast<uint32_t>(jids[i])); + nativeMapView->getMap().removeAnnotation(jids[i]); } - - nativeMapView->getMap().removeAnnotations(ids); } jni::jarray<jlong>* nativeGetAnnotationsInBounds(JNIEnv *env, jni::jobject* obj, jlong nativeMapViewPtr, jni::jobject* latLngBounds_) { diff --git a/platform/darwin/src/MGLGeometry_Private.h b/platform/darwin/src/MGLGeometry_Private.h index 0538cd94ea..fc57460128 100644 --- a/platform/darwin/src/MGLGeometry_Private.h +++ b/platform/darwin/src/MGLGeometry_Private.h @@ -6,6 +6,7 @@ #endif #import <mbgl/util/geo.hpp> +#import <mbgl/util/geometry.hpp> /// Returns the smallest rectangle that contains both the given rectangle and /// the given point. @@ -15,6 +16,10 @@ NS_INLINE mbgl::LatLng MGLLatLngFromLocationCoordinate2D(CLLocationCoordinate2D return mbgl::LatLng(coordinate.latitude, coordinate.longitude); } +NS_INLINE mbgl::Point<double> MGLPointFromLocationCoordinate2D(CLLocationCoordinate2D coordinate) { + return mbgl::Point<double>(coordinate.longitude, coordinate.latitude); +} + NS_INLINE CLLocationCoordinate2D MGLLocationCoordinate2DFromLatLng(mbgl::LatLng latLng) { return CLLocationCoordinate2DMake(latLng.latitude, latLng.longitude); } diff --git a/platform/darwin/src/MGLMultiPoint_Private.h b/platform/darwin/src/MGLMultiPoint_Private.h index f7a7bd4ffd..aa52a02fcb 100644 --- a/platform/darwin/src/MGLMultiPoint_Private.h +++ b/platform/darwin/src/MGLMultiPoint_Private.h @@ -3,7 +3,7 @@ #import "MGLGeometry.h" #import "MGLTypes.h" -#import <mbgl/annotation/shape_annotation.hpp> +#import <mbgl/annotation/annotation.hpp> #import <vector> #import <CoreGraphics/CoreGraphics.h> @@ -22,7 +22,7 @@ NS_ASSUME_NONNULL_BEGIN - (BOOL)intersectsOverlayBounds:(MGLCoordinateBounds)overlayBounds; /** Constructs a shape annotation object, asking the delegate for style values. */ -- (mbgl::ShapeAnnotation)shapeAnnotationObjectWithDelegate:(id <MGLMultiPointDelegate>)delegate; +- (mbgl::Annotation)annotationObjectWithDelegate:(id <MGLMultiPointDelegate>)delegate; @end diff --git a/platform/darwin/src/MGLPolygon.mm b/platform/darwin/src/MGLPolygon.mm index 47be070246..c009d9e3d6 100644 --- a/platform/darwin/src/MGLPolygon.mm +++ b/platform/darwin/src/MGLPolygon.mm @@ -36,19 +36,19 @@ return result; } -- (mbgl::ShapeAnnotation)shapeAnnotationObjectWithDelegate:(id <MGLMultiPointDelegate>)delegate { - mbgl::FillAnnotationProperties fillProperties; - fillProperties.opacity = [delegate alphaForShapeAnnotation:self]; - fillProperties.outlineColor = [delegate strokeColorForShapeAnnotation:self]; - fillProperties.color = [delegate fillColorForPolygonAnnotation:self]; - +- (mbgl::Annotation)annotationObjectWithDelegate:(id <MGLMultiPointDelegate>)delegate { mbgl::Polygon<double> geometry; geometry.push_back(self.ring); for (MGLPolygon *polygon in self.interiorPolygons) { geometry.push_back(polygon.ring); } - return mbgl::ShapeAnnotation(geometry, fillProperties); + mbgl::FillAnnotation annotation { geometry }; + annotation.opacity = [delegate alphaForShapeAnnotation:self]; + annotation.outlineColor = [delegate strokeColorForShapeAnnotation:self]; + annotation.color = [delegate fillColorForPolygonAnnotation:self]; + + return annotation; } @end diff --git a/platform/darwin/src/MGLPolyline.mm b/platform/darwin/src/MGLPolyline.mm index ebba5c862e..15ea5a0952 100644 --- a/platform/darwin/src/MGLPolyline.mm +++ b/platform/darwin/src/MGLPolyline.mm @@ -13,12 +13,7 @@ return [[self alloc] initWithCoordinates:coords count:count]; } -- (mbgl::ShapeAnnotation)shapeAnnotationObjectWithDelegate:(id <MGLMultiPointDelegate>)delegate { - mbgl::LineAnnotationProperties lineProperties; - lineProperties.opacity = [delegate alphaForShapeAnnotation:self]; - lineProperties.color = [delegate strokeColorForShapeAnnotation:self]; - lineProperties.width = [delegate lineWidthForPolylineAnnotation:self]; - +- (mbgl::Annotation)annotationObjectWithDelegate:(id <MGLMultiPointDelegate>)delegate { NSUInteger count = self.pointCount; CLLocationCoordinate2D *coordinates = self.coordinates; @@ -28,7 +23,12 @@ geometry.push_back(mbgl::Point<double>(coordinates[i].longitude, coordinates[i].latitude)); } - return mbgl::ShapeAnnotation(geometry, lineProperties); + mbgl::LineAnnotation annotation { geometry }; + annotation.opacity = [delegate alphaForShapeAnnotation:self]; + annotation.color = [delegate strokeColorForShapeAnnotation:self]; + annotation.width = [delegate lineWidthForPolylineAnnotation:self]; + + return annotation; } @end diff --git a/platform/default/glfw_view.cpp b/platform/default/glfw_view.cpp index 4a04595c33..2280c3f2ae 100644 --- a/platform/default/glfw_view.cpp +++ b/platform/default/glfw_view.cpp @@ -1,6 +1,5 @@ #include <mbgl/platform/default/glfw_view.hpp> -#include <mbgl/annotation/point_annotation.hpp> -#include <mbgl/annotation/shape_annotation.hpp> +#include <mbgl/annotation/annotation.hpp> #include <mbgl/sprite/sprite_image.hpp> #include <mbgl/style/property_transition.hpp> #include <mbgl/gl/gl.hpp> @@ -208,14 +207,10 @@ void GLFWView::onKey(GLFWwindow *window, int key, int /*scancode*/, int action, } } -mbgl::LatLng GLFWView::makeRandomLatLng() const { +mbgl::Point<double> GLFWView::makeRandomPoint() const { const double x = width * double(std::rand()) / RAND_MAX; const double y = height * double(std::rand()) / RAND_MAX; - return map->latLngForPixel({ x, y }); -} - -mbgl::Point<double> GLFWView::makeRandomPoint() const { - mbgl::LatLng latLng = makeRandomLatLng(); + mbgl::LatLng latLng = map->latLngForPixel({ x, y }); return { latLng.longitude, latLng.latitude }; } @@ -259,53 +254,34 @@ void GLFWView::nextOrientation() { } void GLFWView::addRandomCustomPointAnnotations(int count) { - std::vector<mbgl::PointAnnotation> points; - for (int i = 0; i < count; i++) { static int spriteID = 1; const auto name = std::string{ "marker-" } + mbgl::util::toString(spriteID++); map->addAnnotationIcon(name, makeSpriteImage(22, 22, 1)); spriteIDs.push_back(name); - points.emplace_back(makeRandomLatLng(), name); + annotationIDs.push_back(map->addAnnotation(mbgl::SymbolAnnotation { makeRandomPoint(), name })); } - - auto newIDs = map->addPointAnnotations(points); - annotationIDs.insert(annotationIDs.end(), newIDs.begin(), newIDs.end()); } void GLFWView::addRandomPointAnnotations(int count) { - std::vector<mbgl::PointAnnotation> points; - for (int i = 0; i < count; i++) { - points.emplace_back(makeRandomLatLng(), "default_marker"); + annotationIDs.push_back(map->addAnnotation(mbgl::SymbolAnnotation { makeRandomPoint(), "default_marker" })); } - - auto newIDs = map->addPointAnnotations(points); - annotationIDs.insert(annotationIDs.end(), newIDs.begin(), newIDs.end()); } void GLFWView::addRandomShapeAnnotations(int count) { - std::vector<mbgl::ShapeAnnotation> shapes; - - mbgl::FillAnnotationProperties properties; - properties.opacity = .1; - for (int i = 0; i < count; i++) { mbgl::Polygon<double> triangle; triangle.push_back({ makeRandomPoint(), makeRandomPoint(), makeRandomPoint() }); - shapes.emplace_back(triangle, properties); + annotationIDs.push_back(map->addAnnotation(mbgl::FillAnnotation { triangle, .1 })); } - - auto newIDs = map->addShapeAnnotations(shapes); - annotationIDs.insert(annotationIDs.end(), newIDs.begin(), newIDs.end()); } void GLFWView::clearAnnotations() { - if (annotationIDs.empty()) { - return; + for (const auto& id : annotationIDs) { + map->removeAnnotation(id); } - map->removeAnnotations(annotationIDs); annotationIDs.clear(); } diff --git a/platform/ios/src/MGLMapView.mm b/platform/ios/src/MGLMapView.mm index eacd2f7b74..87d821fba9 100644 --- a/platform/ios/src/MGLMapView.mm +++ b/platform/ios/src/MGLMapView.mm @@ -7,8 +7,7 @@ #import <OpenGLES/EAGL.h> #include <mbgl/mbgl.hpp> -#include <mbgl/annotation/point_annotation.hpp> -#include <mbgl/annotation/shape_annotation.hpp> +#include <mbgl/annotation/annotation.hpp> #include <mbgl/sprite/sprite_image.hpp> #include <mbgl/map/camera.hpp> #include <mbgl/map/mode.hpp> @@ -1776,9 +1775,9 @@ mbgl::Duration MGLDurationInSeconds(NSTimeInterval duration) // but safely updated. if (annotation == [self annotationWithTag:annotationTag]) { - const mbgl::LatLng latLng = MGLLatLngFromLocationCoordinate2D(annotation.coordinate); + const mbgl::Point<double> point = MGLPointFromLocationCoordinate2D(annotation.coordinate); MGLAnnotationImage *annotationImage = [self imageOfAnnotationWithTag:annotationTag]; - _mbglMap->updatePointAnnotation(annotationTag, { latLng, annotationImage.styleIconIdentifier.UTF8String ?: "" }); + _mbglMap->updateAnnotation(annotationTag, mbgl::SymbolAnnotation { point, annotationImage.styleIconIdentifier.UTF8String ?: "" }); if (annotationTag == _selectedAnnotationTag) { [self deselectAnnotation:annotation animated:YES]; @@ -2796,11 +2795,6 @@ mbgl::Duration MGLDurationInSeconds(NSTimeInterval duration) if ( ! annotations) return; [self willChangeValueForKey:@"annotations"]; - NSMutableArray *userPoints = [NSMutableArray array]; - std::vector<mbgl::PointAnnotation> points; - NSMutableArray *userShapes = [NSMutableArray array]; - std::vector<mbgl::ShapeAnnotation> shapes; - NSMutableDictionary *annotationImagesForAnnotation = [NSMutableDictionary dictionary]; NSMutableDictionary *annotationViewsForAnnotation = [NSMutableDictionary dictionary]; @@ -2820,8 +2814,11 @@ mbgl::Duration MGLDurationInSeconds(NSTimeInterval duration) if (!multiPoint.pointCount) { continue; } - shapes.emplace_back([multiPoint shapeAnnotationObjectWithDelegate:self]); - [userShapes addObject:annotation]; + + MGLAnnotationTag annotationTag = _mbglMap->addAnnotation([multiPoint annotationObjectWithDelegate:self]); + MGLAnnotationContext context; + context.annotation = annotation; + _annotationContextsByAnnotationTag[annotationTag] = context; } else if ([annotation isKindOfClass:[MGLMultiPolyline class]] || [annotation isKindOfClass:[MGLMultiPolygon class]] @@ -2877,22 +2874,11 @@ mbgl::Duration MGLDurationInSeconds(NSTimeInterval duration) annotationImagesForAnnotation[annotationValue] = annotationImage; } - [userPoints addObject:annotation]; - points.emplace_back(MGLLatLngFromLocationCoordinate2D(annotation.coordinate), symbolName.UTF8String ?: ""); - } - } + MGLAnnotationTag annotationTag = _mbglMap->addAnnotation(mbgl::SymbolAnnotation { + MGLPointFromLocationCoordinate2D(annotation.coordinate), + symbolName.UTF8String ?: "" + }); - if (points.size()) - { - // refactor this to build contexts above and just associate with tags here - - std::vector<MGLAnnotationTag> annotationTags = _mbglMap->addPointAnnotations(points); - - for (size_t i = 0; i < annotationTags.size(); ++i) - { - id<MGLAnnotation> annotation = userPoints[i]; - NSValue *annotationValue = [NSValue valueWithNonretainedObject:annotation]; - MGLAnnotationContext context; context.annotation = annotation; MGLAnnotationImage *annotationImage = annotationImagesForAnnotation[annotationValue]; @@ -2900,13 +2886,11 @@ mbgl::Duration MGLDurationInSeconds(NSTimeInterval duration) if (annotationImage) { context.imageReuseIdentifier = annotationImage.reuseIdentifier; } - MGLAnnotationView *annotationView = annotationViewsForAnnotation[annotationValue]; if (annotationView) { context.annotationView = annotationView; context.viewReuseIdentifier = annotationView.reuseIdentifier; } - MGLAnnotationTag annotationTag = annotationTags[i]; _annotationContextsByAnnotationTag[annotationTag] = context; if ([annotation isKindOfClass:[NSObject class]]) { NSAssert(![annotation isKindOfClass:[MGLMultiPoint class]], @"Point annotation should not be MGLMultiPoint."); @@ -2915,21 +2899,6 @@ mbgl::Duration MGLDurationInSeconds(NSTimeInterval duration) } } - if (shapes.size()) - { - std::vector<MGLAnnotationTag> annotationTags = _mbglMap->addShapeAnnotations(shapes); - - for (size_t i = 0; i < annotationTags.size(); ++i) - { - MGLAnnotationTag annotationTag = annotationTags[i]; - id <MGLAnnotation> annotation = userShapes[i]; - - MGLAnnotationContext context; - context.annotation = annotation; - _annotationContextsByAnnotationTag[annotationTag] = context; - } - } - [self updateAnnotationContainerViewWithAnnotationViews:newAnnotationViews]; [self didChangeValueForKey:@"annotations"]; @@ -3072,8 +3041,7 @@ mbgl::Duration MGLDurationInSeconds(NSTimeInterval duration) { if ( ! annotations) return; - std::vector<MGLAnnotationTag> annotationTagsToRemove; - annotationTagsToRemove.reserve(annotations.count); + [self willChangeValueForKey:@"annotations"]; for (id <MGLAnnotation> annotation in annotations) { @@ -3088,8 +3056,6 @@ mbgl::Duration MGLDurationInSeconds(NSTimeInterval duration) MGLAnnotationContext &annotationContext = _annotationContextsByAnnotationTag.at(annotationTag); MGLAnnotationView *annotationView = annotationContext.annotationView; [annotationView removeFromSuperview]; - - annotationTagsToRemove.push_back(annotationTag); if (annotationTag == _selectedAnnotationTag) { @@ -3102,15 +3068,12 @@ mbgl::Duration MGLDurationInSeconds(NSTimeInterval duration) { [(NSObject *)annotation removeObserver:self forKeyPath:@"coordinate" context:(void *)(NSUInteger)annotationTag]; } - } - if ( ! annotationTagsToRemove.empty()) - { - [self willChangeValueForKey:@"annotations"]; - _mbglMap->removeAnnotations(annotationTagsToRemove); - [self didChangeValueForKey:@"annotations"]; - UIAccessibilityPostNotification(UIAccessibilityLayoutChangedNotification, nil); + _mbglMap->removeAnnotation(annotationTag); } + + [self didChangeValueForKey:@"annotations"]; + UIAccessibilityPostNotification(UIAccessibilityLayoutChangedNotification, nil); } - (void)addOverlay:(id <MGLOverlay>)overlay @@ -3675,8 +3638,8 @@ mbgl::Duration MGLDurationInSeconds(NSTimeInterval duration) { if ([pair.second.imageReuseIdentifier isEqualToString:reuseIdentifier]) { - const mbgl::LatLng latLng = MGLLatLngFromLocationCoordinate2D(pair.second.annotation.coordinate); - _mbglMap->updatePointAnnotation(pair.first, { latLng, iconIdentifier.UTF8String ?: "" }); + const mbgl::Point<double> point = MGLPointFromLocationCoordinate2D(pair.second.annotation.coordinate); + _mbglMap->updateAnnotation(pair.first, mbgl::SymbolAnnotation { point, iconIdentifier.UTF8String ?: "" }); } } } diff --git a/platform/osx/src/MGLMapView.mm b/platform/osx/src/MGLMapView.mm index 019f497649..03b94c25ba 100644 --- a/platform/osx/src/MGLMapView.mm +++ b/platform/osx/src/MGLMapView.mm @@ -18,7 +18,7 @@ #import "MGLMapViewDelegate.h" #import <mbgl/mbgl.hpp> -#import <mbgl/annotation/point_annotation.hpp> +#import <mbgl/annotation/annotation.hpp> #import <mbgl/map/camera.hpp> #import <mbgl/platform/darwin/reachability.h> #import <mbgl/gl/gl.hpp> @@ -481,9 +481,9 @@ public: // match a valid annotation tag, the annotation will be unnecessarily // but safely updated. if (annotation == [self annotationWithTag:annotationTag]) { - const mbgl::LatLng latLng = MGLLatLngFromLocationCoordinate2D(annotation.coordinate); + const mbgl::Point<double> point = MGLPointFromLocationCoordinate2D(annotation.coordinate); MGLAnnotationImage *annotationImage = [self imageOfAnnotationWithTag:annotationTag]; - _mbglMap->updatePointAnnotation(annotationTag, { latLng, annotationImage.styleIconIdentifier.UTF8String ?: "" }); + _mbglMap->updateAnnotation(annotationTag, mbgl::SymbolAnnotation { point, annotationImage.styleIconIdentifier.UTF8String ?: "" }); if (annotationTag == _selectedAnnotationTag) { [self deselectAnnotation:annotation]; } @@ -1604,12 +1604,6 @@ public: BOOL delegateHasImagesForAnnotations = [self.delegate respondsToSelector:@selector(mapView:imageForAnnotation:)]; - NSMutableArray *userPoints = [NSMutableArray array]; - std::vector<mbgl::PointAnnotation> points; - NSMutableArray *userShapes = [NSMutableArray array]; - std::vector<mbgl::ShapeAnnotation> shapes; - NSMutableArray *annotationImages = [NSMutableArray arrayWithCapacity:annotations.count]; - for (id <MGLAnnotation> annotation in annotations) { NSAssert([annotation conformsToProtocol:@protocol(MGLAnnotation)], @"Annotation does not conform to MGLAnnotation"); @@ -1619,8 +1613,11 @@ public: if (!multiPoint.pointCount) { continue; } - shapes.emplace_back([multiPoint shapeAnnotationObjectWithDelegate:self]); - [userShapes addObject:annotation]; + + MGLAnnotationTag annotationTag = _mbglMap->addAnnotation([multiPoint annotationObjectWithDelegate:self]); + MGLAnnotationContext context; + context.annotation = annotation; + _annotationContextsByAnnotationTag[annotationTag] = context; } else if ([annotation isKindOfClass:[MGLMultiPolyline class]] || [annotation isKindOfClass:[MGLMultiPolygon class]] || [annotation isKindOfClass:[MGLShapeCollection class]]) { @@ -1647,28 +1644,12 @@ public: self.annotationImagesByIdentifier[annotationImage.reuseIdentifier] = annotationImage; [self installAnnotationImage:annotationImage]; } - [annotationImages addObject:annotationImage]; - - [userPoints addObject:annotation]; - points.emplace_back(MGLLatLngFromLocationCoordinate2D(annotation.coordinate), symbolName.UTF8String ?: ""); - - // Opt into potentially expensive tooltip tracking areas. - if (annotation.toolTip.length) { - _wantsToolTipRects = YES; - } - } - } - - // Add any point annotations to mbgl and our own index. - if (points.size()) { - std::vector<MGLAnnotationTag> annotationTags = _mbglMap->addPointAnnotations(points); - - for (size_t i = 0; i < annotationTags.size(); ++i) { - MGLAnnotationTag annotationTag = annotationTags[i]; - MGLAnnotationImage *annotationImage = annotationImages[i]; - annotationImage.styleIconIdentifier = @(points[i].icon.c_str()); - id <MGLAnnotation> annotation = userPoints[i]; - + + MGLAnnotationTag annotationTag = _mbglMap->addAnnotation(mbgl::SymbolAnnotation { + MGLPointFromLocationCoordinate2D(annotation.coordinate), + symbolName.UTF8String ?: "" + }); + MGLAnnotationContext context; context.annotation = annotation; context.imageReuseIdentifier = annotationImage.reuseIdentifier; @@ -1678,23 +1659,14 @@ public: NSAssert(![annotation isKindOfClass:[MGLMultiPoint class]], @"Point annotation should not be MGLMultiPoint."); [(NSObject *)annotation addObserver:self forKeyPath:@"coordinate" options:0 context:(void *)(NSUInteger)annotationTag]; } + + // Opt into potentially expensive tooltip tracking areas. + if (annotation.toolTip.length) { + _wantsToolTipRects = YES; + } } } - - // Add any shape annotations to mbgl and our own index. - if (shapes.size()) { - std::vector<MGLAnnotationTag> annotationTags = _mbglMap->addShapeAnnotations(shapes); - - for (size_t i = 0; i < annotationTags.size(); ++i) { - MGLAnnotationTag annotationTag = annotationTags[i]; - id <MGLAnnotation> annotation = userShapes[i]; - - MGLAnnotationContext context; - context.annotation = annotation; - _annotationContextsByAnnotationTag[annotationTag] = context; - } - } - + [self didChangeValueForKey:@"annotations"]; [self updateAnnotationTrackingAreas]; @@ -1765,16 +1737,14 @@ public: return; } - std::vector<MGLAnnotationTag> annotationTagsToRemove; - annotationTagsToRemove.reserve(annotations.count); - + [self willChangeValueForKey:@"annotations"]; + for (id <MGLAnnotation> annotation in annotations) { NSAssert([annotation conformsToProtocol:@protocol(MGLAnnotation)], @"Annotation does not conform to MGLAnnotation"); MGLAnnotationTag annotationTag = [self annotationTagForAnnotation:annotation]; NSAssert(annotationTag != MGLAnnotationTagNotFound, @"No ID for annotation %@", annotation); - annotationTagsToRemove.push_back(annotationTag); - + if (annotationTag == _selectedAnnotationTag) { [self deselectAnnotation:annotation]; } @@ -1788,10 +1758,10 @@ public: ![annotation isKindOfClass:[MGLMultiPoint class]]) { [(NSObject *)annotation removeObserver:self forKeyPath:@"coordinate" context:(void *)(NSUInteger)annotationTag]; } + + _mbglMap->removeAnnotation(annotationTag); } - [self willChangeValueForKey:@"annotations"]; - _mbglMap->removeAnnotations(annotationTagsToRemove); [self didChangeValueForKey:@"annotations"]; [self updateAnnotationTrackingAreas]; diff --git a/platform/qt/include/qmapbox.hpp b/platform/qt/include/qmapbox.hpp index f2cf363ea3..3200da2729 100644 --- a/platform/qt/include/qmapbox.hpp +++ b/platform/qt/include/qmapbox.hpp @@ -20,11 +20,9 @@ typedef quint32 AnnotationID; typedef QList<AnnotationID> AnnotationIDs; typedef QPair<Coordinate, QString> PointAnnotation; -typedef QList<PointAnnotation> PointAnnotations; // FIXME: We need to add support for custom style properties typedef QPair<CoordinateSegments, QString> ShapeAnnotation; -typedef QList<ShapeAnnotation> ShapeAnnotations; enum NetworkMode { Online, // Default diff --git a/platform/qt/include/qmapboxgl.hpp b/platform/qt/include/qmapboxgl.hpp index 3b10dadc9c..8ce6b02f47 100644 --- a/platform/qt/include/qmapboxgl.hpp +++ b/platform/qt/include/qmapboxgl.hpp @@ -165,15 +165,11 @@ public: QStringList getClasses() const; QMapbox::AnnotationID addPointAnnotation(const QMapbox::PointAnnotation &); - QMapbox::AnnotationIDs addPointAnnotations(const QMapbox::PointAnnotations &); - QMapbox::AnnotationID addShapeAnnotation(const QMapbox::ShapeAnnotation &); - QMapbox::AnnotationIDs addShapeAnnotations(const QMapbox::ShapeAnnotations &); void updatePointAnnotation(QMapbox::AnnotationID, const QMapbox::PointAnnotation &); void removeAnnotation(QMapbox::AnnotationID); - void removeAnnotations(const QMapbox::AnnotationIDs &); bool isRotating() const; bool isScaling() const; diff --git a/platform/qt/src/qmapboxgl.cpp b/platform/qt/src/qmapboxgl.cpp index 976da9a1eb..1f8657c044 100644 --- a/platform/qt/src/qmapboxgl.cpp +++ b/platform/qt/src/qmapboxgl.cpp @@ -1,7 +1,6 @@ #include "qmapboxgl_p.hpp" -#include <mbgl/annotation/point_annotation.hpp> -#include <mbgl/annotation/shape_annotation.hpp> +#include <mbgl/annotation/annotation.hpp> #include <mbgl/gl/gl.hpp> #include <mbgl/map/camera.hpp> #include <mbgl/map/map.hpp> @@ -376,40 +375,23 @@ QStringList QMapboxGL::getClasses() const return classNames; } -mbgl::PointAnnotation fromPointAnnotation(const PointAnnotation &pointAnnotation) { +mbgl::Annotation fromPointAnnotation(const PointAnnotation &pointAnnotation) { const Coordinate &coordinate = pointAnnotation.first; const QString &icon = pointAnnotation.second; - return { { coordinate.first, coordinate.second }, icon.toStdString() }; + return mbgl::SymbolAnnotation { mbgl::Point<double> { coordinate.second, coordinate.first }, icon.toStdString() }; } AnnotationID QMapboxGL::addPointAnnotation(const PointAnnotation &pointAnnotation) { - return d_ptr->mapObj->addPointAnnotation(fromPointAnnotation(pointAnnotation)); -} - -AnnotationIDs QMapboxGL::addPointAnnotations(const PointAnnotations &pointAnnotations) -{ - std::vector<mbgl::PointAnnotation> mbglPointAnnotations; - mbglPointAnnotations.reserve(pointAnnotations.size()); - - for (const PointAnnotation &pointAnnotation : pointAnnotations) { - mbglPointAnnotations.emplace_back(fromPointAnnotation(pointAnnotation)); - } - - AnnotationIDs ids; - for (const mbgl::AnnotationID &id : d_ptr->mapObj->addPointAnnotations(mbglPointAnnotations)) { - ids << id; - } - - return ids; + return d_ptr->mapObj->addAnnotation(fromPointAnnotation(pointAnnotation)); } void QMapboxGL::updatePointAnnotation(AnnotationID id, const PointAnnotation &pointAnnotation) { - d_ptr->mapObj->updatePointAnnotation(id, fromPointAnnotation(pointAnnotation)); + d_ptr->mapObj->updateAnnotation(id, fromPointAnnotation(pointAnnotation)); } -mbgl::ShapeAnnotation fromQMapboxGLShapeAnnotation(const ShapeAnnotation &shapeAnnotation) { +mbgl::Annotation fromQMapboxGLShapeAnnotation(const ShapeAnnotation &shapeAnnotation) { const CoordinateSegments &segments = shapeAnnotation.first; const QString &styleLayer = shapeAnnotation.second; @@ -427,29 +409,12 @@ mbgl::ShapeAnnotation fromQMapboxGLShapeAnnotation(const ShapeAnnotation &shapeA polygon.emplace_back(linearRing); } - return { polygon, styleLayer.toStdString() }; + return mbgl::StyleSourcedAnnotation { polygon, styleLayer.toStdString() }; } AnnotationID QMapboxGL::addShapeAnnotation(const ShapeAnnotation &shapeAnnotation) { - return d_ptr->mapObj->addShapeAnnotation(fromQMapboxGLShapeAnnotation(shapeAnnotation)); -} - -AnnotationIDs QMapboxGL::addShapeAnnotations(const ShapeAnnotations &shapeAnnotations) -{ - std::vector<mbgl::ShapeAnnotation> mbglShapeAnnotations; - mbglShapeAnnotations.reserve(shapeAnnotations.size()); - - for (const ShapeAnnotation &shapeAnnotation : shapeAnnotations) { - mbglShapeAnnotations.emplace_back(fromQMapboxGLShapeAnnotation(shapeAnnotation)); - } - - AnnotationIDs ids; - for (const mbgl::AnnotationID &id : d_ptr->mapObj->addShapeAnnotations(mbglShapeAnnotations)) { - ids << id; - } - - return ids; + return d_ptr->mapObj->addAnnotation(fromQMapboxGLShapeAnnotation(shapeAnnotation)); } void QMapboxGL::removeAnnotation(AnnotationID annotationID) @@ -457,18 +422,6 @@ void QMapboxGL::removeAnnotation(AnnotationID annotationID) d_ptr->mapObj->removeAnnotation(annotationID); } -void QMapboxGL::removeAnnotations(const AnnotationIDs &annotationIDs) -{ - std::vector<mbgl::AnnotationID> mbglAnnotationIds; - mbglAnnotationIds.reserve(annotationIDs.size()); - - for (const AnnotationID annotationID : annotationIDs) { - mbglAnnotationIds.emplace_back(annotationID); - } - - d_ptr->mapObj->removeAnnotations(mbglAnnotationIds); -} - bool QMapboxGL::isRotating() const { return d_ptr->mapObj->isRotating(); diff --git a/src/mbgl/annotation/annotation_manager.cpp b/src/mbgl/annotation/annotation_manager.cpp index e5f43eb3b6..4d7059f80f 100644 --- a/src/mbgl/annotation/annotation_manager.cpp +++ b/src/mbgl/annotation/annotation_manager.cpp @@ -1,5 +1,9 @@ #include <mbgl/annotation/annotation_manager.hpp> #include <mbgl/annotation/annotation_tile.hpp> +#include <mbgl/annotation/symbol_annotation_impl.hpp> +#include <mbgl/annotation/line_annotation_impl.hpp> +#include <mbgl/annotation/fill_annotation_impl.hpp> +#include <mbgl/annotation/style_sourced_annotation_impl.hpp> #include <mbgl/source/source.hpp> #include <mbgl/style/style.hpp> #include <mbgl/layer/symbol_layer.hpp> @@ -18,63 +22,54 @@ AnnotationManager::AnnotationManager(float pixelRatio) AnnotationManager::~AnnotationManager() = default; -AnnotationIDs -AnnotationManager::addPointAnnotations(const std::vector<PointAnnotation>& points, const uint8_t) { - AnnotationIDs annotationIDs; - annotationIDs.reserve(points.size()); - - for (const auto& point : points) { - const uint32_t annotationID = nextID++; - auto annotation = std::make_shared<PointAnnotationImpl>(annotationID, point); - pointTree.insert(annotation); - pointAnnotations.emplace(annotationID, annotation); - annotationIDs.push_back(annotationID); - } - - return annotationIDs; +AnnotationID AnnotationManager::addAnnotation(const Annotation& annotation, const uint8_t maxZoom) { + AnnotationID id = nextID++; + updateAnnotation(id, annotation, maxZoom); + return id; } -AnnotationIDs -AnnotationManager::addShapeAnnotations(const std::vector<ShapeAnnotation>& shapes, const uint8_t maxZoom) { - AnnotationIDs annotationIDs; - annotationIDs.reserve(shapes.size()); +void AnnotationManager::updateAnnotation(const AnnotationID& id, const Annotation& annotation, const uint8_t maxZoom) { + removeAnnotation(id); + Annotation::visit(annotation, [&] (const auto& annotation_) { + this->add(id, annotation_, maxZoom); + }); +} - for (const auto& shape : shapes) { - const uint32_t annotationID = nextID++; - shapeAnnotations.emplace(annotationID, - std::make_unique<ShapeAnnotationImpl>(annotationID, shape, maxZoom)); - annotationIDs.push_back(annotationID); +void AnnotationManager::removeAnnotation(const AnnotationID& id) { + if (symbolAnnotations.find(id) != symbolAnnotations.end()) { + symbolTree.remove(symbolAnnotations.at(id)); + symbolAnnotations.erase(id); + } else if (shapeAnnotations.find(id) != shapeAnnotations.end()) { + obsoleteShapeAnnotationLayers.push_back(shapeAnnotations.at(id)->layerID); + shapeAnnotations.erase(id); } +} - return annotationIDs; +void AnnotationManager::add(const AnnotationID& id, const SymbolAnnotation& annotation, const uint8_t) { + auto impl = std::make_shared<SymbolAnnotationImpl>(id, annotation); + symbolTree.insert(impl); + symbolAnnotations.emplace(id, impl); } -void AnnotationManager::updatePointAnnotation(const AnnotationID& id, const PointAnnotation& point, const uint8_t) { - auto foundAnnotation = pointAnnotations.find(id); - if (foundAnnotation != pointAnnotations.end()) { - auto updatedAnnotation = std::make_shared<PointAnnotationImpl>(id, point); - pointTree.remove(foundAnnotation->second); - pointTree.insert(updatedAnnotation); - foundAnnotation->second = updatedAnnotation; - } +void AnnotationManager::add(const AnnotationID& id, const LineAnnotation& annotation, const uint8_t maxZoom) { + shapeAnnotations.emplace(id, + std::make_unique<LineAnnotationImpl>(id, annotation, maxZoom)); } -void AnnotationManager::removeAnnotations(const AnnotationIDs& ids) { - for (const auto& id : ids) { - if (pointAnnotations.find(id) != pointAnnotations.end()) { - pointTree.remove(pointAnnotations.at(id)); - pointAnnotations.erase(id); - } else if (shapeAnnotations.find(id) != shapeAnnotations.end()) { - obsoleteShapeAnnotationLayers.push_back(shapeAnnotations.at(id)->layerID); - shapeAnnotations.erase(id); - } - } +void AnnotationManager::add(const AnnotationID& id, const FillAnnotation& annotation, const uint8_t maxZoom) { + shapeAnnotations.emplace(id, + std::make_unique<FillAnnotationImpl>(id, annotation, maxZoom)); +} + +void AnnotationManager::add(const AnnotationID& id, const StyleSourcedAnnotation& annotation, const uint8_t maxZoom) { + shapeAnnotations.emplace(id, + std::make_unique<StyleSourcedAnnotationImpl>(id, annotation, maxZoom)); } AnnotationIDs AnnotationManager::getPointAnnotationsInBounds(const LatLngBounds& bounds) const { AnnotationIDs result; - pointTree.query(boost::geometry::index::intersects(bounds), + symbolTree.query(boost::geometry::index::intersects(bounds), boost::make_function_output_iterator([&](const auto& val){ result.push_back(val->id); })); @@ -83,7 +78,7 @@ AnnotationIDs AnnotationManager::getPointAnnotationsInBounds(const LatLngBounds& } std::unique_ptr<AnnotationTile> AnnotationManager::getTile(const CanonicalTileID& tileID) { - if (pointAnnotations.empty() && shapeAnnotations.empty()) + if (symbolAnnotations.empty() && shapeAnnotations.empty()) return nullptr; auto tile = std::make_unique<AnnotationTile>(); @@ -94,7 +89,7 @@ std::unique_ptr<AnnotationTile> AnnotationManager::getTile(const CanonicalTileID LatLngBounds tileBounds(tileID); - pointTree.query(boost::geometry::index::intersects(tileBounds), + symbolTree.query(boost::geometry::index::intersects(tileBounds), boost::make_function_output_iterator([&](const auto& val){ val->updateLayer(tileID, pointLayer); })); diff --git a/src/mbgl/annotation/annotation_manager.hpp b/src/mbgl/annotation/annotation_manager.hpp index aaa60278cf..6862739ebb 100644 --- a/src/mbgl/annotation/annotation_manager.hpp +++ b/src/mbgl/annotation/annotation_manager.hpp @@ -1,8 +1,7 @@ #pragma once #include <mbgl/annotation/annotation.hpp> -#include <mbgl/annotation/point_annotation_impl.hpp> -#include <mbgl/annotation/shape_annotation_impl.hpp> +#include <mbgl/annotation/symbol_annotation_impl.hpp> #include <mbgl/sprite/sprite_store.hpp> #include <mbgl/sprite/sprite_atlas.hpp> #include <mbgl/util/geo.hpp> @@ -11,13 +10,14 @@ #include <string> #include <vector> #include <set> +#include <unordered_map> namespace mbgl { -class PointAnnotation; -class ShapeAnnotation; class AnnotationTile; class AnnotationTileMonitor; +class SymbolAnnotationImpl; +class ShapeAnnotationImpl; class Style; class AnnotationManager : private util::noncopyable { @@ -25,10 +25,9 @@ public: AnnotationManager(float pixelRatio); ~AnnotationManager(); - AnnotationIDs addPointAnnotations(const std::vector<PointAnnotation>&, const uint8_t maxZoom); - AnnotationIDs addShapeAnnotations(const std::vector<ShapeAnnotation>&, const uint8_t maxZoom); - void updatePointAnnotation(const AnnotationID&, const PointAnnotation&, const uint8_t maxZoom); - void removeAnnotations(const AnnotationIDs&); + AnnotationID addAnnotation(const Annotation&, const uint8_t maxZoom); + void updateAnnotation(const AnnotationID&, const Annotation&, const uint8_t maxZoom); + void removeAnnotation(const AnnotationID&); AnnotationIDs getPointAnnotationsInBounds(const LatLngBounds&) const; @@ -46,12 +45,22 @@ public: static const std::string PointLayerID; private: + void add(const AnnotationID&, const SymbolAnnotation&, const uint8_t); + void add(const AnnotationID&, const LineAnnotation&, const uint8_t); + void add(const AnnotationID&, const FillAnnotation&, const uint8_t); + void add(const AnnotationID&, const StyleSourcedAnnotation&, const uint8_t); + std::unique_ptr<AnnotationTile> getTile(const CanonicalTileID&); AnnotationID nextID = 0; - PointAnnotationImpl::Tree pointTree; - PointAnnotationImpl::Map pointAnnotations; - ShapeAnnotationImpl::Map shapeAnnotations; + + using SymbolAnnotationTree = boost::geometry::index::rtree<std::shared_ptr<const SymbolAnnotationImpl>, boost::geometry::index::rstar<16, 4>>; + using SymbolAnnotationMap = std::unordered_map<AnnotationID, std::shared_ptr<SymbolAnnotationImpl>>; + using ShapeAnnotationMap = std::unordered_map<AnnotationID, std::unique_ptr<ShapeAnnotationImpl>>; + + SymbolAnnotationTree symbolTree; + SymbolAnnotationMap symbolAnnotations; + ShapeAnnotationMap shapeAnnotations; std::vector<std::string> obsoleteShapeAnnotationLayers; std::set<AnnotationTileMonitor*> monitors; diff --git a/src/mbgl/annotation/fill_annotation_impl.cpp b/src/mbgl/annotation/fill_annotation_impl.cpp new file mode 100644 index 0000000000..2555f90439 --- /dev/null +++ b/src/mbgl/annotation/fill_annotation_impl.cpp @@ -0,0 +1,36 @@ +#include <mbgl/annotation/fill_annotation_impl.hpp> +#include <mbgl/annotation/annotation_manager.hpp> +#include <mbgl/style/style.hpp> +#include <mbgl/layer/fill_layer.hpp> + +namespace mbgl { + +namespace geojsonvt = mapbox::geojsonvt; + +FillAnnotationImpl::FillAnnotationImpl(const AnnotationID id_, const FillAnnotation& annotation_, const uint8_t maxZoom_) + : ShapeAnnotationImpl(id_, maxZoom_), + annotation(annotation_) { +} + +void FillAnnotationImpl::updateStyle(Style& style) const { + if (style.getLayer(layerID)) + return; + + std::unique_ptr<FillLayer> layer = std::make_unique<FillLayer>(); + + layer->paint.fillOpacity = annotation.opacity; + layer->paint.fillColor = annotation.color; + layer->paint.fillOutlineColor = annotation.outlineColor; + + layer->id = layerID; + layer->source = AnnotationManager::SourceID; + layer->sourceLayer = layer->id; + + style.addLayer(std::move(layer), AnnotationManager::PointLayerID); +} + +const Geometry<double>& FillAnnotationImpl::geometry() const { + return annotation.geometry; +} + +} // namespace mbgl diff --git a/src/mbgl/annotation/fill_annotation_impl.hpp b/src/mbgl/annotation/fill_annotation_impl.hpp new file mode 100644 index 0000000000..1d98505c43 --- /dev/null +++ b/src/mbgl/annotation/fill_annotation_impl.hpp @@ -0,0 +1,19 @@ +#pragma once + +#include <mbgl/annotation/shape_annotation_impl.hpp> +#include <mbgl/annotation/annotation.hpp> + +namespace mbgl { + +class FillAnnotationImpl : public ShapeAnnotationImpl { +public: + FillAnnotationImpl(const AnnotationID, const FillAnnotation&, const uint8_t maxZoom); + + void updateStyle(Style&) const final; + const Geometry<double>& geometry() const final; + +private: + const FillAnnotation annotation; +}; + +} // namespace mbgl diff --git a/src/mbgl/annotation/line_annotation_impl.cpp b/src/mbgl/annotation/line_annotation_impl.cpp new file mode 100644 index 0000000000..e22c36bcbe --- /dev/null +++ b/src/mbgl/annotation/line_annotation_impl.cpp @@ -0,0 +1,37 @@ +#include <mbgl/annotation/line_annotation_impl.hpp> +#include <mbgl/annotation/annotation_manager.hpp> +#include <mbgl/style/style.hpp> +#include <mbgl/layer/line_layer.hpp> + +namespace mbgl { + +namespace geojsonvt = mapbox::geojsonvt; + +LineAnnotationImpl::LineAnnotationImpl(const AnnotationID id_, const LineAnnotation& annotation_, const uint8_t maxZoom_) + : ShapeAnnotationImpl(id_, maxZoom_), + annotation(annotation_) { +} + +void LineAnnotationImpl::updateStyle(Style& style) const { + if (style.getLayer(layerID)) + return; + + std::unique_ptr<LineLayer> layer = std::make_unique<LineLayer>(); + layer->layout.lineJoin = LineJoinType::Round; + + layer->paint.lineOpacity = annotation.opacity; + layer->paint.lineWidth = annotation.width; + layer->paint.lineColor = annotation.color; + + layer->id = layerID; + layer->source = AnnotationManager::SourceID; + layer->sourceLayer = layer->id; + + style.addLayer(std::move(layer), AnnotationManager::PointLayerID); +} + +const Geometry<double>& LineAnnotationImpl::geometry() const { + return annotation.geometry; +} + +} // namespace mbgl diff --git a/src/mbgl/annotation/line_annotation_impl.hpp b/src/mbgl/annotation/line_annotation_impl.hpp new file mode 100644 index 0000000000..05a79fc0c3 --- /dev/null +++ b/src/mbgl/annotation/line_annotation_impl.hpp @@ -0,0 +1,19 @@ +#pragma once + +#include <mbgl/annotation/shape_annotation_impl.hpp> +#include <mbgl/annotation/annotation.hpp> + +namespace mbgl { + +class LineAnnotationImpl : public ShapeAnnotationImpl { +public: + LineAnnotationImpl(const AnnotationID, const LineAnnotation&, const uint8_t maxZoom); + + void updateStyle(Style&) const final; + const Geometry<double>& geometry() const final; + +private: + const LineAnnotation annotation; +}; + +} // namespace mbgl diff --git a/src/mbgl/annotation/shape_annotation_impl.cpp b/src/mbgl/annotation/shape_annotation_impl.cpp index a96c4eae72..a5116be72f 100644 --- a/src/mbgl/annotation/shape_annotation_impl.cpp +++ b/src/mbgl/annotation/shape_annotation_impl.cpp @@ -1,83 +1,21 @@ #include <mapbox/geojsonvt/convert.hpp> #include <mbgl/annotation/shape_annotation_impl.hpp> -#include <mbgl/annotation/annotation_manager.hpp> #include <mbgl/annotation/annotation_tile.hpp> -#include <mbgl/util/constants.hpp> -#include <mbgl/util/string.hpp> -#include <mbgl/style/style.hpp> -#include <mbgl/layer/line_layer.hpp> -#include <mbgl/layer/fill_layer.hpp> +#include <mbgl/tile/tile_id.hpp> +#include <mbgl/math/wrap.hpp> #include <mbgl/math/clamp.hpp> +#include <mbgl/util/string.hpp> +#include <mbgl/util/constants.hpp> namespace mbgl { namespace geojsonvt = mapbox::geojsonvt; -ShapeAnnotationImpl::ShapeAnnotationImpl(const AnnotationID id_, - const ShapeAnnotation& shape_, - const uint8_t maxZoom_) -: id(id_), - layerID("com.mapbox.annotations.shape." + util::toString(id)), - shape(shape_), - maxZoom(maxZoom_) { -} - -void ShapeAnnotationImpl::updateStyle(Style& style) { - if (style.getLayer(layerID)) - return; - - if (shape.properties.is<LineAnnotationProperties>()) { - type = geojsonvt::ProjectedFeatureType::LineString; - - std::unique_ptr<LineLayer> layer = std::make_unique<LineLayer>(); - layer->layout.lineJoin = LineJoinType::Round; - - const LineAnnotationProperties& properties = shape.properties.get<LineAnnotationProperties>(); - layer->paint.lineOpacity = properties.opacity; - layer->paint.lineWidth = properties.width; - layer->paint.lineColor = properties.color; - - layer->id = layerID; - layer->source = AnnotationManager::SourceID; - layer->sourceLayer = layer->id; - - style.addLayer(std::move(layer), AnnotationManager::PointLayerID); - - } else if (shape.properties.is<FillAnnotationProperties>()) { - type = geojsonvt::ProjectedFeatureType::Polygon; - - std::unique_ptr<FillLayer> layer = std::make_unique<FillLayer>(); - - const FillAnnotationProperties& properties = shape.properties.get<FillAnnotationProperties>(); - layer->paint.fillOpacity = properties.opacity; - layer->paint.fillColor = properties.color; - layer->paint.fillOutlineColor = properties.outlineColor; - - layer->id = layerID; - layer->source = AnnotationManager::SourceID; - layer->sourceLayer = layer->id; - - style.addLayer(std::move(layer), AnnotationManager::PointLayerID); - - } else { - const StyleLayer* sourceLayer = style.getLayer(shape.properties.get<std::string>()); - if (!sourceLayer) return; - - std::unique_ptr<StyleLayer> layer = sourceLayer->clone(); - - type = layer->is<LineLayer>() - ? geojsonvt::ProjectedFeatureType::LineString - : geojsonvt::ProjectedFeatureType::Polygon; - - layer->id = layerID; - layer->ref = ""; - layer->source = AnnotationManager::SourceID; - layer->sourceLayer = layer->id; - layer->visibility = VisibilityType::Visible; - - style.addLayer(std::move(layer), sourceLayer->id); - } +ShapeAnnotationImpl::ShapeAnnotationImpl(const AnnotationID id_, const uint8_t maxZoom_) + : id(id_), + maxZoom(maxZoom_), + layerID("com.mapbox.annotations.shape." + util::toString(id)) { } struct ToGeoJSONVT { @@ -166,7 +104,7 @@ void ShapeAnnotationImpl::updateTile(const CanonicalTileID& tileID, AnnotationTi const double tolerance = baseTolerance / (maxAmountOfTiles * util::EXTENT); std::vector<geojsonvt::ProjectedFeature> features = { - Geometry<double>::visit(shape.geometry, ToGeoJSONVT(tolerance)) + Geometry<double>::visit(geometry(), ToGeoJSONVT(tolerance)) }; mapbox::geojsonvt::Options options; diff --git a/src/mbgl/annotation/shape_annotation_impl.hpp b/src/mbgl/annotation/shape_annotation_impl.hpp index fb3ef2d893..f342c4b1fc 100644 --- a/src/mbgl/annotation/shape_annotation_impl.hpp +++ b/src/mbgl/annotation/shape_annotation_impl.hpp @@ -3,12 +3,9 @@ #include <mapbox/geojsonvt.hpp> #include <mbgl/annotation/annotation.hpp> -#include <mbgl/annotation/shape_annotation.hpp> -#include <mbgl/util/geo.hpp> -#include <memory> #include <string> -#include <map> +#include <memory> namespace mbgl { @@ -18,20 +15,17 @@ class CanonicalTileID; class ShapeAnnotationImpl { public: - using Map = std::map<AnnotationID, std::unique_ptr<ShapeAnnotationImpl>>; + ShapeAnnotationImpl(const AnnotationID, const uint8_t maxZoom); + virtual ~ShapeAnnotationImpl() = default; - ShapeAnnotationImpl(const AnnotationID, const ShapeAnnotation&, const uint8_t maxZoom); + virtual void updateStyle(Style&) const = 0; + virtual const Geometry<double>& geometry() const = 0; - void updateStyle(Style&); void updateTile(const CanonicalTileID&, AnnotationTile&); const AnnotationID id; - const std::string layerID; - const ShapeAnnotation shape; - -private: const uint8_t maxZoom; - mapbox::geojsonvt::ProjectedFeatureType type; + const std::string layerID; std::unique_ptr<mapbox::geojsonvt::GeoJSONVT> shapeTiler; }; diff --git a/src/mbgl/annotation/style_sourced_annotation_impl.cpp b/src/mbgl/annotation/style_sourced_annotation_impl.cpp new file mode 100644 index 0000000000..5d8f1f0da1 --- /dev/null +++ b/src/mbgl/annotation/style_sourced_annotation_impl.cpp @@ -0,0 +1,38 @@ +#include <mbgl/annotation/style_sourced_annotation_impl.hpp> +#include <mbgl/annotation/annotation_manager.hpp> +#include <mbgl/style/style.hpp> +#include <mbgl/style/style_layer.hpp> + +namespace mbgl { + +namespace geojsonvt = mapbox::geojsonvt; + +StyleSourcedAnnotationImpl::StyleSourcedAnnotationImpl(const AnnotationID id_, const StyleSourcedAnnotation& annotation_, const uint8_t maxZoom_) + : ShapeAnnotationImpl(id_, maxZoom_), + annotation(annotation_) { +} + +void StyleSourcedAnnotationImpl::updateStyle(Style& style) const { + if (style.getLayer(layerID)) + return; + + const StyleLayer* sourceLayer = style.getLayer(annotation.layerID); + if (!sourceLayer) + return; + + std::unique_ptr<StyleLayer> layer = sourceLayer->clone(); + + layer->id = layerID; + layer->ref = ""; + layer->source = AnnotationManager::SourceID; + layer->sourceLayer = layer->id; + layer->visibility = VisibilityType::Visible; + + style.addLayer(std::move(layer), sourceLayer->id); +} + +const Geometry<double>& StyleSourcedAnnotationImpl::geometry() const { + return annotation.geometry; +} + +} // namespace mbgl diff --git a/src/mbgl/annotation/style_sourced_annotation_impl.hpp b/src/mbgl/annotation/style_sourced_annotation_impl.hpp new file mode 100644 index 0000000000..734f6c8290 --- /dev/null +++ b/src/mbgl/annotation/style_sourced_annotation_impl.hpp @@ -0,0 +1,19 @@ +#pragma once + +#include <mbgl/annotation/shape_annotation_impl.hpp> +#include <mbgl/annotation/annotation.hpp> + +namespace mbgl { + +class StyleSourcedAnnotationImpl : public ShapeAnnotationImpl { +public: + StyleSourcedAnnotationImpl(const AnnotationID, const StyleSourcedAnnotation&, const uint8_t maxZoom); + + void updateStyle(Style&) const final; + const Geometry<double>& geometry() const final; + +private: + const StyleSourcedAnnotation annotation; +}; + +} // namespace mbgl diff --git a/src/mbgl/annotation/point_annotation_impl.cpp b/src/mbgl/annotation/symbol_annotation_impl.cpp index a1367f3901..5ad6142eec 100644 --- a/src/mbgl/annotation/point_annotation_impl.cpp +++ b/src/mbgl/annotation/symbol_annotation_impl.cpp @@ -1,24 +1,29 @@ -#include <mbgl/annotation/point_annotation_impl.hpp> +#include <mbgl/annotation/symbol_annotation_impl.hpp> #include <mbgl/annotation/annotation_tile.hpp> #include <mbgl/math/clamp.hpp> namespace mbgl { -PointAnnotationImpl::PointAnnotationImpl(const AnnotationID id_, const PointAnnotation& point_) +SymbolAnnotationImpl::SymbolAnnotationImpl(const AnnotationID id_, const SymbolAnnotation& annotation_) : id(id_), - point(point_) { + annotation(annotation_) { + if (!annotation.geometry.is<Point<double>>()) { + throw std::runtime_error("unsupported symbol annotation geometry type"); + } } -void PointAnnotationImpl::updateLayer(const CanonicalTileID& tileID, AnnotationTileLayer& layer) const { +void SymbolAnnotationImpl::updateLayer(const CanonicalTileID& tileID, AnnotationTileLayer& layer) const { std::unordered_map<std::string, std::string> featureProperties; - featureProperties.emplace("sprite", point.icon.empty() ? std::string("default_marker") : point.icon); + featureProperties.emplace("sprite", annotation.icon.empty() ? std::string("default_marker") : annotation.icon); + + const Point<double>& p = annotation.geometry.get<Point<double>>(); // Clamp to the latitude limits of Web Mercator. - const double constrainedLatitude = util::clamp(point.position.latitude, -util::LATITUDE_MAX, util::LATITUDE_MAX); + const double constrainedLatitude = util::clamp(p.y, -util::LATITUDE_MAX, util::LATITUDE_MAX); // Project a coordinate into unit space in a square map. const double sine = std::sin(constrainedLatitude * util::DEG2RAD); - const double x = point.position.longitude / util::DEGREES_MAX + 0.5; + const double x = p.x / util::DEGREES_MAX + 0.5; const double y = 0.5 - 0.25 * std::log((1.0 + sine) / (1.0 - sine)) / M_PI; Point<double> projected(x, y); diff --git a/src/mbgl/annotation/point_annotation_impl.hpp b/src/mbgl/annotation/symbol_annotation_impl.hpp index d8852fca9e..43c490140d 100644 --- a/src/mbgl/annotation/point_annotation_impl.hpp +++ b/src/mbgl/annotation/symbol_annotation_impl.hpp @@ -1,7 +1,6 @@ #pragma once #include <mbgl/annotation/annotation.hpp> -#include <mbgl/annotation/point_annotation.hpp> #include <mbgl/util/geo.hpp> #include <string> @@ -36,31 +35,29 @@ namespace mbgl { class AnnotationTileLayer; class CanonicalTileID; -class PointAnnotationImpl { +class SymbolAnnotationImpl { public: - using Map = std::map<AnnotationID, std::shared_ptr<PointAnnotationImpl>>; - using Tree = boost::geometry::index::rtree<std::shared_ptr<const PointAnnotationImpl>, boost::geometry::index::rstar<16, 4>>; - - PointAnnotationImpl(const AnnotationID, const PointAnnotation&); + SymbolAnnotationImpl(const AnnotationID, const SymbolAnnotation&); void updateLayer(const CanonicalTileID&, AnnotationTileLayer&) const; const AnnotationID id; - const PointAnnotation point; + const SymbolAnnotation annotation; }; } // namespace mbgl -// Tell Boost Geometry how to access a std::shared_ptr<mbgl::PointAnnotation> object. +// Tell Boost Geometry how to access a std::shared_ptr<mbgl::SymbolAnnotation> object. namespace boost { namespace geometry { namespace index { template <> -struct indexable<std::shared_ptr<const mbgl::PointAnnotationImpl>> { - using result_type = const mbgl::LatLng&; - inline const mbgl::LatLng& operator()(const std::shared_ptr<const mbgl::PointAnnotationImpl>& v) const { - return v->point.position; +struct indexable<std::shared_ptr<const mbgl::SymbolAnnotationImpl>> { + using result_type = mbgl::LatLng; + inline mbgl::LatLng operator()(const std::shared_ptr<const mbgl::SymbolAnnotationImpl>& v) const { + const mbgl::Point<double>& p = v->annotation.geometry.get<mbgl::Point<double>>(); + return mbgl::LatLng(p.y, p.x); } }; diff --git a/src/mbgl/map/map.cpp b/src/mbgl/map/map.cpp index e0a73c2a06..f89fde1f03 100644 --- a/src/mbgl/map/map.cpp +++ b/src/mbgl/map/map.cpp @@ -3,8 +3,6 @@ #include <mbgl/map/view.hpp> #include <mbgl/map/transform.hpp> #include <mbgl/map/transform_state.hpp> -#include <mbgl/annotation/point_annotation.hpp> -#include <mbgl/annotation/shape_annotation.hpp> #include <mbgl/annotation/annotation_manager.hpp> #include <mbgl/style/style.hpp> #include <mbgl/style/style_observer.hpp> @@ -693,37 +691,19 @@ double Map::getTopOffsetPixelsForAnnotationIcon(const std::string& name) { return impl->annotationManager->getTopOffsetPixelsForIcon(name); } -AnnotationID Map::addPointAnnotation(const PointAnnotation& annotation) { - return addPointAnnotations({ annotation }).front(); -} - -AnnotationIDs Map::addPointAnnotations(const std::vector<PointAnnotation>& annotations) { - auto result = impl->annotationManager->addPointAnnotations(annotations, getMaxZoom()); - update(Update::Annotations); - return result; -} - -AnnotationID Map::addShapeAnnotation(const ShapeAnnotation& annotation) { - return addShapeAnnotations({ annotation }).front(); -} - -AnnotationIDs Map::addShapeAnnotations(const std::vector<ShapeAnnotation>& annotations) { - auto result = impl->annotationManager->addShapeAnnotations(annotations, getMaxZoom()); +AnnotationID Map::addAnnotation(const Annotation& annotation) { + auto result = impl->annotationManager->addAnnotation(annotation, getMaxZoom()); update(Update::Annotations); return result; } -void Map::updatePointAnnotation(AnnotationID annotationId, const PointAnnotation& annotation) { - impl->annotationManager->updatePointAnnotation(annotationId, annotation, getMaxZoom()); +void Map::updateAnnotation(AnnotationID id, const Annotation& annotation) { + impl->annotationManager->updateAnnotation(id, annotation, getMaxZoom()); update(Update::Annotations); } void Map::removeAnnotation(AnnotationID annotation) { - removeAnnotations({ annotation }); -} - -void Map::removeAnnotations(const AnnotationIDs& annotations) { - impl->annotationManager->removeAnnotations(annotations); + impl->annotationManager->removeAnnotation(annotation); update(Update::Annotations); } diff --git a/test/api/annotations.cpp b/test/api/annotations.cpp index 3c73fb444c..d2e2a63a56 100644 --- a/test/api/annotations.cpp +++ b/test/api/annotations.cpp @@ -1,8 +1,7 @@ #include <mbgl/test/util.hpp> #include <mbgl/test/stub_file_source.hpp> -#include <mbgl/annotation/point_annotation.hpp> -#include <mbgl/annotation/shape_annotation.hpp> +#include <mbgl/annotation/annotation.hpp> #include <mbgl/sprite/sprite_image.hpp> #include <mbgl/map/map.hpp> #include <mbgl/platform/default/headless_display.hpp> @@ -29,7 +28,7 @@ void checkRendering(Map& map, const char * name) { } // end namespace -TEST(Annotations, PointAnnotation) { +TEST(Annotations, SymbolAnnotation) { util::RunLoop loop; auto display = std::make_shared<mbgl::HeadlessDisplay>(); @@ -39,7 +38,7 @@ TEST(Annotations, PointAnnotation) { Map map(view, fileSource, MapMode::Still); map.setStyleJSON(util::read_file("test/fixtures/api/empty.json"), ""); map.addAnnotationIcon("default_marker", namedMarker("default_marker.png")); - map.addPointAnnotation(PointAnnotation({ 0, 0 }, "default_marker")); + map.addAnnotation(SymbolAnnotation { Point<double>(0, 0), "default_marker" }); checkRendering(map, "point_annotation"); } @@ -56,11 +55,11 @@ TEST(Annotations, LineAnnotation) { LineString<double> line = {{ { 0, 0 }, { 45, 45 } }}; - LineAnnotationProperties properties; - properties.color = {{ 255, 0, 0, 1 }}; - properties.width = 5; + LineAnnotation annotation { line }; + annotation.color = {{ 255, 0, 0, 1 }}; + annotation.width = 5; - map.addShapeAnnotation(ShapeAnnotation(line, properties)); + map.addAnnotation(annotation); checkRendering(map, "line_annotation"); } @@ -77,10 +76,10 @@ TEST(Annotations, FillAnnotation) { Polygon<double> polygon = {{ {{ { 0, 0 }, { 0, 45 }, { 45, 45 }, { 45, 0 } }} }}; - FillAnnotationProperties properties; - properties.color = {{ 255, 0, 0, 1 }}; + FillAnnotation annotation { polygon }; + annotation.color = {{ 255, 0, 0, 1 }}; - map.addShapeAnnotation(ShapeAnnotation(polygon, properties)); + map.addAnnotation(annotation); checkRendering(map, "fill_annotation"); } @@ -97,7 +96,7 @@ TEST(Annotations, StyleSourcedShapeAnnotation) { Polygon<double> polygon = {{ {{ { 0, 0 }, { 0, 45 }, { 45, 45 }, { 45, 0 } }} }}; - map.addShapeAnnotation(ShapeAnnotation(polygon, "annotation")); + map.addAnnotation(StyleSourcedAnnotation { polygon, "annotation" }); checkRendering(map, "style_sourced_shape_annotation"); } @@ -112,11 +111,11 @@ TEST(Annotations, AddMultiple) { Map map(view, fileSource, MapMode::Still); map.setStyleJSON(util::read_file("test/fixtures/api/empty.json"), ""); map.addAnnotationIcon("default_marker", namedMarker("default_marker.png")); - map.addPointAnnotation(PointAnnotation({ 0, -10 }, "default_marker")); + map.addAnnotation(SymbolAnnotation { Point<double> { -10, 0 }, "default_marker" }); test::render(map); - map.addPointAnnotation(PointAnnotation({ 0, 10 }, "default_marker")); + map.addAnnotation(SymbolAnnotation { Point<double> { 10, 0 }, "default_marker" }); checkRendering(map, "add_multiple"); } @@ -135,10 +134,10 @@ TEST(Annotations, NonImmediateAdd) { Polygon<double> polygon = {{ {{ { 0, 0 }, { 0, 45 }, { 45, 45 }, { 45, 0 } }} }}; - FillAnnotationProperties properties; - properties.color = {{ 255, 0, 0, 1 }}; + FillAnnotation annotation { polygon }; + annotation.color = {{ 255, 0, 0, 1 }}; - map.addShapeAnnotation(ShapeAnnotation(polygon, properties)); + map.addAnnotation(annotation); checkRendering(map, "non_immediate_add"); } @@ -153,7 +152,7 @@ TEST(Annotations, UpdateIcon) { Map map(view, fileSource, MapMode::Still); map.setStyleJSON(util::read_file("test/fixtures/api/empty.json"), ""); map.addAnnotationIcon("flipped_marker", namedMarker("default_marker.png")); - map.addPointAnnotation(PointAnnotation({ 0, 0 }, "flipped_marker")); + map.addAnnotation(SymbolAnnotation { Point<double> { 0, 0 }, "flipped_marker" }); test::render(map); @@ -175,11 +174,11 @@ TEST(Annotations, UpdatePoint) { map.setStyleJSON(util::read_file("test/fixtures/api/empty.json"), ""); map.addAnnotationIcon("default_marker", namedMarker("default_marker.png")); map.addAnnotationIcon("flipped_marker", namedMarker("flipped_marker.png")); - AnnotationID point = map.addPointAnnotation(PointAnnotation({ 0, 0 }, "default_marker")); + AnnotationID point = map.addAnnotation(SymbolAnnotation { Point<double> { 0, 0 }, "default_marker" }); test::render(map); - map.updatePointAnnotation(point, PointAnnotation({ 0, -10 }, "flipped_marker")); + map.updateAnnotation(point, SymbolAnnotation { Point<double> { -10, 0 }, "flipped_marker" }); checkRendering(map, "update_point"); } @@ -194,7 +193,7 @@ TEST(Annotations, RemovePoint) { Map map(view, fileSource, MapMode::Still); map.setStyleJSON(util::read_file("test/fixtures/api/empty.json"), ""); map.addAnnotationIcon("default_marker", namedMarker("default_marker.png")); - AnnotationID point = map.addPointAnnotation(PointAnnotation({ 0, 0 }, "default_marker")); + AnnotationID point = map.addAnnotation(SymbolAnnotation { Point<double> { 0, 0 }, "default_marker" }); test::render(map); @@ -212,13 +211,13 @@ TEST(Annotations, RemoveShape) { LineString<double> line = {{ { 0, 0 }, { 45, 45 } }}; - LineAnnotationProperties properties; - properties.color = {{ 255, 0, 0, 1 }}; - properties.width = 5; + LineAnnotation annotation { line }; + annotation.color = {{ 255, 0, 0, 1 }}; + annotation.width = 5; Map map(view, fileSource, MapMode::Still); map.setStyleJSON(util::read_file("test/fixtures/api/empty.json"), ""); - AnnotationID shape = map.addShapeAnnotation(ShapeAnnotation(line, properties)); + AnnotationID shape = map.addAnnotation(annotation); test::render(map); @@ -235,7 +234,7 @@ TEST(Annotations, ImmediateRemoveShape) { StubFileSource fileSource; Map map(view, fileSource, MapMode::Still); - map.removeAnnotation(map.addShapeAnnotation(ShapeAnnotation(LineString<double>(), {}))); + map.removeAnnotation(map.addAnnotation(LineAnnotation { LineString<double>() })); map.setStyleJSON(util::read_file("test/fixtures/api/empty.json"), ""); test::render(map); @@ -251,7 +250,7 @@ TEST(Annotations, SwitchStyle) { Map map(view, fileSource, MapMode::Still); map.setStyleJSON(util::read_file("test/fixtures/api/empty.json"), ""); map.addAnnotationIcon("default_marker", namedMarker("default_marker.png")); - map.addPointAnnotation(PointAnnotation({ 0, 0 }, "default_marker")); + map.addAnnotation(SymbolAnnotation { Point<double> { 0, 0 }, "default_marker" }); test::render(map); @@ -270,12 +269,11 @@ TEST(Annotations, QueryRenderedFeatures) { Map map(view, fileSource, MapMode::Still); map.setStyleJSON(util::read_file("test/fixtures/api/empty.json"), ""); map.addAnnotationIcon("default_marker", namedMarker("default_marker.png")); - const LatLng latLng(0, 0); - map.addPointAnnotation(PointAnnotation(latLng, "default_marker")); + map.addAnnotation(SymbolAnnotation { Point<double> { 0, 0 }, "default_marker" }); test::render(map); - auto point = map.pixelForLatLng(latLng); + auto point = map.pixelForLatLng({ 0, 0 }); auto features = map.queryRenderedFeatures(point); EXPECT_EQ(features.size(), 1); } diff --git a/test/style/source.cpp b/test/style/source.cpp index 622ec7ae7e..5023a9efea 100644 --- a/test/style/source.cpp +++ b/test/style/source.cpp @@ -16,6 +16,8 @@ #include <mbgl/layer/line_layer.hpp> #include <mbgl/annotation/annotation_manager.hpp> +#include <mapbox/geojsonvt.hpp> + using namespace mbgl; class SourceTest { |