美文网首页好文Swift
iOS MKMapView 基础

iOS MKMapView 基础

作者: 夜雨聲煩_ | 来源:发表于2018-09-05 15:30 被阅读0次

    综述

    地图相关类前缀CL: Core Location。

    一.定位

    CLLocationManager

    The CLLocationManager object is your entry point to the location service.
    用于定位

    构造方法
    - (CLLocationManager *)locationManager
    {
        if (!_locationManager) {
            //判断定位功能是否打开
            if ([CLLocationManager locationServicesEnabled]) {
                _locationManager = [[CLLocationManager alloc]init];
                _locationManager.delegate = self;
                [_locationManager requestWhenInUseAuthorization];
                
                //设置寻址精度
                _locationManager.desiredAccuracy = kCLLocationAccuracyBest;
                _locationManager.distanceFilter = 5.0;
                [_locationManager startUpdatingLocation];
            }
        }
        return _locationManager;
    }
    
    定位权限
    - (void)getUserLocationAuthorization{
        //判断当前设备定位服务是否打开
        if (![CLLocationManager locationServicesEnabled]) {
            NSLog(@"设备尚未打开定位服务");
        }
        
        //判断当前设备版本大于iOS8以后的话执行里面的方法
        if ([UIDevice currentDevice].systemVersion.floatValue >=8.0) {
            //当用户使用的时候授权
            [self.locationManager requestWhenInUseAuthorization];
        }
        if ([CLLocationManager authorizationStatus] == kCLAuthorizationStatusDenied) {
            NSString *message = @"您的手机目前未开启定位服务,如欲开启定位服务,请至设定开启定位服务功能";
            UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"无法定位" message:message delegate:nil cancelButtonTitle:@"确定" otherButtonTitles: nil];
            [alertView show];
        }
    }
    
    设置显示范围

    遵循CLLocationManagerDelegate协议,实现代理方法

    -(void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray<CLLocation *> *)locations
    {
        [self.locationManager stopUpdatingHeading];
        //地址
        self.userLocation = [locations lastObject];
        //显示范围
        double latitudeSpan = fabs(self.latitude - self.userLocation.coordinate.latitude) * 3;
        double longitudeSpan = fabs(self.longitude - self.userLocation.coordinate.longitude) *3;
        
        MKCoordinateSpan span = MKCoordinateSpanMake(latitudeSpan, longitudeSpan);
        MKCoordinateRegion regoin = MKCoordinateRegionMake(self.userLocation.coordinate, span);
        [self.mapView setRegion:regoin animated:YES];
    }
    

    二.地图

    初始化
    - (MKMapView *)mapView
    {
        if (!_mapView) {
            _mapView = [[MKMapView alloc] initWithFrame:CGRectMake(0,0, kScreenWidth, kScreenHeight)];
            //设置用户的跟踪模式
            _mapView.userTrackingMode = MKUserTrackingModeFollow;
            //设置标准地图
            _mapView.mapType = MKMapTypeStandard;
            // 不显示罗盘和比例尺
            if (@available(iOS 9.0, *)) {
                _mapView.showsCompass = NO;
                _mapView.showsScale = NO;
            }
            // 开启定位
            _mapView.showsUserLocation = YES;
            _mapView.delegate = self;
            //初始位置及显示范围
            MKCoordinateSpan span=MKCoordinateSpanMake(0.021251, 0.016093);
            [_mapView setRegion:MKCoordinateRegionMake(self.mapView.userLocation.coordinate, span) animated:YES];
        }
        return _mapView;
    }
    
    设置覆盖物
    - (void)initCarPoint{
        //创建CLLocation 设置经纬度
        CLLocation *loc = [[CLLocation alloc]initWithLatitude:self.latitude longitude:self.longitude];
        CLLocationCoordinate2D coord = [loc coordinate];
        //创建标题
        NSString *titile = @"救护车";
        MSCarPoint *myPoint = [[MSCarPoint alloc] initWithCoordinate:coord andTitle:titile];
        //添加标注
        [self.mapView addAnnotation:myPoint];
    }
    
    - (MKAnnotationView *)mapView:(MKMapView *)mapView viewForAnnotation:(id<MKAnnotation>)annotation{
        static NSString *placemarkIdentifier = @"PointAnnotation";
        if ([annotation isKindOfClass:[MSCarPoint class]]){
            MKAnnotationView *annotationView = [[MKAnnotationView alloc] initWithAnnotation:annotation reuseIdentifier:placemarkIdentifier];
            if([annotation.title isEqualToString:@"救护车"]){
                //救护车
                annotationView.image = [UIImage imageNamed:@"icon"];
            }
            return annotationView;
        }
        return nil;
    }
    
    重定位我的位置
    - (void)resetLocation:(id)sender {
        // 定位到我的位置
        [self.mapView setCenterCoordinate:_mapView.userLocation.coordinate animated:YES];
    }
    

    三.地理编码

    CLGeocoder

    CLGeocoder: 地理编码。
    地理编码:根据给定的地名,获得具体的位置信息(比如经纬度、地址的全称等)
    反地理编码:根据给定的经纬度,获得具体的位置信息

    CLPlacemark

    CLPlacemark: 详细的地址位置信息,包括如下主要属性。
    地理位置     @property (nonatomic, readonly) CLLocation *location;
    区域       @property (nonatomic, readonly) CLRegion *region;
    详细的地址信息 @property (nonatomic, readonly) NSDictionary *addressDictionary;
    地址名称    @property (nonatomic, readonly) NSString *name;
    城市      @property (nonatomic, readonly) NSString *locality;

    CLLocation

    CLLocation:地理位置

    根据地名进行标注代码实例
    //初始化地理编码器
    let coder = CLGeocoder()
    //根据地名字符串返回CLPlacemark数组和error
    coder.geocodeAddressString(area.name) { (placeMark, error) in
        //使用guard进行前置条件判断,为空时打印错误然后终止方法
        guard placeMark != nil else {
            print(error ?? "未知错误")
            return
        }
        //获取地理位置详细信息数组中第一个
        let place = placeMark?.first
        //初始化标注
        let annotation = MKPointAnnotation()
        //指定标注标题及副标题
        annotation.title = self.area.name
        annotation.subtitle = self.area.province
        
        //获取CLPlacemark中的CLLocation
        if let location = place?.location{
            //设置标注经纬度
            annotation.coordinate = location.coordinate
            //显示标注
            self.mapView.showAnnotations([annotation], animated: true)
            //选中标注
            self.mapView.selectAnnotation(annotation, animated: true)
        }
    }
    

    自定义图钉视图

    遵循MKMapViewDelegate协议,实现如下代理方法。
    - (nullable MKAnnotationView *)mapView:(MKMapView *)mapView viewForAnnotation:(id <MKAnnotation>)annotation;
    代码如下。

    // MARK: - map delegate
    func mapView(_ mapView: MKMapView, viewFor annotation: MKAnnotation) -> MKAnnotationView? {
        //判断是否是用户位置
        if annotation is MKUserLocation {
            //如果是用户当前位置,终止方法
            return nil
        }
        //指定标注重用标识符
        let mapId = "myAnnotationId"
        //根据重用标识符获取标注视图(与cell重用原理类似)。 注:取出标注视图转为MKPinAnnotationView,自带图钉(只自定义左附加视图图片)
        var annotationView = mapView.dequeueReusableAnnotationView(withIdentifier: mapId) as? MKPinAnnotationView
        //判断标注视图是否存在
        if annotationView == nil {
            //如果标注视图不存在,根据标注和标注重用标识符创建标注视图
            annotationView = MKPinAnnotationView(annotation: annotation, reuseIdentifier: mapId)
            annotationView?.canShowCallout = true
        }
        //设置自定义icon视图
        let iconView = UIImageView(frame: CGRect(x: 0, y: 0, width: 53, height: 53))
        iconView.image = UIImage(named: "dislike")
        //设置左附加视图图片
        annotationView?.leftCalloutAccessoryView = iconView
        
        //自定义图钉颜色 IOS9+
        annotationView?.pinTintColor = UIColor.blue
        
        //返回标注视图
        return annotationView
    }
    

    相关文章

      网友评论

        本文标题:iOS MKMapView 基础

        本文链接:https://www.haomeiwen.com/subject/kvmawftx.html