http://sam.dods.co/blog/2014/08/03/secondary-delegate/
delegate代理(截取delegate消息用)
#import <Foundation/Foundation.h> #import <UIKit/UIKit.h> @interface MovieSDKDelegateProxy : NSObject <UITableViewDelegate> @property (nonatomic, weak)id primaryDelegate; @property (nonatomic, weak)id secondaryDelegate; @end
@implementation MovieSDKDelegateProxy - (BOOL)respondsToSelector:(SEL)aSelector { return ([self.primaryDelegate respondsToSelector:aSelector] || [self.secondaryDelegate respondsToSelector:aSelector]); } - (NSMethodSignature *)methodSignatureForSelector:(SEL)selector { NSObject *delegateForResonse = [self.primaryDelegate respondsToSelector:selector] ? self.primaryDelegate : self.secondaryDelegate; return [delegateForResonse respondsToSelector:selector] ? [delegateForResonse methodSignatureForSelector:selector] : nil; } - (void)forwardInvocation:(NSInvocation *)invocation { [self invokeInvocation:invocation onDelegate:self.primaryDelegate]; [self invokeInvocation:invocation onDelegate:self.secondaryDelegate]; } - (void)invokeInvocation:(NSInvocation *)invocation onDelegate:(id)delegate { if ([delegate respondsToSelector:invocation.selector]) { [invocation invokeWithTarget:delegate]; } } @end
use:注意设置每个delegate时必须重新将_proxy设置给tableView的delegate。这样才能保证tableView重新检查delegate支持的方法。(tableView会在设置delegate时将大多数方法都检查一下是否支持,回调时不再检查)
@implementation MovieSDKRefreshTableView { MovieSDKDelegateProxy *_proxy; } - (instancetype)initWithFrame:(CGRect)frame style:(UITableViewStyle)style { self = [super initWithFrame:frame style:style]; if (self) { _proxy = [MovieSDKDelegateProxy new]; _proxy.primaryDelegate = self; [super setDelegate:self]; } return self; } - (id<UITableViewDelegate>)delegate { return _proxy.secondaryDelegate; } - (void)setDelegate:(id<UITableViewDelegate>)delegate { _proxy.secondaryDelegate = delegate; [super setDelegate:nil]; //Important:must reset delegate, because tableView check all response to @selecter when set delegate [super setDelegate:_proxy]; } @end