As a todo list app, The Hit List follows a pretty standard design in one sense: We list tasks using a table view, and each cell of the table contains a checkbox for marking the task as completed.
How do you wire up such a cell?
Direct to controller
There’s a controller of some sort managing the table, likely a UITableViewController subclass. Hook up the button’s action straight to the view controller, and you wind up with code like this:
Yuck. Surely there’s got to be a better way.
Via the cell
Instead, we subclass UITableViewCell and it takes on a role to coordinate things a bit better:
That’s all very well as a start. How can we concretely achieve this?
My friend Pete Callaway favours a delegate protocol:
(please excuse the shoddy delegate method naming)
It’s easy to wire up the cell’s delegate outlet in Interface Builder. This approach has the nice bonus that you can fairly easily use an object other than view controller as the delegate.
You might choose to make the cell aware of the task object it’s associated with, which makes the lookup portion nicer: The controller only has to ask the cell for the task, rather than looking up the cell’s index path.
So far I’ve been favouring using the responder chain (possibly just because it makes me feel clever). You could try something like this:
That seems to work pretty nicely. There’s no need to wire up a delegate outlet which is nice, but hardly life-changing. Again you can directly associate the cell with its model object to make look up simple, or work by index path.
But turns out the above has a rather nasty flaw. If there’s a first responder outside of your controller — e.g. a search bar — that use of the responder chain will stop working as messages are being directed to the wrong place.
So I had to revise my technique to something that turns out to be much simpler:
So there you go, two perfectly workable techniques. I have to admit after writing this, I think I’m favouring the delegation-based one, but it’s entirely up to you.
Followup: Block-based approach