地图的使用-King

本文介绍了苹果地图MapKit和CoreLocation框架的使用,包括CoreLocation的定位服务步骤,地理编码与反地理编码,以及MapKit的MKMapView控件,用户跟踪模式和地图类型。同时,讲解了自定义大头针和导航画线的基本方法。
摘要由CSDN通过智能技术生成

前言:

        苹果在天朝使用的是高德地图,使用起来还算是比较方便,当然在国内还有百度地图sdk也很不错.我这里简单介绍下苹果原生的地图使用方式,很多地方也许说的不到位,还请看出来的大神指点一下,文中有些地方我觉得用我自己的话解释可能说的不是很清楚,所以有些地方是从网上摘抄,请不要介意.


在使用苹果地图时需要导入MapKit 框架,但是与这个框架生死相随的另外一个框架也是很重要的,那就是CoreLocation 框架,我这里就首先从这个CoreLocation框架先简单的介绍下.


一.CoreLocation定位服务

        顾名思义,这个英文单词汉语的直译就是核心定位,要想使用这个库,需要以下三个步骤:       

        1.在TARGETS->Build Phases->Link Binary With Libraries中导入 CoreLocation.framework 静态库

        2.在info.plist中加入对应的缺省字段 ,值设置为YES(前台定位写上边字段,前后台定位写下边字段)

        <key>NSLocationWhenInUseUsageDescription</key>    //允许在前台获取GPS的描述

        <true/>

        <key>NSLocationAlwaysUsageDescription</key>       //允许在前、后台获取GPS的描述

        <true/>

        3.在需要使用定位服务的类中导入#import <CoreLocation/CoreLocation.h>

我现在的解决办法:

1)在Capabilities中选择BackgroundModes,并且勾选Location updates。

2)在info.plist中添加Privacy - Location Usage Description字段,后面添加你想描述的文字。

3)在创建manager的方法中实现以下代码。

  
  
  1. if ([[[UIDevice currentDevice] systemVersion] floatValue] >= 8){
  2. //[_locationManager requestWhenInUseAuthorization];//只在前台开启定位
  3. [self.manager requestAlwaysAuthorization];//在后台也可定位
  4. }
  5. if ([[[UIDevice currentDevice] systemVersion] floatValue] >= 9){
  6. self.manager.allowsBackgroundLocationUpdates = YES;
  7. }

        做完以上步骤就可以使用定位服务了.

        从iOS 6开始,苹果在保护用户隐私方面做了很大的加强,以下操作都必须经过用户批准授权

            要想获得用户的位置;

            想访问用户的通讯录、日历、相机、相册等等;

        当想访问用户的隐私信息时,系统会自动弹出一个对话框让用户授权.


        在CoreLocation中左右数据类型的前缀都是CL开头的,并且使用CoreLocationManager对象来做用户定位的相关操作.

 
 
  1. CLLocationManager *manager = [[CLLocationManager alloc]init];

 
 
  1. // 开始定位用户的位置

  2. [manager startUpdatingLocation];

 
 
  1. // 停止定位用户的位置

  2. [manager stopUpdatingLocation];

       遵循<CLLocationManagerDelegate>设置好代理,并且调用上述的startUpdatingLocation方法后

 
 
  1. manager.delegate = self;

    这时系统会频繁的调用下述代理方法

- (void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray<CLLocation *> *)locations;

其中locations数组中装载着的是CLLocation对象,也就是存储着一系列用户位置的数组,其中这个数组的第一个对象是比较准确的位置.(ps.手机个用户定位时并不是一个点的位置,而是一系列的定位的点)


