額...... 簡書居然沒有復制富文本的功能, 我在有道上記的筆記, 拷到這里就純文本了。。。
不過還好,后來花了些時間,重新使用markdown排了下版
先附上我參考的博客
http://www.cnblogs.com/kenshincui/p/3972100.html#overviewiOS開發(fā)系列--讓你的應用“動”起來 - KenshinCui - 博客園
上面寫得很詳細, 很多概念, 分析, 我只關心實現(xiàn)代碼, 因為我記性差, 只夠記代碼.
基礎動畫
//1.創(chuàng)建動畫并指定動畫屬性
CABasicAnimation *basicAnimation =
[CABasicAnimation animationWithKeyPath:@"transform.rotation.z"];
//@“transform.rotation.z” 以z軸旋轉(x, y類似)
//@“transform.rotation.z” 以z軸旋轉
//@“position” 移動動畫
// 2. 設置動畫屬性初始值, 結束值
// basicAnimation.fromValue=[NSNumber numberWithInt:M_PI_2];
basicAnimation.toValue = [NSNumber numberWithFloat:M_PI * 2];
//初始值一般不需要設置
//當是旋轉動畫時, toValue為結束時的角度
//當是移動動畫時, toValue為結束時的位置CGPoint
basicAnimation.toValue = [NSValue valueWithCGPoint:location];
// 設置其他動畫屬性
basicAnimation.duration = 5.0; // 動畫時間
// basicAnimation.autoreverses = true;//旋轉后再旋轉到原來的位置
// basicAnimation.repeatCount = HUGE_VALF; //設置重復次數(shù),HUGE_VALF可看做無窮大,起到循環(huán)動畫的效果
// 4. 添加動畫到圖層
[_layer addAnimation:basicAnimation forKey:@"KCBasicAnimation_Rotation"];
=========簡潔版, 需要用時, 直接過來copy, paste, 我不懂得
CABasicAnimation *basicAnimation =
[CABasicAnimation animationWithKeyPath:@"transform.rotation.z"];
basicAnimation.toValue = [NSNumber numberWithFloat:M_PI * 2];
basicAnimation.duration = 5.0;
basicAnimation.repeatCount = HUGE_VALF;
[_layer addAnimation:basicAnimation forKey:@"KCBasicAnimation_Rotation”];
關鍵幀動畫
// 1. 創(chuàng)建關鍵幀動畫并設置動畫屬性
CAKeyframeAnimation *keyframeAnimation =
[CAKeyframeAnimation animationWithKeyPath:@"position"];
#if 0
// 直線關鍵幀
// 2. 設置關鍵幀, 這里有4個關鍵幀
NSValue *key1 = [NSValue valueWithCGPoint:_layer.position]; // 關鍵幀動畫不能省略初始值
NSValue *key2 = [NSValue valueWithCGPoint:CGPointMake(250, 300)];
NSValue *key3 = [NSValue valueWithCGPoint:CGPointMake(200, 400)];
NSValue *key4 = [NSValue valueWithCGPoint:CGPointMake(300, 490)];
NSArray *values = @[key1, key2, key3, key4];
keyframeAnimation.values = values;
#else
// 貝塞爾曲線關鍵幀
// 2. 設置路徑, 繪制貝塞爾曲線
CGMutablePathRef path = CGPathCreateMutable();
CGPathMoveToPoint(path, NULL, 200, 200); // 起始點
CGPathAddCurveToPoint(path, NULL, 100, 300, 300, 500, 200, 600);
// CGPathAddCurveToPoint(path, NULL, 控制點1.x, 控制點1.y, 控制點2.x, 控制點2.y, 終點.x, 終點.y);
// 設置path屬性
keyframeAnimation.path = path;
CGPathRelease(path);
#endif
// 設置其他屬性
keyframeAnimation.duration = 4;
keyframeAnimation.beginTime = CACurrentMediaTime() + 1; // 設置延遲2秒執(zhí)行, 不設置這個屬性, 默認直接執(zhí)行
// 3. 添加動畫到圖層, 會自動執(zhí)行
[_layer addAnimation:keyframeAnimation forKey:@"GGKeyframeAnimation"];
=========簡潔版
CAKeyframeAnimation *keyframeAnimation =
[CAKeyframeAnimation animationWithKeyPath:@"position"];
#if 0
// 直線關鍵幀
NSValue *key1 = [NSValue valueWithCGPoint:_layer.position];
NSValue *key2 = [NSValue valueWithCGPoint:CGPointMake(250, 300)];
NSValue *key3 = [NSValue valueWithCGPoint:CGPointMake(200, 400)];
NSValue *key4 = [NSValue valueWithCGPoint:CGPointMake(300, 490)];
NSArray *values = @[key1, key2, key3, key4];
keyframeAnimation.values = values;
#else
// 貝塞爾曲線關鍵幀
CGMutablePathRef path = CGPathCreateMutable();
CGPathMoveToPoint(path, NULL, 200, 200);
CGPathAddCurveToPoint(path, NULL, 100, 300, 300, 500, 200, 600);
keyframeAnimation.path = path;
CGPathRelease(path);
#endif
keyframeAnimation.duration = 4;
keyframeAnimation.beginTime = CACurrentMediaTime() + 1;
[_layer addAnimation:keyframeAnimation forKey:@"GGKeyframeAnimation"];
動畫組
#pragma mark -----------基礎旋轉動畫-----------
- (CABasicAnimation *)rotationAnimation {
CABasicAnimation *basicAnimation =
[CABasicAnimation animationWithKeyPath:@"transform.rotation.z"];
NSNumber *toValue = [NSNumber numberWithDouble:M_PI*2/3];
basicAnimation.toValue = toValue;
basicAnimation.repeatCount = HUGE_VALF;
basicAnimation.removedOnCompletion = NO;
//[basicAnimation setValue:toValue forKey:@"GGBasicAnimationRotation_ToValue”]; // 這里保存終止狀態(tài)在后面會有用
return basicAnimation;
}
#pragma mark -----------關鍵幀移動動畫-----------
- (CAKeyframeAnimation *)translationAnimation {
CAKeyframeAnimation *keyframeAnimation =
[CAKeyframeAnimation animationWithKeyPath:@"position"];
CGPoint endPoint = CGPointMake(200, 600);
CGMutablePathRef path = CGPathCreateMutable();
CGPathMoveToPoint(path, NULL, _layer.position.x, _layer.position.y);
CGPathAddCurveToPoint(path, NULL, 100, 300, 300, 500, endPoint.x, endPoint.y);
keyframeAnimation.path = path;
CGPathRelease(path);
//[keyframeAnimation setValue:[NSValue valueWithCGPoint:endPoint] forKey:@"GGKeyframeAnimation_endPoint"];
return keyframeAnimation;
}
#pragma mark -----------動畫組-----------
// 1. 創(chuàng)建動畫組
CAAnimationGroup *animationGroup = [CAAnimationGroup animation];
// 2. 設置動畫組中的動畫和其他屬性
CABasicAnimation *baseAnimation = [self rotationAnimation]; // 創(chuàng)建單個動畫時, 只需要設置好初始值,結束值
CAKeyframeAnimation *keyframeAnimation = [self translationAnimation]; // 只需要設置好關鍵幀,或畫好運動路徑
// 可以在動畫組里添加多種動畫效果, 基本動畫或關鍵幀動畫都可以組合
animationGroup.animations = @[baseAnimation, keyframeAnimation];
// 其他設置可以統(tǒng)一使用animationGroup設置
animationGroup.duration = 2; // 設置動畫時間, 如果動畫組中動畫已經(jīng)設置過則動畫屬性不再生效
// animationGroup.beginTime = CACurrentMediaTime()+1;
// 3. 給圖層添加動畫
[_layer addAnimation:animationGroup forKey:nil];
動畫結束后, 狀態(tài)(位置, 旋轉角度)會復原
圖層動畫的本質(zhì)就是將圖層內(nèi)部的內(nèi)容轉化為位圖經(jīng)硬件操作形成一種動畫效果,其實圖層本身并沒有任何的變化。
解決辦法: 設置動畫的代理, 實現(xiàn) - (void)animationDidStop:(CAAnimation *)anim finished:(BOOL)flag
當動畫結束時, 把動畫的狀態(tài)設置為動畫停止時的狀態(tài)
CABasicAnimation, CAKeyframeAnimation, CAAnimationGroup 都可以設置代理, 實現(xiàn)代理方法
// e.g 對上述動畫組實現(xiàn)的動畫實現(xiàn)狀態(tài)修改
- (void)animationDidStop:(CAAnimation *)anim finished:(BOOL)flag {
CAAnimationGroup *animationGroup = (CAAnimationGroup *)anim;
CABasicAnimation *basicAnimation = animationGroup.animations[0];
CAKeyframeAnimation *keyframeAnimation = animationGroup.animations[1];
// 通過在前面設置的key名, 獲取到停止狀態(tài)的值
NSNumber *toValue = [basicAnimation valueForKey:@"GGBasicAnimationRotation_ToValue"];
CGPoint endPoint = [[keyframeAnimation valueForKey:@"GGKeyframeAnimation_endPoint"] CGPointValue];
[CATransaction begin];
[CATransaction setDisableActions:YES];
// 設置視圖的屬性為停止狀態(tài)的值
_layer.position = endPoint;
_layer.transform = CATransform3DMakeRotation([toValue doubleValue], 0, 0, 1);
[CATransaction commit];
}
// 由于圖層具有動畫效果, 直接設置屬性, 會導致隱式動畫出現(xiàn), 為了取消隱式動畫, 需要將設置屬性的代碼寫在. . . .位置
[CATransaction begin];
[CATransaction setDisableActions:YES];
. . . . . .
[CATransaction commit];