summaryrefslogtreecommitdiff
path: root/platform
diff options
context:
space:
mode:
Diffstat (limited to 'platform')
-rw-r--r--platform/darwin/src/MGLFeature.h28
-rw-r--r--platform/darwin/src/MGLFeature.mm263
-rw-r--r--platform/darwin/src/MGLFeature_Private.h4
3 files changed, 150 insertions, 145 deletions
diff --git a/platform/darwin/src/MGLFeature.h b/platform/darwin/src/MGLFeature.h
index 389b8ab67f..b593ff70e4 100644
--- a/platform/darwin/src/MGLFeature.h
+++ b/platform/darwin/src/MGLFeature.h
@@ -89,10 +89,6 @@ NS_ASSUME_NONNULL_BEGIN
<a href="https://www.mapbox.com/mapbox-gl-style-spec/#sources">tile source</a>.
*/
@interface MGLPointFeature : MGLPointAnnotation <MGLFeature>
-
-@property (nonatomic, copy, nullable, readwrite) id identifier;
-@property (nonatomic, copy, readwrite) NS_DICTIONARY_OF(NSString *, id) *attributes;
-
@end
/**
@@ -100,10 +96,6 @@ NS_ASSUME_NONNULL_BEGIN
<a href="https://www.mapbox.com/mapbox-gl-style-spec/#sources">tile source</a>.
*/
@interface MGLPolylineFeature : MGLPolyline <MGLFeature>
-
-@property (nonatomic, copy, nullable, readwrite) id identifier;
-@property (nonatomic, copy, readwrite) NS_DICTIONARY_OF(NSString *, id) *attributes;
-
@end
/**
@@ -111,10 +103,6 @@ NS_ASSUME_NONNULL_BEGIN
<a href="https://www.mapbox.com/mapbox-gl-style-spec/#sources">tile source</a>.
*/
@interface MGLPolygonFeature : MGLPolygon <MGLFeature>
-
-@property (nonatomic, copy, nullable, readwrite) id identifier;
-@property (nonatomic, copy, readwrite) NS_DICTIONARY_OF(NSString *, id) *attributes;
-
@end
/**
@@ -122,10 +110,6 @@ NS_ASSUME_NONNULL_BEGIN
<a href="https://www.mapbox.com/mapbox-gl-style-spec/#sources">tile source</a>.
*/
@interface MGLMultiPointFeature : MGLMultiPoint <MGLFeature>
-
-@property (nonatomic, copy, nullable, readwrite) id identifier;
-@property (nonatomic, copy, readwrite) NS_DICTIONARY_OF(NSString *, id) *attributes;
-
@end
/**
@@ -133,10 +117,6 @@ NS_ASSUME_NONNULL_BEGIN
<a href="https://www.mapbox.com/mapbox-gl-style-spec/#sources">tile source</a>.
*/
@interface MGLMultiPolylineFeature : MGLMultiPolyline <MGLFeature>
-
-@property (nonatomic, copy, nullable, readwrite) id identifier;
-@property (nonatomic, copy, readwrite) NS_DICTIONARY_OF(NSString *, id) *attributes;
-
@end
/**
@@ -144,10 +124,6 @@ NS_ASSUME_NONNULL_BEGIN
<a href="https://www.mapbox.com/mapbox-gl-style-spec/#sources">tile source</a>.
*/
@interface MGLMultiPolygonFeature : MGLMultiPolygon <MGLFeature>
-
-@property (nonatomic, copy, nullable, readwrite) id identifier;
-@property (nonatomic, copy, readwrite) NS_DICTIONARY_OF(NSString *, id) *attributes;
-
@end
/**
@@ -155,10 +131,6 @@ NS_ASSUME_NONNULL_BEGIN
<a href="https://www.mapbox.com/mapbox-gl-style-spec/#sources">tile source</a>.
*/
@interface MGLShapeCollectionFeature : MGLShapeCollection <MGLFeature>
-
-@property (nonatomic, copy, nullable, readwrite) id identifier;
-@property (nonatomic, copy, readwrite) NS_DICTIONARY_OF(NSString *, id) *attributes;
-
@end
NS_ASSUME_NONNULL_END
diff --git a/platform/darwin/src/MGLFeature.mm b/platform/darwin/src/MGLFeature.mm
index 68c57a193a..3e60b2061b 100644
--- a/platform/darwin/src/MGLFeature.mm
+++ b/platform/darwin/src/MGLFeature.mm
@@ -6,10 +6,116 @@
#import "MGLMultiPoint_Private.h"
+@protocol MGLFeaturePrivate <MGLFeature>
+
+@property (nonatomic, copy, nullable, readwrite) id identifier;
+@property (nonatomic, copy, readwrite) NS_DICTIONARY_OF(NSString *, id) *attributes;
+
+@end
+
+@interface MGLPointFeature () <MGLFeaturePrivate>
+@end
+
+@implementation MGLPointFeature
+
+@synthesize identifier;
+@synthesize attributes;
+
+- (id)attributeForKey:(NSString *)key {
+ return self.attributes[key];
+}
+
+@end
+
+@interface MGLPolylineFeature () <MGLFeaturePrivate>
+@end
+
+@implementation MGLPolylineFeature
+
+@synthesize identifier;
+@synthesize attributes;
+
+- (id)attributeForKey:(NSString *)key {
+ return self.attributes[key];
+}
+
+@end
+
+@interface MGLPolygonFeature () <MGLFeaturePrivate>
+@end
+
+@implementation MGLPolygonFeature
+
+@synthesize identifier;
+@synthesize attributes;
+
+- (id)attributeForKey:(NSString *)key {
+ return self.attributes[key];
+}
+
+@end
+
+@interface MGLMultiPointFeature () <MGLFeaturePrivate>
+@end
+
+@implementation MGLMultiPointFeature
+
+@synthesize identifier;
+@synthesize attributes;
+
+- (id)attributeForKey:(NSString *)key {
+ return self.attributes[key];
+}
+
+@end
+
+@interface MGLMultiPolylineFeature () <MGLFeaturePrivate>
+@end
+
+@implementation MGLMultiPolylineFeature
+
+@synthesize identifier;
+@synthesize attributes;
+
+- (id)attributeForKey:(NSString *)key {
+ return self.attributes[key];
+}
+
+@end
+
+@interface MGLMultiPolygonFeature () <MGLFeaturePrivate>
+@end
+
+@implementation MGLMultiPolygonFeature
+
+@synthesize identifier;
+@synthesize attributes;
+
+- (id)attributeForKey:(NSString *)key {
+ return self.attributes[key];
+}
+
+@end
+
+@interface MGLShapeCollectionFeature () <MGLFeaturePrivate>
+@end
+
+@implementation MGLShapeCollectionFeature
+
+@synthesize identifier;
+@synthesize attributes;
+
+- (id)attributeForKey:(NSString *)key {
+ return self.attributes[key];
+}
+
+@end
+
+/**
+ Recursively transforms a C++ type into the corresponding Foundation type.
+ */
class PropertyValueEvaluator {
public:
- PropertyValueEvaluator() {}
-
id operator()(const std::nullptr_t &) const {
return [NSNull null];
}
@@ -37,10 +143,9 @@ public:
id operator()(const std::vector<mbgl::Value> &values) const {
std::vector<id> objects;
objects.reserve(values.size());
- std::transform(values.begin(), values.end(), std::back_inserter(objects), ^id (const mbgl::Value &value) {
- PropertyValueEvaluator evaluator;
- return mbgl::Value::visit(value, evaluator);
- });
+ for (const auto &v : values) {
+ objects.push_back(mbgl::Value::visit(v, *this));
+ }
return [NSArray arrayWithObjects:&objects[0] count:objects.size()];
}
@@ -51,49 +156,34 @@ public:
objects.reserve(items.size());
for (auto &item : items) {
keys.push_back(@(item.first.c_str()));
- PropertyValueEvaluator evaluator;
- objects.push_back(mbgl::Value::visit(item.second, evaluator));
+ objects.push_back(mbgl::Value::visit(item.second, *this));
}
return [NSDictionary dictionaryWithObjects:&objects[0] forKeys:&keys[0] count:keys.size()];
}
};
+/**
+ Transforms an `mbgl::geometry::geometry` type into an instance of the
+ corresponding Objective-C geometry class.
+ */
template <typename T>
class GeometryEvaluator {
public:
- GeometryEvaluator()
- : attributes([NSMutableDictionary dictionary]) {}
-
- GeometryEvaluator(const mbgl::Feature &feature)
- : tag(feature.id ? @(*feature.id) : nullptr),
- attributes([NSMutableDictionary dictionaryWithCapacity:feature.properties.size()]) {
- for (auto &pair : feature.properties) {
- auto &value = pair.second;
- PropertyValueEvaluator evaluator;
- attributes[@(pair.first.c_str())] = mbgl::Value::visit(value, evaluator);
- }
- }
-
- MGLShape <MGLFeature> * operator()(const mapbox::geometry::point<T> &geometry) const {
+ MGLShape <MGLFeaturePrivate> * operator()(const mapbox::geometry::point<T> &geometry) const {
MGLPointFeature *feature = [[MGLPointFeature alloc] init];
feature.coordinate = coordinateFromPoint(geometry);
- feature.identifier = tag;
- feature.attributes = attributes;
return feature;
}
- MGLShape <MGLFeature> * operator()(const mapbox::geometry::line_string<T> &geometry) const {
+ MGLShape <MGLFeaturePrivate> * operator()(const mapbox::geometry::line_string<T> &geometry) const {
std::vector<CLLocationCoordinate2D> coordinates;
coordinates.reserve(geometry.size());
std::transform(geometry.begin(), geometry.end(), std::back_inserter(coordinates), coordinateFromPoint);
- MGLPolylineFeature *feature = [[MGLPolylineFeature alloc] initWithCoordinates:&coordinates[0] count:coordinates.size()];
- feature.identifier = tag;
- feature.attributes = attributes;
- return feature;
+ return [[MGLPolylineFeature alloc] initWithCoordinates:&coordinates[0] count:coordinates.size()];
}
- MGLShape <MGLFeature> * operator()(const mapbox::geometry::polygon<T> &geometry) const {
+ MGLShape <MGLFeaturePrivate> * operator()(const mapbox::geometry::polygon<T> &geometry) const {
// TODO: MGLPolygon doesn’t support holes, so what to do?
auto &linearRing = geometry.front();
@@ -101,24 +191,18 @@ public:
coordinates.reserve(linearRing.size());
std::transform(linearRing.begin(), linearRing.end(), std::back_inserter(coordinates), coordinateFromPoint);
- MGLPolygonFeature *feature = [[MGLPolygonFeature alloc] initWithCoordinates:&coordinates[0] count:coordinates.size()];
- feature.identifier = tag;
- feature.attributes = attributes;
- return feature;
+ return [[MGLPolygonFeature alloc] initWithCoordinates:&coordinates[0] count:coordinates.size()];
}
- MGLShape <MGLFeature> * operator()(const mapbox::geometry::multi_point<T> &geometry) const {
+ MGLShape <MGLFeaturePrivate> * operator()(const mapbox::geometry::multi_point<T> &geometry) const {
std::vector<CLLocationCoordinate2D> coordinates;
coordinates.reserve(geometry.size());
std::transform(geometry.begin(), geometry.end(), std::back_inserter(coordinates), coordinateFromPoint);
- MGLMultiPointFeature *feature = [[MGLMultiPointFeature alloc] initWithCoordinates:&coordinates[0] count:coordinates.size()];
- feature.identifier = tag;
- feature.attributes = attributes;
- return feature;
+ return [[MGLMultiPointFeature alloc] initWithCoordinates:&coordinates[0] count:coordinates.size()];
}
- MGLShape <MGLFeature> * operator()(const mapbox::geometry::multi_line_string<T> &geometry) const {
+ MGLShape <MGLFeaturePrivate> * operator()(const mapbox::geometry::multi_line_string<T> &geometry) const {
NSMutableArray *polylines = [NSMutableArray arrayWithCapacity:geometry.size()];
for (auto &lineString : geometry) {
std::vector<CLLocationCoordinate2D> coordinates;
@@ -129,13 +213,10 @@ public:
[polylines addObject:polyline];
}
- MGLMultiPolylineFeature *feature = [MGLMultiPolylineFeature multiPolylineWithPolylines:polylines];
- feature.identifier = tag;
- feature.attributes = attributes;
- return feature;
+ return [MGLMultiPolylineFeature multiPolylineWithPolylines:polylines];
}
- MGLShape <MGLFeature> * operator()(const mapbox::geometry::multi_polygon<T> &geometry) const {
+ MGLShape <MGLFeaturePrivate> * operator()(const mapbox::geometry::multi_polygon<T> &geometry) const {
NSMutableArray *polygons = [NSMutableArray arrayWithCapacity:geometry.size()];
for (auto &polygon : geometry) {
// TODO: MGLPolygon doesn’t support holes, so what to do?
@@ -149,29 +230,21 @@ public:
[polygons addObject:polygonObject];
}
- MGLMultiPolygonFeature *feature = [MGLMultiPolygonFeature multiPolygonWithPolygons:polygons];
- feature.identifier = tag;
- feature.attributes = attributes;
- return feature;
+ return [MGLMultiPolygonFeature multiPolygonWithPolygons:polygons];
}
- MGLShape <MGLFeature> * operator()(const mapbox::geometry::geometry_collection<T> &collection) const {
+ MGLShape <MGLFeaturePrivate> * operator()(const mapbox::geometry::geometry_collection<T> &collection) const {
NSMutableArray *shapes = [NSMutableArray arrayWithCapacity:collection.size()];
for (auto &geometry : collection) {
+ // This is very much like the transformation that happens in MGLFeaturesFromMBGLFeatures(), but these are raw geometries with no associated feature IDs or attributes.
GeometryEvaluator<T> evaluator;
- id <MGLFeature> feature = mapbox::geometry::geometry<T>::visit(geometry, evaluator);
- [shapes addObject:feature];
+ MGLShape <MGLFeaturePrivate> *shape = mapbox::geometry::geometry<T>::visit(geometry, evaluator);
+ [shapes addObject:shape];
}
- MGLShapeCollectionFeature *feature = [MGLShapeCollectionFeature shapeCollectionWithShapes:shapes];
- feature.identifier = tag;
- feature.attributes = attributes;
- return feature;
+ return [MGLShapeCollectionFeature shapeCollectionWithShapes:shapes];
}
private:
- NSNumber *tag = nullptr;
- NS_MUTABLE_DICTIONARY_OF(NSString *, id) *attributes;
-
static CLLocationCoordinate2D coordinateFromPoint(const mapbox::geometry::point<T> &point) {
return CLLocationCoordinate2DMake(point.y, point.x);
}
@@ -181,64 +254,20 @@ NS_ARRAY_OF(MGLShape <MGLFeature> *) *MGLFeaturesFromMBGLFeatures(const std::vec
std::vector<MGLShape <MGLFeature> *> shapes;
shapes.reserve(features.size());
std::transform(features.begin(), features.end(), std::back_inserter(shapes), ^MGLShape <MGLFeature> * (const mbgl::Feature &feature) {
- GeometryEvaluator<double> evaluator(feature);
- return mapbox::geometry::geometry<double>::visit(feature.geometry, evaluator);
+ NSMutableDictionary *attributes = [NSMutableDictionary dictionaryWithCapacity:feature.properties.size()];
+ for (auto &pair : feature.properties) {
+ auto &value = pair.second;
+ PropertyValueEvaluator evaluator;
+ attributes[@(pair.first.c_str())] = mbgl::Value::visit(value, evaluator);
+ }
+
+ GeometryEvaluator<double> evaluator;
+ MGLShape <MGLFeaturePrivate> *shape = mapbox::geometry::geometry<double>::visit(feature.geometry, evaluator);
+ if (feature.id) {
+ shape.identifier = @(*feature.id);
+ }
+ shape.attributes = attributes;
+ return shape;
});
return [NSArray arrayWithObjects:&shapes[0] count:shapes.size()];
}
-
-@implementation MGLPointFeature
-
-- (id)attributeForKey:(NSString *)key {
- return self.attributes[key];
-}
-
-@end
-
-@implementation MGLPolylineFeature
-
-- (id)attributeForKey:(NSString *)key {
- return self.attributes[key];
-}
-
-@end
-
-@implementation MGLPolygonFeature
-
-- (id)attributeForKey:(NSString *)key {
- return self.attributes[key];
-}
-
-@end
-
-@implementation MGLMultiPointFeature
-
-- (id)attributeForKey:(NSString *)key {
- return self.attributes[key];
-}
-
-@end
-
-@implementation MGLMultiPolylineFeature
-
-- (id)attributeForKey:(NSString *)key {
- return self.attributes[key];
-}
-
-@end
-
-@implementation MGLMultiPolygonFeature
-
-- (id)attributeForKey:(NSString *)key {
- return self.attributes[key];
-}
-
-@end
-
-@implementation MGLShapeCollectionFeature
-
-- (id)attributeForKey:(NSString *)key {
- return self.attributes[key];
-}
-
-@end
diff --git a/platform/darwin/src/MGLFeature_Private.h b/platform/darwin/src/MGLFeature_Private.h
index 837461871e..fbc7f88559 100644
--- a/platform/darwin/src/MGLFeature_Private.h
+++ b/platform/darwin/src/MGLFeature_Private.h
@@ -4,4 +4,8 @@
#import <mbgl/util/geo.hpp>
#import <mbgl/util/feature.hpp>
+/**
+ Returns an array of `MGLFeature` objects converted from the given vector of
+ vector tile features.
+ */
NS_ARRAY_OF(MGLShape <MGLFeature> *) *MGLFeaturesFromMBGLFeatures(const std::vector<mbgl::Feature> &features);