CATransition动画精讲

来源:互联网 发布:linux文件绝对路径 编辑:程序博客网 时间:2024/05/16 06:03

前言


曾经,笔者对动画一无所知,当他人问起时,总是似懂非懂。每一次别人说起动画效果时,笔者都不好意思插话,因此懂得太少,只是会使用UIView的那几个添加动画的方法。现在,不再等待,一步一步地学习其基础知识并开始尝试写一些常用的动画效果。

如果您也一样迷茫,那就不要迷茫了,实践出真知!!!

基础知识


我们直接看官方声明:

/** Transition animation subclass. **/@interface CATransition : CAAnimation/* The name of the transition. Current legal transition types include * `fade', `moveIn', `push' and `reveal'. Defaults to `fade'. */@property(copy) NSString *type;/* An optional subtype for the transition. E.g. used to specify the * transition direction for motion-based transitions, in which case * the legal values are `fromLeft', `fromRight', `fromTop' and * `fromBottom'. */@property(nullable, copy) NSString *subtype;/* The amount of progress through to the transition at which to begin * and end execution. Legal values are numbers in the range [0,1]. * `endProgress' must be greater than or equal to `startProgress'. * Default values are 0 and 1 respectively. */@property float startProgress;@property float endProgress;/* An optional filter object implementing the transition. When set the * `type' and `subtype' properties are ignored. The filter must * implement `inputImage', `inputTargetImage' and `inputTime' input * keys, and the `outputImage' output key. Optionally it may support * the `inputExtent' key, which will be set to a rectangle describing * the region in which the transition should run. Defaults to nil. */@property(nullable, strong) id filter;@end

CATransition类继承于CAAnimation类,提供的是过滤的效果,如pushfadereveal等。

type属性是用于指定效果类型,当前官方提供的效果有fade, moveIn, pushreveal. 默认为fade。对于其它类型,如cube立体效果这种官方没有公开,也不清楚是否是使用私有。

subtype属性是可选的,主要用于指定动画的方向。比如动作类动画效果中,有从左边进入、从右边进入等效果。

@property float startProgress;@property float endProgress;

这两个属性可以设置动画动作的进度,默认为0->1。

filter属性默认为nil,一旦设置了此属性,typesubtype就会被忽略。 这个属性意思就是滤镜的意思吧,它需要实现inputImageinputTargetImageinputTimeoutputImage,当然还有一个可选的inputExtent,不要求实现。

更多基础知识,请参考:CAAnimation精讲

实战练习做动画


先看看我们做效果图:

image

常用的transition动画几乎都有了,而且笔者在学习的同时,也这将些动画封装成了一个类方法,只需要一行代码就可以实现动画效果了哦!

头文件声明

这里只公共了一个方法,并将常用的动画使用一个枚举类型来指定,不用再记着那些单词了。

////  HYBTransitionAnimation.h//  CATransitionOfObjCDemo////  Created by huangyibiao on 15/12/14.//  Copyright © 2015年 huangyibiao. All rights reserved.//#import <Foundation/Foundation.h>#import <UIKit/UIKit.h>typedef NS_ENUM(NSUInteger, HYBTransitionType) {  kHYBTransitionFade = 1,     // 淡入淡出  kHYBTransitionPush,         // 推进效果  kHYBTransitionReveal,       // 揭开效果  kHYBTransitionMoveIn,       // 慢慢进入并覆盖效果  kHYBTransitionCube,         // 立体翻转效果  kHYBTransitionSuckEffect,   // 像被吸入瓶子的效果  kHYBTransitionRippleEffect, // 波纹效果  kHYBTransitionPageCurl,     // 翻页效果  kHYBTransitionPageUnCurl,   // 反翻页效果  kHYBTransitionCameraOpen,   // 开镜头效果  kHYBTransitionCameraClose,  // 关镜头效果  kHYBTransitionCurlDown,     // 下翻页效果  kHYBTransitionCurlUp,       // 上翻页效果  kHYBTransitionFlipFromLeft, // 左翻转效果  kHYBTransitionFlipFromRight,// 右翻转效果  kHYBTransitionOglFlip       // 翻转};typedef NS_ENUM(NSUInteger, HYBTransitionSubtype) {  kHYBTransitionSubtypeFromLeft = 1,  // 从左边进入  kHYBTransitionSubtypeFromRight,     // 从右边进入  kHYBTransitionSubtypeFromTop,       // 从顶部进入  kHYBTransitionSubtypeFromBottom     // 从底部进入};@interface HYBTransitionAnimation : NSObject+ (void)transitionForView:(UIView *)aView                               type:(HYBTransitionType)type                            subtype:(HYBTransitionSubtype)subtype                           duration:(NSTimeInterval)duration;@end

实现文件

其实实现的代码也很简单,只是对枚举类型判断一下,然后添加动画:

