When is tableView:numberOfRowsInSection: called in UITableView? - ios

tableView:numberOfRowsInSection is sent to the delegate of a UITableView to find out how many rows it needs to have in a given section.
My question is, when and how often is this method called?

The method is called very first time the tableview is getting loaded and if you are more interested in the delegates then put a breakpoint and check when and where which delegate is called and how many times.

Below are the instances when that function will get called,
For the first time when table is loaded
the time you reload the table data
the time you add/update/delete your row or sections dynamically.

The method - (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section is a protocol method of the UITableViewDataSource - protocol. It will be called
the very first time your table view is loaded based on that you have set the dataSource properly, e.g.
self.yourTableView.dataSource = self;
If you are interested in updating your table again at a later time you can call
[self.yourTableView reloadData];
in order to reload the entire table. If you are only interested in reloading a part of your table you can do something similar to
NSIndexSet *reloadSet = [NSIndexSet indexSetWithIndexesInRange:NSMakeRange(0, [self numberOfSectionsInTableView:self.yourTableView])];
[self.yourTableView reloadSections:reloadSet withRowAnimation:UITableViewRowAnimationAutomatic];
Hope it helps!

My question is, when and how often is this method called?
Short Answer : When your UITableView needs to update something.
Long Answer : Delegates Methods generally called themselves however it may be called multiple times when your UITableView needs to update something. By default, it's called very first time the tableview is getting loaded or updated (reloaded).

It depends on how often user will scroll UITable view to section and how many sections there are. This value, which is returned by this function and is casched. Method will need be revoked if you will update content of table view (filtering results, or updating data via reloadData).
Best thing for you will be to add logging to this function and check this yourself.

Related

I need to delay the call of UITableView until other methods have finished executing

I am building an ios app, that uses google places api to locate certain places and then display the details in a table view. But the problem, that I am facing is that
-(NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
method gets called before the data acquired from the api is stored in the memory. So it (obviously) returns 0, and details are not displayed. Is there some way I can delay the call of Table View?
Well your only option is to not show the table view until there is data there.
Assuming this is not viable, why not just show an activity popup indicating that you are loading information and then when its loaded, drop the activity indicator and call [self.tableview reloadData];
You can reload your Table by below line,
[tableView reloadData];
You can make the tableview invisible and make it visible right before reloading the table.

What is More reliable way to reload UITableView Data?

I have found 2 functions to reload my rows of UITableView
1st.
[tableView reloadRowsAtIndexPaths:[tableView indexPathsForVisibleRows]
withRowAnimation:UITableViewRowAnimationNone];
2nd.
[tableView reloadData];
What is more specific way to reload UITableView Data
Both are "reliable" and possibly "specific" (depending on what you mean by specific) -- in fact, there are even more ways:
reloadData
reloadRowsAtIndexPaths:withRowAnimation:
reloadSections:withRowAnimation:
reloadSectionIndexTitles
Check the developer documentation (https://developer.apple.com/library/ios/documentation/UIKit/Reference/UITableView_Class/index.html) on the differences, but the short answer is that they are all reliable -- it just depends on how much information you want to reload, and if you want to do it with animation.
For example, if you only want to reload certain rows, you can use reloadRowsAtIndexPaths:withRowAnimation:. If you want to reload a whole section, use reloadSections:withRowAnimation:.
This answer may have two cases,
a) You've the table with at least a single section (with a title or returning a view for section)
In this case, if you call reloadData then it'll also reload section too. But reloadRowsAtIndexPaths:withRowAnimation: will only reload the visible cells and not the section.
b) You've the table with at least a single section (without a title or returning a view for section)
In this case, if you call reloadData or reloadRowsAtIndexPaths:withRowAnimation: both will reload only the visible cells.
So which one is the better?
As I explained, based on the case, you should call any of the one method. If you have sections which you don't want to reload then you should call reloadRowsAtIndexPaths:withRowAnimation: method. Or if you want to reload cells along with section then should call reloadData method.

Refresh the UITableView with a complete refresh of the data

I have a view which shows a list of entries in a UITableView. The data for the list is an NSArray. When the user is on this view, there is an asynchronous call to a webservice to retrieve the latest entries. When I have downloaded the latest entries, I update the NSArray and then I send off a notification to the notification center. The UITableView is listening to this event and will try to reload the table.
But with this approach I get an error which is on the lines of "The object was mutated during reading".
After going through similar questions here on SO, I see the suggested approach is to remove objects and add objects at individual indexes and ask the table view to reload the data.
Is there a way to replace the array completely and ask the table view to reload the data ?
UITableView's reloadData method should do the trick.
From Apple's documentation:
Call this method to reload all the data that is used to construct the
table, including cells, section headers and footers, index arrays, and
so on. For efficiency, the table view redisplays only those rows that
are visible. It adjusts offsets if the table shrinks as a result of
the reload. The table view's delegate or data source calls this
method when it wants the table view to completely reload its data. It
should not be called in the methods that insert or delete rows,
especially within an animation block implemented with calls to
beginUpdates and endUpdates
https://developer.apple.com/library/prerelease/ios/documentation/UIKit/Reference/UITableView_Class/index.html#//apple_ref/occ/instm/UITableView/reloadData
if you have Updated NSArray Object
Then you can use directly following method of UITableView
[tableView reloadData]

Insert a new section in UITableView

I am developing an application that shows all the courses that take place in a class room depending on the time and date. In the prototype I was thinking to implement a UITableView, with two sections, one for previous clases(top) and one for next classes. I want to add the previous button as the header of the section with following classes and when I press it I want to programatically add a new section and populate it with the previous courses. I am not sure how to implement this, what methods I should override, etc.
I found something quite similar but I couldn't find any details of how he actually implemented it.
Thank you.
You will need to read up on UITableViews and the delegate methods. The sections are controlled in:
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
You can put conditional logic here to control how many sections you need. Button pressed calls [tableView reloadData]; and will update the sections with it. How you control the data going into the table is up to you, but this should get you started.
- (void)sectionPreviousBunttonPress:(id)sender {
...
[sections addObject:section];
[courses addObjectsFromArray:fetchedCourses];
[table reloadData];
}

Reload UITableView with a different number of rows

I've got a UITableView set up and working, and now I have a little issue. I need to reload the tableView's data whenever the view loads, and one thing which I can't get working is attempting to reload the data, when there was no data in the table view to begin with.
Basically the list is of variable length, and the contents are loaded from a file, what I want to know is, is there I way I can force the table to reload and not have it ignore the datasource methods, as is what happens whenever [tableView reloadData] is called.
[tableView reloadData] relies entirely on the data source methods! So, the only way you would see your data source methods beind ignored would be that you have not set the data source (and perhaps delegate) of your table view to be the object you want to be the data source. You can set these through Interface Builder, or programatically, e.g.:
tableView.dataSource = self;
tableView.delegate = self;
whenever the view loads
Where do you call reloadData? Do you call it in -viewDidLoad method? If yes it is probably incorrect, because -viewDidLoad is called only once - when view of the corresponding UIViewController is created (on the first usage). Maybe you should take a look at -viewWillAppear which is called(assuming correct usage of UIViewController) whenever view is going to be displayed.
The other possible reason is that if you do use -viewWillAppear (or -viewDidAppear) it is not triggered at all. This can happen if you use a custom UIViewController hierarchy. In that case you must call it with your own hands (there are exceptions - UINavigationController for example does this for you, but simple [someView addSubview:myController.view] doesn't).
Also please check if delegates are set correctly and tableView is not equal to nil (as you know messages to nil are just ignored).
datasource methods aren't ignored when u call [tableView reloadData];
Did u set the IBOUTLET and the sources right?

Resources