I understood before thatDelegate
pattern is used only for invoking events to delegate instance
and getting controls (like size / font / etc...).
Datasource
pattern is only for getting data from datasource instance
(like views / title / description / etc...)
But seems it was a nice illusion, after looking to Apple's UITableViewDelegate protocol
I got confused because
- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath;
- (CGFloat)tableView:(UITableView *)tableView heightForHeaderInSection:(NSInteger)section;
- (CGFloat)tableView:(UITableView *)tableView heightForFooterInSection:(NSInteger)section;
Are delegate methods (but I was thinking that they are UITableViewDatasource
methods)
Is this a dirty code from Apple, or I'm missing something important too understand difference between datasource and delegate?
EDIT: Thanks @DBD for nice answer, here is more confusion
Here is UITableViewDelegate method that returns View for drawing
- (UIView *)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section;
And also there is a configuration in UITableViewDataSource
- (NSString *)tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section;
And oops, we can see a method that returns a View in UITableViewDataSource
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath;
Here we have question why cellForRowAtIndexPath:
and viewForHeaderInSection:
are not in UITableViewDataSource
This is how I've always thought about it.
UITableViewDataSource
to be primary data. What are the actual contents of the table. How many rows? What is the content of row X?
UITableViewDelegate
was secondary and display data. How tall should it be, should it display in the selected state, and call backs for "hey I'm about to do something."
However I admit I see some of it as a fine line (and I don't buy some of the choices)
UITableViewDataSource
has titleForHeaderInSection
.
UITableViewDelegate
has viewForHeaderInSection
.
So if it's pure "data" title, it's the data source, but if includes a display wrapper with a view, it's the delegate. But wait, cellForRowAtIndexPath
is a view and that's part of the data source, so why would you put viewForHeaderInSection
in the delegate? While I can barely see the distinction between as "cell" as data and "title view" as delegate, I think the confusion of splitting "title" methods into different protocols is not preferable. I'm sure many might disagree with me, but it's just my opinion.
I think the critical distinction here arises from what you consider "data." From your question, I think you understand "data" to mean "any return value" – that is, methods which return void
are delegate methods, and methods which return non-void
are data source methods (since they pass something back to the sending table view).
This can sometimes be a useful approximation, but here is inaccurate. A table view's data is the contents that it displays – the stuff in the cells, the titles of sections, etc. Any other information, including that about layout (like row height) or display (like section headers) properly belongs in the delegate, since it is not about the contents of the table – merely about how to display those contents.
The two are very often related, which is why more often than not the same UITableViewController subclass implements both the delegate and data source, but imagine: you could have one object act as the data source and vend cells, then have a different object act as the delegate and provide heights for your rows based on completely different criteria. (Imagine a table where the user can resize rows, for example. You still provide the contents of each row, but the height – the delegate's responsibility – is drawing from a very different set of information.)
dataSource
and delegate
are both protocols but they are separated into two terms so that we can better understand what the methods are designed to do.
This means:
dataSource
protocol defines an API that supplies the data where delegate
supplies the behavior.dataSource
is in the model layer and the delegate is in the control layer.I think this is the correct outlook.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With