CABasicAnimation 動(dòng)畫

import "ViewController.h"

import <QuartzCore/QuartzCore.h>

define View_Side 80

define Screen_Width 320

define Screen_Height 460

import "AnimationDelegate.h"

@interface ViewController ()<CAAnimationDelegate>
{
UIView *_demoView;
}

@end

@implementation ViewController

/**

  • initialize the demoview.
    */
  • (void)initDemoView
    {
    _demoView = [[UIView alloc] initWithFrame:CGRectMake(20, 20, View_Side, View_Side)];
    _demoView.backgroundColor = [UIColor orangeColor];
    [self.view addSubview:_demoView];
    }

  • (void)viewDidLoad
    {
    [super viewDidLoad];
    [self initDemoView];

    [self performSelector:@selector(starAnimationScale1) withObject:nil afterDelay:2.0f];
    }

/*!
設(shè)定動(dòng)畫
屬性 說明
duration 動(dòng)畫的時(shí)長
repeatCount 重復(fù)的次數(shù)。不停重復(fù)設(shè)置為 HUGE_VALF
repeatDuration 設(shè)置動(dòng)畫的時(shí)間橄登。在該時(shí)間內(nèi)動(dòng)畫一直執(zhí)行嘹履,不計(jì)次數(shù)丰滑。
beginTime 指定動(dòng)畫開始的時(shí)間稍走。從開始延遲幾秒的話哗总,設(shè)置為【CACurrentMediaTime() + 秒數(shù)】 的方式
timingFunction 設(shè)置動(dòng)畫的速度變化
autoreverses 動(dòng)畫結(jié)束時(shí)是否執(zhí)行逆動(dòng)畫
fromValue 所改變屬性的起始值
toValue 所改變屬性的結(jié)束時(shí)的值
byValue 所改變屬性相同起始值的改變量
removedOnCompletion 防止動(dòng)畫結(jié)束后回到初始狀態(tài) 所以為了使動(dòng)畫結(jié)束之后layer保持結(jié)束狀態(tài)舔涎,應(yīng)將removedOnCompletion設(shè)置為NO
fillMode 防止動(dòng)畫結(jié)束后回到初始狀態(tài) 該屬性定義了你的動(dòng)畫在開始和結(jié)束時(shí)的動(dòng)作誊役。默認(rèn)值是 kCAFillModeRemoved获列。
speed speed 改變動(dòng)畫的速度 可以直接設(shè)置動(dòng)畫上的speed屬性贫母,這樣只有這個(gè)動(dòng)畫速度压昼。
speed兩點(diǎn)需注意的:
(1)如果設(shè)置動(dòng)畫時(shí)間為4s闹啦,speed設(shè)置為2蛾坯,則動(dòng)畫只需2s即可執(zhí)行完。
(2)如果同時(shí)設(shè)置了動(dòng)畫的speed和layer 的speed抑钟,則實(shí)際的speed為兩者相乘叛本。

*/

-(void)scaleopcity{
CABasicAnimation *animaiton = [CABasicAnimation animationWithKeyPath:@"transform.rotation.z"];
animaiton.fromValue = @(M_PI_4);
animaiton.toValue = @(M_PI);
animaiton.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut];
animaiton.autoreverses = NO;
animaiton.repeatCount = HUGE_VALF;
animaiton.beginTime = CACurrentMediaTime() + 1;
animaiton.delegate = self;//協(xié)議
animaiton.delegate = [[AnimationDelegate alloc]init];

// 防止動(dòng)畫結(jié)束后回到初始狀態(tài)
animaiton.removedOnCompletion = NO;
animaiton.fillMode = kCAFillModeForwards;

/*!
 kCAFillModeForwards    kCAFillModeForwards 設(shè)置為該值知染,動(dòng)畫即使之后layer的狀態(tài)將保持在動(dòng)畫的最后一幀艺玲,而removedOnCompletion的默認(rèn)屬性           
                        值是 YES括蝠,所以為了使動(dòng)畫結(jié)束之后layer保持結(jié)束狀態(tài),應(yīng)將removedOnCompletion設(shè)置為NO板驳。
 kCAFillModeBackwards   kCAFillModeBackwards 設(shè)置為該值又跛,將會(huì)立即執(zhí)行動(dòng)畫的第一幀碍拆,不論是否設(shè)置了 beginTime屬性若治。觀察發(fā)現(xiàn),設(shè)置該值感混,剛開
                        始視圖不見端幼,還不知道應(yīng)用在哪里。
 kCAFillModeBoth        kCAFillModeBoth 該值是 kCAFillModeForwards 和 kCAFillModeBackwards的組合狀態(tài)
 kCAFillModeRemoved     kCAFillModeRemoved 設(shè)置為該值弧满,動(dòng)畫將在設(shè)置的 beginTime 開始執(zhí)行(如沒有設(shè)置beginTime屬性婆跑,則動(dòng)畫立即執(zhí)行),動(dòng)
                        畫執(zhí)行完成后將會(huì)layer的改變恢復(fù)原狀庭呜。
 */
