關(guān)于 Core Animation
Core Animation是一組非常強(qiáng)大的動(dòng)畫處理API,使用它能做出很多優(yōu)雅的動(dòng)畫效果鸠珠。能用的動(dòng)畫類有4個(gè)子類:CABasicAnimation、CAKeyframeAnimation秋麸、CATransition渐排、CAAnimationGroup
開(kāi)發(fā)步驟:
- 初始化一個(gè)動(dòng)畫對(duì)象(CAAnimation)并設(shè)置一些動(dòng)畫相關(guān)屬性.
- 添加動(dòng)畫對(duì)象到層(CALayer)中,開(kāi)始執(zhí)行動(dòng)畫.
CALayer中很多屬性都可以通過(guò)CAAnimation實(shí)現(xiàn)動(dòng)畫效果, 包括opacity, position, transform, bounds, contents等,具體可以在API文檔中查找
通過(guò)調(diào)用CALayer的addAnimation:forKey:增加動(dòng)畫到層(CALayer)中,這樣就能觸發(fā)動(dòng)畫了.通過(guò)調(diào)用removeAnimationForKey:可以停止層中的動(dòng)畫.
注:Core Animation的動(dòng)畫執(zhí)行過(guò)程都是在后臺(tái)操作的,不會(huì)阻塞主線程.
創(chuàng)建動(dòng)畫時(shí)你可能用到的屬性
屬性 | 解讀
----|------|----
Autoreverses | 設(shè)定這個(gè)屬性為 YES 時(shí),在它到達(dá)目的地之后,動(dòng)畫的返回到開(kāi)始的值,代替了直接跳轉(zhuǎn)到開(kāi)始的值灸蟆,過(guò)渡平滑
Duration |設(shè)定開(kāi)始值到結(jié)束值花費(fèi)的時(shí)間驯耻。期間會(huì)被速度的屬性所影響
RemovedOnCompletion | 這個(gè)屬性默認(rèn)為 YES,在指定的時(shí)間段完成后,動(dòng)畫就自動(dòng)的從層上移除了。
FillMode | 這個(gè)屬性一般和 RemovedOnCompletion 配合使用,保持動(dòng)畫狀態(tài)可缚。其中kCAFillModeForwards 當(dāng)動(dòng)畫結(jié)束后,layer會(huì)一直保持著動(dòng)畫最后的狀態(tài).此時(shí)將RemovedOnCompletion設(shè)為NO
Speed | 默認(rèn)的值為 1.0.如果你改變這個(gè)值為 2.0,動(dòng)畫會(huì)用 2 倍的速度播放孽水。這樣的影響就是使持續(xù)時(shí)間減半。如果你指定的持續(xù)時(shí)間為 6 秒,速度為 2.0,動(dòng)畫就會(huì)播放 3 秒鐘即一半的持續(xù)時(shí)間城看。
RepeatCount | 默認(rèn)的是 0,動(dòng)畫只會(huì)播放一次。如果指定一個(gè)無(wú)限大的重復(fù)次數(shù),使用 MAXFLOAT 杏慰。這個(gè)不應(yīng)該和 repeatDration 屬性一塊使用
RepeatDuration | 這個(gè)屬性指定了動(dòng)畫應(yīng)該被重復(fù)多久测柠。動(dòng)畫會(huì)一直重復(fù),直到設(shè)定的時(shí)間用完。同上它不應(yīng)該和 repeatCount 一起使用
FromValue | 設(shè)置動(dòng)畫的初始值
ToValue | 設(shè)置動(dòng)畫的到達(dá)值
TimingFunction | 控制動(dòng)畫運(yùn)行的節(jié)奏. kCAMediaTimingFunctionLinear(線性):勻速缘滥,給你一個(gè)相對(duì)靜態(tài)的感覺(jué) kCAMediaTimingFunctionEaseIn(漸進(jìn)):動(dòng)畫緩慢進(jìn)入轰胁,然后加速離開(kāi) kCAMediaTimingFunctionEaseOut(漸出):動(dòng)畫全速進(jìn)入,然后減速的到達(dá)目的地 kCAMediaTimingFunctionEaseInEaseOut(漸進(jìn)漸出):動(dòng)畫緩慢的進(jìn)入朝扼,中間加速赃阀,然后減速的到達(dá)目的地。這個(gè)是默認(rèn)的動(dòng)畫行為擎颖。
BeginTime | 可以用來(lái)設(shè)置動(dòng)畫延遲執(zhí)行時(shí)間榛斯,若想延遲1s,就設(shè)置為CACurrentMediaTime()+1搂捧,CACurrentMediaTime()為圖層的當(dāng)前時(shí)間
巧妙的運(yùn)用這些可以屬性實(shí)現(xiàn)很棒的動(dòng)畫效果驮俗,比如下面:用CABasicAnimation實(shí)現(xiàn)的動(dòng)畫
CABasicAnimation動(dòng)畫
簡(jiǎn)單的呼吸和搖擺動(dòng)畫
簡(jiǎn)單的代碼
1.呼吸動(dòng)畫
CABasicAnimation *animation =[CABasicAnimation animationWithKeyPath:@"opacity"];
animation.fromValue = [NSNumber numberWithFloat:1.0f];
animation.toValue = [NSNumber numberWithFloat:0.0f];
animation.autoreverses = YES; //回退動(dòng)畫(動(dòng)畫可逆,即循環(huán))
animation.duration = 1.0f;
animation.repeatCount = MAXFLOAT;
animation.removedOnCompletion = NO;
animation.fillMode = kCAFillModeForwards;//removedOnCompletion,fillMode配合使用保持動(dòng)畫完成效果
animation.timingFunction=[CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseIn];
[self.alphaTagButton.layer addAnimation:animation forKey:@"aAlpha"];
2.搖擺動(dòng)畫
//設(shè)置旋轉(zhuǎn)原點(diǎn)
self.sharkTagButton.layer.anchorPoint = CGPointMake(0.5, 0);
CABasicAnimation* rotationAnimation = [CABasicAnimation animationWithKeyPath:@"transform.rotation.z"];
//角度轉(zhuǎn)弧度(這里用1允跑,-1簡(jiǎn)單處理一下)
rotationAnimation.toValue = [NSNumber numberWithFloat:1];
rotationAnimation.fromValue = [NSNumber numberWithFloat:-1];
rotationAnimation.duration = 1.0f;
rotationAnimation.repeatCount = MAXFLOAT;
rotationAnimation.removedOnCompletion = NO;
rotationAnimation.autoreverses = YES;
rotationAnimation.timingFunction = [CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut];
rotationAnimation.fillMode = kCAFillModeForwards;
[self.sharkTagButton.layer addAnimation:rotationAnimation forKey:@"revItUpAnimation"];
陀螺儀&加速儀的動(dòng)畫
ps:好吧 這個(gè)屬于亂入王凑,和上面的搖擺動(dòng)畫差不多的效果,只是這個(gè)是手動(dòng)的 哈哈
3聋丝、陀螺儀&加速儀的動(dòng)畫
self.motionManager = [[CMMotionManager alloc] init];
self.motionManager.deviceMotionUpdateInterval = 1.0f/100.0f; //1秒100次
self.sharkTagButton.layer.anchorPoint = CGPointMake(0.5, 0);
[self.motionManager startDeviceMotionUpdatesToQueue:[NSOperationQueue currentQueue] withHandler:^(CMDeviceMotion *motion, NSError *error) {
if(fabs(motion.attitude.roll)<1.0f)
{
[UIView animateWithDuration:0.6 animations:^{
self.sharkTagButton.layer.transform = CATransform3DMakeRotation(-(motion.attitude.roll), 0, 0, 1);
}];
}else if (fabs(motion.attitude.roll)<1.5f)
{
[UIView animateWithDuration:0.6 animations:^{
int s;
if (motion.attitude.roll>0)
{
s=-1;
}else
{
s = 1;
}
self.sharkTagButton.layer.transform = CATransform3DMakeRotation(s*M_PI_2, 0, 0, 1);
}];
}
if ((motion.attitude.pitch)<0)
{
[UIView animateWithDuration:0.6 animations:^{
self.sharkTagButton.layer.transform = CATransform3DMakeRotation(M_PI, 0, 0, 1);
}];
}
}];
Demo地址:
https://github.com/yongliangP/CABasicAnimationDemo
CATransition之簡(jiǎn)單的轉(zhuǎn)場(chǎng)動(dòng)畫
CAAnimation的子類索烹,用于做轉(zhuǎn)場(chǎng)動(dòng)畫,能夠?yàn)閷犹峁┮瞥銎聊缓鸵迫肫聊坏膭?dòng)畫效果弱睦。
屬性 | 解讀 |
---|---|
type | 動(dòng)畫過(guò)渡類型 |
subtype | 動(dòng)畫過(guò)渡方向 |
- 常用動(dòng)畫類型:
type的值 | 解讀 | 對(duì)應(yīng)常量 |
---|---|---|
fade | 淡入淡出 | kCATransitionFade |
push | 推擠 | kCATransitionPush |
reveal | 揭開(kāi) | kCATransitionReveal |
moveIn | 覆蓋 | kCATransitionMoveIn |
cube | 立方體 | 私有API |
suckEffect | 吮吸 | 私有API |
oglFlip | 翻轉(zhuǎn) | 私有API |
rippleEffect | 波紋 | 私有API |
pageCurl | 反翻頁(yè) | 私有API |
cameraIrisHollowOpen | 開(kāi)鏡頭 | 私有API |
cameraIrisHollowClose | 關(guān)鏡頭 | 私有API |
注:私有API只能通過(guò)字符串使用哈
- 過(guò)渡方向參數(shù):
subtype的值 | 解讀 |
---|---|
kCATransitionFromRight | 從右轉(zhuǎn)場(chǎng) |
kCATransitionFromLeft | 從左轉(zhuǎn)場(chǎng) |
kCATransitionFromBottom | 從下轉(zhuǎn)場(chǎng) |
kCATransitionFromTop | 從上轉(zhuǎn)場(chǎng) |
簡(jiǎn)單的CATransition動(dòng)畫
-(void)animationWithType:(NSString*)type
{
//- 創(chuàng)建一個(gè)轉(zhuǎn)場(chǎng)動(dòng)畫:
CATransition *transition = [CATransition animation];
transition.repeatCount = 5;
// - 確定動(dòng)畫類型:
transition.type = type;
// - 確定子類型(方向等)
transition.subtype = kCATransitionFromLeft;
// - 確定動(dòng)畫時(shí)間
transition.duration = 1;
// - 添加動(dòng)畫
[self.imageView.layer addAnimation:transition forKey:nil];
}
使用時(shí)只用傳你的想要的動(dòng)畫類型就好百姓,私有API只能通過(guò)字符串使用哈。
[self animationWithType:self.dataArray[indexPath.row]];
DEMO地址:https://github.com/yongliangP/CATransitionDemo
---20160908更新
CAKeyframeAnimation
先看圖每篷,就是那個(gè)在跑的小圓球瓣戚,為了方便,把動(dòng)畫集成在了一個(gè)Demo里了
- 1 .簡(jiǎn)單介紹
CAKeyframeAnimation是CApropertyAnimation的子類焦读,跟CABasicAnimation的區(qū)別是:CABasicAnimation只能從一個(gè)數(shù)值(fromValue)變到另一個(gè)數(shù)值(toValue)子库,而CAKeyframeAnimation會(huì)使用一個(gè)NSArray保存這些數(shù)值,是一種更靈活的動(dòng)畫方式矗晃。
- 2 .屬性介紹
屬性 | 解讀 |
---|---|
values | NSArray對(duì)象仑嗅,里面的元素稱為”關(guān)鍵幀”(keyframe)。動(dòng)畫對(duì)象會(huì)在指定的時(shí)間(duration)內(nèi),依次顯示values數(shù)組中的每一個(gè)關(guān)鍵幀 |
path | 可以設(shè)置一個(gè)CGPathRef\CGMutablePathRef,讓層跟著路徑移動(dòng)仓技。path只對(duì)CALayer的anchorPoint和position起作用鸵贬。如果你設(shè)置了path,那么values將被忽略 |
keyTimes | 可以為對(duì)應(yīng)的關(guān)鍵幀指定對(duì)應(yīng)的時(shí)間點(diǎn),其取值范圍為[0,1],keyTimes中的每一個(gè)時(shí)間值都對(duì)應(yīng)values中的每一幀.當(dāng)keyTimes沒(méi)有設(shè)置的時(shí)候,各個(gè)關(guān)鍵幀的時(shí)間是平分的 |
- 3 .實(shí)現(xiàn)
- 3.1 values方式實(shí)現(xiàn)
-(void)setUpCAKeyframeAnimationUseValues
{
CAKeyframeAnimation *animation = [CAKeyframeAnimation animation];
animation.keyPath = @"position";
NSValue *value1 = [NSValue valueWithCGPoint:CGPointMake(50, 50)];
NSValue *value2 = [NSValue valueWithCGPoint:CGPointMake(kWindowWidth - 50, 50)];
NSValue *value3 = [NSValue valueWithCGPoint:CGPointMake(kWindowWidth - 50, kWindowHeight-50)];
NSValue *value4 = [NSValue valueWithCGPoint:CGPointMake(50, kWindowHeight-50)];
NSValue *value5 = [NSValue valueWithCGPoint:CGPointMake(50, 50)];
animation.values = @[value1,value2,value3,value4,value5];
animation.repeatCount = MAXFLOAT;
animation.removedOnCompletion = NO;
animation.fillMode = kCAFillModeForwards;
animation.duration = 6.0f;
animation.timingFunction=[CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut];
[self.keyButton.layer addAnimation:animation forKey:@"values"];
}
- 3.2 path方式實(shí)現(xiàn)
-(void)setUpCAKeyframeAnimationUsePath
{
CAKeyframeAnimation *animation = [CAKeyframeAnimation animation];
animation.keyPath = @"position";
CGMutablePathRef path = CGPathCreateMutable();
//矩形線路
CGPathAddRect(path, NULL, CGRectMake(50,50, kWindowWidth - 100,kWindowHeight - 100));
animation.path=path;
CGPathRelease(path);
animation.repeatCount = MAXFLOAT;
animation.removedOnCompletion = NO;
animation.fillMode = kCAFillModeForwards;
animation.duration = 10.0f;
animation.timingFunction=[CAMediaTimingFunction functionWithName:kCAMediaTimingFunctionEaseInEaseOut];
[self.keyButton.layer addAnimation:animation forKey:@"path"];
}
- 3.3 keyTimes演示
-(void)setUpCAKeyframeAnimationUsekeyTimes
{
CAKeyframeAnimation *animation = [CAKeyframeAnimation animation];
// animation.keyPath = @"transform.translation.x";
animation.keyPath = @"position.x";
animation.values = @[@0, @20, @-20, @20, @0];
animation.keyTimes = @[ @0, @(1 / 6.0), @(3 / 6.0), @(5 / 6.0), @1 ];
animation.duration = 0.5;
animation.additive = YES;
[self.sharkTagButton.layer addAnimation:animation forKey:@"keyTimes"];
}
---20160921更新
CAAnimationGroup
看圖脖捻,就是那個(gè)下方的小長(zhǎng)方形阔逼,簡(jiǎn)單實(shí)現(xiàn)
動(dòng)畫組,顧名思義就是動(dòng)畫的組合地沮,具體動(dòng)畫可以參考上文嗜浮,不同的腦洞會(huì)出現(xiàn)不同的化學(xué)反應(yīng)。
簡(jiǎn)單示例:
CABasicAnimation * animationScale = [CABasicAnimation animation];
animationScale.keyPath = @"transform.scale";
animationScale.toValue = @(0.1);
CABasicAnimation *animationRota = [CABasicAnimation animation];
animationRota.keyPath = @"transform.rotation";
animationRota.toValue = @(M_PI_2);
CAAnimationGroup * group = [[CAAnimationGroup alloc] init];
group.duration = 3.0;
group.fillMode = kCAFillModeForwards;
group.removedOnCompletion = NO;
group.repeatCount = MAXFLOAT;
group.animations = @[animationScale,animationRota];
[self.groupButton.layer addAnimation:group forKey:nil];
附:關(guān)于keyPath你可能用到的屬性
屬性 | 解讀 |
---|---|
transform.rotation.x | 圍繞x軸翻轉(zhuǎn)摩疑。y,z同理 參數(shù):角度 |
transform.rotation | 默認(rèn)圍繞z軸 |
transform.scale.x | x方向縮放危融。y,z同理 |
transform.scale | 所有方向縮放 |
transform.translation.x | x軸方向移動(dòng),參數(shù):x軸上的坐標(biāo)。y,z同理 |
transform.translation | 移動(dòng)到的點(diǎn) |
zPosition | 平面的位置 |
opacity | 透明度 |
backgroundColor | 背景顏色 參數(shù):顏色 (id)[[UIColor redColor] CGColor] |
cornerRadius | layer圓角 |
borderWidth | 邊框?qū)挾?/td> |
bounds | 大小 參數(shù):CGRect |
contents | 內(nèi)容 參數(shù):CGImage |
contentsRect | 可視內(nèi)容 參數(shù):CGRect 值是0~1之間的小數(shù) |
position | 位置,效果和transform.rotation差不多 |
shadowColor | 陰影顏色 |
shadowOffset | 陰影偏移 |
shadowOpacity | 陰影透明度 |
shadowRadius | 陰影角度 |
照例放Demo
Demo地址:
https://github.com/yongliangP/CABasicAnimationDemo
如果你覺(jué)得對(duì)你有幫助請(qǐng)點(diǎn)喜歡哦雷袋,也可以關(guān)注我吉殃,每周至少一篇技術(shù)。
或者關(guān)注 我的專題 每周至少5篇更新楷怒,多謝支持哈蛋勺。
(ps:核心動(dòng)畫編程pdf中文版想要的可以私信我)