Button Action in Mkannotation View Not Working

Button action in mkannotation view not working?

You need to set frame for this button. which is not really seen in the code. Adjust frame as you want by x position and y position.

UIButton *tembtn=[UIButton buttonWithType:UIButtonTypeCustom];

// Frame required to render on position and size. Add below line
[tembtn setFrame:CGRectMake(0, 0, 100, 50)];

[tembtn setTitle:@"More info" forState:UIControlStateNormal];
[tembtn addTarget:self action:@selector(annotationBtnAction:)
forControlEvents:UIControlEventTouchUpInside];
tembtn.backgroundColor=[UIColor grayColor];
[view addSubview:tembtn];

Edit:

Found the reason you can only tap on area, in which annotation is rendered.

Here is simple demo for custom call out:

Custom Callout Demo

Sample Image

Not getting button action/ Single tap on custom MKannotation call out view

Finally I got the answer. It;s here

Followed this tutorial. Really great solution.

https://github.com/nfarina/calloutview

Happy coding!!

How to add a button to an annotation, current solution not working

You need to add the delegate MKMapViewDelegate. And use the function,

func mapView(_ mapView: MKMapView, didSelect view: MKAnnotationView) {

}

MKAnnotationView Swift Adding Info button

Am using Xcode 8.1 and Swift 3.0 . For Some reason Delegate methods are not firing until you set delegate in storyboard:

func mapView(_ mapView: MKMapView, viewFor annotation: MKAnnotation) -> MKAnnotationView?
{
if annotation is MKUserLocation {return nil}

let reuseId = "pin"

var pinView = mapView.dequeueReusableAnnotationView(withIdentifier: reuseId) as? MKPinAnnotationView
if pinView == nil {
pinView = MKPinAnnotationView(annotation: annotation, reuseIdentifier: reuseId)
pinView!.canShowCallout = true
pinView!.animatesDrop = true
let calloutButton = UIButton(type: .DetailDisclosure)
pinView!.rightCalloutAccessoryView = calloutButton
pinView!.sizeToFit()
}
else {
pinView!.annotation = annotation
}

return pinView
}

for button Action

func mapView(_ mapView: MKMapView, annotationView view: MKAnnotationView, calloutAccessoryControlTapped control: UIControl) {
if control == view.rightCalloutAccessoryView {
print("button tapped")
}
}

I am attaching sample project for your issue

Map Sample Project Swift 3. 0 Xcode 8.1

UIButton Not Loading Properly For MKAnnotationView

Before the didSelectAnnotationView delegate method is called, the map view has already prepared the callout view based on the annotation view's properties (before your changes).

So the callout you see the on the first tap is without the changes the app makes in didSelectAnnotationView. On the following taps, the callout could be based on the values set from the previous tap (this actually depends on how annotation view re-use is handled in viewForAnnotation).

It looks like the only things the code is doing in didSelectAnnotationView and buttonForAnnotation is setting the button action and tag.

I assume you're using the "tag" approach because the presentAnnotationPhoto: method needs to reference the selected annotation's properties.

You don't need to use a tag to get the selected annotation in your action method. Instead, there are a couple of better options:

  • Your custom action method can get the selected annotation from the map view's selectedAnnotations property. See this question for an example of how to do this.
  • Use the map view's own delegate method calloutAccessoryControlTapped instead of a custom action method. The delegate method passes a reference to the annotation view which contains a property pointing to its annotation (ie. view.annotation) so there's no guessing, searching, or question as to what annotation was selected. I recommend this option.

In the first option, do the addTarget in viewForAnnotation and don't bother setting the tag. You also don't need the buttonForAnnotation method. Then in the button action method, get the selected annotation from mapView.selectedAnnotations.

Currently, your action method is on self.delegate so you might have some trouble accessing the map view from that other controller. What you can do is create a local button action method in the map controller which gets the selected annotation and then calls the presentAnnotationPhoto: action method on self.delegate (except now that method can be written to accept an annotation parameter instead of being a button tap handler).

The second option is similar except you don't need to do any addTarget and in the calloutAccessoryControlTapped method, call presentAnnotationPhoto: on self.delegate.

For both options, I suggest modifying the presentAnnotationPhoto: method to accept the annotation object itself (FlickrPhotoAnnotation *) instead of the current UIButton * and in the map controller, do an addTarget on a method local to the map controller (or use calloutAccessoryControlTapped) and from that method, manually call presentAnnotationPhoto: and pass it the annotation.



Related Topics



Leave a reply



Submit