NightFury
NightFury

Reputation: 13546

UITableview in UITableviewcontroller - cellforrowatindexpath not called on reload

I am stucked in a stupid problem since two days. I have got a UITableViewController pushed in Navigation Controller. When it loads, since there is no data, so empty table is visible:

But when I receive data from server, and call [self.tableView reloadData], both numberOfRowsInSection and heightForRowAtIndexPath get invoke except cellForRowAtIndexPath and my controller is shown without table:

I can't really understand that why it is happening. All datasource methods are called except for cellForRowAtIndexPath. Please someone guide me... Thanks..

ActLogController.h

@interface ActLogController : UITableViewController<ASIHTTPRequestDelegate,UITableViewDataSource,UITableViewDelegate>

@property(strong) NSMutableArray *activityKeys;

@end

ActLogController.m

- (void)viewDidLoad
{
    [super viewDidLoad];

    activityKeys = [[NSMutableArray alloc] init];
    self.tableView.dataSource = self;
}

-(void) viewWillAppear:(BOOL)animated
{
    [super viewWillAppear:animated];
    [self retrieveActivityLogFromServer];
}

- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
    return 1;
}

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
    return activityKeys.count;
}

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    static NSString *CellIdentifier = @"Cell";
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];

    if(cell == nil)
    {
        cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
    }
    // Configure the cell...
    ActivityLogUnit *act = [activityKeys objectAtIndex:indexPath.row];
    cell.textLabel.text = act.price;

    return cell;
}

-(CGFloat) tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath
{
    return 50.0;
}

-(void) requestFinished:(ASIHTTPRequest *)request
{
    NSArray *list = [request.responseString JSONValue];

    for (int i = 0; i < list.count; i++) {

        NSArray *singleTrade = [[list objectAtIndex:i] JSONValue];

        ActivityLogUnit *unit = [[ActivityLogUnit alloc] init];

        unit.symbol = [singleTrade objectAtIndex:0];
        unit.type = [singleTrade objectAtIndex:1];
        unit.price = [singleTrade objectAtIndex:2];
        unit.volTraded = [singleTrade objectAtIndex:3];
        unit.remVol = [singleTrade objectAtIndex:4];
        unit.actualVol = [singleTrade objectAtIndex:5];
        unit.recordID = [singleTrade objectAtIndex:6];
        unit.orderNo = [singleTrade objectAtIndex:7];
        unit.time = [singleTrade objectAtIndex:8];

        [activityKeys addObject:unit];

    }

    if(activityKeys.count > 0)
    {
        [self.tableView reloadData];//it is called and I have got 6 items confirm
    }
}

EDIT

I set some dummy data in my array activityKeys, Data is being displayed in table, and cellforrowatindexpath is called successfully. But as I reload data after sometime, other methods are called except this one and table disappears as shown in 2nd pic. Any ideas?

Upvotes: 4

Views: 14721

Answers (7)

Michael
Michael

Reputation: 2993

For me the problem was my stubbed-out code returning 0 as the number of sections (so it never asked how many rows were in the section, and never got their data). Just change that to 1 if it's your problem also. Additionally, I was working in Swift, where the issue mentioned by @shahid-rasheed is coded (slightly) differently:

dispatch_async(dispatch_get_main_queue(), {
    self.tableView.reloadData()
})

Upvotes: 1

Yan Yi
Yan Yi

Reputation: 773

I had the same symptoms too. In my case, the first time I loaded the data (from core data) in viewDidLoad, NSSortDescriptor was used to sort the data.

On the click of a button, the core data was fetched again (this time with changes) and tableView data reloaded. It initially gave me a blank table view after the button was clicked because I forgot to sort the data the second time I fetched it.

Learning points: Remember to call all methods which modify the cell (like background color mentioned by iAnum, or NSSortDescriptor in my case) if you have used them in the beginning!

Upvotes: 0

NightFury
NightFury

Reputation: 13546

At last I got it worked. cellForRowAtIndexPath was not being called because of a line of code I didn't mention here... which was actually removing some color background layer from view. It was causing reloading issue. After removing it, everything works fine.

Thank you all of you for your cooperation :)

Upvotes: 0

shahid-rasheed
shahid-rasheed

Reputation: 509

Looks like you in secondary thread, do reloadData in main thread by using following code

[self.tableView performSelectorOnMainThread@selector(reloadData) withObject:nil waitUntilDone:NO]

You can always use [NSThread isMainThread] to check whether you are in main thread or not.

Upvotes: 5

Groot
Groot

Reputation: 14251

Your problem is that you probably download the data content on a background thread. Since you cannot update the UI on a background you need to call [self.tableView reloadData] on the main thread once the download is finished!

Hope it helps!

Upvotes: 5

SAMIR RATHOD
SAMIR RATHOD

Reputation: 3510

you have to write in viewdidload

self.tableView.dataSource = self;
self.tableView.delegate = self;

Edit

You have no xib then where you are declared/sets your tableview's properties. Like

self.tableView.frame = CGRectMake(0, 45, 320, 500);
self.tableView.rowHeight = 34.0f;
self.tableView.separatorStyle=UITableViewCellSeparatorStyleNone;
[self.view addSubview:self.tableView];

[self.tableView setBackgroundColor:[UIColor clearColor]];
self.tableView.showsVerticalScrollIndicator=NO;
self.tableView.dataSource = self;
self.tableView.delegate = self;

Try with

 @property(nonatomic,strong) NSMutableArray *activityKeys;

Upvotes: 4

Apple_iOS0304
Apple_iOS0304

Reputation: 1102

Firstly I strongly believe that the instance name of the tableview should not be similar to the local variable (i.e. tableView in class should not be equal to tableView in delegate and data source methods).

Second in your question posted I could not see the delegate set for the table view. answer Posted By Samir Rathod should work if you have @property for the table view set in you .h or .m file.

You can also do this if you have a XIB file. Press ctrl and click + drag the tableview to the files owner and set the delegate and datasource.

Upvotes: 1

Related Questions