iOS核心动画 - CAEmitterLayer&CAEmitt

2020-02-21  本文已影响0人  ShIwEn9

通常我们的点赞效果,下emoji雨等效果都被称为粒子效果,通常我们都是通过CAEmitterLayer&CAEmitterCell相结合实现的。


上图是 CALayer 常用的一些子类,通过上图可以发现:CAEmitterLayer&CAEmitterCell是 CALyaer的子类,所以自然的遵循继承的相关准则。而我们知道CALayer的底层是对OpenGL的一层封装,暴露其接口而组成的一个簇,所以自然如果我们要是不用CAEmitterLayer来实现粒子效果自然就会很麻烦。

一、CAEmitterLayer&CAEmitterCell的相关介绍
  1. CAEmitterLayer&CAEmitterCell的关系:
    首先我们得知道,要实现粒子效果,单单的使用CAEmitterLayer或CAEmitterCell是实现不了的,只能两者搭配起来使用才可以。
    发射类:CAEmitterLayer
    发射的离子:CAEmitterCell
    CAEmitterLayer 是 CAEmitterCell 个数数组:
 @property(nullable, copy) NSArray<CAEmitterCell *> *emitterCells;
  1. CAEmitterLayer相关属性:
产生离子的速度(产生率)
 @property float birthRate;
 
 离子的生命周期 默认为1
 @property float lifetime;

 离子发射的中心点 默认为屏幕的中心
 @property CGPoint emitterPosition;
 离子的深度 z轴
 @property CGFloat emitterZPosition;

 离子发射的尺寸 —— 离子发射源的尺寸
 @property CGSize emitterSize;
 离子发射的深度
 @property CGFloat emitterDepth;

 离子发射的形状 默认点形状
 @property(copy) CAEmitterLayerEmitterShape emitterShape;

 离子发射的模式
 @property(copy) CAEmitterLayerEmitterMode emitterMode;

 离子渲染的模式
 @property(copy) CAEmitterLayerRenderMode renderMode;

 离子是否需要深度
 @property BOOL preservesDepth;

 离子的速度 默认1.0
 @property float velocity;

 离子的缩放比例 默认1.0
 @property float scale;

 离子的自旋
 @property float spin;

 随机的发射器
 @property unsigned int seed;

大部分的属性看着翻译过来的注释就可以理解;那就对少部分个人觉得需要着重理解记忆的进行解释:

这些形状可以在调试的时候修改来看看有什么不同,比如我们设置的红包效果,就是用的kCAEmitterLayerLine

redpacketLayer.emitterPosition = CGPointMake(100, 100);
redpacketLayer.emitterSize = CGSizeMake(20, 0);
redpacketLayer.emitterShape = kCAEmitterLayerLine;
达到的效果

birthRate: 粒子产生系数,默认1.0;
每个粒子cell的产生率乘以这个粒子产生系数,得出每一秒产生这个粒子的个数。 即:每秒粒子产生个数 = layer.birthRate * cell.birthRate ;
lifetime:粒子的生命周期系数,默认1.0。计算方式同上;
velocity:粒子速度系数, 默认1.0。计算方式同上;
scale:粒子的缩放比例系数, 默认1.0。计算方式同上;
spin:自旋转速度系数, 默认1.0。计算方式同上;

  1. CAEmitterCell 相关的属性和方法:
+ (instancetype)emitterCell;

 + (nullable id)defaultValueForKey:(NSString *)key;
 - (BOOL)shouldArchiveValueForKey:(NSString *)key;

 @property(nullable, copy) NSString *name;

 @property(getter=isEnabled) BOOL enabled;

 @property float birthRate;

 生命周期
 @property float lifetime;
 生命周期的范围
 @property float lifetimeRange;

 x轴和z轴 平面之间的夹角
 @property CGFloat emissionLatitude;
 x轴和y轴 平面之间的夹角
 @property CGFloat emissionLongitude;
 发射的角度
 @property CGFloat emissionRange;

 离子发射的速度
 @property CGFloat velocity;
 离子发射的速度的范围
 @property CGFloat velocityRange;

 加速度
 @property CGFloat xAcceleration;
 @property CGFloat yAcceleration;
 @property CGFloat zAcceleration;

 缩放比例
 @property CGFloat scale;
 @property CGFloat scaleRange;
 @property CGFloat scaleSpeed;

 自旋
 @property CGFloat spin;
 @property CGFloat spinRange;

 颜色
 @property(nullable) CGColorRef color;

 颜色范围
 @property float redRange;
 @property float greenRange;
 @property float blueRange;
 @property float alphaRange;

 颜色变换速度
 @property float redSpeed;
 @property float greenSpeed;
 @property float blueSpeed;
 @property float alphaSpeed;redc/gfdsa 

 内容
 @property(nullable, strong) id contents;

 内容的大小
 @property CGRect contentsRect;
 内容的缩放比例
 @property CGFloat contentsScale;

 纹理
 @property(copy) NSString *minificationFilter;
 @property(copy) NSString *magnificationFilter;
 @property float minificationFilterBias;

 嵌套的离子
 @property(nullable, copy) NSArray<CAEmitterCell *> *emitterCells;
 
 @property(nullable, copy) NSDictionary *style;

AEmitterLayer就是粒子的工厂,但是要实现效果就必须需要CAEmitterCell的帮助

在CAEmitterCell属性中,可以发现很多的属性都是一个 range 值:

snowCell.lifetime = 20.f;  // 粒子的生命周期
    snowCell.color = [[UIColor colorWithRed:0.f green:1.f blue:1.f alpha:1.f]CGColor];
    snowCell.redSpeed = 0.2;

这里设置了粒子颜色的RGBA,以及redSpeed,其他的没设置默认为0。粒子的生命周期(lifetime)为20秒,那么这个粒子从产生到消失的时间就是20秒。它的Red值为0,redSpeed为0.2,那么在粒子的这个生命周期内,粒子的每秒钟的Rde值就会增加0.2 * 255,表现在外观上的状态就是粒子颜色在不断变化,接近白色。最后粒子生命周期结束的时候,粒子的color正好是RGBA(1,1,1,1)。当然个变化的速度也可以负数,计算方式相同。比如要设置烟花的效果,那么要让在爆炸的过程中颜色变化,就是通过这样的设置达到的效果。

ios核心动画 - CAEmitterLayer&CAEmitterCell粒子效果的大致介绍就是这些,欢迎补充和批评

参考文章:【iOS】CALayer之CAEmitterLayer粒子发射器的神奇效果

上一篇下一篇

猜你喜欢

热点阅读