delegate, notificationCenter, and block for communication between objects

Keywords: Attribute

In project development, communication between objects is often involved. In order to reduce the coupling between objects, delegate, notification center and block are used. For their use, everyone may be familiar with them, but for how to create, beginners may only know a little. This article does not cover a long story, just through simple examples.Help you learn how to use the three, and hope to help friends who do not know the above three.

1. delegate

It is estimated that the most commonly used delegate is UITableViewDelegate, so how can we write a proxy ourselves?As an example, we often listen for button clicks in a view in the controller.If there is a Button in the DTestView, we want to listen for the button click in the DTestViewController and pass an array to the DTestViewController when the Button is clicked, then the code is as follows:

//1. Declare the protocol in the DTestView.h file and create the protocol method
@class DTestView;
@protocol DTestViewDelegate <NSObject>
@optional
/**Click the button and pass the array information*/
- (void)dTestViewDidClickBtn:(DTestView*)dTestView withArr:(NSArray *)position;
@end

//2. Declare the delegate attribute in the DTestView.h file
@interface DTestView : UIView
@property (nonatomic, weak) id <DTestViewDelegate> delegate;
@end

//3. Call the protocol method of delegate in the click event of Button in DTestView.m file
- (void)btnClick {
   if ([self.delegate respondsToSelector:@selector(dTestViewDidClickBtn:withArr:)]) {
      NSArray *arr = @["test", "delegate"];
      [self.delegate dTestViewDidClickBtn:self withArr:arr];
  }         
}

There are 3 steps to creating an agent. Is that easy?But there are also a few things to note:

1. Naming specifications: class name + Delegate.

2. @optional keyword: After following the protocol, the protocol method may not be implemented. The default protocol method is @required modification, that is, it must be implemented after following the protocol. It is recommended that not all methods that must be implemented be modified with @optional.

3. In ARC environment, the delegate attribute is modified with weak ness.

4. Use the respondsToSelector method to determine if the proxy method exists before calling the proxy method.

These are the precautions when creating delegate. You can think about why you should do this. If you don't understand something, you are welcome to ask questions. If you have something wrong, you are welcome to correct it.

Next is the use of delegate, which, in a nutshell, is also a three-step process:

//1. Set up proxy
- (void)viewDidLoad {
   [super viewDidLoad];
   dTestView *view = [[dTestView alloc] init];
   view.delegate = self;
   [self.view addSubview:view];    
}

//2. Follow the agreement
@interface DTestViewController ()<DTestViewDelegate>

//3. Implementation of protocol
- (void)dTestViewDidClickBtn:(DtestView *)dTestView withArr:(NSArray *)arr {
   NSLog(@"%@", arr);
}

Okay, this is a simple delegate creation and use.

2. Notification Center

Notification centers are relatively simple, but still use the example of listening buttons clicking and passing an array to publish notifications in NTestView:

//Publish notifications in Button's addTarget click event
- (void)btnClick {
   NSArray *arr = @[@"test", @"notificationCenter"];
   [[NSNotificationCenter defaultCenter] postNotificationName:@"Click the button" object:nil userInfo:arr];
}

Finished?That's it. Next, add an observer to NTestViewController:

//Add an observer
- (void)viewDidLoad {
   [super viewDidLoad];
   [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(nTestViewDidClickBtn:) name:@"Click the button" object:nil];
}
/**Call this method when a notification is received*/
- (void)nTestViewDidClickBtn:(NSNotification *)note {
   NSArray *arr = note.userInfo;
   NSLog(@"%@", arr);
}

//Remove Observer
- (void)dealloc
{
    [[NSNotificationCenter defaultCenter] removeObserver:self];
}

Explain the parameters:

Name:The name of the notification

Object: the object to be passed

userInfo: Publishing a notification is the information passed (this parameter is accepted by default when adding observers)

Above is the simple use of notificationCenter.Note: Observers must be removed when no monitoring is required.

3. block (Closure)

The simple use of block s still takes the example of listening for button clicks and passing an array:

//1. In the BtestView.h file, we can provide a class method to initialize:
@interface BTestView : UIView
/**block attribute*/
@property(nonatomic,copy) void(^arrBlock)(NSArray *);

/**Initialization Method*/
+ (instancetype)bTestViewWithArrBlock:(void(^)(NSArray *arr))arrBlock;
@end

//2. In the BTestView.m file, implement this method:
+ (instancetype)bTestViewWithaArrBlock:(void(^)(NSArray *arr))arrBlock {
    BTestView *view = [[BTestView alloc] init];
    _arrBlock = arrBlock;
    return view;
}

//3. Call arrBlock in Button's addTarge t Click Event
- (void)clickBtn {
  NSArray *arr = @[@"test", @"notificationCenter"];
  _arrBlock(arr); 
}

Use block s in NTestViewController:

- (void)viewDidLoad {
   [super viewDidLoad];
   BTestView *view = [BTestView bTestViewWithArrBlock:^(NSArray *arr){
    NSLog(@"%@", arr);
  }]; 
  [self.view addSubview:view]; 
}

I don't know if you're familiar with block usage?

Note: block attributes should be modified with copy, and be careful not to cause circular references when using them.

As to which of these three modes of communication should be used?This must be combined with actual projects to make a choice. A common saying is that one-to-many communication uses notification center, one-to-one communication uses block with fewer methods, and delegate with more methods.

Note: None of the above code has passed the actual test. This article only provides a simple way of using it.

Posted by daniel244rock on Thu, 20 Jun 2019 10:18:41 -0700