-1

I am trying to use obj c library in swift but I am having issue with the following error:

fatal error: unexpectedly found nil while unwrapping an Optional value

I think that I am missing something in var annotationView:MKPinAnnotationView! declaration is wrong but can't find a way around.
Code is:

func mapView(mapView: MKMapView!, viewForAnnotation annotation: MKAnnotation!) -> MKAnnotationView! {
var annotationView:MKPinAnnotationView!

        if(annotation is KPAnnotation){

            var kingpinAnnotation = annotation as KPAnnotation

            if (kingpinAnnotation.isCluster()){

                annotationView = mapView.dequeueReusableAnnotationViewWithIdentifier("cluster") as MKPinAnnotationView // THIS IS THE ERROR LINE

                if (annotationView == nil) {
                    annotationView = MKPinAnnotationView(annotation: kingpinAnnotation, reuseIdentifier: "cluster")
                }

                annotationView.pinColor = .Purple;

            } else {

                annotationView = mapView.dequeueReusableAnnotationViewWithIdentifier("pin") as MKPinAnnotationView

                if (annotationView == nil) {
                    annotationView = MKPinAnnotationView(annotation: kingpinAnnotation, reuseIdentifier: "pin")

                }

                annotationView.pinColor = .Red;

            }

            annotationView.canShowCallout = true;

            return annotationView;
        }
1110
  • 7,829
  • 55
  • 176
  • 334
  • Could you please specify which rule produces the error? You unwrap multiple optionals. Which of the optionals you unwrap does matter to the answer :D – milo526 Mar 14 '15 at 10:30

1 Answers1

2

The "forced cast" as MKPinAnnotationView (to a non-optional type) aborts with a runtime exception if mapView.dequeueReusableAnnotationViewWithIdentifier() returns nil.

You can use an optional cast as? instead:

annotationView = mapView.dequeueReusableAnnotationViewWithIdentifier("cluster")
                      as? MKPinAnnotationView

which assigns nil to annotationView in that case.

If it is guaranteed that all elements in the reuse queue have the type MKPinAnnotationView then a cast to an implicitly unwrapped optional would work as well:

annotationView = mapView.dequeueReusableAnnotationViewWithIdentifier("cluster")
                      as MKPinAnnotationView!

but the first version is the safer one.

Martin R
  • 529,903
  • 94
  • 1,240
  • 1,382