/*
 kCAMediaTimingFunctionLinear           傳這個(gè)值滑进,在整個(gè)動(dòng)畫時(shí)間內(nèi)動(dòng)畫都是以一個(gè)相同的速度來改變。也就是勻速運(yùn)動(dòng)募谎。
 kCAMediaTimingFunctionEaseIn           使用該值扶关,動(dòng)畫開始時(shí)會(huì)較慢,之后動(dòng)畫會(huì)加速数冬。
 kCAMediaTimingFunctionEaseOut          使用該值节槐,動(dòng)畫在開始時(shí)會(huì)較快,之后動(dòng)畫速度減慢。
 kCAMediaTimingFunctionEaseInEaseOut    使用該值铜异,動(dòng)畫在開始和結(jié)束時(shí)速度較慢哥倔,中間時(shí)間段內(nèi)速度較快。
 kCAMediaTimingFunctionDefault

 */
//添加動(dòng)畫
[_demoView.layer addAnimation:animaiton forKey:@"Animation"];

}

//其實(shí)比較重要的是有多個(gè)動(dòng)畫的時(shí)候如何在代理方法中區(qū)分不同的動(dòng)畫
//方式一:
//如果我們添加動(dòng)畫的視圖是全局變量揍庄,可使用該方法咆蒿。
//添加動(dòng)畫時(shí),我們使用了

//動(dòng)畫開始時(shí)

  • (void)animationDidStart:(CAAnimation *)anim
    {
    if ([anim isEqual:[_demoView.layer animationForKey:@"Animation"]]) {
    NSLog(@"動(dòng)畫組執(zhí)行了");
    }
    }

//動(dòng)畫結(jié)束時(shí)

  • (void)animationDidStop:(CAAnimation *)anim finished:(BOOL)flag
    {
    //方法中的flag參數(shù)表明了動(dòng)畫是自然結(jié)束還是被打斷,比如調(diào)用了removeAnimationForKey:方法或removeAnimationForKey方法币绩,flag為NO蜡秽,如果是正常結(jié)束,flag為YES缆镣。
    NSLog(@"結(jié)束了");
    }

//方式二
//添加動(dòng)畫的視圖是局部變量時(shí)芽突,可使用該方法
//添加動(dòng)畫給動(dòng)畫設(shè)置key-value對
-(void)animationCustomDidStart{
// [positionAnima setValue:@"PositionAnima" forKey:@"AnimationKey"];
// [transformAnima setValue:@"TransformAnima" forKey:@"AnimationKey"];
}
//動(dòng)畫結(jié)束時(shí)
//- (void)animationDidStop:(CAAnimation *)anim finished:(BOOL)flag
//{
// if ([[anim valueForKey:@"AnimationKey"]isEqualToString:@"PositionAnima"]) {
// NSLog(@"位置移動(dòng)動(dòng)畫執(zhí)行結(jié)束");
// }
// else if ([[anim valueForKey:@"AnimationKey"]isEqualToString:@"TransformAnima"]){
// NSLog(@"旋轉(zhuǎn)動(dòng)畫執(zhí)行結(jié)束");
// }
//}

//y上下跳
-(void)starAnimationScale{
CABasicAnimation *positionAnima = [CABasicAnimation animationWithKeyPath:@"position.y"];
positionAnima.duration = 0.8;
positionAnima.fromValue = @(_demoView.center.y);
positionAnima.toValue = @(_demoView.center.y-30);
positionAnima.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseIn];
positionAnima.repeatCount = HUGE_VALF;
positionAnima.repeatDuration = 2;
positionAnima.removedOnCompletion = NO;
positionAnima.fillMode = kCAFillModeForwards;

[_demoView.layer addAnimation:positionAnima forKey:@"AnimationMoveY"];

}

//centery 中心點(diǎn)旋轉(zhuǎn)
-(void)starAnimationScale1{
CABasicAnimation *positionAnima = [CABasicAnimation animationWithKeyPath:@"position.y"];
positionAnima.fromValue = @(_demoView.center.y);
positionAnima.toValue = @(_demoView.center.y-30);
positionAnima.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseIn];

CABasicAnimation *transformAnima = [CABasicAnimation animationWithKeyPath:@"transform.rotation.y"];
transformAnima.fromValue = @(0);
transformAnima.toValue = @(M_PI);
transformAnima.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut];

