When a use selects an annotation in a map, I show a bottom view with informations, such as the google maps app. I'm showing it in the map's delegate :
- (void)mapView:(MKMapView *)mapView didSelectAnnotationView:(MKAnnotationView *)view
When the user deselects it (by taping anywhere on the map), I hide my bottom view. This is done in the opposite delegate method :
- (void)mapView:(MKMapView *)mapView didDeselectAnnotationView:(MKAnnotationView *)view
It works well, I'm happy with it. However, if a user selects a second annotation (ie: he taps a first annotation, then taps another one, without deselecting first the annotation in the meantime), I don't want to hide my bottom view then show it again. I'd just like to change informations in it.
However, as mapView:didDeselectAnnotationView:
is called before mapView:didSelectAnnotationView:
, I can't figure out how to detect the situation I'm describing above.
My question is : how can I detect that a user selects a second annotation OR, how should I solve this problem in any other way ?
This can be accomplished without adding an explicit delay by executing asynchronously on the main queue.
var currentSelection: MKAnnotationView?
func mapView(_ mapView: MKMapView, didSelect view: MKAnnotationView) {
currentSelection = view
*** select code goes here ***
}
func mapView(_ mapView: MKMapView, didDeselect view: MKAnnotationView) {
DispatchQueue.main.async { [weak self] in
self?.delayedDeselect(view: view)
}
}
func delayedDeselect(view: MKAnnotationView) {
if currentSelection == view {
*** deselect code goes here ***
}
}
Maybe try put a delay in your didDeselectAnnotationView method to hide your bottomView. You need to store a reference to your last selected annotation view though.
Example:
@interface MyViewController
{
MKAnnotationView *lastSelectedAnnotationView;
}
@end
@implementation MyViewController
...
- (void)mapView:(MKMapView *)mapView didSelectAnnotationView:(MKAnnotationView *)view
{
...
[self updateBottomViewInfoWithAnnotationView:view];
lastSelectedAnnotationView = view;
}
- (void)mapView:(MKMapView *)mapView didDeselectAnnotationView:(MKAnnotationView *)view
{
// ------------------------------------------------------------------
// perform check to hide bottomView after a delay, to give
// didSelectAnnotationView a chance to select new annotation
// ------------------------------------------------------------------
[self performSelector:@selector(checkShouldHideBottomView:) withObject:view afterDelay:0.5];
}
-(void)checkShouldHideBottomView:(MKAnnotationView *)lastDeselectedAnnotationView
{
// ----------------------------------------------------------------------
// Only hide bottom view if user did not select a new annotation or
// last selected annotation is the same as the one being deselected
// ----------------------------------------------------------------------
if(lastSelectedAnnotationView == nil || lastDeselectedAnnotationView == lastSelectedAnnotationView)
{
// hide your bottom view example
self.bottomView.alpha = 0;
// clear lastSelectedAnnotationView reference
lastSelectedAnnotationView = nil;
}
}
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With