Основы подклассификации Objective-C, как добавить пользовательское свойство; - PullRequest
11 голосов
/ 13 марта 2011

У меня проблема с подклассами MKPolygon.

Я хочу добавить простое свойство int tag, но я продолжаю получать экземпляр MKPolygon вместо моего пользовательского класса, поэтому вызов setTag: вызывает исключение.

Проблема в том, что MKPolygons создаются с использованием метода класса: polygonWithCoordinates: count:, и я не знаю, как превратить это в экземпляр моего класса (который включает свойство тега).

Как бы вы добавили свойство тега в MKPolygon?

Спасибо!

Ответы [ 6 ]

20 голосов
/ 13 марта 2011

Вы должны оба использовать категорию (как предлагает @Seva) и objc_setAssociatedObject (как предлагает @hoha).

@interface MKPolygon (TagExtensions)
@property (nonatomic) int tag;
@end

@implementation MKPolygon (TagExtensions)
static char tagKey;

- (void) setTag:(int)tag {
    objc_setAssociatedObject( self, &tagKey, [NSNumber numberWithInt:tag], OBJC_ASSOCIATION_RETAIN );
}

- (int) tag {
    return [objc_getAssociatedObject( self, &tagKey ) intValue];
}

@end

Вы также можете обратиться к разделу Ассоциативные ссылки в Руководстве ObjC , в дополнение к API @hoha, связанному с.

5 голосов
/ 13 марта 2011

Похоже, что разработчики MKPolygon не сделали его дружественным для наследования. Если все, что вам нужно, это добавить какой-либо тег к этим экземплярам, ​​вы можете

1) сохранить карту (NSDictionary или CFDictionary) из MKPolygon адресов экземпляров в тегах. Это решение хорошо работает, если все теги требуются в том же классе, в котором они установлены.

2) использовать среду выполнения для непосредственного прикрепления тега к полигонам - objc_setAssociatedObject ( Справочник по Objective-C )

2 голосов
/ 29 марта 2012

Я столкнулся с той же проблемой. Простое решение состоит в том, чтобы просто использовать свойство Title MKPolygon, чтобы сохранить то, что вы бы сохранили в теге. По крайней мере, в моем случае, когда мне не нужна ссылка на объект, а просто число, оно работает

1 голос
/ 13 марта 2011
SpecialPolygon *polygon = [SpecialPolygon polygonWithCoordinates:count:];
[polygon setInt: 3];

Ключ в том, что при использовании фабричного метода SpecialPolygon вместо MKPolygon вы получите желаемый подкласс SpecialPolygon.

0 голосов
/ 13 марта 2011

, так как похоже, что авторы приложили все усилия, чтобы помешать вам создать подкласс (по крайней мере, это одна из возможных причин для открытого интерфейса), рассмотрите возможность использования формы композиции:

http://en.wikipedia.org/wiki/Object_composition

0 голосов
/ 13 марта 2011

Вы говорите о MKPolygons, созданном вашим кодом или где-то еще? Если первый, просто переопределите метод polygonWithStuff. Если последнее, рассмотрим категорию над MKPolygon. Тогда все MKPolygons в вашем проекте будут иметь тег.

...