[Swift] Event notification pattern

One object asks another object to process it, Event notifications occur between objects when announcing the start or end of a particular process.

When multiple objects notify each other of events It's not just a matter of blindly referencing objects.

Such an implementation would make the dependencies too complicated. ** Maintenance may become impossible and memory leaks may occur. ** **

There are three methods for event notification between objects. ** ・ Delegate pattern ·closure ・ Observer pattern **

This time, I will explain the delegate pattern in this. I didn't understand it well, so I created the article while researching it.

So please understand that there may be some points that cannot be reached.

Delegate pattern

The delegate pattern is, as the name implies, delegate. ** It is a pattern that leaves the processing of one object to another object. ** **

Delegate source object at the right time, Sends a message to the delegated object.

The delegated object receives the message and ** Changes the state of yourself or another object, or returns some result. ** **

Implementation method

The delegate pattern declares the delegation process as a protocol method. ** Make sure the delegated object complies with the protocol and responds. ** **

Explaining the delegate on the playground is a hassle Let's explain using Storyboard!

As an example, I created the function of the count-up app. Let the left view be screen 1 and the right view be screen 2.

As the processing content, ** ・ If you press the + button, the number on the left screen 1 will increase. ・ Press the next screen button to switch to screen 2. -> At this time, the numbers on screen 1 are displayed on screen 2. ・ Press the back button to return to screen 1. -> At this time, return the number on screen 1 to 0 ** is.

I would like to make screen 1 the delegate destination and screen 2 the delegate source.

スクリーンショット 2020-12-20 15.37.03.png

ViewController (Screen 1)



import UIKit

class ViewController: UIViewController, CountZeroDelegate {
    @IBOutlet weak var countLabel: UILabel!
    var count = 0
    
    override func viewDidLoad() {
        super.viewDidLoad()
    }

    //Plus button
    @IBAction func plusButton(_ sender: Any) {
        count += 1
        countLabel.text = String(count)
    }
    
    //Next screen button
    @IBAction func nextButton(_ sender: Any) {
        performSegue(withIdentifier: "next", sender: nil)
    }
    
    //Called when performSegue is executed
    override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
        let nextVC = segue.destination as! NextViewController
        //Changing the value of the count property of NextViewController
        nextVC.count = self.count
        //Delegating the NextViewController delegate to yourself
        nextVC.delegate = self
    }
    
    //Delegate method
    func countZero() {
        count = 0
        countLabel.text = String(count)
    }
}

NextViewController (Screen 2)



import UIKit

//Delegate protocol
protocol CountZeroDelegate {
    func countZero()
}

class NextViewController: UIViewController {

    @IBOutlet weak var countLabel: UILabel!
    var count = 0
    var delegate: CountZeroDelegate?
    
    override func viewDidLoad() {
        super.viewDidLoad()
        //Assign the value of count to Label
        countLabel.text = String(count)
    }

    //back button
    @IBAction func backButton(_ sender: Any) {
        dismiss(animated: true, completion: nil)
        //When you press the back button
        //Have the delegated object execute the delegate method
        delegate?.countZero()
    }
}

I think it's hard to understand even if you show this much, so I will explain it. Below is where the delegate is defined.

It is the same method as the definition of the protocol so far. ** The delegate defines the method. ** **

NextViewController



protocol CountZeroDelegate {
    func countZero()
}

Define delegate as ①, Describe as ② at the place where you want to execute the delegate.

NextViewController


// ①
var delegate: CountZeroDelegate?

//② Please execute it before the delegate! And event notification
delegate?.countZero()

Since the scope where delegate? .CountZero () is described is the back button, Causes the countZero () property to be executed when the back button is pressed.

** The target to be executed is the object to be delegated. ** **

Since the delegate destination object is going to be a view controller this time, define it as follows.

ViewController



//Since it is a delegate destination, it will be able to respond in compliance with the delegate protocol.
class ViewController: UIViewController, CountZeroDelegate {

Since the contents defined in the compliant protocol must be implemented, Define the countZero () method.

ViewController



    func countZero() {
        count = 0
        countLabel.text = String(count)
    }

And after that, it has to be delegated from the delegate source, so It is delegated as follows.

** The processing content of the protocol defined in the delegate source (NextViewController) is Since it is defined here (view controller of the delegate destination), please delegate the processing! ** **

It is an image. (Hard to understand···)

ViewController


    //Delegating the NextViewController delegate to yourself
    nextVC.delegate = self

I'm not good at explaining, so I'd be happy if you could read it from the code ...

As a scene to use a delegate, ** I think it's useful for many kinds of event notifications between two objects **.

For example ** ① Display a message when the process starts. (2) Display a message periodically during the process. (3) Display a message when the processing is completed.

Delegate is used for many kinds of event notifications between two objects, Closures can be used for simple event notifications (loading is complete, display only), etc. Observers should be used for one-to-many event notifications.

This concludes the explanation of delegates.

There may have been a better explanation, I would appreciate it if you could forgive me around here.

Thank you for watching until the end.

Recommended Posts

[Swift] Event notification pattern
[Swift] Event notification by delegate
[Swift] Loop pattern matching by case-let
[Swift] How to send a notification