ios 动画基础(一)

每个UIView都有关联的CALayer对象,被称之为rootLayer。

隐式动画

隐式动画指我们没有指定任何动画类型,只是改变了layer的属性,有框架自动完成动画效果,默认持续时间是0.25s;但是只有非rootLayer(自己创建的)才有隐式动画,具体原因如下:

我们把改变属性时CALayer自动应用的动画称作action,当CALayer的属性被修改时候,它会调用actionForKey:方法,传递属性的名称。具体见如下步骤:

  • 图层首先检测它是否有委托,并且是否实现CALayerDelegate协议指定的actionForLayer:forKey方法。如果有,直接调用并返回结果。
  • 如果没有委托,或者委托没有实现-actionForLayer:forKey方法,图层接着检查包含属性名称对应行为映射的actions字典。
  • 如果actions字典没有包含对应的属性,那么图层接着在它的style字典接着搜索属性名。
  • 最后,如果在style里面也找不到对应的行为,那么图层将会直接调用定义了每个属性的标准行为的-defaultActionForKey:方法。
    在一轮完整的搜索结束之后,-actionForKey:要么返回空(这种情况下将不会有动画发生),要么返回CAAction协议的对象,最后CALayer拿这个结果去做动画。

每个UIView对它关联的图层都扮演了一个委托,并且提供了-actionForLayer:forKey的实现方法。当不在一个动画块的实现中,UIView对所有图层行为返回nil,但是在动画block范围之内,它就返回了一个非空值。

 NSLog(@"Outside: %@", [self.view actionForLayer:self.view.layer forKey:@"backgroundColor"]);
 //begin animation block
 [UIView beginAnimations:nil context:nil];
 //test layer action when inside of animation block
 NSLog(@"Inside: %@", [self.view actionForLayer:self.view.layer forKey:@"backgroundColor"]);
 //end animation block
 [UIView commitAnimations];

打印结果如下
Outside: <null>
Inside: <CABasicAnimation: 0x7ff3e9d28f40>

具体可见官方文档
objc中View-Layer 协作也有说明

  1. Layer可动画属性 ,如
  • bounds:用于设置CALayer的宽度和高度,修改这个属性会产生缩放动画;
  • backgroundColor:用于设置CALayer的背景色,修改这个属性会产生背景色的渐变动画;
  • position:用于设置CALayer的位置,修改这个属性会产生平移动画等等,可以在CALayer的头文件中看到
  1. 利用CATransaction来改变默认的隐式动画
    CATransaction说明
    [CATransaction begin];
    [CATransaction setAnimationDuration:1.0];
    self.colorLayer.backgroundColor = [[UIColor yellowColor] CGColor];
    [CATransaction commit];

显式动画

  1. 属性动画:作用于图层的某个单一属性,并指定了它的一个目标值,或者一连串将要做动画的值。
  2. 动画组:将多个属性动画组合到一起。
  3. 动画过渡:不像属性动画那样平滑地在两个值之间做动画,而是影响到整个图层的变化;过渡动画首先展示之前的图层样子,然后过渡到新的样子。


    core animation结构

    先来介绍属性动画下基础动画

CABasicAnimation

1.先看一个实现平移动画的🌰

    CALayer *layer = [[CALayer alloc]init];
    layer.backgroundColor = [[UIColor grayColor]CGColor];
    layer.frame = CGRectMake(40, 20, 40, 40);
    layer.cornerRadius = 5;
    [self.view.layer addSublayer:layer];
    //平移动画
    CABasicAnimation *animation = [CABasicAnimation animationWithKeyPath:@"position"];
    animation.duration = 3.0;
    animation.autoreverses = YES;
    animation.repeatCount = HUGE_VALF;
    animation.fromValue = [NSValue valueWithCGPoint:layer.position];
    CGPoint toPoint = layer.position;
    toPoint.x = toPoint.x+180;
    animation.toValue = [NSValue valueWithCGPoint:toPoint];
    [layer addAnimation:animation forKey:@"move"];

先是新建了一个layer,然后利用keyPath创建了一个动画,通过设置属性定义动画效果,最后将动画添加到layer上。
keyPath的值,这边列出比较常用,还有一些和上面叙述的layer的属性类似

keyPath的值 说明
position 位置变化,引起平移动画
transform.scale 比例变化,放大缩小
transform.scale.x 宽度缩放
transform.scale.y 高度缩放
transform.rotation 旋转
transform.rotation.x 沿x轴旋转
transform.rotation.y 沿y轴旋转
transform.rotation.z 沿z轴旋转
opacity 透明度
backgroundColor 背景颜色
cornerRadius 圆角

animation的属性

属性 说明
fromValue 动画改变的属性初始值
toValue 动画改变的属性结束值
byValue 过程中属性相对初始值改变的值
duration 动画持续时长
repeatCount 动画重复次数,不停重复设置为 HUGE_VALF
repeatDuration 动画应该被重复多久,动画会一直重复,直到设定的时间流逝完;它不应该和 repeatCount 一起使用。
autoreverses 动画结束时是否执行逆动画,当你设定这个属性为 YES 时,在它到达目的地之后,动画的返回到开始的值,代替了直接跳转到 开始的值。
beginTime 指定动画开始的时间。从开始延迟几秒的话,设置为【CACurrentMediaTime() + 秒数】 的方式
timingFunction 设置动画的速度变化,这个略复杂,稍候介绍

2.如果要定义动画开始之前或结束之后的状态,可以用fillMode;不过要注意要在CABasicAnimation 中fillMode启作用,需要将removedOnCompletion设为NO,具体见CABasicAnimation fillMode和removedOnCompletion

scaleAnimation.removedOnCompletion = NO;
scaleAnimation.fillMode = kCAFillModeForwards;

解释:为什么动画结束后返回原状态?
layer有两个重要属性modelLayer和presentationLayer(还有一个renderingLayer,是私有的);modelLayer表现了我们看到的layer状态,当改变layer的属性值,modelLayer的属性值也即刻改变;presentationLayer则表现的是动画过程中状态值。
而当我们给一个layer添加动画时,动画开始时 presentation layer在不断变化,动画结束时,presentation layer从屏幕上移除,原始layer显示。如果没有改变过modelLayer的值,那么在动画结束之后就会返回到原状态。

3.其他例子

    //旋转动画
    CABasicAnimation *rotateAnimation = [CABasicAnimation animationWithKeyPath:@"transform.rotation.x"];
    rotateAnimation.duration = 3.0;
    rotateAnimation.repeatCount = HUGE_VALF;
    rotateAnimation.autoreverses = YES;
    rotateAnimation.fromValue = [NSNumber numberWithFloat:0];
    rotateAnimation.toValue = [NSNumber numberWithFloat:6*M_PI];
    [rotateLayer addAnimation:rotateAnimation forKey:@"rotate"];
    //....
    //放大、缩小
    CABasicAnimation *scaleAnimation = [CABasicAnimation animationWithKeyPath:@"transform.scale.x"];
    scaleAnimation.duration = 3.0;
    scaleAnimation.repeatCount = HUGE_VALF;
    scaleAnimation.autoreverses = YES;
    scaleAnimation.removedOnCompletion = NO;
    scaleAnimation.fromValue = [NSNumber numberWithFloat:1.0];
    scaleAnimation.toValue = [NSNumber numberWithFloat:2.5];
    scaleAnimation.fillMode = kCAFillModeForwards;
    [scaleLayer addAnimation:scaleAnimation forKey:@"scale"];

参考资料

core animation官方文档
浅谈animation
CABasicAnimation使用总结
显式动画
隐式动画
让你的动画动起来

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

推荐阅读更多精彩内容