summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJesse Bounds <jesse@rebounds.net>2016-06-28 12:07:12 -0700
committerGitHub <noreply@github.com>2016-06-28 12:07:12 -0700
commit16b859ff5f0463f27d7250bf1e82fa7236304285 (patch)
tree1148b6296cd9da9be5be947e0333d4815a205772
parentc96b7dae687f43a7ca233698554aa33eb3180f0a (diff)
downloadqtlocation-mapboxgl-16b859ff5f0463f27d7250bf1e82fa7236304285.tar.gz
[ios] Always set map view reference when annotation view is created. (#5496)
This fixes two issues with annotation views that were exposed when dragging them: 1) The annotation view's mapView property was not set until it was moved (in `updateAnnotations:`) so it did not always call its delegate back about the map view delegate dragging methods. This adds a call to set the property when an annotation view is created so the delegate methods are always called. 2) Since the mapView is now always set, a call to the map view's callout view for selected annotation was added to the annotation view drag handler. This forces the callout to close and eliminates an issue where the callout would remain visible as an annotation was dragged away which had the visual effect of a detached callout. To make 2 possible, the map views selected callout view was exposed in the private header.
-rw-r--r--platform/ios/src/MGLAnnotationView.mm7
-rw-r--r--platform/ios/src/MGLMapView.mm1
-rw-r--r--platform/ios/src/MGLMapView_Internal.h3
-rw-r--r--platform/ios/test/MGLAnnotationViewTests.m38
4 files changed, 42 insertions, 7 deletions
diff --git a/platform/ios/src/MGLAnnotationView.mm b/platform/ios/src/MGLAnnotationView.mm
index e086e3bde5..7068cdc0db 100644
--- a/platform/ios/src/MGLAnnotationView.mm
+++ b/platform/ios/src/MGLAnnotationView.mm
@@ -187,7 +187,7 @@
{
CGPoint center = [sender locationInView:sender.view.superview];
[self setCenter:center pitch:self.mapView.camera.pitch];
-
+
if (sender.state == UIGestureRecognizerStateEnded) {
self.dragState = MGLAnnotationViewDragStateNone;
}
@@ -206,9 +206,10 @@
if (dragState == MGLAnnotationViewDragStateStarting)
{
+ [self.mapView.calloutViewForSelectedAnnotation dismissCalloutAnimated:animated];
[self.superview bringSubviewToFront:self];
}
-
+
if (dragState == MGLAnnotationViewDragStateEnding)
{
if ([self.mapView.delegate respondsToSelector:@selector(mapView:didDragAnnotationView:toCoordinate:)])
@@ -231,7 +232,7 @@
{
return NO;
}
-
+
return YES;
}
diff --git a/platform/ios/src/MGLMapView.mm b/platform/ios/src/MGLMapView.mm
index 25cf23c878..cd41f41d21 100644
--- a/platform/ios/src/MGLMapView.mm
+++ b/platform/ios/src/MGLMapView.mm
@@ -3004,6 +3004,7 @@ mbgl::Duration MGLDurationInSeconds(NSTimeInterval duration)
if (annotationView)
{
annotationView.annotation = annotation;
+ annotationView.mapView = self;
CGRect bounds = UIEdgeInsetsInsetRect({ CGPointZero, annotationView.frame.size }, annotationView.alignmentRectInsets);
_largestAnnotationViewSize = CGSizeMake(MAX(_largestAnnotationViewSize.width, CGRectGetWidth(bounds)),
diff --git a/platform/ios/src/MGLMapView_Internal.h b/platform/ios/src/MGLMapView_Internal.h
index 6225e11749..9133aca857 100644
--- a/platform/ios/src/MGLMapView_Internal.h
+++ b/platform/ios/src/MGLMapView_Internal.h
@@ -5,6 +5,9 @@ extern const CGSize MGLAnnotationAccessibilityElementMinimumSize;
@interface MGLMapView (Internal)
+/// Currently shown popover representing the selected annotation.
+@property (nonatomic) UIView<MGLCalloutView> *calloutViewForSelectedAnnotation;
+
/** Triggers another render pass even when it is not necessary. */
- (void)setNeedsGLDisplay;
diff --git a/platform/ios/test/MGLAnnotationViewTests.m b/platform/ios/test/MGLAnnotationViewTests.m
index 541c43b5a1..6cc5698393 100644
--- a/platform/ios/test/MGLAnnotationViewTests.m
+++ b/platform/ios/test/MGLAnnotationViewTests.m
@@ -3,6 +3,17 @@
static NSString * const MGLTestAnnotationReuseIdentifer = @"MGLTestAnnotationReuseIdentifer";
+@interface MGLAnnotationView (Test)
+@property (nonatomic) MGLMapView *mapView;
+@property (nonatomic, readwrite) MGLAnnotationViewDragState dragState;
+
+- (void)setDragState:(MGLAnnotationViewDragState)dragState;
+@end
+
+@interface MGLMapView (Test)
+@property (nonatomic) UIView<MGLCalloutView> *calloutViewForSelectedAnnotation;
+@end
+
@interface MGLTestAnnotation : NSObject <MGLAnnotation>
@property (nonatomic, assign) CLLocationCoordinate2D coordinate;
@end
@@ -10,6 +21,19 @@ static NSString * const MGLTestAnnotationReuseIdentifer = @"MGLTestAnnotationReu
@implementation MGLTestAnnotation
@end
+@interface MGLTestCalloutView: UIView<MGLCalloutView>
+@property (nonatomic) BOOL didCallDismissCalloutAnimated;
+@end
+
+@implementation MGLTestCalloutView
+
+- (void)dismissCalloutAnimated:(BOOL)animated
+{
+ _didCallDismissCalloutAnimated = YES;
+}
+
+@end
+
@interface MGLAnnotationViewTests : XCTestCase <MGLMapViewDelegate>
@property (nonatomic) XCTestExpectation *expectation;
@property (nonatomic) MGLMapView *mapView;
@@ -28,15 +52,21 @@ static NSString * const MGLTestAnnotationReuseIdentifer = @"MGLTestAnnotationReu
- (void)testAnnotationView
{
_expectation = [self expectationWithDescription:@"annotation property"];
-
+
MGLTestAnnotation *annotation = [[MGLTestAnnotation alloc] init];
[_mapView addAnnotation:annotation];
-
+
[self waitForExpectationsWithTimeout:1 handler:nil];
-
+
XCTAssert(_mapView.annotations.count == 1, @"number of annotations should be 1");
XCTAssertNotNil(_annotationView.annotation, @"annotation property should not be nil");
-
+ XCTAssertNotNil(_annotationView.mapView, @"mapView property should not be nil");
+
+ MGLTestCalloutView *testCalloutView = [[MGLTestCalloutView alloc] init];
+ _mapView.calloutViewForSelectedAnnotation = testCalloutView;
+ _annotationView.dragState = MGLAnnotationViewDragStateStarting;
+ XCTAssertTrue(testCalloutView.didCallDismissCalloutAnimated, @"callout view was not dismissed");
+
[_mapView removeAnnotation:_annotationView.annotation];
XCTAssert(_mapView.annotations.count == 0, @"number of annotations should be 0");