浏览器版本低!无法浏览完整内容,建议升级或更换浏览器。

文档全面上新

更科技的视觉体验,更高效的页面结构,快前往体验吧!

体验新版
更新时间:2023-04-06
点标记简介

点标记用来在地图上标记任何位置,例如用户位置、车辆位置、店铺位置等一切带有位置属性的事物。

百度地图iOS SDK 提供的点标记功能包含两大部分,一部分是点(俗称Annotation)、另一部分是浮于点上方的信息窗体(俗称 PaopaoView)。同时,SDK对Annotation和PaopaoView封装了大量的触发事件,例如点击事件、长按事件、拖拽事件。

Annotation和 PaopaoView 有默认风格,同时也支持自定义。

添加默认样式标记

iOS地图SDK预置了基本的标注点(BMKPointAnnotation)和一个大头针标注View(BMKPinAnnotationView),您可以直接使用来显示标注。

iOS地图SDK提供的大头针标注BMKPinAnnotationView,通过它可以设置大头针颜色、是否显示动画等。

1添加标注数据对象
Objective-C
Swift
BMKPointAnnotation* annotation = [[BMKPointAnnotation alloc]init];
annotation.coordinate = CLLocationCoordinate2DMake(39.915, 116.404);
//设置标注的标题
annotation.title = @"北京";
//副标题
annotation.subtitle = @"天安门";
[_mapView addAnnotation:annotation];
//初始化标注类BMKPointAnnotation的实例
annotation = BMKPointAnnotation.init()
//设置标注的经纬度坐标
annotation?.coordinate = CLLocationCoordinate2D(latitude: 39.915, longitude: 116.404)
//设置标注的标题
annotation?.title = "北京"
//副标题
annotation?.subtitle = "天安门"
/**
 
 当前地图添加标注,需要实现BMKMapViewDelegate的-mapView:viewForAnnotation:方法
 来生成标注对应的View
 @param annotation 要添加的标注
 */
mapView.addAnnotation(annotation)
2设置标注样式

实现 <BMKMapViewDelegate> 协议中的 mapView:viewForAnnotation:回调函数,设置标注样式。代码如下所示:

Objective-C
Swift
#pragma mark - BMKMapViewDelegate
- (BMKAnnotationView *)mapView:(BMKMapView *)mapView viewForAnnotation:(id <BMKAnnotation>)annotation
{
    if ([annotation isKindOfClass:[BMKPointAnnotation class]])
    {
        static NSString *reuseIndetifier = @"annotationReuseIndetifier";
        BMKAnnotationView *annotationView = [mapView dequeueReusableAnnotationViewWithIdentifier:reuseIndetifier];
        if (annotationView == nil)
        {
            annotationView = [[BMKAnnotationView alloc] initWithAnnotation:annotation
                                                              reuseIdentifier:reuseIndetifier];
        }
        return annotationView;
    }
    return nil;
}
//MARK:BMKMapViewDelegate
/**
 根据anntation生成对应的annotationView
 
 @param mapView 地图View
 @param annotation 指定的标注
 @return 生成的标注View
 */
func mapView(_ mapView: BMKMapView!, viewFor annotation: BMKAnnotation!) -> BMKAnnotationView! {
    if annotation.isKind(of: BMKPointAnnotation.self) {
        /**
         根据指定标识查找一个可被复用的标注,用此方法来代替新创建一个标注,返回可被复用的标注
         */
        var annotationView: BMKPinAnnotationView? = mapView.dequeueReusableAnnotationView(withIdentifier: annotationViewIdentifier) as? BMKPinAnnotationView
        if annotationView == nil {
            /**
             初始化并返回一个annotationView
             
             @param annotation 关联的annotation对象
             @param reuseIdentifier 如果要重用view,传入一个字符串,否则设为nil,建议重用view
             @return 初始化成功则返回annotationView,否则返回nil
             */
            annotationView = BMKPinAnnotationView.init(annotation: annotation, reuseIdentifier: annotationViewIdentifier)
        }
        return annotationView
    }
    return nil
}
3运行程序

在地图显示对应的标注点,点击标注弹出气泡,效果如图:

IMG_0297.PNG

添加自定义样式点标记

iOS 地图SDK可自定义标注(包括自定义标注图标和自定义气泡图标),均通过BMKAnnotationView来实现。

自定义标注图标

若大头针样式的标注不能满足您的需求,您可以自定义标注图标。代码如下:

