随记(九)--确定两个地点的经纬度,自制驾车路线并计算其距离
2016-04-01 17:00
816 查看
使用地图,使用最多的也是百度地图API,以前使用百度地图只是表面地引用一下方法,很少点进方法或者对应属性的文件中,去查看其对应的说明与含义。
1.百度地图两点之间的距离
BMKMetersBetweenMapPoints方法只是两个经纬度之间的直线距离
2.路线实际距离
将MBKDrivingRouteLine实例化,通过distance属性获取实际驾车路线距离
长话段说,直接贴上我的代码
在XXX.h文件中
在XXX.m文件中
1.百度地图两点之间的距离
/** *计算指定两点之间的距离 *@param a 第一个坐标点 *@param b 第二个坐标点 *@return 两点之间的距离,单位:米 */ UIKIT_EXTERN CLLocationDistance BMKMetersBetweenMapPoints(BMKMapPoint a, BMKMapPoint b);
BMKMetersBetweenMapPoints方法只是两个经纬度之间的直线距离
2.路线实际距离
///此类表示一条驾车路线 @interface BMKDrivingRouteLine : BMKRouteLine{ bool _isSupportTraffic;//从2.7.0开始,废弃 NSArray* _wayPoints; } ///该路线所在区域是否含有交通流量信息,从2.7.0开始,废弃 @property (nonatomic) bool isSupportTraffic; ///路线途经点列表,成员类型为BMKPlanNode @property (nonatomic, strong) NSArray* wayPoints; @end
///此类表示路线数据结构的基类,表示一条路线,路线可能包括:路线规划中的换乘/驾车/步行路线 ///此类为路线数据结构的基类,一般关注其子类对象即可,无需直接生成该类对象 @interface BMKRouteLine : NSObject{ int _distance; BMKTime* _duration; BMKRouteNode* _starting; BMKRouteNode* _terminal; NSString* _title; NSArray* _steps; } ///路线长度 单位: 米 @property (nonatomic) int distance; ///路线耗时 单位: 秒 @property (nonatomic, strong) BMKTime* duration; ///路线起点信息 @property (nonatomic, strong) BMKRouteNode* starting; ///路线终点信息 @property (nonatomic, strong) BMKRouteNode* terminal; ///路线名称(预留字段,现为空) @property (nonatomic, strong) NSString* title; ///路线中的所有路段,成员类型为BMKWalkingStep,BMKDrivingStep,BMKTransitStep @property (nonatomic, strong) NSArray* steps; @end
将MBKDrivingRouteLine实例化,通过distance属性获取实际驾车路线距离
长话段说,直接贴上我的代码
在XXX.h文件中
#import <UIKit/UIKit.h> #import "BMapKit.h" @interface XXXViewController : UIViewController //@property (weak, nonatomic) IBOutlet BMKMapView *mapView; @property (nonatomic, assign) CLLocationCoordinate2D startCoor; @property (nonatomic, assign) CLLocationCoordinate2D endCoor; @property (nonatomic, copy) NSString *addrName; @end
在XXX.m文件中
#import "XXX.h" #import "UIImage+Rotate.h" #import <MapKit/MapKit.h> #define MYBUNDLE_NAME @ "mapapi.bundle" #define MYBUNDLE_PATH [[[NSBundle mainBundle] resourcePath] stringByAppendingPathComponent: MYBUNDLE_NAME] #define MYBUNDLE [NSBundle bundleWithPath: MYBUNDLE_PATH] @interface RouteAnnotation : BMKPointAnnotation { int _type; ///<0:起点 1:终点 2:公交 3:地铁 4:驾乘 5:途经点 int _degree; } @property (nonatomic) int type; @property (nonatomic) int degree; @end @implementation RouteAnnotation @synthesize type = _type; @synthesize degree = _degree; @end @interface ServerRepairViewController () <BMKMapViewDelegate, BMKRouteSearchDelegate> { BMKRouteSearch* _routesearch; BMKMapView *_mapView; UILabel *_distanceLab; } @end @implementation ServerRepairViewController - (void)viewDidLoad { [super viewDidLoad]; self.title = @"外出服务"; // self.navigationItem.rightBarButtonItem = [[UIBarButtonItem alloc] initWithTitle:@"驾车" style:UIBarButtonItemStylePlain target:self action:@selector(driveSearchAction)]; _mapView = [[BMKMapView alloc] initWithFrame:CGRectMake(0, 0, K_ScreenWidth, K_ScreenHeight - 64)]; [self.view addSubview:_mapView]; _routesearch = [[BMKRouteSearch alloc] init]; _mapView.delegate = self; _routesearch.delegate = self; _distanceLab = [[UILabel alloc] initWithFrame:CGRectMake(0, K_ScreenHeight - 64 - 40, K_ScreenWidth, 40)]; _distanceLab.backgroundColor = [UIColor whiteColor]; _distanceLab.textColor = [UIColor blueColor]; [self.view addSubview:_distanceLab]; // 计算两点之间直线距离 // CLLocationDistance distance = BMKMetersBetweenMapPoints(BMKMapPointMake(self.startCoor.latitude, self.startCoor.longitude), BMKMapPointMake(self.endCoor.latitude, self.endCoor.longitude)); } - (void)viewWillAppear:(BOOL)animated { [_mapView viewWillAppear]; _mapView.delegate = self; _routesearch.delegate = self; [self driveSearchAction]; } - (void)viewWillDisappear:(BOOL)animated { [_mapView viewWillDisappear]; _mapView.delegate = nil; _routesearch.delegate = nil; } -(void)dealloc { if (_mapView != nil) { _mapView = nil; } if (_routesearch != nil) { _routesearch = nil; } } - (void)driveSearchAction { // NSLog(@"1 = %lf, %lf, %lf, %lf",self.startCoor.latitude, self.startCoor.longitude, self.endCoor.latitude, self.endCoor.longitude); BMKPlanNode *start = [[BMKPlanNode alloc] init]; start.pt = self.startCoor; BMKPlanNode *end = [[BMKPlanNode alloc] init]; end.pt = self.endCoor; end.name = self.addrName; BMKDrivingRoutePlanOption *drivingRoutePlanOption = [[BMKDrivingRoutePlanOption alloc] init]; drivingRoutePlanOption.from = start; drivingRoutePlanOption.to = end; BOOL flag = [_routesearch drivingSearch:drivingRoutePlanOption]; if (flag) { NSLog(@"car检索发送成功"); } else { NSLog(@"car检索发送失败"); } } #pragma mark - BMKMapViewDelegate - (BMKAnnotationView *)mapView:(BMKMapView *)view viewForAnnotation:(id <BMKAnnotation>)annotation { if ([annotation isKindOfClass:[RouteAnnotation class]]) { return [self getRouteAnnotationView:view viewForAnnotation:(RouteAnnotation*)annotation]; } return nil; } - (BMKOverlayView*)mapView:(BMKMapView *)map viewForOverlay:(id<BMKOverlay>)overlay { if ([overlay isKindOfClass:[BMKPolyline class]]) { BMKPolylineView* polylineView = [[BMKPolylineView alloc] initWithOverlay:overlay]; polylineView.fillColor = [[UIColor alloc] initWithRed:0 green:1 blue:1 alpha:1]; polylineView.strokeColor = [[UIColor alloc] initWithRed:0 green:0 blue:1 alpha:0.7]; polylineView.lineWidth = 3.0; return polylineView; } return nil; } #pragma mark - BMKRouteSearchDelegate - (void)onGetDrivingRouteResult:(BMKRouteSearch*)searcher result:(BMKDrivingRouteResult*)result errorCode:(BMKSearchErrorCode)error { NSArray* array = [NSArray arrayWithArray:_mapView.annotations]; [_mapView removeAnnotations:array]; array = [NSArray arrayWithArray:_mapView.overlays]; [_mapView removeOverlays:array]; if (error == BMK_SEARCH_NO_ERROR) { BMKDrivingRouteLine* plan = (BMKDrivingRouteLine*)[result.routes objectAtIndex:0]; _distanceLab.text = [NSString stringWithFormat:@"总路线:%.2lf公里", plan.distance * 2 / 1000.0]; // 计算路线方案中的路段数目 NSInteger size = [plan.steps count]; int planPointCounts = 0; for (int i = 0; i < size; i++) { BMKDrivingStep* transitStep = [plan.steps objectAtIndex:i]; if(i==0){ RouteAnnotation* item = [[RouteAnnotation alloc]init]; item.coordinate = plan.starting.location; item.title = @"起点"; item.type = 0; [_mapView addAnnotation:item]; // 添加起点标注 }else if(i==size-1){ RouteAnnotation* item = [[RouteAnnotation alloc]init]; item.coordinate = plan.terminal.location; item.title = @"终点"; item.type = 1; [_mapView addAnnotation:item]; // 添加起点标注 } //添加annotation节点 RouteAnnotation* item = [[RouteAnnotation alloc]init]; item.coordinate = transitStep.entrace.location; item.title = transitStep.entraceInstruction; item.degree = transitStep.direction * 30; item.type = 4; [_mapView addAnnotation:item]; //轨迹点总数累计 planPointCounts += transitStep.pointsCount; } // 添加途经点 if (plan.wayPoints) { for (BMKPlanNode* tempNode in plan.wayPoints) { RouteAnnotation* item = [[RouteAnnotation alloc]init]; item = [[RouteAnnotation alloc]init]; item.coordinate = tempNode.pt; item.type = 5; item.title = tempNode.name; [_mapView addAnnotation:item]; } } //轨迹点 BMKMapPoint * temppoints = new BMKMapPoint[planPointCounts]; int i = 0; for (int j = 0; j < size; j++) { BMKDrivingStep* transitStep = [plan.steps objectAtIndex:j]; int k=0; for(k=0;k<transitStep.pointsCount;k++) { temppoints[i].x = transitStep.points[k].x; temppoints[i].y = transitStep.points[k].y; i++; } } // 通过points构建BMKPolyline BMKPolyline* polyLine = [BMKPolyline polylineWithPoints:temppoints count:planPointCounts]; [_mapView addOverlay:polyLine]; // 添加路线overlay delete []temppoints; [self mapViewFitPolyLine:polyLine]; } } #pragma mark - 私有 - (NSString*)getMyBundlePath1:(NSString *)filename { NSBundle * libBundle = MYBUNDLE ; if ( libBundle && filename ){ NSString * s=[[libBundle resourcePath ] stringByAppendingPathComponent : filename]; return s; } return nil ; } - (BMKAnnotationView*)getRouteAnnotationView:(BMKMapView *)mapview viewForAnnotation:(RouteAnnotation*)routeAnnotation { BMKAnnotationView* view = nil; switch (routeAnnotation.type) { case 0: { view = [mapview dequeueReusableAnnotationViewWithIdentifier:@"start_node"]; if (view == nil) { view = [[BMKAnnotationView alloc]initWithAnnotation:routeAnnotation reuseIdentifier:@"start_node"]; view.image = [UIImage imageWithContentsOfFile:[self getMyBundlePath1:@"images/icon_nav_start.png"]]; view.centerOffset = CGPointMake(0, -(view.frame.size.height * 0.5)); view.canShowCallout = TRUE; } view.annotation = routeAnnotation; } break; case 1: { view = [mapview dequeueReusableAnnotationViewWithIdentifier:@"end_node"]; if (view == nil) { view = [[BMKAnnotationView alloc]initWithAnnotation:routeAnnotation reuseIdentifier:@"end_node"]; view.image = [UIImage imageWithContentsOfFile:[self getMyBundlePath1:@"images/icon_nav_end.png"]]; view.centerOffset = CGPointMake(0, -(view.frame.size.height * 0.5)); view.canShowCallout = TRUE; } view.annotation = routeAnnotation; } break; case 2: { view = [mapview dequeueReusableAnnotationViewWithIdentifier:@"bus_node"]; if (view == nil) { view = [[BMKAnnotationView alloc]initWithAnnotation:routeAnnotation reuseIdentifier:@"bus_node"]; view.image = [UIImage imageWithContentsOfFile:[self getMyBundlePath1:@"images/icon_nav_bus.png"]]; view.canShowCallout = TRUE; } view.annotation = routeAnnotation; } break; case 3: { view = [mapview dequeueReusableAnnotationViewWithIdentifier:@"rail_node"]; if (view == nil) { view = [[BMKAnnotationView alloc]initWithAnnotation:routeAnnotation reuseIdentifier:@"rail_node"]; view.image = [UIImage imageWithContentsOfFile:[self getMyBundlePath1:@"images/icon_nav_rail.png"]]; view.canShowCallout = TRUE; } view.annotation = routeAnnotation; } break; case 4: { view = [mapview dequeueReusableAnnotationViewWithIdentifier:@"route_node"]; if (view == nil) { view = [[BMKAnnotationView alloc]initWithAnnotation:routeAnnotation reuseIdentifier:@"route_node"]; view.canShowCallout = TRUE; } else { [view setNeedsDisplay]; } UIImage* image = [UIImage imageWithContentsOfFile:[self getMyBundlePath1:@"images/icon_direction.png"]]; view.image = [image imageRotatedByDegrees:routeAnnotation.degree]; view.annotation = routeAnnotation; } break; case 5: { view = [mapview dequeueReusableAnnotationViewWithIdentifier:@"waypoint_node"]; if (view == nil) { view = [[BMKAnnotationView alloc]initWithAnnotation:routeAnnotation reuseIdentifier:@"waypoint_node"]; view.canShowCallout = TRUE; } else { [view setNeedsDisplay]; } UIImage* image = [UIImage imageWithContentsOfFile:[self getMyBundlePath1:@"images/icon_nav_waypoint.png"]]; view.image = [image imageRotatedByDegrees:routeAnnotation.degree]; view.annotation = routeAnnotation; } break; default: break; } return view; } //根据polyline设置地图范围 - (void)mapViewFitPolyLine:(BMKPolyline *) polyLine { CGFloat ltX, ltY, rbX, rbY; if (polyLine.pointCount < 1) { return; } BMKMapPoint pt = polyLine.points[0]; ltX = pt.x, ltY = pt.y; rbX = pt.x, rbY = pt.y; for (int i = 1; i < polyLine.pointCount; i++) { BMKMapPoint pt = polyLine.points[i]; if (pt.x < ltX) { ltX = pt.x; } if (pt.x > rbX) { rbX = pt.x; } if (pt.y > ltY) { ltY = pt.y; } if (pt.y < rbY) { rbY = pt.y; } } BMKMapRect rect; rect.origin = BMKMapPointMake(ltX , ltY); rect.size = BMKMapSizeMake(rbX - ltX, rbY - ltY); [_mapView setVisibleMapRect:rect]; _mapView.zoomLevel = _mapView.zoomLevel - 0.3; } @end
相关文章推荐
- ubuntu 修改中文乱码命令
- CHttpFile GET/POST 提交数据
- Page的IsCrossPagePostBack属性
- apache 虚拟主机配置
- LDAP的特定错误
- 常用的正则表达式
- 服务器常用的内核调优
- JSONObject转换JSON--将Date转换为指定格式
- Mysql编辑工具中使用(Navicat查询结果显示行号)
- node-firefox 二三事
- APNS远程推送(转发)
- Redis 环境安装与C++接口
- CentOS 网络地址设置
- 关于ActiveX在WebBrowser不加载问题
- SVMrank——Support Vector Machine for Ranking(SVMrank——使用svm的排序)
- 文件名 文件路径
- opencv:Load Caffe framework models
- ReactNative学习四-版本更新
- iOS拍照和录制视频 摄像头使用
- Your build settings specify a provisioning profile with the UUID, no provisioning profile was found