CAAnimationGroup *animaGroup = [CAAnimationGroup animation];
animaGroup.duration = 2.0f;
animaGroup.fillMode = kCAFillModeForwards;
animaGroup.removedOnCompletion = NO;
animaGroup.animations = @[positionAnima,transformAnima];

[_demoView.layer addAnimation:animaGroup forKey:@"Animation"];

}

pragma mark - 我的旋轉(zhuǎn) 順時(shí)針

-(void)startAnimation{
CABasicAnimation* rotationAnimation = [CABasicAnimation animationWithKeyPath:@"transform.rotation.z"];
rotationAnimation.toValue = [NSNumber numberWithFloat: M_PI * 2.0 ];
rotationAnimation.duration = 5.0;
rotationAnimation.cumulative = YES;
rotationAnimation.repeatCount = 1000;
[_demoView.layer addAnimation:rotationAnimation forKey:@"rotationAnimation"];
}

-(void)opacity{
// CABasicAnimation *animation = [self opacityForever_Animation:3.0];
CABasicAnimation *animation = [self scale:[NSNumber numberWithInt:1] orgin:[NSNumber numberWithInt:1] durTimes:3.3 Rep:3];
[_demoView.layer addAnimation:animation forKey:nil];
}

pragma mark =====縮放-=============

-(CABasicAnimation *)scale:(NSNumber *)Multiple orgin:(NSNumber *)orginMultiple durTimes:(float)time Rep:(float)repertTimes
{
CABasicAnimation *animation = [CABasicAnimation animationWithKeyPath:@"transform.scale"];
animation.fromValue = Multiple;
animation.toValue = orginMultiple;
animation.autoreverses = YES;
animation.repeatCount = repertTimes;
animation.duration = time;//不設(shè)置時(shí)候的話,有一個(gè)默認(rèn)的縮放時(shí)間.
animation.removedOnCompletion = NO;
animation.fillMode = kCAFillModeForwards;
return animation;
}

pragma mark ====旋轉(zhuǎn)動(dòng)畫======

-(CABasicAnimation *)rotation:(float)dur degree:(float)degree direction:(int)direction repeatCount:(int)repeatCount
{
//第一個(gè)參數(shù)是旋轉(zhuǎn)角度董瞻,后面三個(gè)參數(shù)形成一個(gè)圍繞其旋轉(zhuǎn)的向量寞蚌,起點(diǎn)位置由UIView的center屬性標(biāo)識(shí)。
CATransform3D rotationTransform = CATransform3DMakeRotation(degree, 0, 0, direction);
CABasicAnimation *animation = [CABasicAnimation animationWithKeyPath:@"transform"];
animation.toValue = [NSValue valueWithCATransform3D:rotationTransform];
animation.duration = dur;
animation.autoreverses = NO;
animation.cumulative = NO;
animation.fillMode = kCAFillModeForwards;
animation.repeatCount = repeatCount;
return animation;

}

pragma mark === 永久閃爍的動(dòng)畫 ======

-(CABasicAnimation *)opacityForever_Animation:(float)time
{
CABasicAnimation *animation = [CABasicAnimation animationWithKeyPath:@"opacity"];//必須寫opacity才行钠糊。
animation.fromValue = [NSNumber numberWithFloat:1.0f];
animation.toValue = [NSNumber numberWithFloat:0.0f];//這是透明度挟秤。
animation.autoreverses = YES;
animation.duration = time;
animation.repeatCount = MAXFLOAT;
animation.removedOnCompletion = NO;
animation.fillMode = kCAFillModeForwards;
animation.timingFunction=[CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseIn];///沒有的話是均勻的動(dòng)畫。
return animation;
}

/**

  • CABasicAnimation test
    */
  • (void)demoViewBasicAnimation
    {
    CABasicAnimation *animation = [CABasicAnimation animationWithKeyPath:@"position"];

    animation.fromValue = [NSValue valueWithCGPoint:CGPointMake(_demoView.center.x, _demoView.center.y)]; //可以省略...
    animation.toValue = [NSValue valueWithCGPoint:CGPointMake(270, 410)];
    animation.duration = 3.0f;
    animation.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut]; //動(dòng)畫速度設(shè)置
    animation.fillMode = kCAFillModeForwards;
    animation.removedOnCompletion = NO;

    [_demoView.layer addAnimation:animation forKey:nil];
    }

