summaryrefslogtreecommitdiff
path: root/platform/ios/src/MGLMapView.mm
diff options
context:
space:
mode:
Diffstat (limited to 'platform/ios/src/MGLMapView.mm')
-rw-r--r--platform/ios/src/MGLMapView.mm99
1 files changed, 80 insertions, 19 deletions
diff --git a/platform/ios/src/MGLMapView.mm b/platform/ios/src/MGLMapView.mm
index d2496d8627..90a67840fe 100644
--- a/platform/ios/src/MGLMapView.mm
+++ b/platform/ios/src/MGLMapView.mm
@@ -41,6 +41,8 @@
#import "MGLMultiPoint_Private.h"
#import "MGLOfflineStorage_Private.h"
#import "MGLFoundation_Private.h"
+#import "MGLCameraChangeReason_Private.h"
+
#import "MGLRendererFrontend.h"
#import "MGLRendererConfiguration.h"
@@ -209,7 +211,9 @@ public:
@property (nonatomic) UILongPressGestureRecognizer *quickZoom;
@property (nonatomic) UIPanGestureRecognizer *twoFingerDrag;
-@property (nonatomic) MGLCameraChangeReason cameraChangeReason;
+/// Camera change reason handling.
+@property (nonatomic) MGLCameraChangeReasonBitmask cameraChangeReasonBitmask;
+@property (nonatomic, readonly) MGLCameraChangeReason cameraChangeReason;
/// Mapping from reusable identifiers to annotation images.
@property (nonatomic) NS_MUTABLE_DICTIONARY_OF(NSString *, MGLAnnotationImage *) *annotationImagesByIdentifier;
@@ -555,7 +559,7 @@ public:
options.padding = padding;
options.zoom = 0;
- _cameraChangeReason = MGLCameraChangeReasonNone;
+ _cameraChangeReasonBitmask = MGLCameraChangeReasonBitmaskNone;
_mbglMap->jumpTo(options);
_pendingLatitude = NAN;
@@ -1243,7 +1247,7 @@ public:
- (void)handleCompassTapGesture:(__unused id)sender
{
- self.cameraChangeReason |= MGLCameraChangeReasonResetNorth;
+ self.cameraChangeReasonBitmask |= MGLCameraChangeReasonBitmaskResetNorth;
[self resetNorthAnimated:YES];
@@ -1296,6 +1300,8 @@ public:
// Check delegates first
if ([self.delegate respondsToSelector:@selector(mapView:shouldChangeFromCamera:toCamera:reason:)])
{
+
+
return [self.delegate mapView:self shouldChangeFromCamera:oldCamera toCamera:newCamera reason:self.cameraChangeReason];
}
else if ([self.delegate respondsToSelector:@selector(mapView:shouldChangeFromCamera:toCamera:)])
@@ -1316,7 +1322,7 @@ public:
MGLMapCamera *oldCamera = self.camera;
- self.cameraChangeReason |= MGLCameraChangeReasonGesturePan;
+ self.cameraChangeReasonBitmask |= MGLCameraChangeReasonGesturePan;
if (pan.state == UIGestureRecognizerStateBegan)
{
@@ -1386,7 +1392,7 @@ public:
CGPoint centerPoint = [self anchorPointForGesture:pinch];
MGLMapCamera *oldCamera = self.camera;
- self.cameraChangeReason |= MGLCameraChangeReasonGesturePinch;
+ self.cameraChangeReasonBitmask |= MGLCameraChangeReasonBitmaskGesturePinch;
if (pinch.state == UIGestureRecognizerStateBegan)
{
@@ -1485,7 +1491,7 @@ public:
CGPoint centerPoint = [self anchorPointForGesture:rotate];
MGLMapCamera *oldCamera = self.camera;
- self.cameraChangeReason |= MGLCameraChangeReasonGestureRotate;
+ self.cameraChangeReasonBitmask |= MGLCameraChangeReasonGestureRotate;
if (rotate.state == UIGestureRecognizerStateBegan)
{
@@ -1671,7 +1677,7 @@ public:
if (doubleTap.state == UIGestureRecognizerStateEnded)
{
- self.cameraChangeReason |= MGLCameraChangeReasonGestureZoomIn;
+ self.cameraChangeReasonBitmask |= MGLCameraChangeReasonBitmaskGestureZoomIn;
MGLMapCamera *oldCamera = self.camera;
@@ -1708,7 +1714,7 @@ public:
_mbglMap->cancelTransitions();
- self.cameraChangeReason |= MGLCameraChangeReasonGestureZoomOut;
+ self.cameraChangeReasonBitmask |= MGLCameraChangeReasonBitmaskGestureZoomOut;
if (twoFingerTap.state == UIGestureRecognizerStateBegan)
{
@@ -1747,7 +1753,7 @@ public:
_mbglMap->cancelTransitions();
- self.cameraChangeReason |= MGLCameraChangeReasonGestureQuickZoom;
+ self.cameraChangeReasonBitmask |= MGLCameraChangeReasonBitmaskGestureOneFingerZoom;
if (quickZoom.state == UIGestureRecognizerStateBegan)
{
@@ -1792,7 +1798,7 @@ public:
_mbglMap->cancelTransitions();
- self.cameraChangeReason |= MGLCameraChangeReasonGesturePitch;
+ self.cameraChangeReasonBitmask |= MGLCameraChangeReasonBitmaskGestureTwoFingerDrag;
if (twoFingerDrag.state == UIGestureRecognizerStateBegan)
{
@@ -1980,6 +1986,7 @@ public:
- (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldRecognizeSimultaneouslyWithGestureRecognizer:(UIGestureRecognizer *)otherGestureRecognizer
{
+ // If you update these, please check to see if `-cameraChangeReason` needs updating.
NSArray *validSimultaneousGestures = @[ self.pan, self.pinch, self.rotate ];
return ([validSimultaneousGestures containsObject:gestureRecognizer] && [validSimultaneousGestures containsObject:otherGestureRecognizer]);
@@ -2889,7 +2896,7 @@ public:
{
self.userTrackingMode = MGLUserTrackingModeNone;
- self.cameraChangeReason |= MGLCameraChangeReasonProgrammatic;
+ self.cameraChangeReasonBitmask |= MGLCameraChangeReasonBitmaskProgrammatic;
[self _setCenterCoordinate:centerCoordinate edgePadding:self.contentInset zoomLevel:zoomLevel direction:direction duration:animated ? MGLAnimationDuration : 0 animationTimingFunction:nil completionHandler:completion];
}
@@ -2941,7 +2948,7 @@ public:
_mbglMap->cancelTransitions();
- self.cameraChangeReason |= MGLCameraChangeReasonProgrammatic;
+ self.cameraChangeReasonBitmask |= MGLCameraChangeReasonBitmaskProgrammatic;
_mbglMap->easeTo(cameraOptions, animationOptions);
}
@@ -2966,7 +2973,7 @@ public:
if (zoomLevel == self.zoomLevel) return;
_mbglMap->cancelTransitions();
- self.cameraChangeReason |= MGLCameraChangeReasonProgrammatic;
+ self.cameraChangeReasonBitmask |= MGLCameraChangeReasonBitmaskProgrammatic;
CGFloat duration = animated ? MGLAnimationDuration : 0;
@@ -3057,7 +3064,7 @@ public:
{
self.userTrackingMode = MGLUserTrackingModeNone;
- self.cameraChangeReason |= MGLCameraChangeReasonProgrammatic;
+ self.cameraChangeReasonBitmask |= MGLCameraChangeReasonBitmaskProgrammatic;
[self _setVisibleCoordinates:coordinates count:count edgePadding:insets direction:direction duration:duration animationTimingFunction:function completionHandler:completion];
}
@@ -3109,7 +3116,7 @@ public:
[self willChangeValueForKey:@"visibleCoordinateBounds"];
_mbglMap->cancelTransitions();
- self.cameraChangeReason |= MGLCameraChangeReasonProgrammatic;
+ self.cameraChangeReasonBitmask |= MGLCameraChangeReasonBitmaskProgrammatic;
_mbglMap->easeTo(cameraOptions, animationOptions);
[self didChangeValueForKey:@"visibleCoordinateBounds"];
@@ -3144,7 +3151,7 @@ public:
CGFloat duration = animated ? MGLAnimationDuration : 0;
- self.cameraChangeReason |= MGLCameraChangeReasonProgrammatic;
+ self.cameraChangeReasonBitmask |= MGLCameraChangeReasonBitmaskProgrammatic;
if (self.userTrackingMode == MGLUserTrackingModeNone)
{
@@ -3231,7 +3238,7 @@ public:
[self willChangeValueForKey:@"camera"];
_mbglMap->cancelTransitions();
- self.cameraChangeReason |= MGLCameraChangeReasonProgrammatic;
+ self.cameraChangeReasonBitmask |= MGLCameraChangeReasonBitmaskProgrammatic;
mbgl::CameraOptions cameraOptions = [self cameraOptionsObjectForAnimatingToCamera:camera edgePadding:edgePadding];
_mbglMap->easeTo(cameraOptions, animationOptions);
@@ -3290,7 +3297,7 @@ public:
[self willChangeValueForKey:@"camera"];
_mbglMap->cancelTransitions();
- self.cameraChangeReason |= MGLCameraChangeReasonProgrammatic;
+ self.cameraChangeReasonBitmask |= MGLCameraChangeReasonBitmaskProgrammatic;
mbgl::CameraOptions cameraOptions = [self cameraOptionsObjectForAnimatingToCamera:camera edgePadding:insets];
_mbglMap->flyTo(cameraOptions, animationOptions);
@@ -3456,9 +3463,61 @@ public:
- (void)resetCameraChangeReason
{
- self.cameraChangeReason = MGLCameraChangeReasonNone;
+ self.cameraChangeReasonBitmask = MGLCameraChangeReasonBitmaskNone;
+}
+
+- (MGLCameraChangeReason)cameraChangeReason
+{
+ static NSDictionary *reasonMap = nil;
+
+ static dispatch_once_t onceToken;
+ dispatch_once(&onceToken, ^{
+ reasonMap =
+ @{
+ // Pan, Rotate and Pinch can all be recognized simultaneously
+ @(MGLCameraChangeReasonBitmaskGesturePan) : @(MGLCameraChangeReasonGesturePan),
+ @(MGLCameraChangeReasonBitmaskGestureRotate) : @(MGLCameraChangeReasonGestureRotate),
+ @(MGLCameraChangeReasonBitmaskGesturePinch) : @(MGLCameraChangeReasonGestureZoom),
+
+ @(MGLCameraChangeReasonBitmaskGesturePan|MGLCameraChangeReasonBitmaskGestureRotate) : @(MGLCameraChangeReasonGesturePanAndRotate),
+ @(MGLCameraChangeReasonBitmaskGesturePan|MGLCameraChangeReasonBitmaskGesturePinch) : @(MGLCameraChangeReasonGesturePanAndZoom),
+ @(MGLCameraChangeReasonBitmaskGestureRotate|MGLCameraChangeReasonBitmaskGesturePinch) : @(MGLCameraChangeReasonGestureRotateAndZoom),
+
+ @(MGLCameraChangeReasonBitmaskGesturePan|MGLCameraChangeReasonBitmaskGestureRotate|MGLCameraChangeReasonBitmaskGesturePinch) : @(MGLCameraChangeReasonGesturePanRotateAndZoom),
+
+ // Tilt
+ @(MGLCameraChangeReasonBitmaskGestureTwoFingerDrag) : @(MGLCameraChangeReasonGestureTilt),
+
+ // Custom gestures that can map to existing reasons
+ @(MGLCameraChangeReasonBitmaskResetNorth|MGLCameraChangeReasonBitmaskProgrammatic) : @(MGLCameraChangeReasonGestureRotate),
+ @(MGLCameraChangeReasonBitmaskGestureZoomIn) : @(MGLCameraChangeReasonGestureZoom),
+ @(MGLCameraChangeReasonBitmaskGestureZoomOut) : @(MGLCameraChangeReasonGestureZoom),
+ @(MGLCameraChangeReasonBitmaskGestureOneFingerZoom) : @(MGLCameraChangeReasonGestureZoom),
+ };
+ });
+
+ // For the end user we provide an enum for the change reason, so we need to map from our internal
+ // mask to this enum. We don't cover all possible combinations since only a subset of gestures
+ // can be recognized simultaneously. If you change -gestureRecognizer:shouldRecognizeSimultaneouslyWithGestureRecognizer:
+ // then please be sure to make sure this method is updated if necessary.
+
+ NSNumber *reason = reasonMap[@(self.cameraChangeReasonBitmask)];
+ if (reason)
+ {
+ return (MGLCameraChangeReason)[reason unsignedIntegerValue];
+ }
+ else if (self.cameraChangeReasonBitmask & MGLCameraChangeReasonBitmaskProgrammatic)
+ {
+ return MGLCameraChangeReasonProgrammatic;
+ }
+ else
+ {
+ NSAssert(0, @"Camera change reason: %ld missing from mapping table.", self.cameraChangeReasonBitmask);
+ return MGLCameraChangeReasonInvalid;
+ }
}
+
#pragma mark - Styling -
- (NS_ARRAY_OF(NSURL *) *)bundledStyleURLs
@@ -5467,6 +5526,8 @@ public:
if (respondsToSelectorWithReason)
{
+
+
[self.delegate mapView:self regionDidChangeWithReason:self.cameraChangeReason animated:animated];
}
else if (respondsToSelector)