如何在Core Data / NSFetchedResultsController支持的UITableView顶部插入新对象?

时间:2010-07-28 22:52:57

标签: core-data uitableview

我有一个成功合并NSFetchedResultsController的tableview。但是,我需要在tableview中最顶层的单元格中读取“添加新对象”并使用UITableViewCellEditingStyleInsert而不是默认的UITableViewCellEditingStyleDelete。

FetchResultsController想要检查managedObjectContext中的对象 - 既可以确定行数也可以填充表格单元格。我能想到解决这个问题的唯一方法是创建一个虚拟对象,但我觉得应该有一个更优雅的解决方案。

UPDATE:

对于那些可能对我最终解决的问题感到好奇的人,我决定让我的插入细胞位于底部,而不是顶部。以下是相关代码:

- (void)viewDidLoad {
    [super viewDidLoad];

    // Uncomment the following line to preserve selection between presentations.
    //self.clearsSelectionOnViewWillAppear = NO;

    self.editing = YES;
    self.tableView.allowsSelectionDuringEditing = YES;
    self.tableView.delegate = self;

    RubricAppDelegate *appDelegate = (RubricAppDelegate *)[[UIApplication sharedApplication] delegate];
    managedObjectContext = [appDelegate managedObjectContext];
    NSEntityDescription *entity = [NSEntityDescription entityForName:@"myClass" inManagedObjectContext:managedObjectContext];
    NSFetchRequest *request = [[[NSFetchRequest alloc] init] autorelease];
    [request setEntity:entity];

NSSortDescriptor *sortDescriptor = [[NSSortDescriptor alloc] initWithKey:@"classID" ascending:YES];
    NSArray *sortDescriptors = [NSArray arrayWithObject:sortDescriptor];
    [request setSortDescriptors:sortDescriptors];
    [sortDescriptor release];

    fetchedResultsController = [[NSFetchedResultsController alloc]
                                               initWithFetchRequest:request 
                                               managedObjectContext:self.managedObjectContext
                                               sectionNameKeyPath:nil cacheName:nil];
    NSError *error;
    [fetchedResultsController performFetch:&error];

- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
    NSLog(@"Number of sections = %d", [[fetchedResultsController sections] count]);

    return 1;
}

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
    // Return the number of rows in the section.
    id <NSFetchedResultsSectionInfo> myClass = [[fetchedResultsController sections] objectAtIndex:section];
    NSLog(@"Number of classes = %d", [myClass numberOfObjects]);

    return ([[fetchedResultsController fetchedObjects] count] + 1);

}

// Customize the appearance of table view cells.
- (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] autorelease];
    }

    NSLog(@"FRC count + 1 = %d", ([[fetchedResultsController fetchedObjects] count] + 1));

    if (indexPath.row == ([[fetchedResultsController fetchedObjects] count])) {
        cell.textLabel.text = @"Add New Class";
    }
    else {
        myClass *theClass = [fetchedResultsController objectAtIndexPath:indexPath];
        NSLog(@"Class name is: %@", theClass.classTitle);
        cell.textLabel.text = theClass.classTitle;
    }


    return cell;
}

- (UITableViewCellEditingStyle)tableView:(UITableView *)tableView editingStyleForRowAtIndexPath:(NSIndexPath *)indexPath
{
    if (indexPath.row == [[fetchedResultsController fetchedObjects] count]) {
        return UITableViewCellEditingStyleInsert;
    }
    return UITableViewCellEditingStyleDelete;
}

结果(带有一些垃圾数据):

alt text

现在我唯一的问题是让删除功能正常工作。您可以关注该问题here

上的帖子

1 个答案:

答案 0 :(得分:2)

通常情况下,添加行位于底部。

您可以通过更改-tableView:numberOfRowsInSection:-tableView:cellForRowAtIndexPath:方法来调整细胞计数并进行调整。因此,-tableView:numberOfRowsInSection:将返回N + 1,而-tableView:cellForRowAtIndexPath:将在N-1处获得对象,除非N == 0,否则它将返回“添加新对象”单元格。

没有必要弄乱底层的核心数据元素,因为这严格来说是一个UI问题。

更新

  

但是现在我不确定如何返回我获取的对象的数量(假设这是我在上面的答案中用于“N”)。另外,当indexPath.row =(N + 1)而不是N = 0时,我不希望-tableView:cellForRowAtIndexPath返回我的“添加新对象”单元格吗?我可能误解了“N”等同于什么,但我认为它只是意味着取物的数量。

是的,它是实际物体的数量。

您确实希望-tableView:cellForRowAtIndexPath:为“添加新对象”返回一个单元格,否则有什么意义?您只是希望它返回不同的类型的单元格。

您在此解决方案中所做的只是添加一个不属于NSFetchedResultsController的单元格,然后在从NSFetchedResultsController检索实际对象时以及当用户选择一个时对其进行补偿细胞