iOS实现数字倍数动画效果 CAKeyframeAnimation 关键帧动画的用法

效果图:

实现思路

上代码 看比较清晰

  • IOS 核心动画之CAKeyframeAnimation

  • 简单介绍

是CApropertyAnimation的子类,跟CABasicAnimation的区别是:CABasicAnimation只能从

一个数值(fromValue)变到另一个数值(toValue),而CAKeyframeAnimation会使用一个NSArray保存这些数值

  • 属性解析:

  • values:就是上述的NSArray对象。里面的元素称为”关键帧”(keyframe)。动画对象会在指定的时间(duration)内,依次显示values数组中的每一个关键帧

  • path:可以设置一个CGPathRef\CGMutablePathRef,让层跟着路径移动。path只对CALayer的anchorPoint和position起作用。如果你设置了path,那么values将被忽略

  • keyTimes:可以为对应的关键帧指定对应的时间点,其取值范围为0到1.0,keyTimes中的每一个时间值都对应values中的每一帧.当keyTimes没有设置的时候,各个关键帧的时间是平分的

  • 说明:CABasicAnimation可看做是最多只有2个关键帧的CAKeyframeAnimation

  • Values方式:

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

18

19

20

21

22

23

24

// 数字跳动动画

- (void)labelDanceAnimation:(NSTimeInterval)duration {

 //透明度

 CABasicAnimation *opacityAnimation = [CABasicAnimation animationWithKeyPath:@"opacity"];

 opacityAnimation.duration = 0.4 * duration;

 opacityAnimation.fromValue = @0.f;

 opacityAnimation.toValue = @1.f;

 

 //缩放

 CAKeyframeAnimation *scaleAnimation = [CAKeyframeAnimation animationWithKeyPath:@"transform.scale"];

 scaleAnimation.duration = duration;

 scaleAnimation.values = @[@3.f, @1.f, @1.2f, @1.f];

 scaleAnimation.keyTimes = @[@0.f, @0.16f, @0.28f, @0.4f];

 scaleAnimation.removedOnCompletion = YES;

 scaleAnimation.fillMode = kCAFillModeForwards;

 

 CAAnimationGroup *animationGroup = [CAAnimationGroup animation];

 animationGroup.animations = @[opacityAnimation, scaleAnimation];

 animationGroup.duration = duration;

 animationGroup.removedOnCompletion = YES;

 animationGroup.fillMode = kCAFillModeForwards;

 

 [self.comboLabel.layer addAnimation:animationGroup forKey:@"kComboAnimationKey"];

}

 

利用一个透明度从 0 ~ 1之间的alpha,然后缩放 之后加到动画组实现一下就好了

切记动画完成最好移除 否则可能引起动画内存问题

这里设置斜体字体

1

self.comboLabel.font = [UIFont fontWithName:@"AvenirNext-BoldItalic" size:50];

看着比较明显

最后按钮点击的时候调用

1

2

3

4

5

- (IBAction)clickAction:(UIButton *)sender {

 self.danceCount++;

 [self labelDanceAnimation:0.4];

 self.comboLabel.text = [NSString stringWithFormat:@"+ %tu",self.danceCount];

}

如果实现 dozen动画的话很简单, danceCount % 10 == 0 求模就行了.

总结

这个动画比较适合 有些直播场景的点击操作计数相关.

好了,以上就是这篇文章的全部内容了,希望本文的内容对大家的学习或者工作具有一定的参考学习价值,如果有疑问大家可以留言交流,谢谢大家对脚本之家的支持。

CAKeyframeAnimation 关键帧动画的用法

一、原理

之所以叫做关键帧动画是因为,这个类可以实现,某一属性按照一串的数值进行动画,就好像制作动画的时候一帧一帧的制作一样。

一般使用的时候  首先通过 animationWithKeyPath 方法 创建一个CAKeyframeAnimation实例,

 

CAKeyframeAnimation 的一些比较重要的属性

1. path

这是一个 CGPathRef  对象,默认是空的,当我们创建好CAKeyframeAnimation的实例的时候,可以通过制定一个自己定义的path来让  某一个物体按照这个路径进行动画。这个值默认是nil  当其被设定的时候  values  这个属性就被覆盖 

2. values

一个数组,提供了一组关键帧的值,  当使用path的 时候 values的值自动被忽略。

