7

私のアプリには現在、検索結果に注釈を追加するローカル検索があります。注釈を選択して吹き出しボタンをクリックすると、現在のデバイスの場所から注釈への道順がマップ アプリケーションで表示されるように設定したいと考えています。これにはいくつか問題があります。

まず、注釈の呼び出しボタンが表示されません。第二に、選択した注釈を正しく検出しているとは思いません。

検索と選択した注釈のコードは次のとおりです。

func performSearch() {

    matchingItems.removeAll()
    let request = MKLocalSearchRequest()
    request.naturalLanguageQuery = searchText.text
    request.region = mapView.region

    let search = MKLocalSearch(request: request)

    search.startWithCompletionHandler({(response:
        MKLocalSearchResponse!,
        error: NSError!) in

        if error != nil {
            println("Error occured in search: \(error.localizedDescription)")
        } else if response.mapItems.count == 0 {
            println("No matches found")
        } else {
            println("Matches found")

            for item in response.mapItems as! [MKMapItem] {
                println("Name = \(item.name)")
                println("Phone = \(item.phoneNumber)")

                self.matchingItems.append(item as MKMapItem)
                println("Matching items = \(self.matchingItems.count)")

                var annotation = MKPointAnnotation()
                var coordinates = annotation.coordinate
                annotation.coordinate = item.placemark.coordinate
                annotation.title = item.name
                self.mapView.addAnnotation(annotation)

            }
        }
    })
}



func mapView(mapView: MKMapView!, annotationView view: MKAnnotationView!,
    calloutAccessoryControlTapped control: UIControl!) {

        if self.mapView.selectedAnnotations?.count > 0 {

            if let selectedLoc = self.mapView.selectedAnnotations[0] as? MKAnnotation {
                println("Annotation has been selected")
                let currentLoc = MKMapItem.mapItemForCurrentLocation()
                let mapItems = NSArray(objects: selectedLoc, currentLoc)
                let launchOptions = [MKLaunchOptionsDirectionsModeKey: MKLaunchOptionsDirectionsModeDriving]
                MKMapItem.openMapsWithItems([selectedLoc, currentLoc], launchOptions: launchOptions)
            }
        }

}

事前に感謝します。

4

1 に答える 1

6

最初の問題の場合:

吹き出しボタンはデリゲート メソッドで明示的に設定する必要がありますviewForAnnotation(既定の赤いピンにはありません)。考えられる実装の簡単な例を次に示します。

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

    if annotation is MKUserLocation {
        return nil
    }

    let reuseId = "pin"

    var pinView = mapView.dequeueReusableAnnotationViewWithIdentifier(reuseId) as? MKPinAnnotationView
    if pinView == nil {
        pinView = MKPinAnnotationView(annotation: annotation, reuseIdentifier: reuseId)
        pinView!.canShowCallout = true
        pinView!.pinColor = .Purple

        //next line sets a button for the right side of the callout...
        pinView!.rightCalloutAccessoryView = UIButton.buttonWithType(.DetailDisclosure) as! UIButton
    }
    else {
        pinView!.annotation = annotation
    }

    return pinView
}


2番目の問題について:

まず、 ではcalloutAccessoryControlTapped、 を使用して注釈に直接アクセスできるview.annotationため、selectedAnnotations配列を使用する必要はありません。

次に、はオブジェクトopenMapsWithItemsの配列を期待しMKMapItemますが、渡す配列では ( [selectedLoc, currentLoc])selectedLocはありません。これは、MKMapItemを実装する単なるオブジェクトですMKAnnotation

このコードを実行すると、次のエラーでクラッシュします。

-[MKPointAnnotation dictionaryRepresentation]: 認識されないセレクターがインスタンスに送信されました

マップ アプリが のように使用しようとしたselectedLocときMKMapItem

代わりに、アノテーションMKMapItemからを作成する必要があります。selectedLocこれを行うには、最初に をMKPlacemark使用して注釈から をMKPlacemark(coordinate:addressDictionary:)作成し、次に を使用MKMapItemして目印からを作成しMKMapItem(placemark:)ます。

例:

func mapView(mapView: MKMapView!, annotationView view: MKAnnotationView!,
    calloutAccessoryControlTapped control: UIControl!) {

        let selectedLoc = view.annotation

        println("Annotation '\(selectedLoc.title!)' has been selected")

        let currentLocMapItem = MKMapItem.mapItemForCurrentLocation()

        let selectedPlacemark = MKPlacemark(coordinate: selectedLoc.coordinate, addressDictionary: nil)
        let selectedMapItem = MKMapItem(placemark: selectedPlacemark)

        let mapItems = [selectedMapItem, currentLocMapItem]

        let launchOptions = [MKLaunchOptionsDirectionsModeKey: MKLaunchOptionsDirectionsModeDriving]

        MKMapItem.openMapsWithItems(mapItems, launchOptions:launchOptions)
}
于 2015-05-06T13:17:29.153 に答える