3

I have a class MapItem which implements MKAnnotation protocol. I am using MKMarkerAnnotationView for displaying Annotations on map.

According to Documentation, glyphText property of MKMarkerAnnotationView when set to nil, it produces pin image on the marker.

When Clustering the annotation, I want the same pin image on the marker. But system by default sets this to the number of annotations clustered within this cluster.

I even tried setting this property to nil, but has no effect.

    func mapView(_ mapView: MKMapView, viewFor annotation: MKAnnotation) -> MKAnnotationView? {
    if let item = annotation as? MapItem {
        let annotationView = mapView.dequeueReusableAnnotationView(withIdentifier: "mapItem") as? MKMarkerAnnotationView
            ?? MKMarkerAnnotationView(annotation: annotation, reuseIdentifier: "mapItem")

        annotationView.annotation = item
        annotationView.glyphText = nil
        annotationView.clusteringIdentifier = "mapItemClustered"

        return annotationView
    } else if let cluster = annotation as? MKClusterAnnotation {
        let clusterView = mapView.dequeueReusableAnnotationView(withIdentifier: "clusterView") as? MKMarkerAnnotationView
            ?? MKMarkerAnnotationView(annotation: annotation, reuseIdentifier: "clusterView")

        clusterView.annotation = cluster
        clusterView.glyphText = nil

        return clusterView
    } else {
        return nil
    }
}
Gerd Castan
  • 6,275
  • 3
  • 44
  • 89
FE_Tech
  • 1,534
  • 13
  • 25
  • As far as I can tell MKMarkerAnnotationView is severely broken when clustering. There doesn't seem to be any way to change the glyphImage or glyphText. When using a plain old MKAnnotationView you can set a custom image, but the markers cannot be customized. Has anybody found a work around? – David Dec 27 '18 at 04:52

1 Answers1

1

This is how I do it:

class POIMarkerClusterView: MKMarkerAnnotationView {

    override var annotation: MKAnnotation? {
        willSet {
            update(newValue: newValue)
        }
    }

    private func update(newValue: MKAnnotation?) {
        if let cluster = newValue as? MKClusterAnnotation {

            self.image = POIClusterImage(poiStatistics: poiStatistics, count: count)

            // MKMarkerAnnotationView's default rendering usually hides our own image.
            // so we make it invisible:
            self.glyphText = ""
            self.glyphTintColor = UIColor.clear
            self.markerTintColor = UIColor.clear
        }
    }

}

This means you can set an arbitrary image that is rendered as the annotation view. I create the image dynamically, but you can just borrow the image from the MKMarkerAnnotationView and set it here, so it looks like the pin that you want.

The main trick is to use UIColor.clear to hide what you don't want to see.

Gerd Castan
  • 6,275
  • 3
  • 44
  • 89