Objective-C
Swift
#pragma mark - BMKMapViewDelegate
- (BMKAnnotationView *)mapView:(BMKMapView *)mapView viewForAnnotation:(id <BMKAnnotation>)annotation
{
    if ([annotation isKindOfClass:[BMKPointAnnotation class]])
    {
        static NSString *reuseIndetifier = @"annotationReuseIndetifier";
        BMKAnnotationView *annotationView = [mapView dequeueReusableAnnotationViewWithIdentifier:reuseIndetifier];
        if (annotationView == nil)
        {
            annotationView = [[BMKAnnotationView alloc] initWithAnnotation:annotation
                                                              reuseIdentifier:reuseIndetifier];
        }

        annotationView.image = [UIImage imageNamed:@"poi.png"];
        return annotationView;
    }
    return nil;
}
//MARK:BMKMapViewDelegate
/**
 根据anntation生成对应的annotationView
 
 @param mapView 地图View
 @param annotation 指定的标注
 @return 生成的标注View
 */
func mapView(_ mapView: BMKMapView!, viewFor annotation: BMKAnnotation!) -> BMKAnnotationView! {
    if annotation.isKind(of: BMKPointAnnotation.self) {
        /**
         根据指定标识查找一个可被复用的标注,用此方法来代替新创建一个标注,返回可被复用的标注
         */
        var annotationView: BMKPinAnnotationView? = mapView.dequeueReusableAnnotationView(withIdentifier: annotationViewIdentifier) as? BMKPinAnnotationView
        if annotationView == nil {
            /**
             初始化并返回一个annotationView
             
             @param annotation 关联的annotation对象
             @param reuseIdentifier 如果要重用view,传入一个字符串,否则设为nil,建议重用view
             @return 初始化成功则返回annotationView,否则返回nil
             */
            annotationView = BMKPinAnnotationView.init(annotation: annotation, reuseIdentifier: annotationViewIdentifier)
            //annotationView显示的图片,默认是大头针
            annotationView?.image = UIImage.init(named: "poi.png")
        }
        return annotationView
    }
    return nil
}

效果如图:

IMG_0271.PNG

添加自定义气泡

气泡在iOS中又称为PaopaoView,它由背景和气泡内容构成。

自定义气泡类完整代码如下:

#import <UIKit/UIKit.h>

@interface CustomPaopaoView : UIView
@property (nonatomic, strong) UIImage *image; //商户图
@property (nonatomic, copy) NSString *title; //商户名
@property (nonatomic, copy) NSString *subtitle; //地址
@end

#import "CustomPaopaoView.h"
#define kPortraitMargin     5
#define kPortraitWidth      50
#define kPortraitHeight     50
#define kTitleWidth         120
#define kTitleHeight        20
#define kArrorHeight 0

@interface CustomPaopaoView ()

@property (nonatomic, strong) UIImageView *portraitView;
@property (nonatomic, strong) UILabel *subtitleLabel;
@property (nonatomic, strong) UILabel *titleLabel;
@end
@implementation CustomPaopaoView

#pragma mark - draw rect

- (void)drawRect:(CGRect)rect
{
[self drawInContext:UIGraphicsGetCurrentContext()];

self.layer.shadowColor = [[UIColor blackColor] CGColor];
self.layer.shadowOpacity = 1.0;
self.layer.shadowOffset = CGSizeMake(0.0f, 0.0f);
}

- (void)drawInContext:(CGContextRef)context
{
CGContextSetLineWidth(context, 2.0);
CGContextSetFillColorWithColor(context, [UIColor colorWithRed:0.3 green:0.3 blue:0.3 alpha:0.8].CGColor);

    [self getDrawPath:context];
    CGContextFillPath(context);
}
- (void)getDrawPath:(CGContextRef)context
{
    CGRect rrect = self.bounds;
    CGFloat radius = 6.0;
    CGFloat minx = CGRectGetMinX(rrect),
    midx = CGRectGetMidX(rrect),
    maxx = CGRectGetMaxX(rrect);
    CGFloat miny = CGRectGetMinY(rrect),
    maxy = CGRectGetMaxY(rrect)-kArrorHeight;

    CGContextMoveToPoint(context, midx+kArrorHeight, maxy);
    CGContextAddLineToPoint(context,midx, maxy+kArrorHeight);
    CGContextAddLineToPoint(context,midx-kArrorHeight, maxy);

    CGContextAddArcToPoint(context, minx, maxy, minx, miny, radius);
    CGContextAddArcToPoint(context, minx, minx, maxx, miny, radius);
    CGContextAddArcToPoint(context, maxx, miny, maxx, maxx, radius);
    CGContextAddArcToPoint(context, maxx, maxy, midx, maxy, radius);
    CGContextClosePath(context);
}

- (id)initWithFrame:(CGRect)frame
{
    self = [super initWithFrame:frame];
    if (self) {
        self.backgroundColor = [UIColor clearColor];
        [self initSubViews];
    }
    return self;
}

