Facebook Pop动画框架详细解析(一) —— 基本概览

版本记录

版本号 时间
V1.0 2017.12.16

前言

POP框架是Facebook开发的一个框架,是一个在iOS与OS X上通用的极具扩展性的动画引擎。它在基本的静态动画的基础上增加的弹簧动画与衰减动画,使之能创造出更真实更具物理性的交互动画。POP的API可以快速的与现有的ObjC代码集成并可以作用于任意对象的任意属性。

Overview

Pop是iOS,tvOS和OS X的可扩展动画引擎。除了基本的静态动画之外,它还支持弹簧和衰变动态动画,使其可用于构建逼真的基于物理的交互。 该API允许与现有的Objective-C或Swift代码库快速集成,并可以在任何对象上动画任何属性。 这是一个成熟且经过充分测试的框架,可以驱动Paper中所有的动画和转换。


Installation - 安装

1. 自动安装

对于CocoaPods,可以通过下面方式加入到项目中。

pod 'pop', '~> 1.0'

Bugs首先在master中修复,然后通过指定的版本发布。 您也可以使用以下Podfile条目的Master的Pop。

pod 'pop', :git => 'https://github.com/facebook/pop.git'

2. 手动安装

Framework (manual)

通过将项目添加到项目中,并将pop.embedded框架添加到应用程序目标的“常规”选项卡上的“嵌入式二进制文件Embedded Binaries”部分,您可以在几秒钟内设置pop! 这也可以在头文件模块中使用@import pop语法。

注意:由于Xcode的一些尴尬限制,嵌入式二进制文件必须与模块共享相同的名称,并且必须以.framework作为扩展名。 这意味着在添加嵌入式二进制文件(一个用于OS X,一个用于tvOS,另一个用于iOS)时,您会看到三个pop.frameworks。 你需要确保添加正确的; 它们在列表中出现的相同,但注意列表是按目标顺序填充的。 你可以用<configuration> - <platform>(例如Debug-iphoneos)的格式检查列出框架旁边的路径来验证正确的路径。

注意:这个方法当前不能和工作区很好的兼容。 由于目标target只能依赖和嵌入来自其他目标的产品在同一个项目中,所以只有在将pop.xcodeproj作为子项目添加到当前目标项目时才能起作用。 否则,您需要在scheme中手动设置构建顺序和在产品中的备份。

Static Library (manual)

还有另外一种方案,您可以将项目添加到工作区,并采用提供的配置文件或手动将pop子目录下的文件复制到项目中。 如果手动安装,通过在项目链接器标志中包含-lc ++链接以确保C ++标准库被链接。


Usage - 使用

Pop采用Core Animation显式动画编程模型。 通过下面的引入使用:

Objective-C

#import <pop/POP.h>

或者,如果你使用嵌入式框架

@import pop;

Swift

import pop

1. Start, Stop & Update - 开始、结束和更新

要开始一个动画,将其添加到您想要动画的对象:

Objective-C

POPSpringAnimation *anim = [POPSpringAnimation animation];
...
[layer pop_addAnimation:anim forKey:@"myKey"];

Swift

let anim = POPSpringAnimation()
...
layer.pop_add(anim, forKey: "myKey")

要停止动画,请将其从引用在start上指定的键的对象中移除:

Objective-C

[layer pop_removeAnimationForKey:@"myKey"];

Swift

layer.pop_removeAnimation(forKey: "myKey")

该键也可以用来查询动画的存在。 更新正在运行的动画的toValue可以提供最无缝的方法来更改路线:

Objective-C

anim = [layer pop_animationForKey:@"myKey"];
if (anim) {
  /* update to value to new destination */
  anim.toValue = @(42.0);
} else {
  /* create and start a new animation */
  ....
}

Swift

if let anim = layer.pop_animation(forKey: "myKey") as? POPSpringAnimation {
    /* update to value to new destination */
    anim.toValue = 42.0
} else {
    /* create and start a new animation */
    ....
}

在上面的例子中使用了一个图层,而Pop接口是作为NSObject上的类别添加实现的。 任何NSObject或子类可以动画。

2. Types - 类型

有四种具体的动画类型:spring, decay, basic 和 custom

Spring动画可以用来给对象一个愉快的反弹。 在这个例子中,我们使用弹簧动画来将图层的边界从其当前值设置为(0,0,400,400)

Objective-C

POPSpringAnimation *anim = [POPSpringAnimation animationWithPropertyNamed:kPOPLayerBounds];
anim.toValue = [NSValue valueWithCGRect:CGRectMake(0, 0, 400, 400)];
[layer pop_addAnimation:anim forKey:@"size"];

Swift

if let anim = POPSpringAnimation(propertyNamed: kPOPLayerBounds) {
    anim.toValue = NSValue(cgRect: CGRect(x: 0, y: 0, width: 400, height: 400))
    layer.pop_add(anim, forKey: "size")
}

Decay动画可以用来逐渐减缓对象的停顿。 在这个例子中,我们从一个图层的当前值和速度每秒1000pts衰减一个图层的positionX

Objective-C

POPDecayAnimation *anim = [POPDecayAnimation animationWithPropertyNamed:kPOPLayerPositionX];
anim.velocity = @(1000.);
[layer pop_addAnimation:anim forKey:@"slide"];

Swift

if let anim = POPDecayAnimation(propertyNamed: kPOPLayerPositionX) {
    anim.velocity = 1000.0
    layer.pop_add(anim, forKey: "slide")
}

Basic基本动画可用于在指定的时间段内插值。 要使用缓入式缓出动画在默认持续时间内将视图的Alpha从0.0增加到1.0,请执行以下操作:

