1

The CAMediaTiming protocol defines property timeOffset which is supposed to set additional time offset of an animation or animated layer. By setting layer.speed = 0 it's possible to manually control animation timing by setting layer.timeOffset to a given value.

And I managed to do it in a regular view, however when I try to do it (set time offset of a layer) when the layer is a descendant of UITableViewCell's layer it has no effect.

Here's a quick snippet so you can see what I am trying to achieve and what doesn't work.

-(void) tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {

    UITableViewCell *cell = [tableView cellForRowAtIndexPath:indexPath];

    [tableView deselectRowAtIndexPath:indexPath animated:NO];

    CALayer *layer = [CALayer layer];
    layer.frame = CGRectMake(0, 0, 80, 80);
    layer.backgroundColor = [UIColor redColor].CGColor;
    layer.opacity = .1f;
    [cell.contentView.layer addSublayer:layer];

    CABasicAnimation *animation = [CABasicAnimation animationWithKeyPath:@"opacity"];
    animation.toValue = (id) [NSNumber numberWithFloat:1.f];
    animation.duration = 1.f;
    [layer addAnimation:animation forKey:nil];
    layer.timeOffset = 0.7f;
    layer.speed = 0.f;

}
wczekalski
  • 720
  • 4
  • 21

1 Answers1

0

You must allow the animation to start before you can control its timeOffset. Use a block with very small delay to do so:

    CABasicAnimation* ba = [CABasicAnimation animationWithKeyPath:@"opacity"];
ba.removedOnCompletion = NO;
ba.duration = kAnimationDuration;
ba.autoreverses = YES;
ba.repeatCount = HUGE_VALF;
ba.fromValue = [NSNumber numberWithDouble:kInitialAlpha];
ba.toValue = [NSNumber numberWithDouble:kFinalAlpha];
[self.layer addAnimation:ba forKey:@"opacity"];
dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(.1 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
    double offset = self.alphaOffset * ( kAnimationDuration / kNumAlphaOffsets );
    self.layer.timeOffset = offset;
});
Bobjt
  • 4,040
  • 1
  • 29
  • 29