是否有可能从MKPolyline继承

时间:2011-02-09 18:41:30

标签: ios mapkit

我正在为iPhone构建基于MapKit的应用程序。

我在地图上添加了许多MKPolylines。

但是,我想让我自己的Model类符合添加到地图的MKOverlay协议,而不是拥有MKPolyline,这样我就可以在mapView中创建相应的视图时访问模型属性:viewForOverlay。

问题是我找不到从MKPolyline继承的方法,因为它没有我可以从子类'init调用的任何init方法。您只能使用便捷方法创建它们。

如何将模型属性和MKPolyline行为结合在一起?

5 个答案:

答案 0 :(得分:7)

MANIAK_dobrii的代码是要走的路,但我发现我必须实现一些额外的MKMultiPoint方法才能使它工作,这里是我使用的AnchorLine类的完整标题和实现文件: -

标题AnchorLine.h

#import <MapKit/MapKit.h>

@interface AnchorLine : NSObject <MKOverlay> {
    MKPolyline* polyline;
}

@property (nonatomic, retain) MKPolyline* polyline;

+ (AnchorLine*)initWithPolyline: (MKPolyline*) line;
@end

实施AnchorLine.m

#import "AnchorLine.h"

@implementation AnchorLine

@synthesize polyline;


+ (AnchorLine*)initWithPolyline: (MKPolyline*) line {
    AnchorLine* anchorLine = [[AnchorLine alloc] init];
    anchorLine.polyline = line;
    return [anchorLine autorelease];
}

- (void) dealloc {
    [polyline release];
    polyline = nil;
    [super dealloc];
}

#pragma mark MKOverlay
//@property (nonatomic, readonly) CLLocationCoordinate2D coordinate;
- (CLLocationCoordinate2D) coordinate {
    return [polyline coordinate];
}

//@property (nonatomic, readonly) MKMapRect boundingMapRect;
- (MKMapRect) boundingMapRect {
    return [polyline boundingMapRect];
}

- (BOOL)intersectsMapRect:(MKMapRect)mapRect {
    return [polyline intersectsMapRect:mapRect];
}

- (MKMapPoint *) points {
    return [polyline points];
}


-(NSUInteger) pointCount {
    return [polyline pointCount];
}

- (void)getCoordinates:(CLLocationCoordinate2D *)coords range:(NSRange)range {
    return [polyline getCoordinates:coords range:range];
}

@end

希望能有所帮助。

答案 1 :(得分:4)

你可以set an associated object attribute上课。这允许您将实例变量绑定到现有类。确保你自己清理干净。

答案 2 :(得分:2)

MKPolyline确实没有自己的init方法。事实上,MKPolyline的继承链中唯一具有init方法的类是NSObject。

所以当我将MKPolyline子类化时,我只是覆盖了NSObject定义的init方法......

-(id) init {
    self = [super init];
    if(self) {
        //my initialization here
    }
    return self;
}

然后,当你想用坐标实例化你的子类时,你可能会做这样的事情......

-MyPolyline* myPolyline = (MyPolyline*)[MyPolyline polylineWithCoordinates:coordinates count:coordinateCount];

答案 3 :(得分:2)

更新:还有另一个选项(可能更好)为此使用邮件转发(如-forwardingTargetForSelector或其他内容)。

我今天遇到了同样的问题,但提出了其他解决方案。我没有使用Wayne关联的对象属性建议,而是将MKPolyline封装在另一个类中,并将MKOverlay协议的消息传递给它。

所以我有类似于.h:

的东西
@interface MyOverlay : NSObject <MKOverlay>
{
    MKPolyline* polyline;
    id object;
}

@property (nonatomic, retain) id object;
@property (nonatomic, retain) MKPolyline* polyline;

+ (MyOverlay*)myOverlayWithObject: (id)anObject;

@end

在.m:

@implementation MyOverlay
@synthesize object;
@synthesize polyline;


+ (MyOverlay*)routePartOverlayWithObject: (id)anObject {    

    MyOverlay* myOverlay = [[MyOverlay alloc] init];

    ... generating MKPolyline ...

    myOverlay.polyline = ... generated polyline ...;
    routePartOverlay.object = anObject;


    return [myOverlay autorelease];
}

- (void) dealloc {
    [cdRoutePart release]; cdRoutePart = nil;
    [polyline release]; polyline = nil;

    [super dealloc];
}

#pragma mark MKOverlay
//@property (nonatomic, readonly) CLLocationCoordinate2D coordinate;
- (CLLocationCoordinate2D) coordinate {
    return [polyline coordinate];
}

//@property (nonatomic, readonly) MKMapRect boundingMapRect;
- (MKMapRect) boundingMapRect {
    return [polyline boundingMapRect];
}

- (BOOL)intersectsMapRect:(MKMapRect)mapRect {
    return [polyline intersectsMapRect:mapRect];
}

@end

所以MyOverlay的行为类似于MKPolyline(符合MKOverlay),同时我可以使用它做任何事情,拥有尽可能多的属性。

答案 4 :(得分:0)

到目前为止,这里提到的内容对我来说并不是很有用,但我根据其他答案和一些独立研究设定了解决方案。我不是100%肯定的,但如果你使用在内部调用正确'init'方法的静态方法调用,你可以将MKPolyline转换为自定义子类

(CustomPolyline*)[CustomPolyline polylineWithCoordinates:coordinates count:coordinateCount]

上述操作无效,因为polylineWithCoordinates仅为MKPolyline对象而不是CustomPolyline分配内存。我怀疑内部发生的事情是polylineWithCoordinates以类似于[MKPolyline otherInitMethod:...]的方式调用另一个初始化方法。并且它没有分配适当的内存量,因为它现在使用MKPolyline静态方法调用而不是我们的CustomPolyline静态调用。

但是如果我们使用

(CustomPolyline*)[CustomPolyline polylineWithPoints:polyline.points count:polyline.pointCount];

确实有效。我认为这是因为polylineWithPoints使用的初始值设定项返回id而不仅仅是链接到另一个方法调用。由于我们使用CustomPolyline类调用它,因此初始化程序为CustomPolyline而不是MKPolyline分配内存。

我为什么会这样做完全错了。但我已经测试了这个,似乎工作正常。 MKPolygon可以以类似的方式扩展。在这种情况下,我认为使用正确的静态方法是MKPolygon polygonWithCoordinates:points count:pointSet.count]]

我的实施参考:

CustomPolyline.h

#import <MapKit/MapKit.h>

typedef enum {
    CustomPolylineTypeNone = 0,
    CustomPolylineDifferentStrokes
} CustomPolylineType;

/**
 * CustomPolyline wraps MKPolyline with additional information about a polyline useful for differentiation.
 */
@interface CustomPolyline : MKPolyline

@property CustomPolylineType type;

-(CustomPolyline*)initWithMKPolyline:(MKPolyline*)polyline;

@end

CustomPolyline.m

#import "CustomPolyline.h"

@implementation CustomPolyline

@synthesize type;

/**
 * Takes an MKPolyline and uses its attributes to create a new CustomPolyline
 */
-(CustomPolyline*)initWithMKPolyline:(MKPolyline*)polyline
{
    // We must use the this specific class function in this manner to generate an actual
    // CustomPolyline object as opposed to a MKPolyline by a different name
    return (CustomPolyline*)[CustomPolyline polylineWithPoints:polyline.points count:polyline.pointCount];
}

@end