iOS POP动画简单使用

POP背后的开发者是 Kimon Tsinteris, Push Pop Press 的联合创始人,曾经在Apple担任高级工程师,并参与了 iPhone 和 iPad 上软件的研发(iPhone的指南针以及地图)。2011年的时候 Facebook 收购了他的公司,此后他便加入了 Facebook 负责 Facebook iOS 版本的开发。

POP 使用 Objective-C++ 编写,Objective-C++ 是对 C++ 的扩展,就像 Objective-C 是 C 的扩展。而至于为什么他们用 Objective-C++ 而不是纯粹的 Objective-C,原因是他们更喜欢 Objective-C++ 的语法特性所提供的便利

POP动画是一个十分受欢迎的动画,在这个框架刚出来一周的时候点赞👍量都超过3k,现在点赞量达到17.8k。身为一个iOS开发者必须对这个框架有一定的了解。

7B0CCB7A-9F02-4948-9F19-709EDEC73218.png

效果图

POP动画应用.gif

我在项目中目录

  • pop基础介绍
  • pop项目中PropertyNamed简单介绍
  • 弹性动画
  • 弹出小卡片
  • 画圆
  • 进度条
  • 图像折叠

想要看代码的可以点击这里

项目参考了pop-handapppopping这两个项目,内容也是基于这两个项目写的。

【注意】

在使用pop-handapp的时候,我们pod以后会报Cannot initialize a member subobject of type 'NSUInteger' (aka 'unsigned long') with an rvalue of type 'nullptr_t'这个错误,解决办法,我先把POP库移除,然后随便添加一个AFNetworking库,然后在添加POP库,为啥这样做,我也不知道哦,反正我是这样解决问题的。

参考文献

Facebook POP动效库使用教程
Facebook Pop 使用指南
Facebook POP 进阶指南

基本类型

POP基础.png

使用之前需要先倒入#import <POP.h>

POPBasicAnimation
基础使用
 /*
     设置动画至少需要三步
     1、定义一个animation对象 并指定对应的动画属性
     2、设置初始值和默认值(初始值可以不指定 会默认从当前值开始)
     3、添加到想产生动画的对象上
     
     POPBasicAnimation可配置的属性与默认值为
     duration:0.4    //动画间隔

     */
    POPBasicAnimation *animation = [POPBasicAnimation animationWithPropertyNamed:kPOPLayerPositionX];
    animation.toValue = @(_BaseView.center.y + 200);
    animation.beginTime = CACurrentMediaTime() + 1.0f;
    [_BaseView pop_addAnimation:animation forKey:@"BasicAnimation"];

我们点击进入POPBasicAnimation里面

  • 两个初始化方法

  • + (instancetype)animation;

  • + (instancetype)animationWithPropertyNamed

  • 四个动画方式

  • kCAMediaTimingFunctionLinear

  • kCAMediaTimingFunctionEaseIn

  • kCAMediaTimingFunctionEaseOut

  • kCAMediaTimingFunctionEaseInEaseOut

  • 两个属性

  • duration

  • timingFunction

POPSpringAnimation

POPSpringAnimation也许是大多数人使用POP的理由 其提供一个类似弹簧一般的动画效果

POPSpringAnimation可配置的属性与默认值为

  • springBounciness //[0-20] 弹力 越大则震动幅度越大

  • springSpeed //[0-20] 速度 越大则动画结束越快

  • dynamicsTension //拉力 接下来这三个都跟物理力学模拟相关 数值调整起来也很费时 没事不建议使用哈

  • dynamicsFriction //摩擦 同上

  • dynamicsMass //质量 同上

【注意】
POPSpringAnimation是没有duration字段的 其动画持续时间由以上几个参数决定

简单实用
 POPSpringAnimation *aniSpring = [POPSpringAnimation animationWithPropertyNamed:kPOPLayerPositionY];
    aniSpring.toValue = @(_BaseView.center.x + 100);
    aniSpring.beginTime = CACurrentMediaTime();
    aniSpring.springBounciness = 10.0;
    [_BaseView pop_addAnimation:aniSpring forKey:@"POPSpringAnimation"];

POPDecayAnimation

Decay Animation 就是 POP 提供的另外一个非常特别的动画,他实现了一个衰减的效果。这个动画有一个重要的参数 velocity(速率),一般并不用于物体的自发动画,而是与用户的交互共生

Decay 的动画没有 toValue 只有 fromValue,然后按照 velocity 来做衰减操作

想要理解更深POPDecayAnimation,可以参考小球碰壁反弹效果

代码
#import "DecayAnimationTwo.h"
#import <POP.h>
@interface DecayAnimationTwo ()<POPAnimationDelegate>
@property (nonatomic,strong) UIView *baseView;
@end

@implementation DecayAnimationTwo

- (void)viewDidLoad {
    [super viewDidLoad];
    self.view.backgroundColor = [UIColor whiteColor];
    self.title = @"碰壁反弹效果";
    
    
    _baseView = [[UIView alloc]initWithFrame:CGRectMake(0, 0, 100, 100)];
    _baseView.center = self.view.center;
    _baseView.layer.masksToBounds = YES;
    _baseView.layer.cornerRadius = _baseView.bounds.size.width/2;
    _baseView.backgroundColor = [UIColor redColor];
    [self.view addSubview:_baseView];
    
    
    //拖拽手势
    UIPanGestureRecognizer *pan = [[UIPanGestureRecognizer alloc]initWithTarget:self action:@selector(PanGesture:)];
    [_baseView addGestureRecognizer:pan];
 
}