Objective-C

POPBasicAnimation *anim = [POPBasicAnimation animationWithPropertyNamed:kPOPViewAlpha];
anim.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut];
anim.fromValue = @(0.0);
anim.toValue = @(1.0);
[view pop_addAnimation:anim forKey:@"fade"];

Swift

if let anim = POPBasicAnimation(propertyNamed: kPOPViewAlpha) {
    anim.timingFunction = CAMediaTimingFunction(name: kCAMediaTimingFunctionEaseInEaseOut)
    anim.fromValue = 0.0
    anim.toValue = 1.0
    view.pop_add(anim, forKey: "fade")
}

POPCustomAnimation通过处理CADisplayLink和相关的时间步进管理,使创建自定义动画和转换变得更容易。

3. Properties - 属性

动画属性由POPAnimatableProperty类指定。 在这个例子中,我们创建了一个spring动画,并明确设置了与[CALayer bounds]对应的动画属性:

Objective-C

POPSpringAnimation *anim = [POPSpringAnimation animation];
anim.property = [POPAnimatableProperty propertyWithName:kPOPLayerBounds];

Swift

let anim = POPSpringAnimation()
if let property = POPAnimatableProperty.property(withName: kPOPLayerBounds) as? POPAnimatableProperty {
    anim.property = property
}

该框架提供了许多常用的图层,并且可以查看动画的属性。 您可以通过创建类的新实例来为自定义属性设置动画。 在这个例子中,我们声明了一个自定义volume属性:

Objective-C

prop = [POPAnimatableProperty propertyWithName:@"com.foo.radio.volume" initializer:^(POPMutableAnimatableProperty *prop) {
  // read value
  prop.readBlock = ^(id obj, CGFloat values[]) {
    values[0] = [obj volume];
  };
  // write value
  prop.writeBlock = ^(id obj, const CGFloat values[]) {
    [obj setVolume:values[0]];
  };
  // dynamics threshold
  prop.threshold = 0.01;
}];

Swift

if let prop = POPAnimatableProperty.property(withName: "com.foo.radio.volume", initializer: { prop in
    guard let prop = prop else {
        return
    }
    // read value
    prop.readBlock = { obj, values in
        guard let obj = obj as? Volumeable, let values = values else {
            return
        }

        values[0] = obj.volume
    }
    // write value
    prop.writeBlock = { obj, values in
        guard var obj = obj as? Volumeable, let values = values else {
            return
        }

        obj.volume = values[0]
    }
    // dynamics threshold
    prop.threshold = 0.01
}) as? POPAnimatableProperty {
    anim.property = prop
}

有关提供的动画属性的完整列表,以及有关声明自定义属性的更多信息,请参阅POPAnimatableProperty.h

4. Debugging - 调试

以下是调试时的一些提示。 Pop服从模拟器的切换慢动画Simulator's Toggle Slow Animations设置。 尝试启用它减慢动画,更容易观察交互。

考虑命名你的动画。 这将允许您在引用它们时通过日志记录或在调试器中更容易地识别它们:

Objective-C

anim.name = @"springOpen";

Swift

anim.name = "springOpen"

每个动画都附带一个关联的跟踪器tracer。 跟踪器允许您以快速有效的方式记录所有动画相关事件,允许您在动画完成后查询和分析它们。 以下示例启动跟踪器并将其配置为记录动画完成的所有事件:

Objective-C

POPAnimationTracer *tracer = anim.tracer;
tracer.shouldLogAndResetOnCompletion = YES;
[tracer start];

Swift

if let tracer = anim.tracer {
    tracer.shouldLogAndResetOnCompletion = true
    tracer.start()
}

更多可参阅POPAnimationTracer.h


Testing - 测试

Pop有广泛的单元测试覆盖。 要安装测试依赖关系,请导航到根目录pop目录并输入:

pod install

假设安装了CocoaPods,这将包括对单元测试目标的必要的OCMock依赖。


SceneKit

由于SceneKit需要iOS 8和OS X 10.9,因此不提供POP的SceneKit扩展。 不幸的是,由于Xcode 6.1发行说明中提到的问题,不能使用弱链接weakly linked frameworks的框架。

为了解决这个问题,您可以轻松选择使用SceneKit! 只需将其添加到Xcode项目的“预处理器宏”Preprocessor Macros部分即可:

POP_USE_SCENEKIT=1

Resources - 资源

一系列可能证明有价值的外部资源的链接:

后记

未完,待续~~~

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

推荐阅读更多精彩内容

  • 起因 微信小程序虽然已经有现成的封装好的省市区选择器给开发者使用,然鹅不幸的是,微信地址库的数据和公司用的地址库数...
    简书5025阅读 21,759评论 6 17
  • 我决定写九百九十九首情诗用诗歌倾倒众生消失了战争写诗歌俘获你心直到和你成亲织一张玻璃网遍布你去过的角落得不到你也有...
    飞行先生MRflight阅读 210评论 0 2
  • 昨天又是因为装修的事情搞得很是火大 主要原因 就是装修施工头再次跟我有一项做不了,我当时就火大了,因为工程是刚刚开...
    L一梦阅读 189评论 0 0
  • 装备的工具Ubuntu16.04 , Xshell 使用Xshell链接到Ubuntu使用xshell链接Ubun...
    楚江云阅读 672评论 1 5
  • 终于抵达公司办公室,我把行李箱寄存在门卫室,转过身准备给咱们单位办公大楼拍照的时候,居然发现你和姣姐正在我身后不远...
    砖儿zr阅读 240评论 2 2