Welcome to the Treehouse Community

Want to collaborate on code errors? Have bugs you need feedback on? Looking for an extra set of eyes on your latest project? Get support with fellow developers, designers, and programmers of all backgrounds and skill levels here with the Treehouse Community! While you're at it, check out some resources Treehouse students have shared here.

Looking to learn something new?

Treehouse offers a seven day free trial for new students. Get access to thousands of hours of content and join thousands of Treehouse students and alumni in the community today.

Start your free trial

iOS Delegates in Swift 2 Introduction to Delegates Implementing a Delegate

What is the relationship between the delegate class and the object where the delegate property is declared?

For example, why do we declare the delegate property in the Race class and not the HorseRace class?

2 Answers

Steven Deutsch
Steven Deutsch
21,046 Points

Hey Christine Chang,

Unfortunately I don't have access to the video you're referring to, however, lets talk about delegation in general for a moment.

You can think of delegation as an object handing off some of its responsibilities to another object. So if something is the delegate of an object, that means it can manage some sort of specified functionality for that object. Let's give this some context.

You will quite often see the delegate pattern being used in Apple's frameworks. A common example is the UITableViewDelegate. Please keep in mind this example is done free hand so don't count on it compiling :)

import UIKit

class ChristinesViewController: UITableViewDelegate {

    @IBOutlet weak var tableView: UITableView!

    override func viewDidLoad() {
        super.viewDidLoad()
        tableView.delegate = self // self refers to this current class, ChristinesViewController
    }

    func tableView(tableView: UITableView, didSelectRowAtIndexPath indexPath: NSIndexPath) {
        print("A row was selected!!!")
    }
}

Here we have a very simple view controller, ChristinesViewController, which has a single property, a tableView. Inside of viewDidLoad, we assign ChristinesViewController to the tableView's delegate property. This means that this view controller is now the delegate of the tableView and because of this it can manage some of the functionality for it. Since the view controller conforms to the UITableViewDelegate protocol, we can implement some of the methods listed in this protocol, one of them being didSelectRowAtIndexPath. Now when we select a row in the tableView, the view controller will print "A row was selected!!!". This view controller is managing the functionality of what to do when a user taps on a row for that tableView.

Good Luck

Thanks so much for the example, Steven! That really helped.

I have one more question, though. What is the added advantage of assigning ChristinesViewController to be a delegate, as opposed to simply having it conform to the UITableViewDelegate protocol? If the view controller simply conformed to the protocol, but was not assigned to be a delegate, wouldn't it still be able to implement the UITableViewDelegate protocol's methods? i.e., when you say "managing the functionality," how is that different from simply implementing the protocol's methods?

Steven Deutsch
Steven Deutsch
21,046 Points

If you made ChristinesViewController conform to the UITableViewDelegate protocol, but did not set the delegate property of UITableView, the methods in ChristinesViewController would never get called. Sadly, this is a simple error I commonly make when developing! I forget to assign the delegates and then I sit there wondering why my methods aren't getting called!

The reason why you need to set the delegate property of the tableView is because you need to tell the tableView who its delegate it is so that it knows where to find the methods to manage it. If it doesn't know where to find the methods, they'll never get called. Remember that delegation is all about handing off responsibilities for another object to manage, so we have to make the original object aware of who its delegate is. The reason this whole thing works is because of protocols.

Remember that protocols are a blueprint of a class/structure. If a property/method is listed in a protocol, the object that conforms to the protocol must implement those methods! This is how the requirements are set up so that we know the delegate object can manage the original object. Let's give it some context:

If we take a look at the UITableViewDataSource protocol, we will see that it has 2 required methods.

1) tableView(_:numberOfRowsInSection:)

2) tableView(_:cellForRowAt:)

Now lets make our view controller conform to this protocol by adding these methods:

import UIKit

class ChristinesViewController: UITableViewDataSource {

    @IBOutlet weak var tableView: UITableView!

    override func viewDidLoad() {
        super.viewDidLoad()
        tableView.dataSource = self // ChristinesViewController
    }

    func tableView(tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
       return 10
    }

    func tableView(tableView: UITableView, cellForRowAtIndexPath indexPath: NSIndexPath) -> UITableViewCell {
        return UITableViewCell()
    }
}

You can see in viewDidLoad we set the tableView's dataSource property to ChristinesViewController this time. This is because it conforms to the UITableViewDataSource protocol. Since that protocol has the required methods of numberOfRowsInSection and cellForRowAtIndexPath, and our view controller conforms to this protocol, it can act as our data source for the tableView. Now the tableView can be sure these methods exist in the ViewController and knows where to call them.

When does it call them? Thats all handled behind the scenes in the UIKit framework. Unfortunately, thats Apple's private property and we will never see the implementation of these methods. At some point determined by the tableView object, it will look for its delegate to populate the numberOfRows in the tableView. We just have to let it know where to find it!

Hope this helps.

Ah, thank you for the thorough explanation! It's definitely starting to make more sense now :)

Steven Deutsch
Steven Deutsch
21,046 Points

It took me a really long time to understand this concept... I think it finally clicked when I started making my own delegates. You should experiment with them on your own.