//拖拽手势
- (void)PanGesture:(UIPanGestureRecognizer*)pan{
    //在拖动过程中
    //取出偏移量
    CGPoint offset = [pan translationInView:self.view];
    //让baseView平移
    _baseView.transform = CGAffineTransformTranslate(_baseView.transform, offset.x, offset.y);
    //平移完之后将偏移量重新置为0
    //这很重要,要记住
    [pan setTranslation:CGPointZero inView:self.view];
    
    
    //当拖动手势结束的时候,开始动画
    if (pan.state == UIGestureRecognizerStateEnded) {
        
        POPDecayAnimation *decayAnimation = [POPDecayAnimation animationWithPropertyNamed:kPOPLayerPosition];
        CGPoint velocity = [pan velocityInView:self.view];
        decayAnimation.velocity = [NSValue valueWithCGPoint:velocity];
        [_baseView.layer pop_addAnimation:decayAnimation forKey:@"layerPositionAnimation"];
        
        decayAnimation.delegate = self;
        
    }
 
}

#pragma mark - POPAnimationDelegate
///在小球弹动的过程中判断是否碰壁
- (void)pop_animationDidApply:(POPDecayAnimation *)anim
{
    BOOL baseViewInsideOfSuperView = CGRectContainsRect(self.view.frame, self.baseView.frame);
    if (!baseViewInsideOfSuperView) {
       
        CGPoint currentVelocity = [anim.velocity CGPointValue];
        CGPoint velocity = CGPointMake(currentVelocity.x, -currentVelocity.y);
        POPSpringAnimation *positionAnimation = [POPSpringAnimation animationWithPropertyNamed:kPOPLayerPosition];
        positionAnimation.velocity = [NSValue valueWithCGPoint:velocity];
        positionAnimation.toValue = [NSValue valueWithCGPoint:self.view.center];
        [self.baseView.layer pop_addAnimation:positionAnimation forKey:@"layerPositionAnimation"];
    }
    
}

@end

POPAnimatableProperty

效果图


POPAnimatableProperty.gif
代码
 
    /*
     其组成就是一个readBlock一个writeBlock和一个threashold
     
     readBlock告诉POP当前的属性值
     writeBlock中修改变化后的属性值
     threashold决定了动画变化间隔的阈值 值越大writeBlock的调用次数越少
     */
    UILabel *label = [[UILabel alloc]initWithFrame:CGRectMake(0, SCREEN_HEIGHT - 100, SCREEN_WIDTH, 100)];
    label.textAlignment = NSTextAlignmentCenter;
    [self.view addSubview:label];
    
    POPAnimatableProperty *prop = [POPAnimatableProperty propertyWithName:@"countdown" initializer:^(POPMutableAnimatableProperty *prop) {
       
        prop.readBlock = ^(id obj, CGFloat values[]) {
           
        };
        
        prop.writeBlock = ^(id obj, const CGFloat values[]) {
            UILabel *label = (UILabel*)obj;
            label.text = [NSString stringWithFormat:@"%02d:%02d:%02d",(int)values[0]/60,(int)values[0]%60,(int)(values[0]*100)%100];
        };
       
        prop.threshold = 0.01;
    }];
    
    
    
    POPBasicAnimation *anBasic = [POPBasicAnimation linearAnimation];   //秒表当然必须是线性的时间函数
    anBasic.property = prop;    //自定义属性
    anBasic.fromValue = @(0);   //从0开始
    anBasic.toValue = @(3*60);  //180秒
    anBasic.duration = 3*60;    //持续3分钟
    anBasic.beginTime = CACurrentMediaTime();
    [label pop_addAnimation:anBasic forKey:@"countdown"];

PropertyNamed

一些人可能对PropertyNamed的一些属性不太了解,我这里做了一个简单的demo,对一些简单的属性做了一些解释。

效果图
PropertyNamed.gif

譬如kPOPViewCenter

 POPBasicAnimation *basicAnimation = [POPBasicAnimation animation];
    basicAnimation.property = [POPAnimatableProperty propertyWithName:kPOPViewCenter];
    basicAnimation.toValue=[NSValue valueWithCGPoint:CGPointMake(200, 200)];
    [_baseView pop_addAnimation:basicAnimation forKey:@"kPOPViewCenter"];

具体代码请参考这里,也可以参考详解Fecebook PoP API 及 属性使用!这篇文章,来对属性进行补充

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 204,053评论 6 478
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 85,527评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 150,779评论 0 337
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,685评论 1 276
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,699评论 5 366
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,609评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 37,989评论 3 396
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,654评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 40,890评论 1 298
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,634评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,716评论 1 330
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,394评论 4 319
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 38,976评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,950评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,191评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 44,849评论 2 349
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,458评论 2 342

推荐阅读更多精彩内容

  • 发现 关注 消息 iOS 第三方库、插件、知名博客总结 作者大灰狼的小绵羊哥哥关注 2017.06.26 09:4...
    肇东周阅读 12,016评论 4 62
  • Swift版本点击这里欢迎加入QQ群交流: 594119878最新更新日期:18-09-17 About A cu...
    ylgwhyh阅读 25,276评论 7 249
  • 文/六弄儿 大道理不听,拎着背包去浪,虽然可能注定孤独终老 今天又忽的想起了你。 想起得到你刚离开的消息的时候,你...
    六弄儿阅读 169评论 0 1
  • 让我欢喜让我忧的[小程序]设计指南 还在电脑前埋头钻研APP UI的我,突然被公司的产品经理劝停,告知我它...
    TryNing阅读 367评论 0 1
  • 下午的时候,突然有个高大的身影手里那满了东西,还有许多的植物,跑来我房间,这时我正在和我妈说话,这男的露出温暖的酒...
    勇敢Planet阅读 450评论 0 0