CLLocation是用来表示用户位置的地理信息,一下介绍介个常用的属性

 
 
  1. //经纬度, CLLocationCoordinate2D是个结构体;

  2. @property(readonly, nonatomic) CLLocationCoordinate2D coordinate;

  3. //海拔, CLLocationDistance就是一个double类型;

  4. @property(readonly, nonatomic) CLLocationDistance altitude;

  5. //路线,航向, CLLocationDirection也是一个double类型的值,范围在0~359.9之间,0表示正北方向,负值无效;

  6. @property(readonly, nonatomic) CLLocationDirection course;

  7. //速度, CLLocationSpeed也是一个double类型数据,单位是m/s;

  8. @property(readonly, nonatomic) CLLocationSpeed speed;

  9. //计算两个位置之间的距离;

  10. - (CLLocationDistance)distanceFromLocation:(const CLLocation *)location;

  11. //计算当前位置和所给位置的距离;

  12. - (CLLocationDistance)getDistanceFrom:(const CLLocation *)location;

CLLocationCoordinate2D是一个用来表示经纬度的结构体,定义如下

 
 
  1. typedef struct {

  2.        CLLocationDegrees latitude; // 纬度

  3.        CLLocationDegrees longitude; // 经度

  4. } CLLocationCoordinate2D;

 
 
  1. 一般用CLLocationCoordinate2DMake函数来创建CLLocationCoordinate2D

CLLocationManager用来作为定位服务的管理者,苹果官方给出的解释是一个定位服务的接入点,几乎定位服务的大部分功能由它来调度

 
 
  1. //判断定位服务能否开启;

  2. + (BOOL)locationServicesEnabled;

  3. //指定每个多少米更新一次距离;

  4. @property(assign, nonatomic) CLLocationDistance distanceFilter;

  5. //指定定位精度,但是会更加的消耗你的电能,请在正确的场景使用;

  6. @property(assign, nonatomic) CLLocationAccuracy desiredAccuracy;

定位精度在以下的定义中

 
 
  1. extern const CLLocationAccuracy kCLLocationAccuracyBestForNavigation ;

  2. extern const CLLocationAccuracy kCLLocationAccuracyBest;

  3. extern const CLLocationAccuracy kCLLocationAccuracyNearestTenMeters;

  4. extern const CLLocationAccuracy kCLLocationAccuracyHundredMeters;

  5. extern const CLLocationAccuracy kCLLocationAccuracyKilometer;

  6. extern const CLLocationAccuracy kCLLocationAccuracyThreeKilometers;




二.CLGeocoder 地理编码 和 反地理编码


地理编码    : 根据用户给定的地名,来获得具体的地理位置信息

反地理编码  : 根据用户给定的经纬度,来获得具体的位置信息(常用的场景就是用户定位获取到了自己的经纬度,然后通过反编码来判断所处的位置,因为用户仅仅只知道自己的经纬度没用)

 
 
  1. //地理编码方法

  2. //根据包含地址信息的指点,来编码地理信息

  3. - (void)geocodeAddressDictionary:(NSDictionary *)addressDictionary completionHandler:(CLGeocodeCompletionHandler)completionHandler;

  4. //根据置顶的位置信息来编码地理信息

  5. - (void)geocodeAddressString:(NSString *)addressString completionHandler:(CLGeocodeCompletionHandler)completionHandler;

  6. //根据指定的位置信息和范围来编码地理信息

  7. - (void)geocodeAddressString:(NSString *)addressString inRegion:(nullable CLRegion *)region completionHandler:(CLGeocodeCompletionHandler)completionHandler;

其中CLGeocodeCompletionHandler在系统中的定义是一个代码块,定义如下


typedef void (^CLGeocodeCompletionHandler)(NSArrayCLPlacemark *> * __nullable placemarks, NSError * __nullable error);


地理编码方法编码成功时,会进入到这个代码块中执行

placemarks:里面装载着的是CLPlacemark对象;

error:当编码出错时,存储异常信息;


