iOS 金币入袋(收金币)动画

作者: calary | 来源:发表于2017-09-05 15:43 被阅读208次

前言

碰到个需求,做一个金币入袋的动画,如下图这种效果,因为用的地方比较多,所以我把它进行了封装,使用起来比较方便,加入购物车和这个实现思路一致,大家可以试试。

未命名.gif

思路

拿到后的想法是用粒子动画,参考iOS CAEmitterLayer粒子动画详解,但是后来又觉得不对,因为粒子动画没办法决定动画的终点,所以我觉得这里应该是路径动画实现。

路径动画实现起来还算是比较简单,根据起点终点设置好路径,然后这么多个image用延时的方法逐个生成,最后执行动画即可,动画结束后将创建的image移除掉,这就是总体思路了。
下面看代码。

代码

//.h文件
#import <UIKit/UIKit.h>
@class ShootButtonSetting;

@interface HHShootButton : UIButton

@property (nonatomic, strong) ShootButtonSetting *setting;

- (instancetype)initWithFrame:(CGRect)frame andEndPoint:(CGPoint)point;
@end

typedef NS_OPTIONS(NSUInteger, ShootButtonAnimationType) {
    ShootButtonAnimationTypeLine       = 0,  //直线
    ShootButtonAnimationTypeCurve      = 1,  //曲线
};
//默认设置
@interface ShootButtonSetting : NSObject

@property (nonatomic, assign) int totalCount;//动画产生imagView的个数,默认10个
@property (nonatomic, assign) CGFloat timeSpace; //产生imageView的时间间隔,默认0.1
@property (nonatomic, assign) CGFloat duration;//动画时长, 默认1s
@property (nonatomic, strong) UIImage *iconImage; //图片,默认为button自身图片
@property (nonatomic, assign) ShootButtonAnimationType animationType;//动画类型,默认曲线
// Factory method to help build a default setting
+ (ShootButtonSetting *)defaultSetting;
@end
//.m文件
#import "HHShootButton.h"
@interface HHShootButton()<CAAnimationDelegate>
@property (nonatomic, strong) NSMutableArray *coinTagArray;
@property (nonatomic, assign) CGPoint point;
@end

@implementation HHShootButton

- (instancetype)initWithFrame:(CGRect)frame andEndPoint:(CGPoint)point{
    if (self = [super initWithFrame:frame]){
        _coinTagArray = [[NSMutableArray alloc] init];
        self.setting = [ShootButtonSetting defaultSetting];
        //目的地的位置
        self.point = CGPointMake(point.x - frame.origin.x, point.y - frame.origin.y);
        [self addTarget:self action:@selector(buttonAction) forControlEvents:UIControlEventTouchUpInside];
    }
    return self;
}

- (void)buttonAction{
    for(int i = 0; i < self.setting.totalCount; i ++){
        //延时 注意时间要乘i 这样才会生成一串,要不然就是拥挤在一起的
        dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(i*self.setting.timeSpace * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
            [self initCoinViewWithInt:i];
        });
    }
}

- (void)initCoinViewWithInt:(int)i{
    
    UIImageView *imageView = [[UIImageView alloc] initWithImage:self.setting.iconImage ?: self.imageView.image];
    //设置中心位置
    imageView.center = CGPointMake(self.frame.size.width/2.0, self.frame.size.height/2.0);
    //初始化金币的位置
    imageView.tag = i + 1000; //设置tag时尽量设置大点的数值
    //将tag添加到数组,用于判断移除
    [self.coinTagArray addObject:[NSNumber numberWithInt:(int)imageView.tag]];
    [self addSubview:imageView];
    [self setAnimationWithLayer:imageView];
}

- (void)setAnimationWithLayer:(UIView *)imageView{
    
    UIBezierPath *movePath = [UIBezierPath bezierPath];
    [movePath moveToPoint:CGPointMake(self.frame.size.width/2.0, self.frame.size.height/2.0)];
    
    switch (self.setting.animationType) {
        case ShootButtonAnimationTypeLine://直线
            [movePath addLineToPoint:self.point];
            break;
        case ShootButtonAnimationTypeCurve://曲线
            //抛物线
            [movePath addQuadCurveToPoint:self.point controlPoint:CGPointMake(self.point.x, self.center.y)];
            break;
        default:
            break;
    }
    
    //位移动画
    CAKeyframeAnimation *animation = [CAKeyframeAnimation animationWithKeyPath:@"position"];
    //移动路径
    animation.path = movePath.CGPath;
    animation.duration = self.setting.duration;
    animation.autoreverses = NO;
    animation.repeatCount = 1;
    animation.calculationMode = kCAAnimationPaced;
    animation.delegate = self;
    [imageView.layer addAnimation:animation forKey:@"position"];
}

