Расширение делегата из базового класса

5

У меня есть базовый класс objc:

@protocol BaseClassDelegate;

@interface BaseClass : NSObject

@property (nonatomic, weak) id <BaseClassDelegate> delegate;

@end

@protocol BaseClassDelegate <NSObject>

-(void)baseDelegateMethod;

@end

Я создаю быстрый подкласс, в котором я хочу расширить свой делегат...

protocol SubClassDelegate : BaseClassDelegate {

    func additionalSubClassDelegateMethod();
}

class SubClass: BaseClass {

    @IBAction func onDoSomething(sender: AnyObject) {

        delegate?.additionalSubClassDelegateMethod();  <--- No such method in 'delegate'
    }
}

Теперь, когда я создаю свой подкласс, я могу сказать, что он соответствует SubClassDelegate и задает делегат. Проблема (конечно) заключается в том, что "делегат" не существует в этом подклассе. Есть ли способ сообщить компилятору "расширить" мой делегат в мой подкласс? (или я здесь безумный и пропустил что-то очевидное)

Теги:
delegates
extend

2 ответа

8
Лучший ответ

Я либо создаю делегат-оболочку, чтобы сделать его правильным в SubClass.

class SubClass: BaseClass {
    var myDelegate: SubClassDelegate? {
        get { return delegate as? SubClassDelegate }
        set { delegate = newValue }
    }
    @IBAction func onDoSomething(sender: AnyObject) {
        myDelegate?.additionalSubClassDelegateMethod();
    }
}

Или просто передайте делегат ожидаемому типу:

(delegate as? SubClassDelegate)?.additionalSubClassDelegateMethod();
  • 0
    Благодарю. Второй вариант работал, хотя первый вариант выглядел более делегатским, но приводил к ошибкам компилятора, переопределяющим свойство и тип.
  • 1
    Да, извините, вы не можете переопределить свойство, чтобы сделать его более конкретным, чем родительский класс. Я обновил первый образец.
4

Вот более подробный пример того, как это сделать. Благодаря redent84 для указания меня в правильном направлении.

protocol SubclassDelegate: ClassDelegate {
    func subclassDelegateMethod()
}

class Subclass: Class {
    // here we assume that super.delegate property exists
    @IBAction func buttonPressedOrSomeOtherTrigger() {
        if let delegate: SubclassDelegate = self.delegate as? SubclassDelegate {
            delegate.subclassDelegateMethod()
        }
    }
}

И затем в вашей реализации:

extension SomeOtherClass: SubclassDelegate {
    let someObject = Subclass()
    someObject.delegate = self

    func subclassDelegateMethod() {
        // yay! 
    }
}

Ещё вопросы

Сообщество Overcoder
Наверх
Меню