Dmitry
Dmitry

Reputation: 1041

How to delete row in TTTableViewController (Three20)

The Three20 is great library. It's making the work with tables very easy. But one gap that I noticed - is deletion of rows, with animation. I spent many hours trying to do this, and this is what I'm doing:

// get current index patch
UITableView* table = [super tableView];
NSIndexPath *indexPath = [table indexPathForSelectedRow];

//delete row in data source
TTListDataSource * source = (TTListDataSource *)self.dataSource;
[source.items removeObjectAtIndex:indexPath.row]; 

// delete row from the table, with animation
[table deleteRowsAtIndexPaths:[NSArray arrayWithObject:indexPath] withRowAnimation:UITableViewRowAnimationFade];

After this code runs the error appears: [NSCFArray objectAtIndex:]: index (0) beyond bounds (0)

I'm using the class inherited from the TTTableViewController. And I doesn't implement the DataSourceDelegate or TableViewDelegate because I'm using the Three20 as much as possible. So, this is how I create datasource:

for(NSDictionary *album in (NSArray *)albums){

TTTableRightImageItem *item = [TTTableRightImageItem itemWithText:@"name"  
            imageURL:@"image url" 
           defaultImage:nil 
          imageStyle:TTSTYLE(rounded)
           URL:@"url of selector where I actually catch the tap on a row"];
[tableItems addObject:item];
}
self.dataSource = [TTListDataSource dataSourceWithItems:tableItems];

I read this article (article) but it doesn't help :(

So, I know that this is very simple for gurus from this site. Can you just give me advanced sample of how to do this

Thanks

Upvotes: 2

Views: 3869

Answers (2)

Christian Beer
Christian Beer

Reputation: 2025

I also got "EXC_BAD_ACCESS" in model:didDeleteObject:atIndexPath: but I got that problem solved.

To delete a row in a TTTableViewController you need to implement tableView:commitEditingStyle: in your DataSource implementation like this:

- (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle 
        forRowAtIndexPath:(NSIndexPath *)indexPath {
    if (editingStyle == UITableViewCellEditingStyleDelete) {
        id object = [[self.items objectAtIndex:indexPath.section] objectAtIndex:indexPath.row];

        [self.model didDeleteObject:object atIndexPath:indexPath];
    }
}

You also need to implement tableView:willRemoveObject:atIndexPath: in your DataSource:

- (NSIndexPath*) tableView:(UITableView *)tableView willRemoveObject:(id)object atIndexPath:(NSIndexPath *)indexPath {
    // delete the object
    [object deleteFromDB];

    // removeItemAtIndexPath returns YES if the section is removed
    if ([self removeItemAtIndexPath:indexPath andSectionIfEmpty:YES]) {
        // remove an index path only to that section
        return [NSIndexPath indexPathWithIndex:indexPath.section];
    } else {
        return indexPath;
    }
}

The trick is to change the NSIndexPath you return to only contain the section of it gets empty. Then the code in TTTableViewController removes the section instead of the cell.

HTH

Upvotes: 4

lyonanderson
lyonanderson

Reputation: 2035

The first thing I spot is that you're deleting a row from the table when the table is not in editing mode.

Upvotes: 1

Related Questions