////  HYBTransitionAnimation.m//  CATransitionOfObjCDemo////  Created by huangyibiao on 15/12/14.//  Copyright © 2015年 huangyibiao. All rights reserved.//#import "HYBTransitionAnimation.h"@implementation HYBTransitionAnimation+ (void)transitionForView:(UIView *)aView                               type:(HYBTransitionType)type                            subtype:(HYBTransitionSubtype)subtype                           duration:(NSTimeInterval)duration {  NSString *animationType = nil;  NSString *animationSubtype = nil;  switch (subtype) {    case kHYBTransitionSubtypeFromLeft:      animationSubtype = kCATransitionFromLeft;      break;      case kHYBTransitionSubtypeFromRight:      animationSubtype = kCATransitionFromRight;      break;      case kHYBTransitionSubtypeFromTop:      animationSubtype = kCATransitionFromTop;      break;      case kHYBTransitionSubtypeFromBottom:      animationSubtype = kCATransitionFromBottom;      break;    default:      break;  }  switch (type) {    case kHYBTransitionFade: {      animationType = kCATransitionFade;      break;    }    case kHYBTransitionPush: {      animationType = kCATransitionPush;      break;    }    case kHYBTransitionReveal: {      animationType = kCATransitionReveal;      break;    }    case kHYBTransitionMoveIn: {      animationType = kCATransitionMoveIn;      break;    }    case kHYBTransitionCube: {      animationType = @"cube";      break;    }    case kHYBTransitionSuckEffect: {      animationType = @"suckEffect";      break;    }    case kHYBTransitionRippleEffect: {      animationType = @"rippleEffect";      break;    }    case kHYBTransitionPageCurl: {      animationType = @"pageCurl";      break;    }    case kHYBTransitionPageUnCurl: {      animationType = @"pageUnCurl";      break;    }    case kHYBTransitionCameraOpen: {      animationType = @"cameraIrisHollowOpen";      break;    }    case kHYBTransitionCameraClose: {      animationType = @"cameraIrisHollowClose";      break;    }    case kHYBTransitionCurlDown: {      [self animationForView:aView type:UIViewAnimationTransitionCurlDown duration:duration];      break;    }    case kHYBTransitionCurlUp: {      [self animationForView:aView type:UIViewAnimationTransitionCurlUp duration:duration];      break;    }    case kHYBTransitionFlipFromLeft: {      [self animationForView:aView type:UIViewAnimationTransitionFlipFromLeft duration:duration];      break;    }    case kHYBTransitionFlipFromRight: {      [self animationForView:aView type:UIViewAnimationTransitionFlipFromRight duration:duration];      break;    }      case kHYBTransitionOglFlip:      animationType = @"oglFlip";      break;    default: {      break;    }  }  if (animationType != nil) {    CATransition *animation = [CATransition animation];    animation.duration = duration;    animation.type = animationType;    if (animationSubtype != nil) {      animation.subtype = animationSubtype;    }    animation.timingFunction = UIViewAnimationOptionCurveEaseInOut;    [aView.layer addAnimation:animation forKey:@"animation"];  }}+ (void)animationForView:(UIView *)aView                    type:(UIViewAnimationTransition)type                duration:(NSTimeInterval)duration {  [UIView animateWithDuration:duration animations:^{    [UIView setAnimationCurve:UIViewAnimationCurveEaseInOut];    [UIView setAnimationTransition:type forView:aView cache:YES];  }];}@end

解析

我们的核心添加动画的代码是:

CATransition *animation = [CATransition animation];animation.duration = duration;animation.type = animationType;if (animationSubtype != nil) {  animation.subtype = animationSubtype;}animation.timingFunction = UIViewAnimationOptionCurveEaseInOut;[aView.layer addAnimation:animation forKey:@"animation"];

系统提供给我们一些动画是在UIView上提供的方法,我们可以看看这个枚举:

typedef NS_ENUM(NSInteger, UIViewAnimationTransition) {    UIViewAnimationTransitionNone,    UIViewAnimationTransitionFlipFromLeft,    UIViewAnimationTransitionFlipFromRight,    UIViewAnimationTransitionCurlUp,    UIViewAnimationTransitionCurlDown,};

我们添加动画只需要调用UIView添加动画的方法就可以实现了:

[UIView animateWithDuration:duration animations:^{    [UIView setAnimationCurve:UIViewAnimationCurveEaseInOut];    [UIView setAnimationTransition:type forView:aView cache:YES];}];

测试效果


我们在ViewController这里尝试一下效果,这里只是使用定时器每一秒就自动切换一种效果:

