7

Я пытаюсь оживить внешний вид сегмента круга. Для архивирования я использую CABasicAnimations, который работает спокойно.Анимация удара сегмента круга заканчивается полным ходом

Анимация начинается сверху и прекрасно перемещается на одну треть от всего круга. Но когда анимация заканчивается, круг набирается полностью немедленно.

Как я могу предотвратить это?

Вот исходный код моего пользовательского UIView:

- (void)drawRect:(CGRect)rect 
{ 
    int radius = 100; 
    int strokeWidth = 10; 
    CGColorRef color = [UIColor redColor].CGColor; 
    int timeInSeconds = 5; 

    CGFloat startAngle = 0; 
    CGFloat endAngle = 0.33; 

    CAShapeLayer *circle = [CAShapeLayer layer]; 

    circle.path = [UIBezierPath bezierPathWithRoundedRect:CGRectMake(0, 0, 2.0*radius, 2.0*radius) cornerRadius:radius].CGPath; 

    circle.position = CGPointMake(CGRectGetMidX(self.frame)-radius, CGRectGetMidY(self.frame)-radius); 

    circle.fillColor = [UIColor clearColor].CGColor; 
    circle.strokeColor = color; 
    circle.lineWidth = strokeWidth; 

    [self.layer addSublayer:circle]; 

    CABasicAnimation *drawAnimation = [CABasicAnimation animationWithKeyPath:@"strokeEnd"]; 
    drawAnimation.duration   = timeInSeconds; 
    drawAnimation.repeatCount   = 1.0; 
    drawAnimation.removedOnCompletion = NO; 

    drawAnimation.fromValue = [NSNumber numberWithFloat:startAngle]; 
    drawAnimation.toValue = [NSNumber numberWithFloat:endAngle]; 

    drawAnimation.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut]; 

    [circle addAnimation:drawAnimation forKey:@"drawCircleAnimation"]; 
} 

ответ

18

При применении анимации к слою, Core Animation создает копию слоя и оживляет свойства копии. Оригинальный слой называется модельным слоем, а копия называется уровнем представления. Анимация никогда не изменяет свойства слоя модели.

Вы попытались исправить это, установив removedOnCompletion на номер NO. Вам также необходимо установить fillMode анимации, чтобы сделать эту работу, но это не совсем правильный способ анимировать свойство.

Правильный способ - изменить свойство на уровне модели, а затем применить анимацию.

// Change the model layer's property first. 
circle.strokeEnd = endAngle; 

// Then apply the animation. 
CABasicAnimation *drawAnimation = [CABasicAnimation animationWithKeyPath:@"strokeEnd"]; 
drawAnimation.duration   = timeInSeconds; 
drawAnimation.fromValue = [NSNumber numberWithFloat:startAngle]; 
drawAnimation.toValue = [NSNumber numberWithFloat:endAngle]; 
drawAnimation.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut]; 
[circle addAnimation:drawAnimation forKey:@"drawCircleAnimation"]; 

Это объясняется в Core Animation Essentials video от WWDC 2011. Я очень рекомендую посмотреть его.

+0

Любая идея о прогрессе% (от 0 до 1) во время 'drawAnimation.duration'? – Jack