介绍 EasyAnimation
原文:Introduction EasyAnimation
作者:Marin Todorov
译者:kmyhy
本教程使用 Xcode 7/Swift 2 以上版本。
在
//UIKit view animation
UIView.animateWithDuration(2.0, animations: {self.view.center.x = 200.0
})
而 CoreAnimation 不同,它需要你创建一个动画模型对象,设置它然后传递给 CoreAnimation 服务:
//CoreAnimation 图层动画
let anim = CABasicAnimation(keyPath: "position.x")
anim.fromValue = 100.0
anim.toValue = 200.0
anim.duration = 2.0
anim.fillMode = kCAFillModeBackwards
anim.beginTime = CACurrentMediaTime() + 2.0
anim.timingFunction = CAMediaTimingFunction(name: kCAMediaTimingFunctionEaseOut)
view.layer.addAnimation(anim, forKey: nil)
EasyAnimation 能够明显减少创建图层动画的代码,扩展了 UIKit 原有的动画方法,让你将时间花在你真正想要干的事情上。
在本教程中,你将学习如何轻松地对图层属性进行动画,以及轻松地将动画串联成序列和组(我最喜欢干的)。
开始
我已经准备了一个开始项目,以节省你新建项目和创建 UI 和自动布局的工作。
下载 EAImagePreview-Starter.zip, 解压缩并打开 EAImagePreview.xcodeproj。
EAImagePreview 是一个简单项目,显示了一个照片列表,当点击某个 cell,显示出照片的完整大图。
打开 Main.storyboard,查看项目结构:
在 collection view 的 cell 中显示的是照片的缩略图——在 ViewController.swift 文件底部的扩展中包含了所有的 collection view 数据源方法和委托方法。
你可以运行一下这个 app 看看:
点击其中某张图片,你会看到它的大图。点击大图,它又小时。开始项目是很简单的,你的任务就是使用 EasyAnimation 来增加一些亮点!
首先创建一个 Podfile 文件添加 pod EasyAnimation:
use_frameworks!
pod 'EasyAnimation'
然后安装该 pod,重新打开 Cocoapods 创建的 workspace 文件。你会在工作空间的 Pods 项目文件夹下看到 EasyAnimation 的源文件:
现在来写几句代码!
打开工作看见开始项目中的 ViewController.swift (它不在 Pods 项目中) 找到 showImage(image:) 方法。这个方法用于显示大图。
为了了解 EasyAnimation 能够做些什么,我们来添加几个动画。
首先是在显示大图之前,让照片列表淡出。找到并删除这句代码:
self.preview.addSubview(imgView)
然后在这里开始编写代码:
UIView.animateWithDuration(0.25, delay: 0.0, options: .CurveEaseIn, animations: {//animate collection viewself.collectionView.transform = CGAffineTransformMakeTranslation(-30.0, 0.0)self.collectionView.alpha = 0.5}, completion: {_ in//show the image viewself.preview.addSubview(imgView)
})
在你的 app 中你肯定不止一回用到这个方法了。如果你运行这个 app,你会看到照片列表会慢慢移到一边,然后才显示出大图。
现在——如果你想在第一个动画完成时添加另一个动画时怎么办?你需要在第一个动画的完成块中创建新的动画。如果你想添加第三个动画呢——需要在第二个动画的完成块中创建第三个动画,以此类推……
这种方式最终会让你的代码格式变成一场灾难,因为你的嵌套的块太深了,Xcode 不能很好地缩进你的代码块参数……
让我们来看一看 EasyAnimation 提供的解决方案。EasyAnimation 在 UIView 类上添加了一个新的方法,允许你轻松地将链式动画串在一起:
找到 ViewController.swift 头部,导入 EasyAnimation:
import EasyAnimation
回到 showImage(image:) 方法,将 animateWithDuration 替换成 animateAndChainWithDuration。chain 方法的参数和原来的方法参数是一样的,所以你只要修改下方法名即可:
UIView.animateAndChainWithDuration(0.25, delay: 0.0, options: .CurveEaseIn, animations: {//animate collection view...
如果你运行 app,你会发现结果没有什么不同。
但是,如果回到代码中将方法调用最后的 ] 符号后面加一个 “.”,你会发现你可以以链式调用新的动画方法。比如:
我真的想说:这也太“贴心”了吧 :)
假设要在你的动画序列中添加一个弹簧动画——你的动画代码将变成:
UIView.animateAndChainWithDuration(0.25, delay: 0.0, options: .CurveEaseIn, animations: {//animate collection viewself.collectionView.transform = CGAffineTransformMakeTranslation(-30.0, 0.0)self.collectionView.alpha = 0.5}, completion: {_ in//show the image viewself.preview.addSubview(imgView)
}).animateWithDuration(2.0, delay: 0.0, usingSpringWithDamping: 0.25, initialSpringVelocity: 0.0, options: [], animations: {//second animation here}, completion: nil)
这段代码将先执行第一个动画,然后然后执行完成块中的代码,然后执行新加入的第二个动画。
在 // second animation here (在第二个动画块中)编写:
self.collectionView.transform = CGAffineTransformMakeTranslation(-100.0, 0.0)
第二个动画只是将 collection 向左边再移动一些。如果你运行 app,你会看到列表会出现一个反弹效果。这两个动画的拼接是完全无缝的,因为 EasyAnimation 在内部使用完成块将他们串起来了。
接下来试一下 EasyAnimation 的另一个功能。来点图层动画增加点味道怎么样?
在最后一句后面加入:
imgView.layer.borderWidth = 5.0
啊——使用 EasyAnimation 之后就是这样简单。不需要创建 CABasicAnimation 对象之类的东东,你可以用像对 UIView 属性进行动画的方式来对 CALayer 属性进行动画。
运行 app,你会看到当大图显示后会开始一个小小的边框动画。注意边框也会动——它也是弹簧动画!
实际上,UIKit 自己也会处理一些 CALayer 动画。例如,如果你进行一个 CALayer 变换,UIKit 会自动处理这个动画。最大的好处是,你无需关心哪些动画是 UIKit 来负责,哪些是 EasyAnimation 来负责,因为现在它们都是一样的了。继续添加代码:
var imgFlip = CATransform3DIdentity
imgFlip.m34 = -1.0 / 1000
imgFlip = CATransform3DRotate(imgFlip, CGFloat(-M_PI_4), 0.0, 1.0, 0.0)
imgFlip = CATransform3DTranslate(imgFlip, 100.0, 0.0, 0.0)imgView.layer.transform = imgFlip
注意:如果你不太清楚其中 3D 变换的代码,请参考 iOS Animations by Tutorials 中的第四部分“3D 动画”。
现在的动画更有趣了:
你还需要再添加一个动画到序列中,在大图的周围显示一个漂亮的光晕,才是我们最终的效果。
向上滚动代码,在调用 UIView.animateAndChainWithDuration 一句之前插入代码:
imgView.layer.shadowColor = UIColor.whiteColor().CGColorimgView.layer.shadowOffset = CGSize(width: 0, height: 0)imgView.layer.shadowOpacity = 0.9
这段代码会在 image view 上加上一个光晕(实际上它不过是一个白色阴影,只不过看起来就像白色光晕而已)。然后在动画序列中添加一个新的动画,对这个光晕执行动画:
imgView.layer.transform = imgFlip}, completion: nil).animateWithDuration(2.0, delay: 0.25, usingSpringWithDamping: 0.25, initialSpringVelocity: 0.0, options: [], animations: {//increase the shadow radius (by default it's 3.0)imgView.layer.shadowRadius = 30.0
}, completion: nil)
运行 app,欣赏一下完整的动画序列效果:
如果你想再进一步完善动画效果,你可以找到 closeImage(tap:) 方法,将整个方法包装在一个动画调用中。现在关闭大图的效果变得更好看了。
在这篇短教程里,你学习了如何:
- 将动画串在一起
- 将 UIView 动画和 CALayer 动画放在同一个动画调用里
- 对 CALayer 属性进行弹簧动画
- 将 UIKit 和 EasyAnimate 动画同等对待
如果你想了解更多 EasyAnimation 的例子,请从 GitHub 上克隆并运行它的示例 app: https://github.com/icanzilb/EasyAnimation.
要是你不喜欢出血效果,请参考 dev-marin 分支: https://github.com/icanzilb/EasyAnimation/tree/dev-marin.
接下来做什么?
重新阅读 iOS Animations by Turtorials 第三部分“图层动画”吧——这会让你更好地知道如何用 EasyAnimation 去重构你的 CALayer 动画,让代码更简洁。
如果你准备基于本教程的内容编写一些好玩的东东,请回复这封邮件或者 twitter 给我 @icanzilb。
介绍 EasyAnimation相关推荐
- 简单介绍互联网领域选择与营销方法
在我看来,互联网领域的选择是"安家",而营销方法的不同则表现了"定家"的方式多种多样,只有选对了,"家"才得以"安定". ...
- 常用开源协议介绍以及开源软件规范列表
1. 开源协议介绍 GPL: General Public License,开源项目最常用的许可证,衍生代码的分发需开源并且也要遵守此协议.该协议也有很多变种,不同变种要求会略微不同. MPL: MP ...
- python:Json模块dumps、loads、dump、load介绍
20210831 https://www.cnblogs.com/bigtreei/p/10466518.html json dump dumps 区别 python:Json模块dumps.load ...
- pytorch学习笔记(九):PyTorch结构介绍
PyTorch结构介绍 对PyTorch架构的粗浅理解,不能保证完全正确,但是希望可以从更高层次上对PyTorch上有个整体把握.水平有限,如有错误,欢迎指错,谢谢! 几个重要的类型 和数值相关的 T ...
- Python字节码介绍
了解 Python 字节码是什么,Python 如何使用它来执行你的代码,以及知道它是如何帮到你的. 如果你曾经编写过 Python,或者只是使用过 Python,你或许经常会看到 Python 源代 ...
- Pytest - 使用介绍
1. 概述 pytest是一个非常成熟的全功能的Python测试框架,主要特点有以下几点: 1.简单灵活,容易上手,文档丰富: 2.支持参数化,可以细粒度地控制要测试的测试用例: 3.能够支持简单的单 ...
- 遗传算法的简单介绍以及模式定理的简单证明
遗传算法 遗传算法(Genetic Algorithm,GA),最早是由美国的John holland在20世纪70年代提出.算法通过模拟达尔文生物进化论的自然选择以及遗传学机理的生物进化过程来搜 ...
- k8s核心组件详细介绍教程(配超详细实例演示)
本文实验环境基于上篇文章手把手从零开始搭建k8s集群超详细教程 本文根据B站课程云原生Java架构师的第一课K8s+Docker+KubeSphere+DevOps学习总结而来 k8s核心组件介绍 1 ...
- Tensorrt一些优化技术介绍
Tensorrt一些优化技术介绍 Figure 1. A quantizable AveragePool layer (in blue) is fused with a DQ layer and a ...
最新文章
- 03JavaScript中的数据类型
- typedef struct 先声明后定义_C++模版和C#泛型求同存异录(二)typedef
- 训练日志 2018.8.29
- int转为string类型方法
- WEBGL的测试网站和基础知识
- 如何利用 Visual Studio 自带工具提高开发效率
- 【开源工程】视频主观质量评测工具 video quality compare tool
- 修改tableView侧栏索引的背景色
- oracle本地数据库登录之连接pdb数据库
- [iOS]判断ipa是否脱壳
- 电路板级的EMC设计 (1)概述
- matlab相机标定工具箱下载,matlab相机标定工具箱
- 孩子发烧,别急着降温
- Android应用程序如何进行系统签名
- 社会工程学三本_1.9万人报考,扩招近千人!被戏称为“大三本”的985——东南大学,低调有实力!...
- K-Means检测DGA域名
- Project 视频 来啦
- mes系统是什么?看完本文你就明白了
- 【妄言之言】西南游记
- 掌握电商数据的4个要点,电商平台数据分析其实很简单