高德地图-拖拽地图定位
2018-01-25 本文已影响99人
minjing_lin
高德地图-拖拽地图定位
前几天,有个朋友托我帮他写个Demo,高德地图拖拽定位,我之前写过百度的,参考的是 张哥 的这个例子。写之前大概搜了一下,关于百度地图的实例比较多,高德地图比较少。于是就自己按照官方Demo写了一个简单地拖拽定位,整理一下,记录下来~
老规矩,先看图:
高德地图.gif第一步
(1)到高德开放平台申请iOS key;
(2)集成高德地图SDK,我是通过 CocoaPods 来集成的,好处就不说了~
platform :ios, '8.0'
target 'MJAMapDemo' do
pod 'AMapFoundation' #基础SDK
pod 'AMap3DMap' #3D地图SDK
pod 'AMapLocation' #定位功能
pod 'AMapSearch' #地图SDK搜索功能
end
第二步
(1)在项目的 Info.plist 添加定位权限申请
注意:
1.注意iOS11需要多添加一个权限
2.注释文字要详细说明,不然容易被拒~
<key>NSLocationAlwaysAndWhenInUseUsageDescription</key>
<string>需要使用您的位置</string>
<key>NSLocationAlwaysUsageDescription</key>
<string>需要使用您的位置</string>
<key>NSLocationWhenInUseUsageDescription</key>
<string>需要使用您的位置</string>
(2)配置高德Key至AppDelegate.m文件
#import <AMapFoundationKit/AMapFoundationKit.h>
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions{
……
[AMapServices sharedServices].apiKey = @"您的Key";
……
}
第三步
初始化AMapLocationManager定位、MAMapView地图控件和AMapSearchAPI搜索服务
//定位
self.locationManager = [[AMapLocationManager alloc] init];
self.locationManager.delegate = self;
//kCLLocationAccuracyBest 参数,可以获取到精度在10m左右的定位结果,但是相应的需要付出比较长的时间(10s左右)
//kCLLocationAccuracyHundredMeters,一次还不错的定位,偏差在百米左右
[self.locationManager setDesiredAccuracy:kCLLocationAccuracyHundredMeters];
// 定位超时时间,默认为10s。最小值是2s
self.locationManager.locationTimeout = 5;
// 逆地理请求超时时间,默认为5s。最小值是2s
self.locationManager.reGeocodeTimeout =5;
//地图
self.mapView = [[MAMapView alloc]initWithFrame:CGRectMake(0, MJStatusAndNavHeight, SCREEN_WIDTH, MapH)];
self.mapView.delegate = self;
self.mapView.showsUserLocation = NO;
self.mapView.rotateCameraEnabled = NO;
self.mapView.rotateEnabled = NO;
[self.view addSubview:self.mapView];
//搜索
self.search = [[AMapSearchAPI alloc] init];
self.search.delegate = self;
第四步
开始定位,选择带有逆地理信息,以及定位之后添加大头针,然后开始搜索:
//开始定位
- (void)startLocation {
self.currentGPSCoordinate = kCLLocationCoordinate2DInvalid; //一开始要设置为非法值,等定位成功才设置有效值
[MBProgressHUD showActivityMessageInView:@"定位中..."];
[self.mapView removeAnnotations:self.mapView.annotations];
__weak typeof(self) weakSelf = self;
// 是否带有逆地理信息 YES/NO
[self.locationManager requestLocationWithReGeocode:YES completionBlock:^(CLLocation *location, AMapLocationReGeocode *regeocode, NSError *error) {
[MBProgressHUD hideHUD];
if (error) {
[MBProgressHUD showTipMessageInView:@"定位失败,请重新定位"];
MJLog(@"定位错误:{%ld - %@};", (long)error.code, error.localizedDescription);
return;
}
MJLog(@"坐标:%@",location);
if (regeocode) {
MJLog(@"信息地址:%@",regeocode);
}
weakSelf.currentGPSCoordinate = location.coordinate;
//添加定位点的大头针
MAPointAnnotation *annotation = [[MAPointAnnotation alloc] init];
annotation.coordinate = location.coordinate;
[weakSelf.mapView addAnnotation:annotation];
annotation.lockedToScreen = YES;
annotation.lockedScreenPoint = CGPointMake(weakSelf.mapView.bounds.size.width / 2, weakSelf.mapView.bounds.size.height / 2) ;
//设置地图
[weakSelf.mapView setZoomLevel:15.5 animated:YES];
[weakSelf.mapView selectAnnotation:annotation animated:YES];
[weakSelf.mapView setCenterCoordinate:location.coordinate animated:NO];
// //搜索POI
[weakSelf searchAllPOIAround:location.coordinate];
}];
}
//搜索周边POI
- (void)searchAllPOIAround:(CLLocationCoordinate2D)coordinate {
AMapPOIAroundSearchRequest *request = [[AMapPOIAroundSearchRequest alloc] init];
request.sortrule = 0;
request.offset = 30;
request.location = [AMapGeoPoint locationWithLatitude:coordinate.latitude longitude:coordinate.longitude];
request.radius = 500;
[self.search AMapPOIAroundSearch:request];
}
第五步
实现代理协议,比较重要的就是下面这个移动地图之后,要调用的MAMapViewDelegate
代理协议,搜索地图中心点的经纬度
//地图区域改变完成后会调用此接口
- (void)mapView:(MAMapView *)mapView regionDidChangeAnimated:(BOOL)animated {
if (!CLLocationCoordinate2DIsValid(self.currentGPSCoordinate)) { //非法的时候需返回
return;
}
MJPoiResultViewController *poiResultVC = (MJPoiResultViewController *)self.childViewControllers[0];
self.poiResultVC = poiResultVC;
[self.contentView addSubview:poiResultVC.view];
//搜索POI
[self searchAllPOIAround:mapView.centerCoordinate];
}
注意:大头针是跟TableView的Cell一样具有重用机制的,处理不好界面会有很多消失不去的大头针。
- (MAAnnotationView *)mapView:(MAMapView *)mapView viewForAnnotation:(id<MAAnnotation>)annotation {
if ([annotation isKindOfClass:[MAPointAnnotation class]]) {
static NSString *pointReuseIndetifier = @"pointReuseIndetifier";
MAPinAnnotationView *annotationView = (MAPinAnnotationView *)[mapView dequeueReusableAnnotationViewWithIdentifier:pointReuseIndetifier];
if (annotationView == nil) {
annotationView = [[MAPinAnnotationView alloc] initWithAnnotation:annotation reuseIdentifier:pointReuseIndetifier];
}
annotationView.canShowCallout = NO;
annotationView.animatesDrop = YES;
annotationView.draggable = NO;
return annotationView;
}
return nil;
}
实现 AMapSearchDelegate
的代理,把搜索到的内容,传给TableView的数据源
- (void)onPOISearchDone:(AMapPOISearchBaseRequest *)request response:(AMapPOISearchResponse *)response{
self.POIDataArray = response.pois;
self.poiResultVC.resultListArray = response.pois;
}
以上简单版的Demo,就已经完成,下一步准备把滴滴打车首页面的地图拖拽定位功能实现。
Demo地址,如能帮助到你,请点赞~