- (void)initSubViews
{
    // 添加图片,即商户图
    self.portraitView = [[UIImageView alloc] initWithFrame:CGRectMake(kPortraitMargin, kPortraitMargin, kPortraitWidth, kPortraitHeight)];

    self.portraitView.backgroundColor = [UIColor blackColor];
    [self addSubview:self.portraitView];

    // 添加标题,即商户名
    self.titleLabel = [[UILabel alloc] initWithFrame:CGRectMake(kPortraitMargin * 2 + kPortraitWidth, kPortraitMargin, kTitleWidth, kTitleHeight)];
    self.titleLabel.font = [UIFont boldSystemFontOfSize:14];
    self.titleLabel.textColor = [UIColor whiteColor];
    self.titleLabel.text = self.title;
    [self addSubview:self.titleLabel];

    // 添加副标题,即商户地址
    self.subtitleLabel = [[UILabel alloc] initWithFrame:CGRectMake(kPortraitMargin * 2 + kPortraitWidth, kPortraitMargin * 2 + kTitleHeight, kTitleWidth, kTitleHeight)];
    self.subtitleLabel.font = [UIFont systemFontOfSize:12];
    self.subtitleLabel.textColor = [UIColor lightGrayColor];
    self.subtitleLabel.text = self.subtitle;
    [self addSubview:self.subtitleLabel];
}

- (void)setTitle:(NSString *)title
{
    self.titleLabel.text = title;
}

- (void)setSubtitle:(NSString *)subtitle
{
    self.subtitleLabel.text = subtitle;
}

- (void)setImage:(UIImage *)image
{
    self.portraitView.image = image;
}

@end

以上就是自定义气泡类的全部示例代码,在点击标注时实现弹出自定义的气泡的效果,还需要在BMKMapView的代理方法mapView: viewForAnnotation:设置自定义的paopaoView,完整代码如下:

#pragma mark - BMKMapViewDelegate
- (BMKAnnotationView *)mapView:(BMKMapView *)mapView viewForAnnotation:(id <BMKAnnotation>)annotation
{
    if ([annotation isKindOfClass:[BMKPointAnnotation class]])
    {
        static NSString *reuseIndetifier = @"annotationReuseIndetifier";
        BMKAnnotationView *annotationView = [mapView dequeueReusableAnnotationViewWithIdentifier:reuseIndetifier];
        if (annotationView == nil)
        {
            annotationView = [[BMKAnnotationView alloc] initWithAnnotation:annotation
                                                              reuseIdentifier:reuseIndetifier];
        }

        annotationView.image = [UIImage imageNamed:@"poi.png"];

        annotationView.canShowCallout = YES;
        CustomPaopaoView *customPopView = [[CustomPaopaoView alloc] init];
        customPopView.frame = CGRectMake(0, 0, 120.0f, 70.0f);
        customPopView.image = [UIImage imageNamed:@"poi.png"];
        customPopView.title = @"北京";
        customPopView.subtitle = @"天安门";

        BMKActionPaopaoView *pView = [[BMKActionPaopaoView alloc] initWithCustomView:customPopView];
        pView.backgroundColor = [UIColor lightGrayColor];
        pView.frame = customPopView.frame;
        annotationView.paopaoView = pView;
        return annotationView;
    }
    return nil;
}

效果如图:

sign003.jpg

删除单个点标记

Objective-C
Swift
//删除指定的单个点标记
[_mapView removeAnnotation:annotation];
//删除指定的单个点标记
mapView?.removeAnnotation(annotation)
批量操作Annotation

批量添加Annotation

Objective-C
Swift
/**
 *向地图窗口添加一组标注,需要实现BMKMapViewDelegate的-mapView:viewForAnnotation:函数来生成标注对应的View
 *@param annotations 要添加的标注数组
 */
[_mapView addAnnotations:annotations];
/**
 *向地图窗口添加一组标注,需要实现BMKMapViewDelegate的-mapView:viewForAnnotation:函数来生成标注对应的View
 *@param annotations 要添加的标注数组
 */
mapView?.addAnnotations(annotations)

批量删除Annotation

Objective-C
Swift
/**
 *移除一组标注
 *@param annotation 要移除的标注数组
 */
[_mapView removeAnnotations:annotations];
/**
 *移除一组标注
 *@param annotation 要移除的标注数组
 */
mapView?.removeAnnotations(annotations)
点标记碰撞策略

简介

Since 6.5.0 iOS地图SDK起支持点标记碰撞策略功能

碰撞策略相关属性

BMKAnnotationView新增以下属性,整体碰撞策略优先级:层级限制>强制展示>碰撞优先级>展示优先级>添加顺序

属性 类型 说明
displayMaxLevel float 需要展示的最大级别,大于此级别则不展示,默认22。V6.5.0以后支持
displayMinLevel float 需要展示的最小级别,小于此级别则不展示,默认4。V6.5.0以后支持
isOpenCollisionDetection BOOL 开启碰撞检测,默认NO,关闭。V6.5.0以后支持
collisionDetectionPriority NSInteger 碰撞检测优先级,同一优先级后添加的优先展示。V6.5.0以后支持,默认为0
isForceDisplay BOOL 开启碰撞检测时,是否强制展示,默认NO。V6.5.0以后支持

