在这种情况下,协议确实responseToSelector对我不起作用吗?

时间:2016-06-07 02:03:50

标签: ios objective-c protocols

我在创建协议时遇到问题,responsedsToSelector没有调用该方法。也许有人可以看到我出错的地方。

请参阅我的代码:

Protocol.h

#import <UIKit/UIKit.h>
@protocol CHTumblrMenuDelegate <NSObject>
@required
- (void)dismissView;
@end

typedef void (^CHTumblrMenuViewSelectedBlock)(void);

@interface CHTumblrMenuView : UIView<UIGestureRecognizerDelegate,CHTumblrMenuDelegate>{
    id<CHTumblrMenuDelegate>delegate;
}

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

Protocol.m

- (id)initWithFrame:(CGRect)frame{
     self = [super initWithFrame:frame];
if (self) {
    // Initialization code
    UITapGestureRecognizer *ges = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(dismiss:)];
    ges.delegate = self;
    [self addGestureRecognizer:ges];
    self.backgroundColor = [UIColor clearColor];
    backgroundView_ = [[UIImageView alloc] initWithFrame:self.bounds];
    //backgroundView_.backgroundColor = TumblrBlue;
    backgroundView_.autoresizingMask = UIViewAutoresizingFlexibleHeight | UIViewAutoresizingFlexibleWidth;

    UIGraphicsBeginImageContext(backgroundView_.frame.size);
    [[UIImage imageNamed:@"background"] drawInRect:backgroundView_.bounds];
    UIImage *image = UIGraphicsGetImageFromCurrentImageContext();
    UIGraphicsEndImageContext();
    backgroundView_.backgroundColor = [UIColor colorWithPatternImage:image];

    [self addSubview:backgroundView_];
    buttons_ = [[NSMutableArray alloc] initWithCapacity:6];


}
return self;
}

- (void)dismiss:(id)sender{
    NSLog(@"DIS");

    if (delegate == nil) {
       CHTumblrMenuView *vd = [[CHTumblrMenuView alloc]init];
       delegate = vd;
    }
    [delegate respondsToSelector:@selector(dismissView)];

    [self dropAnimation];
    double delayInSeconds = CHTumblrMenuViewAnimationTime  + CHTumblrMenuViewAnimationInterval * (buttons_.count + 1);
    dispatch_time_t popTime = dispatch_time(DISPATCH_TIME_NOW, (int64_t)(delayInSeconds * NSEC_PER_SEC));
    dispatch_after(popTime, dispatch_get_main_queue(), ^(void){

    [self removeFromSuperview];
});
}

ClassUseProtocol.m

CHTumblrMenuView *menuView = [[CHTumblrMenuView alloc] init];
menuView.delegate = self;

-(void)dismissView{
    NSLog(@"DismissView");
}

日志: 2016-06-06 22:44:07.258 ProtocolExample[7513:4030481] DIS

有没有人知道可能会发生什么?

4 个答案:

答案 0 :(得分:4)

你没有对respondsToSelector的结果做任何事情 - 这会返回一个布尔值,指示对象是否响应指定的选择器。如果它返回true,那么你应该调用委托方法: -

if ([delegate respondsToSelector:@selector(dismissView)]) {
    [delegate dismissView];
}

答案 1 :(得分:0)

您的使用存在一些问题。正确使用是以下代码;

  1. 首先,self.delegate可以执行此方法,该方法由符合此协议CHTumblrMenuDelegate的其他类实现。
  2. 其次,必须由另一个类实现的dismissView方法。 文件CHTumblrMenuView.hCHTumblrMenuView.m要么实现协议CHTumblrMenuDelegate,要么实现必须实现的方法。

    if ([self.delegate respondsToSelector:@selector(dismissView)]) {
           [self.delegate dismissView];
    }
    

    @interface CHTumblrMenuView:NSObject @end

    @implementation CHTumblrMenuView - (无效)dismissView {    的NSLog(@ “dismissView”); } @end

答案 2 :(得分:-2)

你已经双重定义了委托

@interface CHTumblrMenuView : UIView<UIGestureRecognizerDelegate,CHTumblrMenuDelegate>

@property(非原子,弱)id委托;

答案 3 :(得分:-2)

您的协议方法是@required,因此无需检查

 delegate respondsToSelector:@selector(dismissView)

如果是未定义的dismissView方法,则会出现编译时错误。您可以在行下面

 if (self.delegate && [self.delegate conformsToProtocol:@protocol(CHTumblrMenuDelegate)]) {
    [self.delegate dismissView];
 }