下面是一个简单的例子  效果为动画的连续移动一个block到不同的位置

    CGMutablePathRef path = CGPathCreateMutable();
    //将路径的起点定位到(50  120)  
    CGPathMoveToPoint(path,NULL,50.0,120.0);
    //下面5行添加5条直线的路径到path中
    CGPathAddLineToPoint(path, NULL, 60, 130);
    CGPathAddLineToPoint(path, NULL, 70, 140);
    CGPathAddLineToPoint(path, NULL, 80, 150);
    CGPathAddLineToPoint(path, NULL, 90, 160);
    CGPathAddLineToPoint(path, NULL, 100, 170);
    //下面四行添加四条曲线路径到path
    CGPathAddCurveToPoint(path,NULL,50.0,275.0,150.0,275.0,70.0,120.0);
    CGPathAddCurveToPoint(path,NULL,150.0,275.0,250.0,275.0,90.0,120.0);
    CGPathAddCurveToPoint(path,NULL,250.0,275.0,350.0,275.0,110.0,120.0);
    CGPathAddCurveToPoint(path,NULL,350.0,275.0,450.0,275.0,130.0,120.0);
    //以“position”为关键字
 创建 实例
    CAKeyframeAnimation *animation = [CAKeyframeAnimation animationWithKeyPath:@"position"];
    //设置path属性
    [animation setPath:path];
    [animation setDuration:3.0];
    //这句代码表示 是否动画回到原位
    //[animation setAutoreverses:YES];
    CFRelease(path);
    [self.block.layer addAnimation:animation forKey:NULL];
运行后  block会先沿着直线移动,之后再沿着设定的曲线移动,完全按照我们设定的“关键帧”移动。
    CGPoint p1=CGPointMake(50, 120);
    CGPoint p2=CGPointMake(80, 170);
    CGPoint p3=CGPointMake(30, 100);
    CGPoint p4=CGPointMake(100, 190);
    CGPoint p5=CGPointMake(200, 10);
    NSArray *values=[NSArray arrayWithObjects:[NSValue valueWithCGPoint:p1],[NSValue valueWithCGPoint:p2],[NSValue valueWithCGPoint:p3],[NSValue valueWithCGPoint:p4],[NSValue valueWithCGPoint:p5], nil];
    CAKeyframeAnimation *animation = [CAKeyframeAnimation animationWithKeyPath:@"position"];
    [animation setValues:values];
    [animation setDuration:3.0];
    [animation setAutoreverses:YES];
    [self.block.layer addAnimation:animation forKey:NULL];
       也非常简单,到目前位置,只用到了CAKeyframeAnimation的两个关键属性就能完成动画,下面的一些属性提供了更加细致化,更加强大的功能。

设定每一帧的时间

       默认情况下,一帧动画的播放,分割 的时间是动画的总时间除以帧数减去一。你可以通过下面的公式决定每帧动画的时间:总时间/(总帧数-1)。 例如,如果你指定了一个 5 帧,10 秒的动画,那么每帧的时间就是 2.5 秒钟:10/(5-1)=2.5。你可以做更多 的控制通过使用 keyTimes 关键字,你可以给每帧动画指定总时间之内的某个时间点。 

       通过设置属性keyTimes,能实现这个功能,这个属性是一个数组,其成员必须是NSNumber。

       同时 这个属性的设定值要与calculationMode属性相结合,同时他们有一定的规则,

The appropriate values in the keyTimes array are dependent on the calculationMode property.

If the calculationMode is set to kCAAnimationLinear, the first value in the array must be 0.0 and the last value must be 1.0. Values are interpolated between the specified key times.

If the calculationMode is set to kCAAnimationDiscrete, the first value in the array must be 0.0.

If the calculationMode is set to kCAAnimationPaced or kCAAnimationCubicPaced, the keyTimes array is ignored。

如果keyTimes的值不合法,或者不符合上面的规则,那么就会被忽略。

[animation setCalculationMode:kCAAnimationLinear]; 
[animation setKeyTimes:[NSArray arrayWithObjects:[NSNumber numberWithFloat:0.0],[NSNumber numberWithFloat:0.25], [NSNumber numberWithFloat:0.50],[NSNumber numberWithFloat:0.75], [NSNumber numberWithFloat:1.0], nil]];

calculationMode
这个属性用来设定 关键帧中间的值是怎么被计算的

可选的值有

