Saving NSManagedObjectContext casuing UITableView cells to disappear
I'm having the following issue.
I'm writing a RSS reader using CoreData and Apple Recipes example as a guide. I have a refresh button that re-downloads the RSS and verify using NSFetchRequest if there is new data. Once I finish going over the elements I commit the changes via the NSManagedObjectContext save method.
After the context save, the tableView disappears!
I then decided to call reloadData on the tableView to reflect the changes. So, once the NSManagedObjectContext is saved I call:
[self performSelectorOnMainThread:@selector(updateTableItems) withObject:nil waitUntilDone:NO];
-(void) updateTableItems {
[self.tableView reloadData];
}
This action causes the cell to delete the data while scrolling, when I pop the view and go back, I see all the changes and everything is okay.
I also read in one of the threads that I should use NSFetchedResultsController and make sure the UITableView is t开发者_如何学Che delegate, same issue as the previous one.
What am I doing wrong ? Why can't I see the changes in place? Why the cell's content is being deleted?
Thanks!
It sounds like you are using two or more context on separate threads. You commit the save on the background thread context but don't merge the changes with the context connected to the UI on the front thread. This causes the UI context to come out of sync with the store which cause table rows to disappear when you scroll.
When you pop the controller by leaving the view, the context is deallocated such that when you go back to the view a second time, you have a new context aware of the changes to the store.
To prevent this problem, call refreshObject:mergeChanges:
on the front context immediately after you save the background context. Have the front context register for a NSManagedObjectContextDidSaveNotification
from the background context
I have been having a similar issue and it was driving me crazy. Basically in my code there are loads of competing threads trying to update the same data at the same time (the data behind the table view) and I think this some how causes the UITableView to "blow up" and its delegate methods stop firing. (You can prove this by adding NSLog's into the delegate methods).
It happens totally randomly and is really difficult to replicate.
I tried all sorts to fix this but the only thing that seems to reliably ensure that it can't happen was completely recreating my UITableView everytime the data changed as below. (So basically change everywhere where you call [self.tableView reloadData] with the following)
// The UITableView may in rare circumstances all of a sudden failed to render
// correctly. We're not entirely sure why this happens but its something to
// do with multiple threads executing and updating the data behind the view
// which somehow causes the events to stop firing. Resetting the delegate and
// dataSource to self isn't enough to fix things however so we have to
// completely recreate the UITableView and replace the existing one.
UITableView* tempTableView = [[[UITableView alloc] initWithFrame:CGRectMake(0, 0, 320, 387)] autorelease];
tempTableView.separatorColor = [UIColor grayColor];
tempTableView.backgroundColor = [UIColor clearColor];
if (self.tableView != nil)
{
[tempTableView setContentOffset:self.tableView.contentOffset animated:NO];
}
tempTableView.delegate = self;
tempTableView.dataSource = self;
[tempTableView reloadData];
if (self.tableView != nil) {
[self.tableView removeFromSuperview];
self.tableView = nil;
}
[self.view addSubview:tempTableView];
self.tableView = tempTableView;
I know this isn't the ideal fix and doesn't really explain the issue but I think this is an iOS bug. Would welcome any other input however.
精彩评论