将规划出来的驾车路线按照实际的路况显示在地图上。
核心类/接口
类 | 接口 | 说明 | 版本 |
---|---|---|---|
MAMapView | addOverlay: | 向地图窗口添加Overlay。 | V2.0.0版本起 |
addAnnotation: | 向地图窗口添加标注。 | V2.0.0版本起 | |
MAMapViewDelegate | mapView:viewForAnnotation: | 地图上的起始点,终点,拐点的标注的回调,可以自定义图标展示等。 | V2.0.0版本起 |
mapView:rendererForOverlay: | 地图上覆盖物的渲染的回调,可以设置路径线路的宽度,颜色等。 | V3.0.0版本起 | |
AMapSearchAPI | AMapDrivingRouteSearch: | 驾车路径规划查询接口。 | V3.0.0版本起 |
AMapDrivingRouteSearchRequest | strategy | 驾车导航策略([default = 0]) 0-速度优先(时间);1-费用优先(不走收费路段的最快道路);2-距离优先;3-不走快速路;4-结合实时交通(躲避拥堵);5-多策略(同时使用速度优先、费用优先、距离优先三个策略);6-不走高速;7-不走高速且避免收费;8-躲避收费和拥堵;9-不走高速且躲避收费和拥堵 | V3.0.0版本起 |
requireExtension | 是否返回扩展信息,默认NO。 | V3.0.0版本起 | |
AMapRouteSearchBaseRequest | origin | 出发点坐标。 | V3.0.0版本起 |
destination | 目的地坐标。 | V3.0.0版本起 | |
AMapSearchDelegate | onRouteSearchDone:response: | 路径规划查询完成回调。 | V3.0.0版本起 |
1、如何解析驾车规划结果对象。
a)通过 response.route.paths 可以获取到 AMapPath 列表。
b)AMapPath 对象就是一条驾车路线,每个方案都是由多个 AMapStep 构成。
c)可以通过 AMapStep.polyline 属性获取这个路段的坐标点,用于绘制路线;也可通过 AMapStep.action 属性获取该导航路段的动作(如:直行、右转等),用于路线的详情展示 。
在本示例中,MANaviRoute 是一个生成路线 Polyline 和起终点以及中间节点的 Annotaion 的工具类,省去了您去解析 response 对象的成本。
//在地图上显示当前选择的路径
- (void)presentCurrentRouteCourse{
if (self.totalRouteNums <= 0) {
return;
}
[self.naviRoute removeFromMapView]; //清空地图上已有的路线
self.infoLabel.text = [NSString stringWithFormat:@"共%u条路线,当前显示第%u条",(unsigned)self.totalRouteNums,(unsigned)self.currentRouteIndex + 1]; //提示信息
MANaviAnnotationType type = MANaviAnnotationTypeDrive; //驾车类型
AMapGeoPoint *startPoint = [AMapGeoPoint locationWithLatitude:self.startAnnotation.coordinate.latitude longitude:self.startAnnotation.coordinate.longitude]; //起点
AMapGeoPoint *endPoint = [AMapGeoPoint locationWithLatitude:self.destinationAnnotation.coordinate.latitude longitude:self.destinationAnnotation.coordinate.longitude]; //终点
//根据已经规划的路径,起点,终点,规划类型,是否显示实时路况,生成显示方案
self.naviRoute = [MANaviRoute naviRouteForPath:self.route.paths[self.currentRouteIndex] withNaviType:type showTraffic:self.showTrafficSwitch.on startPoint:startPoint endPoint:endPoint];
[self.naviRoute addToMapView:self.mapView]; //显示到地图上
UIEdgeInsets edgePaddingRect = UIEdgeInsetsMake(RoutePlanningPaddingEdge, RoutePlanningPaddingEdge, RoutePlanningPaddingEdge, RoutePlanningPaddingEdge);
//缩放地图使其适应polylines的展示
[self.mapView setVisibleMapRect:[CommonUtility mapRectForOverlays:self.naviRoute.routePolylines]
edgePadding:edgePaddingRect
animated:YES];
}
//在地图上显示当前选择的路径
func presentCurrentRouteCourse() {
if self.totalRouteNums <= 0 {
return
}
self.naviRoute?.removeFromMapView() //清空地图上已有的路线
self.infoLabel.text = "共\(UInt(self.totalRouteNums))条路线,当前显示第\(UInt(self.currentRouteIndex) + 1)条" //提示信息
let type = MANaviAnnotationType.drive //驾车类型
let startPoint = AMapGeoPoint.location(withLatitude: CGFloat(self.startAnnotation.coordinate.latitude), longitude: CGFloat(self.startAnnotation.coordinate.longitude)) //起点
let endPoint = AMapGeoPoint.location(withLatitude: CGFloat(self.destinationAnnotation.coordinate.latitude), longitude: CGFloat(self.destinationAnnotation.coordinate.longitude)) //终点
//根据已经规划的路径,起点,终点,规划类型,是否显示实时路况,生成显示方案
self.naviRoute = MANaviRoute(for: self.route.paths[self.currentRouteIndex], withNaviType: type, showTraffic: self.showTrafficSwitch.isOn, start: startPoint, end: endPoint)
self.naviRoute?.add(to: self.mapView)
//显示到地图上
let edgePaddingRect = UIEdgeInsetsMake(RoutePlanningPaddingEdge, RoutePlanningPaddingEdge, RoutePlanningPaddingEdge, RoutePlanningPaddingEdge)
//缩放地图使其适应polylines的展示
self.mapView.setVisibleMapRect(CommonUtility.mapRect(forOverlays: self.naviRoute?.routePolylines), edgePadding: edgePaddingRect, animated: true)
}
2、如何更改显示在地图上的路线的的样式(包括:出发点和目的地的图标、路线的颜色、宽度等等)。
//地图上的起始点,终点,拐点的标注,可以自定义图标展示等,只要有标注点需要显示,该回调就会被调用
- (MAAnnotationView *)mapView:(MAMapView *)mapView viewForAnnotation:(id<MAAnnotation>)annotation {
if ([annotation isKindOfClass:[MAPointAnnotation class]]) {
//标注的view的初始化和复用
static NSString *routePlanningCellIdentifier = @"RoutePlanningCellIdentifier";
MAAnnotationView *poiAnnotationView = (MAAnnotationView*)[self.mapView dequeueReusableAnnotationViewWithIdentifier:routePlanningCellIdentifier];
if (poiAnnotationView == nil) {
poiAnnotationView = [[MAAnnotationView alloc] initWithAnnotation:annotation reuseIdentifier:routePlanningCellIdentifier];
}
poiAnnotationView.canShowCallout = YES;
poiAnnotationView.image = nil;
//拐点的图标标注
if ([annotation isKindOfClass:[MANaviAnnotation class]]) {
switch (((MANaviAnnotation*)annotation).type) {
case MANaviAnnotationTypeRailway:
poiAnnotationView.image = [UIImage imageNamed:@"railway_station"];
break;
case MANaviAnnotationTypeBus:
poiAnnotationView.image = [UIImage imageNamed:@"bus"];
break;
case MANaviAnnotationTypeDrive:
poiAnnotationView.image = [UIImage imageNamed:@"car"];
break;
case MANaviAnnotationTypeWalking:
poiAnnotationView.image = [UIImage imageNamed:@"man"];
break;
default:
break;
}
}else{
//起点,终点的图标标注
if ([[annotation title] isEqualToString:(NSString*)RoutePlanningViewControllerStartTitle]) {
poiAnnotationView.image = [UIImage imageNamed:@"startPoint"]; //起点
}else if([[annotation title] isEqualToString:(NSString*)RoutePlanningViewControllerDestinationTitle]){
poiAnnotationView.image = [UIImage imageNamed:@"endPoint"]; //终点
}
}
return poiAnnotationView;
}
return nil;
}
func mapView(_ mapView: MAMapView!, viewFor annotation: MAAnnotation!) -> MAAnnotationView! {
if annotation.isKind(of: MAPointAnnotation.self) {
//标注的view的初始化和复用
let pointReuseIndetifier = "RoutePlanningCellIdentifier"
var annotationView: MAAnnotationView? = mapView.dequeueReusableAnnotationView(withIdentifier: pointReuseIndetifier)
if annotationView == nil {
annotationView = MAAnnotationView(annotation: annotation, reuseIdentifier: pointReuseIndetifier)
annotationView!.canShowCallout = true
annotationView!.isDraggable = false
}
annotationView!.image = nil
if annotation.isKind(of: MANaviAnnotation.self) {
let naviAnno = annotation as! MANaviAnnotation
switch naviAnno.type {
case MANaviAnnotationType.railway:
annotationView!.image = UIImage(named: "railway_station")
break
case MANaviAnnotationType.drive:
annotationView!.image = UIImage(named: "car")
break
case MANaviAnnotationType.riding:
annotationView!.image = UIImage(named: "ride")
break
case MANaviAnnotationType.walking:
annotationView!.image = UIImage(named: "man")
break
case MANaviAnnotationType.bus:
annotationView!.image = UIImage(named: "bus")
break
}
}
else {
if annotation.title == "起点" {
annotationView!.image = UIImage(named: "startPoint")
}
else if annotation.title == "终点" {
annotationView!.image = UIImage(named: "endPoint")
}
}
return annotationView!
}
return nil
}
将规划出来的驾车路线按照实际的路况显示在地图上,同时将 DrivingRouteOverlay 开源,帮助您做特殊样式的显示方案。
核心类/接口
类 | 接口 | 说明 | 版本 |
---|---|---|---|
RouteSearch.DriveRouteQuery | DriveRouteQuery(RouteSearch.FromAndTo fromAndTo,int mode,java.util.List<LatLonPoint> passedByPoints,java.util.List<java.util.List<LatLonPoint>> avoidpolygons,java.lang.String avoidRoad) | 构造函数,构造驾车路线规划查询参数对象。 | V2.1.0版本起 |
RouteSearch | calculateDriveRouteAsyn(RouteSearch.DriveRouteQuery driveQuery) | 驾车路线规划异步接口。 | V2.1.0版本起 |
RouteSearch.OnRouteSearchListener | onDriveRouteSearched(DriveRouteResult driveRouteResult, int errorCode) | 驾车路径规划结果的回调方法。 | V2.1.0版本起 |
DriveRouteResult | getPaths() | 返回驾车路径规划方案。 | V2.1.0版本起 |
DrivePath | getSteps() | 返回驾车规划方案的路段列表。 | V2.1.0版本起 |
DriveStep | getPolyline() | 返回驾车路段的坐标点集合。 | V2.1.0版本起 |
1、如何解析驾车路线规划结果对象?
a)通过 DriveRouteResult.getPaths() 方法获取全部的驾车路线规划的列表,列表中是 DrivePath 对象。
b)DrivePath 对象就是一个完整驾车路线方案,每条路线都是由多个 DriveStep 构成。
c)通过 DriveStep 对象,可以通过 getPolyline() 方法获取这个 Step 的坐标点集合,用来在地图上绘制线路;也可以通过 getAction() 方法获取驾车路段的导航主要操作(如:左转、直行等)。
2、如何更改显示在地图上的 DrivingRouteOverlay 的样式(如:起终点图标、线路的颜色、宽度等)?
在本示例中,DrivingRouteOverlay 已对所有开发者开源,您可以参考源码修改 Overlay 的样式。其中: