bdesham bdesham - 6 months ago 68
iOS Question

Allow tapping anywhere on an annotation callout without a callout accessory view

I have a map view that adds annotations more or less like this:

- (MKAnnotationView *)mapView:(MKMapView *)mapView
viewForAnnotation:(id <MKAnnotation>) annotation
MKAnnotationView *annotationView = [[MKPinAnnotationView alloc] initWithAnnotation:annotation
annotationView.canShowCallout = YES;

UIButton *detailButton = [UIButton buttonWithType:UIButtonTypeDetailDisclosure];
[detailButton addTarget:self
annotationView.rightCalloutAccessoryView = detailButton;

return annotationView;

In iOS 7, this puts an “i” icon on the right-hand side of the callout. Tapping on the icon triggers
(on the delegate) and
(on self). I recently realized, though, that you can also tap anywhere else on the callout and the same two methods are fired.

This happens with a button of type
but it doesn’t seem to happen with a
button. The delegate method is also not fired when I tap on the callout when there’s no accessory view at all. (That behavior isn’t surprising, of course; what’s surprising is that if the accessory view is a detail-disclosure button then these two methods are fired regardless of whether you tap on the button itself or just somewhere else in the callout.)

I’d like to get rid of the button in the callout—or at least replace it with a button showing my own image instead of the stock “i” icon—while still allowing the user to tap anywhere on the callout to trigger my action. Is this possible? I don’t see an
method that corresponds to “callout tapped”.


Try to set custom image for button without changing UIButtonTypeDetailDisclosure type.

UIButton *detailButton = [UIButton buttonWithType:UIButtonTypeDetailDisclosure];        
[detailButton setImage:[UIImage imageNamed:@"icon"] forState:UIControlStateNormal];

For iOS7 this image will be tinted by default. If you want to keep original icon use the following

[[UIImage imageNamed:@"icon"] imageWithRenderingMode:UIImageRenderingModeAlwaysOriginal]

Or if you want to remove icon at all

[detailButton setImage:[UIImage new] forState:UIControlStateNormal];