CAShapeLayeranimation(从0到最终大小的弧)

我有一个使用UIBezierPath添加弧的UIBezierPath 。 我在这里看到了几个post(实际上是一个),但似乎没有给我答案。 正如标题所说,我想animation弧(是的,这将是一个饼图)。

怎样才能完成一个从“空”到完全扩展的animation? 有点像弯曲的进度条。 真的不可能通过CoreAnimation来实现吗?

这是我如何“做”的弧。 哦,忽略评论和计算,因为我用来逆时针单位圆和苹果顺时针。 弧线显得很好,我只需要animation:

  //Apple's unit circle goes in clockwise rotation while im used to counter clockwise that's why my angles are mirrored along x-axis workAngle = 6.283185307 - DEGREES_TO_RADIANS(360 * item.value / total); //My unit circle, that's why negative currentAngle [path moveToPoint:CGPointMake(center.x + cosf(outerPaddingAngle - currentAngle) * (bounds.size.width / 2), center.y - (sinf(outerPaddingAngle - currentAngle) * (bounds.size.height / 2)))]; //Apple's unit circle, clockwise rotation, we add the angles [path addArcWithCenter:center radius:120 startAngle:currentAngle endAngle:currentAngle + workAngle clockwise:NO]; //My unit circle, counter clockwise rotation, we subtract the angles [path addLineToPoint:CGPointMake(center.x + cosf(-currentAngle - workAngle) * ((bounds.size.width / 2) - pieWidth), center.y - sinf(-currentAngle - workAngle) * ((bounds.size.height / 2) - pieWidth))]; //Apple's unit circle, clockwise rotation, addition of angles [path addArcWithCenter:center radius:120 - pieWidth startAngle:currentAngle + workAngle endAngle:currentAngle - innerPaddingAngle clockwise:YES]; //No need for my custom calculations since I can simply close the path [path closePath]; shape = [CAShapeLayer layer]; shape.frame = self.bounds; shape.path = path.CGPath; shape.fillColor = kRGBAColor(255, 255, 255, 0.2f + 0.1f * (i + 1)).CGColor; //kRGBAColor is a #defined [self.layer addSublayer:shape]; //THIS IS THE PART IM INTERESTED IN if (_shouldAnimate) { CABasicAnimation *pieAnimation = [CABasicAnimation animationWithKeyPath:@"path"]; pieAnimation.duration = 1.0; pieAnimation.removedOnCompletion = NO; pieAnimation.fillMode = kCAFillModeForwards; //from and to are just dummies so I dont get errors pieAnimation.fromValue = [NSNumber numberWithInt:0]; //from what pieAnimation.toValue = [NSNumber numberWithFloat:1.0f]; //to what [shape addAnimation:pieAnimation forKey:@"animatePath"]; } 

这是一个基于CAShapeLayer的CALayer的实现:

ProgressLayer.h /米

 #import <QuartzCore/QuartzCore.h> @interface ProgressLayer : CAShapeLayer -(void) computePath:(CGRect)r; -(void) showProgress; @end #import "ProgressLayer.h" @implementation ProgressLayer -(id)init { self=[super init]; if (self) { self.path = CGPathCreateWithEllipseInRect(CGRectMake(0, 0, 50, 50), 0); self.strokeColor = [UIColor greenColor].CGColor; self.lineWidth=40; self.lineCap = kCALineCapRound; self.strokeEnd=0.001; } return self; } -(void) computePath:(CGRect)r { self.path = CGPathCreateWithEllipseInRect(r, 0); } -(void)showProgress { float advance=0.1; if (self.strokeEnd>1) self.strokeEnd=0; CABasicAnimation * swipe = [CABasicAnimation animationWithKeyPath:@"strokeEnd"]; swipe.duration=0.25; swipe.fromValue=[NSNumber numberWithDouble:self.strokeEnd]; swipe.toValue= [NSNumber numberWithDouble:self.strokeEnd + advance]; swipe.fillMode = kCAFillModeForwards; swipe.timingFunction= [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut]; swipe.removedOnCompletion=NO; self.strokeEnd = self.strokeEnd + advance; [self addAnimation:swipe forKey:@"strokeEnd animation"]; } @end 

我用这个图层作为UIView的底层:

 #import "ProgressView.h" #import "ProgressLayer.h" @implementation ProgressView -(id)initWithCoder:(NSCoder *)aDecoder { self=[super initWithCoder:aDecoder]; if (self) { [(ProgressLayer *)self.layer computePath:self.bounds]; } return self; } -(void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event { ProgressLayer * l = self.layer; [l showProgress]; } - (void)drawRect:(CGRect)rect { [[UIColor redColor] setStroke]; UIRectFrame(self.bounds); } +(Class)layerClass { return [ProgressLayer class]; } @end 

初始状态

正在进行的动画/ 0

正在进行的动画/ 1

你必须使用正确的键。 “path”和“animatePath”并不意味着什么 – 你必须使用“strokeEnd”作为你的键/键path。 如果你需要填充你的填充颜色,你可以使用fillColor。 完整列表在这里:

https://developer.apple.com/library/ios/documentation/GraphicsImaging/Reference/CAShapeLayer_class/Reference/Reference.html

在创buildanimation之前,您需要将形状的strokeEnd设置为0。

然后,使用键@“strokeEnd”而不是@“path”… CAAnimations的键通常是您要设置animation的属性的名称。

然后你可以做到以下几点:

 [CATransaction begin] CABasicAnimation *animation = [CABasicAnimation animationWithKeyPath:@"strokeEnd"]; animation.duration = 1.0f; animation.removedOnCompletion = NO; animation.fromValue = @0; //shorthand for creating an NSNumber animation.toValue = @1; //shorthand for creating an NSNumber [self addAnimation:animation forKey:@"animateStrokeEnd"]; [CATransaction commit];