CLPlacemark中封装着详细的地址位置信息

 
 
  1. //地理位置

  2. @property (nonatomic, readonly, copy, nullable) CLLocation *location;

  3. //区域

  4. @property (nonatomic, readonly, copy, nullable) CLRegion *region;

  5. //详细的地址信息

  6. @property (nonatomic, readonly, copy, nullable) NSDictionary *addressDictionary;

  7. //地址名称

  8. @property (nonatomic, readonly, copy, nullable) NSString *name;

  9. //城市

  10. @property (nonatomic, readonly, copy, nullable) NSString *locality;

还有更多的属性,在文档中都有说明.


 
 
  1. //反地理编码的方法,用法和上面差不多

  2. - (void)reverseGeocodeLocation:(CLLocation *)location completionHandler:(CLGeocodeCompletionHandler)completionHandler;

其实在这些定位,编码和反编码的类中,也许会有很多让人模糊的属性对象,但是我们只要按住command+鼠标点按,就能看到苹果官方是怎么样定义这些属性的,然后根据对应的中文意思,也就能大概的推测出相应的功能.





三.地图

        

        写完定位终于到重点了,MapKit框架.这是苹果原生自带的地图框架,在我大天朝还有一个响亮的名字,没错,就是高德地图.和CoreLocation一样也有下面两个步骤:

        1.在TARGETS->Build Phases->Link Binary With Libraries中导入 MapKit.framework 静态库.

        2.在需要使用定位服务的类中导入#import <MapKit/MapKit.h>.

         3.创建MKMapView控件,这样就可以在界面上显示地图了.