- (void)animationDidStop:(CAAnimation *)anim finished:(BOOL)flag{
    if (flag){//动画执行结束移除view
        NSLog(@"动画结束");
        UIView *coinView =(UIView *)[self viewWithTag:[[self.coinTagArray firstObject] intValue]];
        [coinView removeFromSuperview];
        [self.coinTagArray removeObjectAtIndex:0];
    }
}

@end

#pragma mark - Setting Methods
@implementation ShootButtonSetting

+ (ShootButtonSetting *)defaultSetting{
    ShootButtonSetting *defaultSetting = [[ShootButtonSetting alloc] init];
    defaultSetting.totalCount = 10;
    defaultSetting.timeSpace = 0.1;
    defaultSetting.duration = 1;
    defaultSetting.animationType = ShootButtonAnimationTypeCurve;
    return defaultSetting;
}
@end

代码中都有很好的注释,这是我封装起来的,具体使用时导入头文件然后像初始化按钮一样初始化,传入目的地的位置,如果没有设置image则默认是按钮的图片,demo中提供了两种,一种是默认button图片,一种是设置了图片。

HHShootButton *shootBtn = [[HHShootButton alloc] initWithFrame:CGRectMake(10, 300, 80, 80) andEndPoint:self.iconImageView.center];
    [shootBtn setImage:[UIImage imageNamed:@"icon_xin"] forState:UIControlStateNormal];
    shootBtn.setting.animationType = ShootButtonAnimationTypeLine;
    [self.view addSubview:shootBtn];

其实,加入购物车的动画和这个大同小异,购物车动画只用生成一个UIImageView,然后加上图片旋转动画即可。
demo地址HHShootButtonDemo,打开它运行即可,希望大家喜欢,记得star✨哦!

参考

http://code1.okbase.net/codefile/ParabolaViewController.m_2014082227116_5.htm

相关文章

  • iOS 金币入袋(收金币)动画

    前言 碰到个需求,做一个金币入袋的动画,如下图这种效果,因为用的地方比较多,所以我把它进行了封装,使用起来比较方便...

  • cocos creator 数值变化+金币移动动画

    数值滚动 金币动画

  • 淘金币变现之道

    收淘金币的小姐姐又来了 Vx-18295846539 淘金币10000/10元 5000起收 天猫积分1000...

  • 动画| 金币抛入红包动画详解

    前言 这个动画效果很早就出来了,也是一个比较经典的关键帧动画和组合动画的运用,通过剖析源码,可以发现实际上这个酷炫...

  • 杰克爷爷的羊丢了

    1.杰克爷爷的羊丢了。 …… 得到一袋金币。 2.杰克爷爷的羊丢了。 杰克爷爷找羊。 找到了吗? 得到一袋金币。 ...

  • 怎么将C4D的动画整成GIF?

    主要想做一个小金币翻转的GIF,然后嵌到原型工具里用。点击金币后有一个金币翻转的小动画,翻转的时候有一个厚度,懒得...

  • 算法——模拟

    金币 题目描述 国王将金币作为工资,发放给忠诚的骑士。第一天,骑士收到一枚金币;之后两天(第二天和第三天),每天收...

  • 玛雅塔罗师的自我修炼——塔罗观牌静心

    金币4 逆位 金币——土元素 一名男子头顶一枚金币,手里环抱一枚金币,脚下分别踩着两枚金币。男子目视着前方,穿着红...

  • 莱信金币的使用跟获得

    [if !supportLists]一、[endif]莱信金币获得方法, 金币可以通过红包、转金币、分润、和平台发...

  • 淘金币报名规则

    金币报名规则 一、金币价格报名规则 1、所有的天猫报名商品必须全部使用“金币加钱购”的工具 (1)什么是金币加钱购...

网友评论

    本文标题:iOS 金币入袋(收金币)动画

    本文链接:https://www.haomeiwen.com/subject/bowujxtx.html