////  ViewController.m//  CATransitionOfObjCDemo////  Created by huangyibiao on 15/12/14.//  Copyright © 2015年 huangyibiao. All rights reserved.//#import "ViewController.h"#import "HYBTransitionAnimation.h"@interface ViewController ()@property (nonatomic, assign) int subtype;@property (nonatomic, strong) NSArray *array;@property (nonatomic, strong) UIImage *img1;@property (nonatomic, strong) UIImage *img2;@property (nonatomic, assign) BOOL isImg1;@property (nonatomic, assign) NSUInteger index;@end@implementation ViewController- (void)viewDidLoad {  [super viewDidLoad];  self.array = @[@(kHYBTransitionFade),                 @(kHYBTransitionPush),                 @(kHYBTransitionReveal),                 @(kHYBTransitionMoveIn),                 @(kHYBTransitionCube),                 @(kHYBTransitionSuckEffect),                 @(kHYBTransitionRippleEffect),                 @(kHYBTransitionPageCurl),                 @(kHYBTransitionPageUnCurl),                 @(kHYBTransitionCameraOpen),                 @(kHYBTransitionCameraClose),                 @(kHYBTransitionCurlDown),                 @(kHYBTransitionCurlUp),                 @(kHYBTransitionFlipFromLeft),                 @(kHYBTransitionFlipFromRight),                 @(kHYBTransitionOglFlip)];  self.img1 = [UIImage imageNamed:@"1.png"];  self.img2 = [UIImage imageWithContentsOfFile:[[NSBundle mainBundle] pathForResource:@"3" ofType:@"jpg"]];  self.view.backgroundColor = [UIColor colorWithPatternImage:self.img1];  self.isImg1 = YES;  [NSTimer scheduledTimerWithTimeInterval:1.0                                   target:self                                 selector:@selector(updateAnimation)                                 userInfo:nil                                  repeats:YES];}- (void)updateAnimation {  if (self.index >= self.array.count) {    self.index = 0;  }  HYBTransitionType type = [[self.array objectAtIndex:self.index++] intValue];  static int s_subtypeValue = 0;  HYBTransitionSubtype subtype = kHYBTransitionSubtypeFromTop;  s_subtypeValue++;  if (s_subtypeValue >= 4) {    s_subtypeValue = 1;  }  subtype = (HYBTransitionSubtype)s_subtypeValue;  [HYBTransitionAnimation transitionForView:self.view                                       type:type                                    subtype:subtype                                   duration:1.0];  if (self.isImg1) {    self.view.backgroundColor = [UIColor colorWithPatternImage:self.img1];  } else {    self.view.backgroundColor = [UIColor colorWithPatternImage:self.img2];  }  self.isImg1 = !self.isImg1;}@end

写在最后


学习不易,写代码不易,且看且珍惜!!!

学习不易,写代码不易,且看且珍惜!!!

学习不易,写代码不易,且看且珍惜!!!

源代码


小伙伴们可以到笔者的GITHUB下载源代码:CATransitionDemo请随手给一个star表示支持

阅读原文

关注我


微信公众号:iOSDevShares
有问必答QQ群:324400294

0 0
原创粉丝点击
热门问题 老师的惩罚 人脸识别 我在镇武司摸鱼那些年 重生之率土为王 我在大康的咸鱼生活 盘龙之生命进化 天生仙种 凡人之先天五行 春回大明朝 姑娘不必设防,我是瞎子 牙黑了有洞怎么办 牙齿内侧掉了一小块怎么办 龋坏的牙齿痛怎么办 2岁半宝宝蛀牙怎么办 3岁宝宝门牙腐蚀怎么办 2岁宝宝门牙有洞怎么办 三岁宝宝有龋齿怎么办 牙龈肿痛脸肿了怎么办 孕妇牙疼的厉害怎么办 智齿引起的牙疼怎么办 蛀牙了有个大洞牙痛怎么办 长了蛀牙牙疼怎么办 面饼表面长黑点怎么办 牙结石自己掉了怎么办 狗狗得了牙结石怎么办 牙结石掉了有洞怎么办 内衣的钩子会掉怎么办? 新胸罩肩带老掉怎么办 牙齿少了一小块怎么办 儿童牙齿有黑斑要怎么办 牙齿又黄又臭怎么办 大牙烂空了很臭怎么办 牙齿已经烂没了怎么办 牙齿已经蛀没了怎么办 牙齿整个蛀掉了怎么办 小孩恒牙长歪了怎么办 孩子换牙长歪了怎么办 9岁门牙磕松动了怎么办 牙齿摔断了一半怎么办 牙齿从根部断了怎么办 牙断了还有牙根怎么办 牙根断在牙龈里怎么办 后槽牙掉了一半怎么办 孩子门牙摔断了怎么办 2岁宝宝牙齿断了怎么办 小孩乳牙摔掉了怎么办 9孩子门牙磕断了怎么办 牙齿断了但没掉怎么办 大人门牙摔断了怎么办 兔子内牙太长了怎么办 牙齿整个摔断了怎么办