MKMapView控件中有个userTrackingMode属性

    @property (nonatomicMKUserTrackingMode userTrackingMode NS_AVAILABLE(NA, 5_0);

    这个是用来跟踪显示用户当前位置的,它有三种属性:

    定义如下:

 
 
  1. typedef NS_ENUM(NSInteger, MKUserTrackingMode) {

  2. MKUserTrackingModeNone = 0, // the user's location is not followed

  3. MKUserTrackingModeFollow, // the map follows the user's location

  4. MKUserTrackingModeFollowWithHeading, // the map follows the user's location and heading

  5. } NS_ENUM_AVAILABLE(NA, 5_0) __WATCHOS_PROHIBITED;

MKUserTrackingModeNone                :        不跟踪用户位置

MKUserTrackingModeFollow              :        跟踪并且在地图上显示用户位置

MKUserTrackingModeFollowWithHeading   :        跟踪并且在地图上显示用户位置,并且还会跟随用户前进方向旋转



下图是显示的用户当前定位位置的大头针



MKMapView控件中有个mapType属性

@property (nonatomicMKMapType mapType;

这个是用来设置地图类型的,在iOS9之前,它有三种类型:(普通地图,卫星云图,普通地图和卫星云图的混合)

但在iOS9之后出现了两个新的类型,SatelliteFlyover(地形和建筑物的三维模型)和HybridFlyover()


    定义如下:

 
 
  1. typedef NS_ENUM(NSUInteger, MKMapType) {

  2.    MKMapTypeStandard = 0,

  3.    MKMapTypeSatellite,

  4.    MKMapTypeHybrid,

  5.    MKMapTypeSatelliteFlyover NS_ENUM_AVAILABLE(10_11, 9_0),

  6.    MKMapTypeHybridFlyover NS_ENUM_AVAILABLE(10_11, 9_0),

  7. } NS_ENUM_AVAILABLE(10_9, 3_0) __WATCHOS_PROHIBITED;

我这里就不贴出图片了.


通过MKMapView的下列方法,可以设置地图显示的位置和区域

设置地图的中心点位置

@property(nonatomic)CLLocationCoordinate2D centerCoordinate;

 
 
  1. - (void)setCenterCoordinate:(CLLocationCoordinate2D)coordinate animated:(BOOL)animated;


设置地图的显示区域

@property (nonatomicMKCoordinateRegion region;

 
 
  1. - (void)setRegion:(MKCoordinateRegion)region animated:(BOOL)animated;

上面的CLGeocoder中提到的CLPlacemark也有个CLRegion属性,他们都是区域范围的意思,

这里的定义是一个结构体,里面包含了两个数据类型,一个是中心点,一个是区域的跨度,简单的理解就是,你有一个中心点后,系统要知道你要现实的具体范围吧,总不能知道了你要显示的中心点,但是系统把整个中国都显示出来吧,就类似于你主动把精确度给系统来进行显示.

 
 
  1. typedef struct {

  2. CLLocationCoordinate2D center;  //区域中心点

  3. MKCoordinateSpan span;  //区域跨度

  4. } MKCoordinateRegion;

 
 
  1. typedef struct {

  2.    CLLocationDegrees latitudeDelta;   //纬度跨度

  3.    CLLocationDegrees longitudeDelta;  //精度跨度

  4. } MKCoordinateSpan;


MKMapView中还有很多常用的属性,我感觉直接按住command+鼠标点进去看看就差不多了.用翻译软件翻译一下中文意思就差不多了.


同其他的UI控件一样,MKMapView也有自己的代理方法,方法很多,我这里也没办法一一例举出来,常见的代理方法有:

 
 
  1. //调用非常频繁,不断监测用户的当前位置

  2. //每次调用,都会把用户的最新位置(userLocation参数)传进来

  3. - (void)mapView:(MKMapView *)mapView didUpdateUserLocation:(MKUserLocation *)userLocation;

  4. //地图的显示区域即将发生改变的时候调用

  5. - (void)mapView:(MKMapView *)mapView regionWillChangeAnimated:(BOOL)animated;

  6. //地图的显示区域已经发生改变的时候调用

  7. - (void)mapView:(MKMapView *)mapView regionDidChangeAnimated:(BOOL)animated;

  8. //添加大头针的时候调用,返回annotationView

  9. - (MKAnnotationView *)mapView:(MKMapView *)mapView viewForAnnotation:(id<MKAnnotation>)annotation;

  10. //点击大头针的时候调用

  11. - (void)mapView:(MKMapView *)mapView didSelectAnnotationView:(MKAnnotationView *)view;


MKUserLocation 其实就是一个大头针模型,就是上图显示的那个蓝色的标志.

 
 
  1. #import <MapKit/MKFoundation.h>

  2. #import <MapKit/MKAnnotation.h>

  3. @class CLLocation;

  4. @class MKUserLocationInternal;

  5. @interface MKUserLocation : NSObject <MKAnnotation>

  6. @property (readonly, nonatomic, getter=isUpdating) BOOL updating;

  7. @property (readonly, nonatomic, nullable) CLLocation *location;// 地理位置信息

  8. @property (readonly, nonatomic, nullable) CLHeading *heading;// 这是iOS9新增的属性,一个指北针所包含的信息

  9. @property (nonatomic, copy, nullable) NSString *title;// 显示在大头针上的标题

  10. @property (nonatomic, copy, nullable) NSString *subtitle;// 显示在大头针上的子标题

  11. @end


大头针的基本操作 

 
 
  1. //添加一个大头针

  2. - (void)addAnnotation:(id <MKAnnotation>)annotation;

  3. //添加多个大头针

  4. - (void)addAnnotations:(NSArray *)annotations;

  5. //移除一个大头针

  6. - (void)removeAnnotation:(id <MKAnnotation>)annotation;

  7. //移除多个大头针

  8. - (void)removeAnnotations:(NSArray *)annotations;

示例:这是一个点击地图的相应位置就添加一个大头针的DEMO,监听点击的方法中,要将获取到得用户点击的point转换为地图上的坐标,HTAnnotation是一个大头针模型,下面回详细介绍.

 
 
  1. // 监听mapView的点击事件

  2.    [self.mapView addGestureRecognizer:[[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(tapMapView:)]];

 
 
  1. /**

  2. *  监听mapView的点击

  3. */

  4. - (void)tapMapView:(UITapGestureRecognizer *)tap

  5. {

  6.    // 1.获得用户在mapView点击的位置(x,y)

  7.    CGPoint point = [tap locationInView:tap.view];

  8.    

  9.    // 2.将数学坐标 转为 地理经纬度坐标

  10.    CLLocationCoordinate2D coordinate = [self.mapView convertPoint:point toCoordinateFromView:self.mapView];

  11.    

  12.    // 3.创建大头针模型,添加大头针到地图上

  13.    HTAnnotation *anno = [[HTAnnotation alloc] init];

  14.    anno.coordinate = coordinate;

  15.    anno.title = @"King";

  16.    anno.subtitle = @"King丶逍遥";

  17.    [self.mapView addAnnotation:anno];

  18. }


关于大头针模型,其实就是继承于NSObject的类对象,并且要遵循<MKAnnotation>协议.

那么怎么建立大头针模型呢?

请看(这个类的.m文件不需要写东西了)

 
 
  1. #import <Foundation/Foundation.h>

  2. #import <MapKit/MapKit.h>

  3. @interface HTAnnotation : NSObject <MKAnnotation>

  4. @property (nonatomic, assign) CLLocationCoordinate2D coordinate;

  5. @property (nonatomic, copy) NSString *title;

  6. @property (nonatomic, copy) NSString *subtitle;

  7. @end

也许第一次学习地图的朋友还是不明白为什么会要这么创建的,那么请看官方是怎么定义这个协议的把.

 
 
  1. @protocol MKAnnotation <NSObject>

  2. // Center latitude and longitude of the annotation view.

  3. // The implementation of this property must be KVO compliant.

  4. @property (nonatomic, readonly) CLLocationCoordinate2D coordinate;

  5. @optional

  6. // Title and subtitle for use by selection UI.

  7. @property (nonatomic, readonly, copy, nullable) NSString *title;

  8. @property (nonatomic, readonly, copy, nullable) NSString *subtitle;

  9. // Called as a result of dragging an annotation view.

  10. - (void)setCoordinate:(CLLocationCoordinate2D)newCoordinate;

  11. @end

看了这些应该知道为什么是那么定义大头针模型了把,要实现<MKAnnotation>协议,就将上述的方法实现,因为大头针包含的是对应的地址信息,所以里面必须包含CLLocationCoordinate2D属性来存储用户地理位置信息,其它的属性也是其它对应的标记,当然你还可以自定义其它的属性,这个在后面也有讲解.下图是title和subtitle对应的现实位置,他们显示的View是MKAnnotationView,设置MKAnnotationView可以显示很多你需要显示的数据.后面会详细说明.





四.自定义大头针

    很显然和大多数iOS控件一样,MapView中的大头针也是可以自定义的,但是要如何自定义呢?

    首先,设置MKMapView的代理.

    其次,实现下面的代理方法,返回大头针控件.

 
 
  1.  - (nullable MKAnnotationView *)mapView:(MKMapView *)mapView viewForAnnotation:(id <MKAnnotation>)annotation;


    最后,根据传进来的(id <MKAnnotation>)annotation模型参数创建并返回对应的大头针控件.


  至于是什么时候调用这个代理方法呢?就是每次在地图上添加大头针时调用,系统自动生成的最前面的蓝色的圆形大头针也会调用这个代理方法.说到这里,也许你对之前的大头针模型理解更深刻了吧,模型中有什么数据,你这里就能使用什么数据来自定义大头针了.不过刚才提到了系统生成的蓝色圆形大头针也会调用这个方法,所以如果不想动这个大头针的话,可以做一次判断.这里提一下,如果返回的是nil,那么返回的是系统的大头针.



MKAnnotationView 大头针控件

 
 
  1. @property (nonatomic, strong) id <MKAnnotation> annotation;

  2. 大头针模型

  3. @property (nonatomic, strong) UIImage *image;

  4. 显示的图片

  5. @property (nonatomic) BOOL canShowCallout;

  6. 是否显示标注

  7. @property (nonatomic) CGPoint calloutOffset;

  8. 标注的偏移量

  9. @property (strong, nonatomic) UIView *rightCalloutAccessoryView;

  10. 标注右边显示什么控件

  11. @property (strong, nonatomic) UIView *leftCalloutAccessoryView;

  12. 标注左边显示什么控件

这些是AnnotationView的一些常用属性,至于还有很多其他的属性设置欢迎参考苹果的文档,其实我感觉做了这么久的IOS开发,只有苹果的官方文档才是注释最全面的,而其他的一些学习的书籍反而解释的不是很透彻,这就需要一个程序员有一定的阅读英文的能力,不过话说回来,我的英文水平很菜,大学时,英语四级也没过,不过,这不影响我偶尔阅读API文档,慢慢看,不懂得就用翻译软件,总还是能看懂的.好吧,下面就放一段annotationView的示例用法:

 
 
  1. - (MKAnnotationView *)mapView:(MKMapView *)mapView viewForAnnotation:(id<MKAnnotation>)annotation

  2. {

  3.    if (![annotation isKindOfClass:[zidigyiAnnotation class]]) return nil;

  4.    

  5.    static NSString *ID = @"zidingyi";

  6.    // 从缓存池中取出可以循环利用的大头针view

  7.    MKAnnotationView *annoView = [mapView dequeueReusableAnnotationViewWithIdentifier:ID];

  8.    if (annoView == nil) {

  9.        annoView = [[MKAnnotationView alloc] initWithAnnotation:annotation reuseIdentifier:ID];

  10.        // 显示子标题和标题

  11.        annoView.canShowCallout = YES;

  12.        // 设置大头针描述的偏移量

  13.        annoView.calloutOffset = CGPointMake(0, -10);

  14.        // 设置大头针描述右边的控件

  15.        annoView.rightCalloutAccessoryView = [UIButton buttonWithType:UIButtonTypeContactAdd];

  16.        // 设置大头针描述左边的控件

  17.        annoView.leftCalloutAccessoryView = [UIButton buttonWithType:UIButtonTypeDetailDisclosure];

  18.    }

  19.    

  20.    // 传递模型

  21.    annoView.annotation = annotation;

  22.    

  23.    // 设置图片

  24.    zidingyiAnnotation *tuangouAnno = annotation;

  25.    annoView.image = [UIImage imageNamed:tuangouAnno.icon];//这个icon是自定义的大头针模型中的数据

  26.    

  27.    return annoView;

  28. }

不过MKAnnotationView有一个子类MKPinAnnotationView,在iOS9之前多了两个属性

 
 
  1. @property (nonatomic) BOOL animatesDrop;//用来设置大头针显示的时候是否是从天而降

  2. @property (nonatomic) MKPinAnnotationColor pinColor NS_DEPRECATED(10_9, 10_11, 3_0, 9_0, "Use pinTintColor instead");

但是注意这个pinColor在iOS9中已经被废弃,被pinTintColor代替用来设置大头针的颜色

 
 
  1. @property (NS_NONATOMIC_IOSONLY, strong, null_resettable) UIColor *pinTintColor NS_AVAILABLE(10_11, 9_0) UI_APPEARANCE_SELECTOR;

 
 
  1. + (UIColor *)redPinColor NS_AVAILABLE(10_11, 9_0);

  2. + (UIColor *)greenPinColor NS_AVAILABLE(10_11, 9_0);

  3. + (UIColor *)purplePinColor NS_AVAILABLE(10_11, 9_0);



五.导航画线

    1.确定需要画线的两个地点,利用CLGeocoder中的(geocodeAddressString: completionHandler:)方法编码出两个地点的地理位置信息(CLPlacemark);

  2.查找路线(设置起点,终点,并且计算路线)

  3.绘制路线(绘制好的路线,利用addOverlay:方法添加地图上的路线,这个方法会调用mapView的一个代理方法来绘制线路)

 
 
  1. - (MKOverlayRenderer *)mapView:(MKMapView *)mapView rendererForOverlay:(id<MKOverlay>)overlay//这里面设置路线的显示样式

下面是一个绘制路线的示例DEMO:

  
  
  1. self.mapView.delegate = self;
  2. NSString *address1 = @"北京";
  3. NSString *address2 = @"广州";
  4.    
  5. [self.geocoder geocodeAddressString:address1 completionHandler:^(NSArray *placemarks, NSError *error) {
  6.        if (error) return;
  7.        
  8.        CLPlacemark *fromPm = [placemarks firstObject];
  9.        
  10.        [self.geocoder geocodeAddressString:address2 completionHandler:^(NSArray *placemarks, NSError *error) {
  11.          
  12.            if (error) return;
  13.            
  14.            CLPlacemark *toPm = [placemarks firstObject];
  15.            
  16.            [self addLineFrom:fromPm to:toPm];
  17.        }];
  18.    }];
   
   
  1. /**
  2. *  添加导航的线路
  3. *
  4. *  @param fromPm 起始位置
  5. *  @param toPm   结束位置
  6. */
  7. - (void)addLineFrom:(CLPlacemark *)fromPm to:(CLPlacemark *)toPm
  8. {
  9.    // 1.添加2个大头针
  10.    HTAnnotation *fromAnno = [[HTAnnotation alloc] init];
  11.    fromAnno.coordinate = fromPm.location.coordinate;
  12.    fromAnno.title = fromPm.name;
  13.    [self.mapView addAnnotation:fromAnno];
  14.    
  15.    HTAnnotation *toAnno = [[HTAnnotation alloc] init];
  16.    toAnno.coordinate = toPm.location.coordinate;
  17.    toAnno.title = toPm.name;
  18.    [self.mapView addAnnotation:toAnno];
  19.    
  20.    // 2.查找路线
  21.    
  22.    // 方向请求
  23.    MKDirectionsRequest *request = [[MKDirectionsRequest alloc] init];
  24.    // 设置起点
  25.    MKPlacemark *sourcePm = [[MKPlacemark alloc] initWithPlacemark:fromPm];
  26.    request.source = [[MKMapItem alloc] initWithPlacemark:sourcePm];
  27.    
  28.    // 设置终点
  29.    MKPlacemark *destinationPm = [[MKPlacemark alloc] initWithPlacemark:toPm];
  30.    request.destination = [[MKMapItem alloc] initWithPlacemark:destinationPm];
  31.    
  32.    // 方向对象
  33.    MKDirections *directions = [[MKDirections alloc] initWithRequest:request];
  34.    
  35.    // 计算路线
  36.    [directions calculateDirectionsWithCompletionHandler:^(MKDirectionsResponse *response, NSError *error) {
  37.        NSLog(@"总共%d条路线", response.routes.count);
  38.        
  39.        // 遍历所有的路线
  40.        for (MKRoute *route in response.routes) {
  41.            // 添加路线遮盖
  42.            [self.mapView addOverlay:route.polyline];
  43.        }
  44.    }];
  45. }
  46. #pragma mark - MKMapViewDelegate
  47. - (MKOverlayRenderer *)mapView:(MKMapView *)mapView rendererForOverlay:(id<MKOverlay>)overlay
  48. {
  49.    MKPolylineRenderer *renderer = [[MKPolylineRenderer alloc] initWithOverlay:overlay];
  50.    renderer.strokeColor = [UIColor redColor];
  51.    return renderer;
  52. }

写到这就差不多完了,我这篇博文还有很多不细致和不严谨的地方,以后会慢慢完善,而且这其中有很多事我很久以前学习的时候做下来的记录,还有很多iOS9 的新特性没有提出来,不足之处还请见谅.











评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值