<span style="margin: 0px; padding: 0px; ">NSString * const kCAAnimationLinear;     默认是这种模式
NSString * const kCAAnimationDiscrete;   只展示关键帧的状态,没有中间过程,没有动画。
NSString * const kCAAnimationPaced;
NSString * const kCAAnimationCubic;
NSString * const kCAAnimationCubicPaced;</span>
<span style="margin: 0px; padding: 0px; ">关键帧动画的基础步骤</span>
1.决定你想要做动画的属性(例如,框架,背景,锚点,位置,边框,等等) 

2.在动画对象值的区域中,指定开始,结束,和中间的值。这些都是你的关键帧(看清单 4-2)
3.使用 duration 这个字段指定动画的时间
4.通常来讲,通过使用 times 这个字段,来给每帧动画指定一个时间。如果你没有指定这些,核心动画就会通过你在 values 这个字段指定的值分割出时间段。

5.通常,指定时间功能来控制步调。 这些都是你需要做的。你创建你的动画和增加他们到层中。调用-addAnimation 就开始了动画。 


二、举例使用

1.使用贝赛尔曲线路径的关键帧动画

     UIBezierPath *path = [UIBezierPath bezierPath];
     [path moveToPoint:CGPointMake(-40, 100)];
     [path addLineToPoint:CGPointMake(360, 100)];
     [path addLineToPoint:CGPointMake(360, 200)];
     [path addLineToPoint:CGPointMake(-40, 200)];
     [path addLineToPoint:CGPointMake(-40, 300)];
     [path addLineToPoint:CGPointMake(360, 300)];
     
     CAKeyframeAnimation *moveAnimation = [CAKeyframeAnimation animationWithKeyPath:@"position"];
     moveAnimation.path = path.CGPath;
     moveAnimation.duration = 8.0f;
     moveAnimation.rotationMode = kCAAnimationRotateAuto;
     [shapeLayer addAnimation:moveAnimation forKey:@"moveAnimation"];

2.使用基于缩放的关键帧动画
     CAKeyframeAnimation *animation = [CAKeyframeAnimation animationWithKeyPath:@"transform"];
     
     CATransform3D scale1 = CATransform3DMakeScale(0.5, 0.5, 1);
     CATransform3D scale2 = CATransform3DMakeScale(1.2, 1.2, 1);
     CATransform3D scale3 = CATransform3DMakeScale(0.9, 0.9, 1);
     CATransform3D scale4 = CATransform3DMakeScale(1.0, 1.0, 1);
     
     NSArray *frameValues = [NSArray arrayWithObjects:
                             [NSValue valueWithCATransform3D:scale1],
                             [NSValue valueWithCATransform3D:scale2],
                             [NSValue valueWithCATransform3D:scale3],
                             [NSValue valueWithCATransform3D:scale4],
                             nil];
     
     [animation setValues:frameValues];
     
     NSArray *frameTimes = [NSArray arrayWithObjects:
                            [NSNumber numberWithFloat:0.0],
                            [NSNumber numberWithFloat:0.5],
                            [NSNumber numberWithFloat:0.9],
                            [NSNumber numberWithFloat:1.0],
                            nil];
     [animation setKeyTimes:frameTimes];
     
     animation.fillMode = kCAFillModeForwards;
     animation.duration = .25;
     
     [self addAnimation:animation forKey:@"DSPopUpAnimation"];
3.使用基于路径的关键帧动画

     CGMutablePathRef path = CGPathCreateMutable();
     
     CGPathMoveToPoint(path, NULL, 50.0, 120.0);
     CGPathAddCurveToPoint(path, NULL, 50.0, 275.0, 150.0, 275.0, 150.0, 120.0);
     CGPathAddCurveToPoint(path,NULL,150.0,275.0,250.0,275.0,250.0,120.0);
     CGPathAddCurveToPoint(path,NULL,250.0,275.0,350.0,275.0,350.0,120.0);
     CGPathAddCurveToPoint(path,NULL,350.0,275.0,450.0,275.0,450.0,120.0);
     
     CAKeyframeAnimation *anim = [CAKeyframeAnimation animationWithKeyPath:@"position"];
     [anim setPath:path];
     [anim setDuration:3.0];
     [anim setAutoreverses:YES];
     CFRelease(path);
     [self.layer addAnimation:anim forKey:@"path"];
