2015-02-25 23 views
5

Tôi đang cố vẽ tuyến đường giữa hai điểm trên bản đồ Apple (mã Swift). Cấu trúc sau được sử dụng để lưu trữ tọa độHiển thị tuyến đường trên bản đồ trong Swift

Trong lớp tùy chỉnh, tôi nhận được tọa độ của các điểm trên bản đồ.

var coordinates = self.foundLocations.map{$0.coordinate} 

Sau đó, tôi vẽ con đường trên bản đồ

self.polyline = MKPolyline(coordinates: &coordinates, count: coordinates.count) 
     self.mapView.addOverlay(self.polyline, level: MKOverlayLevel.AboveRoads) 

Để vẽ con đường tôi sử dụng phương pháp sau đây từ MKMapViewDelegate

func mapView(mapView: MKMapView!, rendererForOverlay overlay: MKOverlay!) -> MKOverlayRenderer! { 
    if let polylineOverlay = overlay as? MKPolyline { 
     let render = MKPolylineRenderer(polyline: polylineOverlay) 
     render.strokeColor = UIColor.blueColor() 
     return render 
    } 
    return nil 
} 

Thay vì con đường thực tế nằm trên đường tôi nhận được chỉ là một đường thẳng giữa hai điểm. Tôi làm cách nào để hiển thị tuyến đường thực tế?

Trả lời

6

Bạn thực sự phải tìm tuyến đường từ máy chủ bản đồ của Apple bằng cách sử dụng calculateDirectionsWithCompletionHandler.

Đầu tiên tạo MKMapItem s có liên quan cho cả nguồn và đích, ví dụ: (. Lặp lại cho các điểm đến)

let geocoder = CLGeocoder() 
let location = CLLocation(latitude: sourceLatitude, longitude: sourceLongitude) 

geocoder.reverseGeocodeLocation(location, completionHandler: { 
     (placemarks:[AnyObject]?, error:NSError?) -> Void in 
     if placemarks?.count > 0 { 
      if let placemark: MKPlacemark = placemarks![0] as? MKPlacemark { 
       self.source = MKMapItem(placemark: placemark) 
      } 
     } 
     }) 

Sau đó lấy MKRoute, ví dụ:

let request:MKDirectionsRequest = MKDirectionsRequest() 

// source and destination are the relevant MKMapItems 
request.setSource(source) 
request.setDestination(destination) 

// Specify the transportation type 
request.transportType = MKDirectionsTransportType.Automobile; 

// If you're open to getting more than one route, 
// requestsAlternateRoutes = true; else requestsAlternateRoutes = false; 
request.requestsAlternateRoutes = true 

let directions = MKDirections(request: request) 

directions.calculateDirectionsWithCompletionHandler ({ 
    (response: MKDirectionsResponse?, error: NSError?) in 

    if error == nil { 
     self.directionsResponse = response 
     // Get whichever currentRoute you'd like, ex. 0 
     self.route = directionsResponse.routes[currentRoute] as MKRoute 
    } 
}) 

Sau đó, sau khi truy xuất số MKRoute, bạn có thể thêm đa giác vào bản đồ như sau:

mapView.addOverlay(route.polyline, level: MKOverlayLevel.AboveRoads) 
+0

bạn có thể thấy lỗi này xin vui lòng http://stackoverflow.com/questions/30775154/error-400-while-adding-route-on-mkmapview? noredirect = 1 # comment49605946_30775154 –

0

Swift 3 và chuyển đổi tái sử dụng của Lyndsey Scott câu trả lời:

final class Route { 

    static func getRouteFor(
     source: CLLocationCoordinate2D, 
     destination: CLLocationCoordinate2D, 
     completion: @escaping (

     _ route: MKRoute?, 
     _ error: String?)->() 

     ) { 

     let sourceLocation = CLLocation(

      latitude: source.latitude, 
      longitude: source.longitude 

     ) 

     let destinationLocation = CLLocation(

      latitude: destination.latitude, 
      longitude: destination.longitude 

     ) 

     let request = MKDirectionsRequest() 

     self.getMapItemFor(location: sourceLocation) { sourceItem, error in 

      if let e = error { 

       completion(nil, e) 

      } 

      if let s = sourceItem { 

       self.getMapItemFor(location: destinationLocation) { destinationItem, error in 

        if let e = error { 

         completion(nil, e) 

        } 

        if let d = destinationItem { 

         request.source = s 

         request.destination = d 

         request.transportType = .walking 

         let directions = MKDirections(request: request) 

         directions.calculate(completionHandler: { response, error in 

          if let r = response { 

           let route = r.routes[0] 

           completion(route, nil) 

          } 

         }) 

        } 

       } 

      } 

     } 

    } 

    static func getMapItemFor(
     location: CLLocation, 
     completion: @escaping (

     _ placemark: MKMapItem?, 
     _ error: String?)->() 

     ) { 

     let geocoder = CLGeocoder() 

     geocoder.reverseGeocodeLocation(location) { placemark, error in 

      if let e = error { 

       completion(nil, e.localizedDescription) 

      } 

      if let p = placemark { 

       if p.count < 1 { 

        completion(nil, "placemark count = 0") 

       } else { 

        if let mark = p[0] as? MKPlacemark { 

         completion(MKMapItem(placemark: mark), nil) 

        } 

       } 

      } 

     } 

    } 

} 

Cách sử dụng:

Route.getRouteFor(source: CLLocationCoordinate2D, destination: CLLocationCoordinate2D) { (MKRoute?, String?) in 
     <#code#> 
} 
Các vấn đề liên quan