Alex Cio
Alex Cio

Reputation: 6052

Slide in UITableViewCells while scrolling

I have a UITableView and would like to animate rows that will appear again. I also want to switch between animations, some cells should get UITableViewRowAnimationLeft and others UITableViewRowAnimationRight. But I don't know how to implement this feature with my UITableViewController. I tried to insert following lines of code into cellForRowAtIndexPath:

[self.tableView beginUpdates];
NSArray *updatePath = [NSArray arrayWithObject:indexPath];
[self.tableView reloadRowsAtIndexPaths:updatePath 
                      withRowAnimation:UITableViewRowAnimationLeft];
[self.tableView endUpdates];

Instead of sliding in the cell, the order of the cells changed or some of them appeared twice. I also tried to insert these lines after cell creation.

if (cell == nil) {
...
} else {
    [self.tableView beginUpdates];
    NSArray *updatePath = [NSArray arrayWithObject:indexPath];
    [self.tableView reloadRowsAtIndexPaths:updatePath 
                          withRowAnimation:UITableViewRowAnimationLeft];
    [self.tableView endUpdates];

Upvotes: 3

Views: 2445

Answers (1)

Timothy Moose
Timothy Moose

Reputation: 9915

I don't think you're going to have success reloading rows once the table has started the process of displaying the cell on screen. reloadRowsAtIndexPath typically results in cellForRowAtIndexPath being called, so I'm surprised you're not getting into an infinite loop. Instead it appears, the table is getting into a bad state.

My recommendation would be to do your own animation in this case, manipulating the cell's transform property in willDisplayCell. You can do something like this:

- (void)tableView:(UITableView *)tableView willDisplayCell:(UITableViewCell *)cell forRowAtIndexPath:(NSIndexPath *)indexPath
{
    if (<should animate cell>) {
        CGFloat direction = <animate from right> ? 1 : -1;
        cell.transform = CGAffineTransformMakeTranslation(cell.bounds.size.width * direction, 0);
        [UIView animateWithDuration:0.25 animations:^{
            cell.transform = CGAffineTransformIdentity;
        }];
    }
}

You'll need to provide logic for "should animate cell" - you probably don't want to animate cells on initial load.

Upvotes: 8

Related Questions