MKMapView与自定义MKAnnotation

我有一个MKMapView。 我想在我的地图上放置一个自定义的MKAnnotation。

他们是一些餐馆的地方。 我该怎么做?

我的问题是我怎样才能做一个自定义的MKAnnotation?

多谢你们。

如果您完全想自定义标注的标注视图..请参阅此链接。http ://blog.asolutions.com/2010/09/building-custom-map-annotation-callouts-part-1/

首先,让我们将自定义定义为不仅仅是标题和副标题。 我们想改变MKAnnotation的大小,并包含一些自定义graphics。

您可能想要自定义的注释有两部分:

  • MKAnnotation
  • MKAnnotationView

对于最基本的MKAnnotation,您只需简单地采用协议,并返回nil作为标题和副标题,但是您也可以在注释中携带更多信息,以便在点击附件指示器时进行扩展标注。 您可以使用addAnnotation将所有注解添加到MKMapView中:例如,在viewDidLoad中。

MKAnnotation标题

@interface CPAnnotation : NSObject <MKAnnotation> { @private CLLocationCoordinate2D _coordinate; NSString *_title; NSString *_subtitle; } @property (nonatomic, readonly) CLLocationCoordinate2D coordinate; @property (nonatomic, readonly, copy) NSString *title; @property (nonatomic, readonly, copy) NSString *subtitle; - (id)initWithCoordinate:(CLLocationCoordinate2D)coordinate; @end 

MKAnnotation实现

 @implementation CPAnnotation @synthesize coordinate = _coordinate; @synthesize title = _title; @synthesize subtitle = _subtitle; - (id)initWithCoordinate:(CLLocationCoordinate2D)coordinate { self = [super init]; if (self != nil) { self.coordinate = coordinate; } return self; } - (NSString *)title { return _title; } - (NSString *)subtitle { return _subtitle; } @end 

接下来的步骤是自定义掉线的标注。 要做到这一点,你需要自定义MKAnnotationView。 根据苹果公司的说法,你不应该在默认情况下做一个大的标注。 他们推荐一个标准大小的标注,有一个button来打开一个更大的标注。 他们使用小写我在一个蓝色的圆形图标。 这些图标可以通过视图的leftCalloutAccessoryView和rightCalloutAccessoryView属性来设置。 如果您已经采用了MKMapViewDelegate协议并将自己设置为MKMapView的委托,您将获得viewForAnnotation:的callback。

MKAnnotationView MKMapViewDelegatecallback

 - (MKAnnotationView *)mapView:(MKMapView *)mapView viewForAnnotation:(id<MKAnnotation>)annotation { static NSString *const kAnnotationReuseIdentifier = @"CPAnnotationView"; MKAnnotationView *annotationView = [mapView dequeueReusableAnnotationViewWithIdentifier:kAnnotationReuseIdentifier]; if (annotationView == nil) { annotationView = [[[MKPinAnnotationView alloc] initWithAnnotation:annotation reuseIdentifier:kAnnotationReuseIdentifier] autorelease]; annotationView.enabled = YES; annotationView.canShowCallout = YES; annotationView.rightCalloutAccessoryView = [UIButton buttonWithType:UIButtonTypeInfoLight]; } return annotationView; } 

您可以在自定义视图中进一步自定义该视图,覆盖drawRect方法,为图像属性提供图像,或者甚至可以在XIB中实现MKAnnotationView。 这是值得一些实验。

Apple的WeatherAnnotationView示例说明了覆盖drawRect。

我曾经遇到过像标准Pin注释那样的情况,但是devise者需要一个自定义的graphics。

我写了一个MKAnnotationView的子类来显示graphics。 唯一的区别是它覆盖了标准类的image

BlipAnnotationView.h

 #import <MapKit/MapKit.h> @interface BlipAnnotationView : MKAnnotationView - (id)initWithAnnotation:(id<MKAnnotation>)annotation reuseIdentifier:(NSString *)reuseIdentifier; @end 

BlipAnnotationView.m

 #import "BlipAnnotationView.h" @implementation BlipAnnotationView - (id)initWithAnnotation:(id<MKAnnotation>)annotation reuseIdentifier:(NSString *)reuseIdentifier { self = [super initWithAnnotation:annotation reuseIdentifier:reuseIdentifier]; if (self) { UIImage *blipImage = [UIImage imageNamed:@"blip.png"]; CGRect frame = [self frame]; frame.size = [blipImage size]; [self setFrame:frame]; [self setCenterOffset:CGPointMake(0.0, -7.0)]; [self setImage:blipImage]; } return self; } @end 

然后在显示地图的类中,我使类实现了MKMapViewDelegate协议。 如果需要, mapView:viewForAnnotation:方法将创build一个BlipAnnotationView的新实例。

 - (MKAnnotationView *)mapView:(MKMapView *)mapView viewForAnnotation:(id<MKAnnotation>)annotation { NSLog(@"mapView:%@ viewForAnnotation:%@", mapView, annotation); static NSString *const kAnnotationIdentifier = @"BlipMapAnnotation"; BlipAnnotationView *annotationView = (BlipAnnotationView *) [mapView dequeueReusableAnnotationViewWithIdentifier:kAnnotationIdentifier]; if (! annotationView) { annotationView = [[BlipAnnotationView alloc] initWithAnnotation:annotation reuseIdentifier:kAnnotationIdentifier]; } [annotationView setAnnotation:annotation]; return annotationView; } 

最后,我将这个类设置为awakeFromNib中的地图视图的委托:

 - (void)awakeFromNib { [...] [_theMapView setDelegate:self]; } 

我不必更改定位注释的代码:

 MKPointAnnotation *annotationPoint = [[MKPointAnnotation alloc] init]; [annotationPoint setCoordinate:[userLocation coordinate]]; [annotationPoint setTitle:label]; [_theMapView addAnnotation:annotationPoint];