是iOS平台和macOS平台负责图形渲染和动画操作的基础框架。如果想要界面有个吊炸天的动画效果,就必须要学会使用。
@interface CAAnimation : NSObject
CAAnimation遵循CAMediaTiming协议,因此可以使用CAMediaTiming的属性
属性 | 名称 |
---|---|
CFTimeInterval beginTime | 开始时间 |
CFTimeInterval duration | 持续时间 |
float speed | 速率 |
float repeatCount | 重复次数 |
CFTimeInterval repeatDuration | 每次重复间隔 |
NSString *fillMode | 视图在非Active时的行为 |
BOOL autoreverses | 执行动画后,按照原动画返回执行 |
CAMediaTimingFunction *timingFunction | 控制动画节奏 |
代理方法 | |
type | 过度动画类型 |
subtype | 过度动画的动画方向 |
CAMediaTimingFunction
- kCAMediaTimingFunctionLinear 线性动画
- kCAMediaTimingFunctionEaseIn 先快后慢
- kCAMediaTimingFunctionEaseOut 先慢后快
- kCAMediaTimingFunctionEaseInEaseOut 先慢后快再慢
- kCAMediaTimingFunctionDefault 默认 中间比较快
delegate
代理方法,能够检测到动画的执行结束
/* Called when the animation begins its active duration. */
- (void)animationDidStart:(CAAnimation *)anim;
/* Called when the animation either completes its active duration or
* is removed from the object it is attached to (i.e. the layer). 'flag'
* is true if the animation reached the end of its active duration
* without being removed. */
- (void)animationDidStop:(CAAnimation *)anim finished:(BOOL)flag;
type和subtype
kCATransitionFade 渐变效果
kCATransitionMoveIn 进入覆盖效果
kCATransitionPush 推出效果
kCATransitionReveal 揭露效果
kCATransitionFromRight 从右侧
kCATransitionFromLeft 从左侧
kCATransitionFromTop 从上面
kCATransitionFromBottom 从下面
UIView的动画调用
[UIView animateWithDuration:5 animations:^{
self.contentView.frame = CGRectMake(ScreenW, 100, 100, 100);
self.contentView.alpha = 0.5;
} completion:^(BOOL finished) {
}];
使用Core Animation调用
CABasicAnimation *animation = [CABasicAnimation animationWithKeyPath:@"position"];
animation.fromValue = [NSValue valueWithCGRect:CGRectMake(0, 100, 100, 100)];
animation.toValue = [NSValue valueWithCGRect:CGRectMake(ScreenW, 100, 100, 100)];
animation.duration = 4;
[self.contentView.layer addAnimation:animation forKey:@"animation"];
路径
CABasicAnimation中三个表示路径的属性
@property(nullable, strong) id fromValue;//动画开始之前的属性
@property(nullable, strong) id toValue;//动画结束之后的值
@property(nullable, strong) id byValue;//动画执行过程中值得改变
注意:这三个属性不能同时赋值
//颜色改变
CALayer *colorLayer = [CALayer layer];
colorLayer.frame = self.contentView.bounds;
colorLayer.backgroundColor = [UIColor redColor].CGColor;
[self.contentView.layer addSublayer:colorLayer];
CGFloat red = arc4random()/INTMAX_MAX;
CGFloat blue = arc4random()/INTMAX_MAX;
CGFloat green = arc4random()/INTMAX_MAX;
UIColor *color = [UIColor colorWithRed:red green:green blue:blue alpha:1];
CABasicAnimation *animation = [CABasicAnimation animation];
animation.keyPath = @"backgroundColor";
animation.duration = 3;
//设置fillMode = kCAFillModeForwards;和removedOnCompletion = NO会使图层保持动画结束状态,但是图层的属性值还是和初始一样,并没有真正改变
animation.fillMode = kCAFillModeForwards;
animation.removedOnCompletion = NO;
[CATransaction begin];
[CATransaction setDisableActions:YES];
animation.toValue = (__bridge id)color.CGColor;
[CATransaction commit];
[colorLayer addAnimation:animation forKey:@"changeColor"];
关键帧动画
CAKeyframeAnimation不限制于设置一个起始值和结束值,可以根据一连随意的值来做动画
UIBezierPath *bezierPath = [[UIBezierPath alloc] init];
[bezierPath moveToPoint:CGPointMake(0, 150)];
[bezierPath addCurveToPoint:CGPointMake(300, 150) controlPoint1:CGPointMake(75, 0) controlPoint2:CGPointMake(225, 300)];
CAShapeLayer *shapLayer = [CAShapeLayer layer];
shapLayer.path = bezierPath.CGPath;
shapLayer.fillColor = [UIColor clearColor].CGColor;
shapLayer.strokeColor = [UIColor redColor].CGColor;
shapLayer.lineWidth = 3;
[self.view.layer addSublayer:shapLayer];
CALayer *layer = [CALayer layer];
layer.frame = CGRectMake(0, 0, 60, 60);
layer.position = CGPointMake(0, 150);
layer.contents = (__bridge id)[UIImage imageNamed:@"111"].CGImage;
[self.view.layer addSublayer:layer];
CAKeyframeAnimation *animation = [CAKeyframeAnimation animation];
animation.keyPath = @"position";
animation.duration = 4;
animation.rotationMode = kCAAnimationRotateAuto;
animation.path = bezierPath.CGPath;
[layer addAnimation:animation forKey:nil];
动画组
CABasicAnimation和CAKeyframeAnimation仅仅作用于单独的属性,CAAnimationGroup可以把这些动画组合在一起。
CAAnimationGroup *group =[CAAnimationGroup animation];
group.animations = @[animation1, animetion2];
group.duration = 4;
[layer addAnimation:group forKey:nil];