/**

  • CAKeyframeAnimation test
    */
  • (void)demoViewKeyframeAnimation
    {
    _demoView.layer.anchorPoint = CGPointMake(0.5, 0.0);
    CAKeyframeAnimation *animaiton = [CAKeyframeAnimation animationWithKeyPath:@"transform.rotation"];

    NSArray *rotationVelues = @[@(M_PI_4), @(-M_PI_4), @(M_PI_4)];
    animaiton.values = rotationVelues;
    animaiton.duration = 3.0f;
    animaiton.repeatCount = HUGE_VALF; // #define HUGE_VALF 1e50f

    [_demoView.layer addAnimation:animaiton forKey:nil];
    }

/**

  • The animation used Bezierpath
    */
  • (void)demoViewBezierPathAnimation
    {
    UIBezierPath *path = [UIBezierPath bezierPath];
    [path moveToPoint:_demoView.center]; //一定要設(shè)置 不然底層的CGPath找不到起始點(diǎn)抄伍,將會(huì)崩潰
    [path addCurveToPoint:CGPointMake(270, 410) controlPoint1:CGPointMake(0, 460) controlPoint2:CGPointMake(320, 0)]; //以左下角和右上角為控制點(diǎn)

    CAKeyframeAnimation *animation = [CAKeyframeAnimation animationWithKeyPath:@"position"];
    animation.path = path.CGPath;
    animation.duration = 3.0f;
    animation.removedOnCompletion = NO;
    animation.fillMode = kCAFillModeForwards;

    [_demoView.layer addAnimation:animation forKey:nil];
    }

@end

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末艘刚,一起剝皮案震驚了整個(gè)濱河市,隨后出現(xiàn)的幾起案子截珍,更是在濱河造成了極大的恐慌攀甚,老刑警劉巖,帶你破解...
    沈念sama閱讀 206,311評論 6 481
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件岗喉,死亡現(xiàn)場離奇詭異秋度,居然都是意外死亡,警方通過查閱死者的電腦和手機(jī)钱床,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 88,339評論 2 382
  • 文/潘曉璐 我一進(jìn)店門荚斯,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人查牌,你說我怎么就攤上這事事期。” “怎么了纸颜?”我有些...
    開封第一講書人閱讀 152,671評論 0 342
  • 文/不壞的土叔 我叫張陵兽泣,是天一觀的道長。 經(jīng)常有香客問我懂衩,道長撞叨,這世上最難降的妖魔是什么金踪? 我笑而不...
    開封第一講書人閱讀 55,252評論 1 279
  • 正文 為了忘掉前任,我火速辦了婚禮牵敷,結(jié)果婚禮上胡岔,老公的妹妹穿的比我還像新娘。我一直安慰自己枷餐,他們只是感情好靶瘸,可當(dāng)我...
    茶點(diǎn)故事閱讀 64,253評論 5 371
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著毛肋,像睡著了一般怨咪。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上润匙,一...
    開封第一講書人閱讀 49,031評論 1 285
  • 那天诗眨,我揣著相機(jī)與錄音,去河邊找鬼孕讳。 笑死匠楚,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的厂财。 我是一名探鬼主播芋簿,決...
    沈念sama閱讀 38,340評論 3 399
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼璃饱!你這毒婦竟也來了与斤?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 36,973評論 0 259
  • 序言:老撾萬榮一對情侶失蹤荚恶,失蹤者是張志新(化名)和其女友劉穎撩穿,沒想到半個(gè)月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體裆甩,經(jīng)...
    沈念sama閱讀 43,466評論 1 300
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡冗锁,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 35,937評論 2 323
  • 正文 我和宋清朗相戀三年齐唆,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了嗤栓。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片。...
    茶點(diǎn)故事閱讀 38,039評論 1 333
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡箍邮,死狀恐怖茉帅,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情锭弊,我是刑警寧澤堪澎,帶...
    沈念sama閱讀 33,701評論 4 323
  • 正文 年R本政府宣布,位于F島的核電站味滞,受9級特大地震影響樱蛤,放射性物質(zhì)發(fā)生泄漏钮呀。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 39,254評論 3 307
  • 文/蒙蒙 一昨凡、第九天 我趴在偏房一處隱蔽的房頂上張望爽醋。 院中可真熱鬧,春花似錦便脊、人聲如沸蚂四。這莊子的主人今日做“春日...
    開封第一講書人閱讀 30,259評論 0 19
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽遂赠。三九已至,卻和暖如春晌杰,著一層夾襖步出監(jiān)牢的瞬間跷睦,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 31,485評論 1 262
  • 我被黑心中介騙來泰國打工肋演, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留送讲,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 45,497評論 2 354
  • 正文 我出身青樓惋啃,卻偏偏與公主長得像哼鬓,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個(gè)殘疾皇子边灭,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 42,786評論 2 345

推薦閱讀更多精彩內(nèi)容