iOS定位服务与地图开发(4)---显示地图
iOS 6之前,苹果使用的是谷歌地图,iOS 6之后,苹果使用了自己的地图(国内好像用的是高德地图),但是API编程接口与iOS 5相比没有太大变化。
iOS 应用程序中使用Map Kit API开发地图应用程序,使用MKMapView类作为地图显示视图,其委托协议是MKMapViewDelegate。
1、显示地图:
.h文件中代码
#import <MapKit/MapKit.h> @interface YXCViewController <MKMapViewDelegate>@end
.m文件类实现代码
@implementation YXCViewController - (void)viewDidLoad { [super viewDidLoad]; // 设置地图的类型 self.mapView.mapType = MKMapTypeStandard; // 设置代理 self.mapView.delegate = self; } #pragma mark - MKMapViewDelegate代理方法 // 失败回调 - (void)mapViewDidFailLoadingMap:(MKMapView *)mapView withError:(NSError *)error { NSLog(@"error : %@",error.localizedDescription); } @end
地图类型有3种:
MKMapTypeStandard:标准地图。
MKMapTypeSatellite:卫星地图类型。
MKMapTypeHybrid:混合地图类型。
2、添加标注:
如果要在地图视图上添加标注点,需要2个步骤:1)触发添加动作;2)实现地图委托方法mapView:viewForAnnotation:,完成添加标注。
1)触发添加动作:
- (IBAction)geocodeQuery:(id)sender { // 从界面文本框获取查询地址字符串 if (_txtQueryKey.text == nil || [_txtQueryKey.text length] == 0) { return ; } CLGeocoder *geocoder = [[CLGeocoder alloc] init]; [geocoder geocodeAddressString:_txtQueryKey.text completionHandler:^(NSArray *placemarks, NSError *error) { NSLog(@"查询记录数:%i",[placemarks count]); if ([placemarks count] > 0) { // 移除目前地图上所有标注点【否则单击查询按钮,你会发现地图上的标注点越来越多】 [self.mapView removeAnnotations:_mapView.annotations]; } for (int i = 0; i < [placemarks count]; i++) { CLPlacemark *placemark = placemarks[i]; // 关闭键盘 [_txtQueryKey resignFirstResponder]; // 调整地图位置和缩放比例 MKCoordinateRegion viewRegion = MKCoordinateRegionMakeWithDistance(placemark.location.coordinate, 1000, 1000); [_mapView setRegion:viewRegion animated:YES]; // 实例化自定义的实现了MKAnnotation协议的地图标注点类 MapLocation *annoation = [[MapLocation alloc] init]; annoation.streetAddress = placemark.thoroughfare; annoation.city = placemark.locality; annoation.state = placemark.administrativeArea; annoation.zip = placemark.postalCode; annoation.coordinate = placemark.location.coordinate; // 把标注点对象添加到地图上 // 该方法一定会调用代理方法mapView: viewForAnnotation: [_mapView addAnnotation:annoation]; } }]; }
MKCoordinateRegionMakeWithDistance()函数封装了一个表示地图区域的结构体:
typedef struct {
CLLocationCoordinate2D center; // 中心点
MKCoordinateSpan span; // 跨度
}MKCoordinateRegion ;
2)实现代理方法,完成添加标注
// 委托方法,在地图视图添加标注的时候回调 - (MKAnnotationView *)mapView:(MKMapView *)mapView viewForAnnotation:(id<MKAnnotation>)annotation { // 获得地图标注对象 MKPinAnnotationView *annoationView = (MKPinAnnotationView *)[_mapView dequeueReusableAnnotationViewWithIdentifier:@"PIN_ANNOATION"]; if (annoationView == nil) { annoationView = [[MKPinAnnotationView alloc] initWithAnnotation:annotation reuseIdentifier:@"PIN_ANNOATION"]; } // 设置大头针标注视图的颜色为紫色 annoationView.pinColor= MKPinAnnotationColorPurple; // 设置标注视图时候是否动画显示在地图上 annoationView.animatesDrop = YES; // 在标注上可以显示一些附加信息,为YES情况下单击“大头针”时会出现一个气泡 // 气泡中文字信息封装在MapLocation对象中 annoationView.canShowCallout = YES; return annoationView; }
自定义标注类MapLocation实现:
首先需要引入<Mapkit/MapKit.h>头文件,因为MKAnnotation协议是包含在该框架中。
- (NSString *)title :标注点上的主标题
- (NSString *)subTitle:标注点上副标题
.h头文件中代码:
#import <MapKit/MapKit.h> @interface MapLocation : NSObject<MKAnnotation> // 地理坐标 @property (nonatomic , readwrite) CLLocationCoordinate2D coordinate; // 街道信息属性 @property (nonatomic , copy) NSString *streetAddress; // 城市信息属性 @property (nonatomic , copy) NSString *city; // 州、省、市信息 @property (nonatomic , copy) NSString *state; // 邮编 @property (nonatomic , copy) NSString *zip; @end
.m中代码:
@implementation MapLocation - (NSString *)title { return @"您的位置!"; } - (NSString *)subtitle { NSMutableString *ret = [[NSMutableString alloc] init]; if (_state) [ ret appendString:_state]; if (_city) { [ret appendString:_city]; } if (_city && _state) { [ret appendString:@","]; } if (_streetAddress && (_city || _state || _zip)) { [ret appendString:@"?"]; } if (_streetAddress) { [ret appendString:_streetAddress]; } if (_zip) { [ret appendFormat:@",%@",_zip]; } return ret; }
效果图:
3、跟踪用户位置变化:
MapKit提供了跟踪用户位置和方向变化的API,可以不用自己编写定位服务代码。开启地图视图的showsUserLocation属性,并设置方法setUserTrackingMode:就可以了,参考代码如下:
- (void)viewDidLoad { [super viewDidLoad]; // 设置地图的类型 self.mapView.mapType = MKMapTypeStandard; // 设置代理 self.mapView.delegate = self; // 允许跟踪显示用户的位置信息 self.mapView.showsUserLocation = YES; // 设置用户跟踪模式(有3种) [self.mapView setUserTrackingMode:MKUserTrackingModeFollow animated:YES]; }
// 实现地图视图的委托方法 // 该方法是在定位服务更新完成用户位置时回调 // 在该方法中重新调整地图的中心点为当前用户的中心点 - (void)mapView:(MKMapView *)mapView didUpdateUserLocation:(MKUserLocation *)userLocation { self.mapView.centerCoordinate = userLocation.location.coordinate; }