实现

1添加标注数据对象
Objective-C
Swift
NSMutableArray *annotations = [NSMutableArray array]; 
  for (NSInteger i = 0; i < 20; i++) { 
    double lat =  (arc4random() % 100) * 0.001; 
    double lon =  (arc4random() % 100) * 0.001; 
    BMKPointAnnotation *annotation = [[BMKPointAnnotation alloc] init]; 
    annotation.coordinate = CLLocationCoordinate2DMake(_basicAnnotationCoordinate.latitude + lat, _basicAnnotationCoordinate.longitude + lon); 
    annotation.title = @"绿"; 
    [annotations addObject:annotation]; 
} 
[self.mapView addAnnotations:annotations];
    let annotations = NSMutableArray();
    for _ in 0..<20 { 
    let lat =  Double((arc4random() % 100)) * 0.001 
    let lon =  Double((arc4random() % 100)) * 0.001 
    let annotation = BMKPointAnnotation() 
    annotation.coordinate = CLLocationCoordinate2D(latitude: basicAnnotationCoordinate!.latitude + lat, longitude: basicAnnotationCoordinate!.longitude + lon) 
    annotation.title = "绿" 
    annotations.add(annotation);
} 
mapView.addAnnotations(annotations as! [BMKAnnotation])
2实现代理方法生成对应的view

实现 <BMKMapViewDelegate> 协议中的 mapView:viewForAnnotation:回调函数,设置标注样式。代码如下所示:

Objective-C
Swift
#pragma mark - BMKMapViewDelegate 
  - (BMKAnnotationView *)mapView:(BMKMapView *)mapView viewForAnnotation:(id<BMKAnnotation>)annotation { 
     BMKPinAnnotationView *pinAnnotationView = (BMKPinAnnotationView *)[mapView dequeueReusableAnnotationViewWithIdentifier:annotationViewIdentifier]; 
    if (!pinAnnotationView) { 
        pinAnnotationView = [[BMKPinAnnotationView alloc] initWithAnnotation:annotation reuseIdentifier:annotationViewIdentifier]; 
    }
    if ([annotation.title isEqualToString:@"红"]) { 
        pinAnnotationView.pinColor = BMKPinAnnotationColorRed;
        // 强制展示 
        pinAnnotationView.isForceDisplay = YES; 
    } else if ([annotation.title isEqualToString:@"紫"]) { 
        pinAnnotationView.pinColor = BMKPinAnnotationColorPurple; 
        // 最大展示级别 
        pinAnnotationView.displayMaxLevel = 19; 
        // 最小展示级别 
        pinAnnotationView.displayMinLevel = 10; 
    } else { 
        pinAnnotationView.pinColor = BMKPinAnnotationColorGreen; 
    }
        // 开启碰撞检测 
    pinAnnotationView.isOpenCollisionDetection = YES; 
    return pinAnnotationView;
}
//MARK:BMKMapViewDelegate
  /** 
  根据anntation生成对应的annotationView

  @param mapView 地图View 
  @param annotation 指定的标注 
  @return 生成的标注View 
  */
func mapView(_ mapView: BMKMapView, viewFor annotation: BMKAnnotation) -> BMKAnnotationView? {
     var annotationView: BMKPinAnnotationView? = mapView.dequeueReusableAnnotationView(withIdentifier: annotationViewIdentifier) as? BMKPinAnnotationView 
     if annotationView == nil { 
          annotationView = BMKPinAnnotationView.init(annotation: annotation, reuseIdentifier: annotationViewIdentifier)
        } 
     if annotation.title?() == "红" { 
        annotationView!.pinColor = UInt(BMKPinAnnotationColorRed); 
        // 强制展示 
        annotationView!.isForceDisplay = true; 
    } else if annotation.title?() == "紫" { 
        annotationView!.pinColor = UInt(BMKPinAnnotationColorPurple); 
        // 最大展示级别 
        annotationView!.displayMaxLevel = 19 
        // 最小展示级别 
        annotationView!.displayMinLevel = 10 
    } else { 
        annotationView!.pinColor = UInt(BMKPinAnnotationColorGreen) 
    } 
    // 开启碰撞检测 
    annotationView!.isOpenCollisionDetection = true 
    return annotationView 
}
3运行程序

效果如下

607350ecc7b4d7b84b26d909f.png

  • 文档根本没法用

  • 文档水平很差

  • 文档水平一般

  • 文档不错

  • 文档写的很好

如发现文档错误,或对此文档有更好的建议,请在下方反馈。问题咨询请前往反馈平台提交工单咨询。

提交反馈

拖动标注工具

添加矩形标注

添加箭头标注

完成

取消