Передача CGColorRef в качестве значения в KVC / KVO - PullRequest
2 голосов
/ 09 мая 2011

Я использую Opacity для создания всех моих иллюстраций Quartz2D, и сейчас я занимаюсь вопросом изменения цвета с помощью KVC / KVO.Непрозрачность определяет все свои цветовые переменные как @dynamic и реализует свои собственные методы доступа как часть определения класса.

Мой вопрос таков;как передать новое значение CGColorRef по значению ключа?

До сих пор (в качестве испытательного стенда) я получил это далеко:

// Testbed ... Testbed ... Testbed ... Testbed ... Testbed ... Testbed ... Testbed ...
      CGColorSpaceRef space = CGColorSpaceCreateDeviceRGB();
      CGFloat components[4] = {1.0f, 1.0f, 1.0f, 1.0f};
      CGColorRef color = CGColorCreate(space, components);

      [myCALayerReceiverObject setValue: color forKey: @"numColour"];
// Testbed ... Testbed ... Testbed ... Testbed ... Testbed ... Testbed ... Testbed ...

Цветовое пространство и код создания непосредственно поднятыиз генератора классов CALayer Opacity (я еще не настолько продвинут), но передача 'color' в качестве значения вызывает сбой симулятора iPhone, и XCode выдает мне очень загадочное предупреждение;

"Несовместимые типы указателей, отправляющие 'CGColorRef'(он же struct' CGColor * ') к параметру типа' id '".

Как мне обернуть CGColorRef, чтобы передать его через KVC получателю?Заранее спасибо.

Ответы [ 3 ]

3 голосов
/ 08 июня 2013

Приведение CGColorRef к (id) работает.Вот пример установки тени на черный цвет:

[layer setValue:(id)[UIColor blackColor].CGColor forKey:@"shadowColor"];
2 голосов
/ 09 мая 2011

Я собирался предложить использовать NSValue , чтобы обернуть ваш цветной объект, но во время тестирования я пришел к выводу, что KVO / KVC не будет работать с CGColors.В соответствии с Руководством по программированию кодирования значения ключа примитивные типы и структуры переносятся с использованием NSValue или NSNumber.Однако при попытке получить доступ к свойству CGColorRef я получаю исключение "не соответствует KVC".Кажется, что указатели на структуры не привязаны к NSValues ​​так же, как сами структуры.Вот мой тестовый код:

@interface MyClass : NSObject {
    CGColorRef color;
}
@property (assign) CGColorRef color;
@end

@implementation MyClass
- (CGColorRef)color { return color; }
- (void)setColor:(CGColorRef)newColor { color = newColor; }
@end

int main(int argc, char **argv) {
    NSAutoreleasePool *p = [NSAutoreleasePool new];
    MyClass *theObject = [MyClass new];
    CGColorRef theColor = CGColorCreateGenericRGB(1.0,1.0,1.0,1.0);
    theObject.color = theColor; // works
    NSLog(@"%@",[theObject valueForKey:@"color"]); // NSValue expected, actually causes exception
    [p release];
    return 0;
}

Один из возможных обходных путей - добавить категорию к соответствующему классу, который определяет средства доступа для другого ключа.Этими средствами доступа будут обертки NSValue для клавиши numColour.

// in the category
- (NSValue *)numColourKVC {
    return [NSValue valueWithPointer:(void*)self.numColour];
}
- (void)setNumColourKVC:(NSValue *)newValue {
    self.numColour = (CGColorRef)[newValue pointerValue];
}

Тогда вы зададите цвет на своем тестовом стенде следующим образом:

[myCALayerReceiverObject setValue:[NSValue valueWithPointer:(void*)color] forKey:@"numColourKVC"];
0 голосов
/ 09 мая 2011

Ошибка довольно очевидна - вам нужно преобразовать CGColorRef в (id). Вне моей головы, это должно работать:

[myCALayerReceiverObject setValue: (id)color forKey: @"numColour"];
...