UITableView с несколькими NSFetchedResultsControllers, вызывающими сбой утверждения - PullRequest
0 голосов
/ 12 января 2011

У меня есть UITableView с 3 разделами, и каждый раздел подается через уникальный NSFetchedResultsController.

Я получаю Ошибка подтверждения от NSFetchedResultsController -controllerDidChangeContent , при вставке, обновлении ... таблицы.

Я думаю, проблема сindexPaths идет в методе ниже, так как каждый контроллер имеет только одну секцию (0) и для контроллера в секции 0 сбой не происходит.

- (void)controller:(NSFetchedResultsController*)controller didChangeObject:(id)anObject atIndexPath:(NSIndexPath*)indexPath forChangeType:(NSFetchedResultsChangeType)type newIndexPath:(NSIndexPath*)newIndexPath
{
    switch(type)
    {
        case NSFetchedResultsChangeInsert:
            [[self atableView] insertRowsAtIndexPaths:[NSArray arrayWithObject:newIndexPath] withRowAnimation:UITableViewRowAnimationLeft];
            break;
        case NSFetchedResultsChangeDelete:
            [[self atableView] deleteRowsAtIndexPaths:[NSArray arrayWithObject:indexPath] withRowAnimation:UITableViewRowAnimationLeft];
            break;
        case NSFetchedResultsChangeUpdate:
            [self configureCell:(DashboardViewCell *) [[self atableView] cellForRowAtIndexPath:indexPath] atIndexPath:indexPath];
            break;
        case NSFetchedResultsChangeMove:
            [[self atableView] deleteRowsAtIndexPaths:[NSArray arrayWithObject:indexPath] withRowAnimation:UITableViewRowAnimationFade];
            [[self atableView] insertRowsAtIndexPaths:[NSArray arrayWithObject:newIndexPath] withRowAnimation:UITableViewRowAnimationFade];
            break;
    } 
}

Итак, мой вопрос, как я могу определить, какой контроллер (изкакой раздел) обрабатывается и соответственно изменяется indexPath, и если это правильный способ сделать это?И, возможно, любые примеры использования нескольких контроллеров nsfetchedresults с одним uitableview.

Ответы [ 2 ]

3 голосов
/ 17 января 2011

Так что мое предположение было на самом деле правильным:

, поскольку каждый контроллер входит в следующую функцию

  • (void) контроллер: (NSFetchedResultsController *) контроллер didChangeObject: (id) anObject atIndexPath :(NSIndexPath *) indexPath forChangeType: (NSFetchedResultsChangeType) type newIndexPath: (NSIndexPath *) newIndexPath

значение indexPath неверно для каждого контроллера, кроме того, который установлен для раздела 0.

* 1010Каждый контроллер имеет только один раздел - 0 в моем случае, но, что более важно, эти разделы не соответствуют разделам таблицы.

Таким образом, обходной путь, который я в настоящее время реализовал (не велик, поэтому, вероятно, переработаю), состоит в проверкеcacheName контроллера и в зависимости от этого изменить раздел для indexPath / newIndexPath

примерно так:

if([[controller cacheName] isEqualToString:@"sectionX"])
{
  indexPath = [NSIndexPath indexPathForRow:indexPath.row inSection:<add correct section>];
  newIndexPath = [NSIndexPath indexPathForRow:indexPath.row inSection:<add correct section>];
}
0 голосов
/ 12 января 2011

Я не уверен, что это FetchedResultController.

В какой-то момент вызов строки вставки и удаления попросит перезагрузить tableView, затем он запросит методы делегата и источника данных для numberOfRowsInSection, cellForRowAtIndexPath и т. Д.

Вероятно, происходит то, что модель и tableView не синхронизированы, и это заставляет контроллер выдавать предупреждение.

    [tableView beginUpdates];

     if (editingStyle == UITableViewCellEditingStyleDelete) {

        NSMutableDictionary *item = [self.itemList objectAtIndex:indexPath.row];
    // Delete the row from the data source
        [tableView deleteRowsAtIndexPaths:[NSArray arrayWithObject:indexPath] withRowAnimation:UITableViewRowAnimationFade];
        [self.itemList removeObjectAtIndex:indexPath.row];      

}   
    [tableView endUpdates];

Попробуйте что-то вроде этого, где все изменения в tableView иБазовая модель обернута в beginUpdates и endUpdates.Это заставит tableView ждать при рисовании ячейки, пока вы не дадите 'OK'.

Если вышеописанное не так, то здесь я обычно работаю с несколькими разделами в tableView.

В вашем заголовке вы объявляете перечисление typedef для разделов;

typedef enum {

    SectionTypeName,
    SectionTypeAge,
    SectionTypeSkills,

} SectionType;

//in the implementation

switch (indexPath.section) {
    case SectionTypeName:
        //do thing in the name section
        break;
    case SectionTypeAge:
        //do thing in the name section
        break;
    case SectionTypeSkills:
        //do thing in the name section
        break;          
    default:
        break;
}

У меня есть switch () почти в каждом методе делегата / источника данных tableView.Это позволяет очень легко определить, какой раздел обрабатывается и что он делает.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...