1.使用到的类
1
2
3
4
5
|
CAKeyframeAnimation
// 核心动画-关键帧动画
CAEmitterLayer
// 粒子发射器(其实就是一个Layer,其父类是CALayer)
CAEmitterCell
// 粒子
PS:核心动画应该不用多说了;
CAEmitterLayer和CAEmitterCell,其实可以比喻成“炮”和“炮弹”,应该不难理解;
|
2.直接上部分关键代码 代码中会有详细的注释
2.1 .m中需要拥有的属性
1
2
|
/** weak类型 粒子发射器 */
@property (nonatomic, weak) CAEmitterLayer *emitterLayer;
|
2.2 initWithFrame:
方法中
1
2
3
4
5
6
7
8
|
- (instancetype)initWithFrame:(CGRect)frame {
self = [
super
initWithFrame:frame];
if
(self) {
// 配置粒子发射器方法
[self setupEmitter];
}
return
self;
}
|
2.3 setSelected:
方法中
1
2
3
4
5
|
- (void)setSelected:(BOOL)selected {
[
super
setSelected:selected];
// 开始关键帧动画
[self keyframeAnimation];
}
|
2.4 layoutSubviews
方法中
1
2
3
4
5
|
- (void)layoutSubviews{
[
super
layoutSubviews];
/// 设置粒子发射器的锚点
_emitterLayer.position = self.imageView.center;
}
|
2.5 setupEmitter
方法中( 配置粒子发射器方法 )
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
|
- (void)setup {
// 粒子使用CAEmitterCell初始化
CAEmitterCell *emitterCell = [CAEmitterCell emitterCell];
// 粒子的名字,在设置喷射个数的时候会用到
emitterCell.name = @
"emitterCell"
;
// 粒子的生命周期和生命周期范围
emitterCell.lifetime = 0.7;
emitterCell.lifetimeRange = 0.3;
// 粒子的发射速度和速度的范围
emitterCell.velocity = 30.00;
emitterCell.velocityRange = 4.00;
// 粒子的缩放比例和缩放比例的范围
emitterCell.scale = 0.1;
emitterCell.scaleRange = 0.02;
// 粒子透明度改变范围
emitterCell.alphaRange = 0.10;
// 粒子透明度在生命周期中改变的速度
emitterCell.alphaSpeed = -1.0;
// 设置粒子的图片
emitterCell.contents = (id)[UIImage imageNamed:@
"Sparkle3"
].CGImage;
/// 初始化粒子发射器
CAEmitterLayer *layer = [CAEmitterLayer layer];
// 粒子发射器的 名称
layer.name = @
"emitterLayer"
;
// 粒子发射器的 形状(可以想象成打仗时,你需要的使用的炮的形状)
layer.emitterShape = kCAEmitterLayerCircle;
// 粒子发射器 发射的模式
layer.emitterMode = kCAEmitterLayerOutline;
// 粒子发射器 中的粒子 (炮要使用的炮弹)
layer.emitterCells = @[emitterCell];
// 定义粒子细胞是如何被呈现到layer中的
layer.renderMode = kCAEmitterLayerOldestFirst;
// 不要修剪layer的边界
layer.masksToBounds = NO;
// z 轴的相对坐标 设置为-1 可以让粒子发射器layer在self.layer下面
layer.zPosition = -1;
// 添加layer
[self.layer addSublayer:layer];
_emitterLayer = layer;
}
|
ps:这里有一点需要详细解释一下,CAEmitterCell
的属性一般有两个参数:一个平均值和一个“Range”,比如:
1
2
3
|
// 粒子的生命周期和生命周期范围
emitterCell.lifetime = 0.7;
emitterCell.lifetimeRange = 0.3;
|
这里苹果的官方文档是这样解释的:
1
2
3
4
5
6
7
8
|
每一个Layer都有它自己的随机数发生器,粒子的属性大部分都被定义为一个平均值和一个范围值,
如粒子的速度,这个属性的值分布的区间为:[ M - R / 2,M + R / 2 ]。
然后 这个公式里面
M:均值(拿上面代码说就是 emitterCell.lifetime)
R:范围值(mitterCell.lifetimeRange)
然后我们就可根据公式算出上面我设置的粒子的生命周期的范围是[0.7-0.3/2 , 0.7+0.3/2]
|
2.6 keyframeAnimation
方法中 (开始关键帧动画)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
|
- (void)animation {
// 创建关键帧动画
CAKeyframeAnimation *animation = [CAKeyframeAnimation animationWithKeyPath:@
"transform.scale"
];
if
(self.selected) {
animation.values = @[@1.5 ,@0.8, @1.0,@1.2,@1.0];
animation.duration = 0.5;
// 粒子发射器 发射
[self startFire];
}
else
{
animation.values = @[@0.8, @1.0];
animation.duration = 0.4;
}
// 动画模式
animation.calculationMode = kCAAnimationCubic;
[self.imageView.layer addAnimation:animation forKey:@
"transform.scale"
];
}
|
这段代码没什么说的,应该很容易理解。
2.7 startFire
方法中 (开炮)
1
2
3
4
5
6
7
8
9
|
- (void)startFire{
// 每秒喷射的80个
[self.emitterLayer setValue:@1000 forKeyPath:@
"emitterCells.emitterCell.birthRate"
];
// 开始
self.emitterLayer.beginTime = CACurrentMediaTime();
// 执行停止
[self performSelector:@selector(stopFire) withObject:nil afterDelay:0.1];
}
|
2.8 stopFire
方法中 (停火)
1
2
3
4
|
- (void)stopFire {
//每秒喷射的个数0个 就意味着关闭了
[self.emitterLayer setValue:@0 forKeyPath:@
"emitterCells.emitterCell.birthRate"
];
}
|
最后放两张效果图
![1480643909543444.png 1501391-b4de12daf6de183c.png](http://cc.cocimg.com/api/uploads/20161202/1480643909543444.png)
![1480643913945363.png 1501391-97e15806177bb473.png](http://cc.cocimg.com/api/uploads/20161202/1480643913945363.png)