Best Technique for Replacing Delegate Methods with Blocks

前端 未结 2 1869
忘掉有多难
忘掉有多难 2021-02-04 14:39

I\'m looking to create a category to replace delegate methods with callbacks blocks for a lot of the simple iOS APIs. Similar to the sendAsyc block on NSURLConnection. There are

相关标签:
2条回答
  • 2021-02-04 14:48

    Here's what I did:

    typedef void(^EmptyBlockType)();
    
    @interface YUYesNoListener : NSObject <UIAlertViewDelegate>
    
    @property (nonatomic, retain) EmptyBlockType yesBlock;
    @property (nonatomic, retain) EmptyBlockType noBlock;
    
    + (void) yesNoWithTitle:(NSString*)title message:(NSString*)message yesBlock:(EmptyBlockType)yesBlock noBlock:(EmptyBlockType)noBlock;
    
    @end
    
    @implementation YUYesNoListener
    
    @synthesize yesBlock = _yesBlock;
    @synthesize noBlock = _noBlock;
    
    - (id) initWithYesBlock:(EmptyBlockType)yesBlock noBlock:(EmptyBlockType)noBlock
    {
        self = [super init];
        if (self)
        {
            self.yesBlock = [[yesBlock copy] autorelease];
            self.noBlock = [[noBlock copy] autorelease];
        }
        return self;
    }
    
    - (void) alertView:(UIAlertView *)alertView clickedButtonAtIndex:(NSInteger)buttonIndex
    {
        if (buttonIndex == 0 && self.noBlock)
            self.noBlock();
        else if (buttonIndex == 1 && self.yesBlock)
            self.yesBlock();
    
        [_yesBlock release];
        [_noBlock release];
        [alertView release];
        [self release];
    }
    
    - (void) alertViewCancel:(UIAlertView *)alertView
    {
        if (self.noBlock)
            self.noBlock();
        [_yesBlock release];
        [_noBlock release];
        [alertView release];
        [self release];
    }
    
    + (void) yesNoWithTitle:(NSString*)title message:(NSString*)message yesBlock:(EmptyBlockType)yesBlock noBlock:(EmptyBlockType)noBlock
    {
        YUYesNoListener* yesNoListener = [[YUYesNoListener alloc] initWithYesBlock:yesBlock noBlock:noBlock];
        [[[UIAlertView alloc] initWithTitle:title message:message delegate:yesNoListener cancelButtonTitle:@"No" otherButtonTitles:@"Yes", nil] show];
    }
    
    @end
    
    0 讨论(0)
  • 2021-02-04 14:55

    I had a similar problem and chose your option 2, but with the 2 small additions:

    1. Explicitly marking the delegate it implements like this:

      @interface __DelegateBlock:NSObject <BlocksDelegate>
      
    2. Check to ensure the callback is not nil before calling:

      if (callbackBlock != nil) {
          callbackBlock(buttonIndex);
      }
      
    0 讨论(0)
提交回复
热议问题