4.使用基于位置点的关键桢动画
     CGPoint pt0 = CGPointMake(50.0, 120.0);
     CGPoint pt1 = CGPointMake(50.0, 275.0);
     CGPoint pt2 = CGPointMake(150.0, 275.0);
     CGPoint pt3 = CGPointMake(150.0, 120.0);
     CGPoint pt4 = CGPointMake(150.0, 275.0);
     CGPoint pt5 = CGPointMake(250.0, 275.0);
     CGPoint pt6 = CGPointMake(250.0, 120.0);
     CGPoint pt7 = CGPointMake(250.0, 275.0);
     CGPoint pt8 = CGPointMake(350.0, 275.0);
     CGPoint pt9 = CGPointMake(350.0, 120.0);
     CGPoint pt10 = CGPointMake(350.0, 275.0);
     CGPoint pt11 = CGPointMake(450.0, 275.0);
     CGPoint pt12 = CGPointMake(450.0, 120.0);
     NSArray *values = [NSArray arrayWithObjects:
                        [NSValue valueWithCGPoint:pt0],
                        [NSValue valueWithCGPoint:pt1],
                        [NSValue valueWithCGPoint:pt2],
                        [NSValue valueWithCGPoint:pt3],
                        [NSValue valueWithCGPoint:pt4],
                        [NSValue valueWithCGPoint:pt5],
                        [NSValue valueWithCGPoint:pt6],
                        [NSValue valueWithCGPoint:pt7],
                        [NSValue valueWithCGPoint:pt8],
                        [NSValue valueWithCGPoint:pt9],
                        [NSValue valueWithCGPoint:pt10],
                        [NSValue valueWithCGPoint:pt11],
                        [NSValue valueWithCGPoint:pt12], nil];
     CAKeyframeAnimation *anim = [CAKeyframeAnimation animationWithKeyPath:@"position"];
     [anim setValues:values];
     [anim setDuration:3.0];
     [anim setAutoreverses:YES];
     
     [self.layer addAnimation:anim forKey:@"path"];

5.使用基于旋转的关键桢动画
CAKeyframeAnimation *keyAnim = [CAKeyframeAnimation animationWithKeyPath:@"transform"];
             CATransform3D rotation1 = CATransform3DMakeRotation(30 * M_PI/180, 0, 0, -1);
             CATransform3D rotation2 = CATransform3DMakeRotation(60 * M_PI/180, 0, 0, -1);
             CATransform3D rotation3 = CATransform3DMakeRotation(90 * M_PI/180, 0, 0, -1);
             CATransform3D rotation4 = CATransform3DMakeRotation(120 * M_PI/180, 0, 0, -1);
             CATransform3D rotation5 = CATransform3DMakeRotation(150 * M_PI/180, 0, 0, -1);
             CATransform3D rotation6 = CATransform3DMakeRotation(180 * M_PI/180, 0, 0, -1);
             
             [keyAnim setValues:[NSArray arrayWithObjects:
                                 [NSValue valueWithCATransform3D:rotation1],
                                 [NSValue valueWithCATransform3D:rotation2],
                                 [NSValue valueWithCATransform3D:rotation3],
                                 [NSValue valueWithCATransform3D:rotation4],
                                 [NSValue valueWithCATransform3D:rotation5],
                                 [NSValue valueWithCATransform3D:rotation6],
                                 nil]];
             [keyAnim setKeyTimes:[NSArray arrayWithObjects:
                                   [NSNumber numberWithFloat:0.0],
                                   [NSNumber numberWithFloat:0.2f],
                                   [NSNumber numberWithFloat:0.4f],
                                   [NSNumber numberWithFloat:0.6f],
                                   [NSNumber numberWithFloat:0.8f],
                                   [NSNumber numberWithFloat:1.0f],
                                   nil]];
             [keyAnim setDuration:4];
             [keyAnim setFillMode:kCAFillModeForwards];
             [keyAnim setRemovedOnCompletion:NO];
             [zhiZhenLayer addAnimation:keyAnim forKey:nil];

添加动画结束的delegate

CAKeyframeAnimation* animation;
    animation = [CAKeyframeAnimation animation];
    animation.delegate = self;
    [animation setValue:@"aaa" forKey:@"TAG"];

- (void)animationDidStop:(CAAnimation *)anim finished:(BOOL)flag
{
    NSString *strTag = [anim valueForKey:@"TAG"];
    if ([strTag isEqualToString:@"aaa"]) {
        aniIsRuning = NO;
    }
}

————————————————
版权声明:本文为CSDN博主「蓝天客」的原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/samuelltk/article/details/9048325

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值