How to properly subclass a delegate property in Objective-C?

后端 未结 2 1928
无人共我
无人共我 2021-02-04 13:52

In subclassing a class, I want to also subclass a delegate of the parent class given that the subclass now has additional functionality. What\'s the best way to go about doing

相关标签:
2条回答
  • 2021-02-04 13:59

    Given this example that produces the warning:

    // Class A
    @protocol ClassADelegete;
    
    @interface ClassA : NSObject
    @property (nonatomic, weak) id<ClassADelegete> delegate;
    @end
    
    @protocol ClassADelegete <NSObject>
    - (void)classADidSomethingInteresting:(ClassA *)classA;
    @end
    
    // Class B
    @protocol ClassBDelegete;
    
    @interface ClassB : ClassA
    @property (nonatomic, weak) id<ClassBDelegete> delegate; // Warning here
    @end
    
    @protocol ClassBDelegete <ClassADelegete>
    - (void)classBDidSomethingElse:(ClassB *)classB;
    @end
    

    Two solutions that remove the warning are.

    1) In the subclass, place the protocol definition before the class definition. This is what UITableViewDelegate in UITableView.h does:

    // Class B
    @class ClassB;
    
    @protocol ClassBDelegete <ClassADelegete>
    - (void)classBDidSomethingElse:(ClassB *)classB;
    @end
    
    @interface ClassB : ClassA
    @property (nonatomic, weak) id<ClassBDelegete> delegate;
    @end
    

    2) In the subclass, add the original protocol alongside the new one:

    // Class B
    @protocol ClassBDelegete;
    
    @interface ClassB : ClassA
    @property (nonatomic, weak) id<ClassADelegete, ClassBDelegete> delegate;
    @end
    
    @protocol ClassBDelegete <ClassADelegete>
    - (void)classBDidSomethingElse:(ClassB *)classB;
    @end
    

    I assume (1) works as Apple do it this way, Option (2) removes the warning but I haven't compiled and run anything setup this way.

    0 讨论(0)
  • 2021-02-04 14:19

    Follow the example of NSTableView and NSOutlineView.

    NSOutlineView is a subclass of NSTableView, and defines its own protocol for its dataSource and delegate.

    NSTableView declares its delegate this way:

    - (void)setDelegate:(id <NSTableViewDelegate>)delegate;
    - (id <NSTableViewDelegate>)delegate;
    

    and NSOutlineView:

    - (void)setDelegate:(id <NSOutlineViewDelegate>)anObject;
    - (id <NSOutlineViewDelegate>)delegate;
    

    Apparently the compiler is more lenient with bare method declarations than it is with property declarations.

    Unlike NSTable/OutlineView, you might want to make the subclass's protocol inherit from the base class's protocol, e.g.

     @protocol SpecializedProtocol <BaseProtocol>
    

    ... it probably depends on the situation.

    0 讨论(0)
提交回复
热议问题