1. 概述
在Core Animation库中还有一个比较有意思的图层,那就是CAEmitterLayer,它是一个高性能的粒子引擎,被用来创建实时粒子动画,比如烟雾、火、雨等这样的效果。
看一下CAEmitterLayer的官方定义:
A layer that emits, animates, and renders a particle system.
一个释放、动画和渲染粒子系统的层。
class CAEmitterLayer : CALayer
CAEmitterLayer只是一个发射容器,而真正的粒子则是CAEmitterCell,CAEmitterCell定义了粒子的一些属性,比如显示内容,大小,速度,方向等等,一个粒子对象还可以再包含CAEmitterCell,也就是说一个粒子还可以再发射粒子。这有点像UITableView和UITableViewCell的关系,UITableView包含UITableViewCell,而UITableViewCell中还可以再嵌套UITableViewCell。
在看一下CAEmitterCell的官方定义:
The definition of a particle emitted by a CAEmitterLayer.
由CAEmitterLayer发射的粒子的定义。
class CAEmitterCell : NSObject
话不多说,先看一个效果:
有个初步了解之后,下面来了解一下CAEmitterLayer和CAEmitterCell的一些常用属性吧。
2. CAEmitterLayer常用属性
属性 | 类型 | 说明 |
---|---|---|
emitterCells | [CAEmitterCell]? | 添加到粒子图层中的粒子cell。 |
renderMode | CAEmitterLayerRenderMode | 决定粒子cell如何渲染到图层中,默认是unordered。 unordered:粒子是无序出现的,多个发射源将混合。 oldestFirst:生命久的粒子会被渲染在最上层。 oldestLast:刚开始的粒子会被渲染在最上层。 backToFront:刚开始的粒子会被渲染在最上层。 additive:这种模式会进行粒子混合。 |
emitterPosition | CGPoint | 粒子发射体中心的位置。 |
emitterShape | CAEmitterLayerEmitterShape | 指定发射源形状,也就是表示粒子从什么形状发射出来。默认是point。 point:点形状,发射源就是一个点,该点坐标为( line:直线形状,发射源就是一条直线,从点( rectangle:矩形形状,发射源就是一个矩形,[emitterPosition.x - emitterSize.width/2, emitterPosition.y - emitterSize.height/2, emitterZPosition], [emitterPosition.x + emitterSize.width/2, emitterPosition.y + emitterSize.height/2, emitterZPosition]. cuboid:立体矩形形状(3D),发射源是一个立体矩形,需要设置z方向的数据,如果不设置,如同rectangle,[emitterPosition.x - emitterSize.width/2, emitterPosition.y - emitterSize.height/2, emitterZPosition - emitterDepth/2], [emitterPosition.x + emitterSize.width/2, emitterPosition.y + emitterSize.height/2, emitterZPosition+emitterDepth/2]. circle:圆形,发射源是一个圆形,圆心( sphere:立体圆形(3D),需要设置z方向的数据,否则同circle,圆心( |
emitterZPosition | CGFloat | 发射源中心沿z轴的距离。 |
emitterDepth | CGFloat | 发射源形状的深度。 |
emitterSize | CGSize | 发射源的尺寸。 |
birthRate | Float | 粒子出生率系数,默认为1.0。每个粒子cell的birthRate乘以这个系数得到每秒生产粒子的个数,即每秒生产粒子数=Layer.birthRath * Cell.birthRate. |
lifetime | Float | 粒子生命周期系数,默认为1.0。计算方式如同上。如果设置为0,那么发射源停止发射粒子,粒子的声明周期为0,屏幕不在渲染了。 |
scale | Float | 粒子缩放比例系数,默认为1.0。计算方式同上。 |
seed | UInt32 | 指定用于初始化随机数生成器的种子。 |
spin | Float | 粒子自旋系数,默认为1.0。计算方式同上。 |
velocity | Float | 粒子速度系数,默认为1.0。计算方式同上。 |
emitterMode | CAEmitterLayerEmitterMode | 即发射模式,进一步决定发射的区域是在发射源形状的哪一部分。默认是volume points:粒子从粒子发射源上的点发射出来。 outline:粒子从粒子发射源的轮廓发射。 surface:粒子从粒子发射源的表面发射出去。 volume:粒子从粒子发射源内的某个位置发射出来。 |
preservesDepth | Bool | 是否开启三维空间效果。默认值false。 |
注:上表中红色的属性,发射过程中改变其值,只会影响后续再发射出来的粒子,不会影响已经发射出去的粒子。
3. CAEmitterCell常用属性
属性 | 类型 | 说明 |
---|---|---|
name | String? | 粒子cell的名字,唯一值。 |
contents | Any? | 显示内容。 |
contentsRect | CGRect | 一个矩形(在单位坐标空间中),指定Layer应该绘制的内容部分,即发射的渲染粒子内容的渲染范围。 |
emitterCells | [CAEmitterCell]? | 添加到粒子cell中的粒子cell。 |
isEnabled | Bool | 该粒子是否被渲染,默认值true。 |
color | CGColor? | 粒子的颜色,默认为不透明的白色。 |
redRange | Float | 粒子的红色成分可以变化的数量,默认值为0.0。 |
greenRange | Float | 粒子的绿色成分可以变化的数量,默认值为0.0。 |
blueRange | Float | 粒子的蓝色成分可以变化的数量,默认值为0.0。 |
alphaRange | Float | 粒子的alpha成分可以变化的数量,默认值为0.0。 |
redSpeed | Float | 红色成分在粒子生命周期内的变化速度(以秒为单位)。 |
greenSpeed | Float | 绿色成分在细胞生命周期内的变化速度(以秒为单位)。 |
blueSpeed | Float | 蓝色成分在细胞生命周期内的变化速度(以秒为单位)。 |
alphaSpeed | Float | alpha成分在细胞生命周期内的变化速度(以秒为单位)。 |
scale: CGFloat | CGFloat | 粒子cell的放缩系数,默认为1.0。 |
scaleRange | CGFloat | 粒子cell的放缩系数变化范围,默认值0.0。 |
contentsScale | CGFloat | 粒子cell内容的放缩系数。 |
spin | CGFloat | 粒子cell的旋转速度,以弧度/秒为单位。 |
spinRange | CGFloat | 粒子cell在其生命周期内的自旋变化量,默认值0.0。 |
emissionLatitude | CGFloat | 发射角的纬度方向。纬度角代表了在x-z轴平面坐标系中与x轴之间的夹角,也就是粒子在xz平面的发射角度,默认0。 |
emissionLongitude | CGFloat | 发射角的经度方向。经度角代表了在x-y轴平面坐标系中与x轴之间的夹角,也就是粒子在xy平面的发射角度,默认0,即沿着x轴向右飞行。顺时针方向是正向,例如emissionLongtitude为0 ,如果想沿着y轴向下飞行,那么设置为PI/2即即90度,如果粒子沿着y轴向上飞行,则可设置为 3*PI/2也可设置为 -PI/2。 |
emissionRange | CGFloat | 发射粒子角度范围,默认0,以锥形分布开的发射角度。角度用弧度制。粒子均匀分布在这个锥形范围内。 |
lifetime | Float | 粒子cell的生命周期,以秒计算。 |
lifetimeRange | Float | 粒子cell的生命周期变化范围。比如lifetime为10秒,lifttimeRange是3秒,那么cell的实际生命周期范围是7到13秒。 |
birthRate | Float | 每秒产生粒子对象的数量。 |
scaleSpeed | CGFloat | 粒子cell的生命周期内,scale每秒的变化速率,默认值0.0。 |
velocity | CGFloat | 粒子cell的初始速度。 |
velocityRange | CGFloat | 粒子cell的速度变化范围。 |
xAcceleration | CGFloat | x轴方向的加速度,默认值为0.0。 |
yAcceleration | CGFloat | y轴方向的加速度,默认值为0.0。 |
zAcceleration | CGFloat | z轴方向的加速度,默认值为0.0。 |
4. Demo示例
上面解释了那么多的属性,估计看起来有些蒙蒙的,现在挑一些主要的属性做个下雪的demo,看看效果就大概明白了。
func makeSnow() {
// 创建一个粒子图层
let emitterLayer = CAEmitterLayer()
// 设置粒子图层的发射模式为沿边框发射
emitterLayer.emitterMode = .outline
// 设置粒子图层发射源尺寸
emitterLayer.emitterSize = self.view.layer.bounds.size
// 设置粒子发射位置的中心点
emitterLayer.emitterPosition = CGPoint(x: self.view.layer.bounds.size.width / 2, y: 0)
// 设置发射源形状,此处设置为直线。
emitterLayer.emitterShape = .line
// 设置渲染模式,无序模式。
emitterLayer.renderMode = .unordered
// 添加到图层。
self.view.layer.addSublayer(emitterLayer)
// 创建粒子
let emitterCell = CAEmitterCell()
// 设置粒子名称
emitterCell.name = "snowCell"
// 设置粒子图片
emitterCell.contents = UIImage(named: "circle_white")?.cgImage
// 设置粒子生命周期,10秒后消失。
emitterCell.lifetime = 10.0
// 设置粒子声明周期变化范围,即实际生命周期为10-6至10+6,也就是4秒到16秒不等。
emitterCell.lifetimeRange = 6.0
// 设置粒子出生率,即每秒发射20个粒子。
emitterCell.birthRate = 20.0
// 设置粒子的初始速度为40.
emitterCell.velocity = 40.0
// 设置粒子的速度变化范围,即粒子的速度为30到50不等。
emitterCell.velocityRange = 10
// 设置粒子的放缩系数,在原基础上放缩到0.2倍。
emitterCell.scale = 0.2
// 设置粒子的放缩系数变化范围,即实际的放缩为0.1到0.3不等。
emitterCell.scaleRange = 0.1
// 设置粒子在y轴方向的加速度为15.
emitterCell.yAcceleration = 15.0
// 设置粒子在x轴方向的加速度为3.
emitterCell.xAcceleration = 3.0
// 设置粒子的发射方向。
emitterCell.emissionLongitude = CGFloat(Double.pi)
// 设置粒子发射方向的偏转范围。
emitterCell.emissionRange = CGFloat(Double.pi/4)
// 添加粒子。
emitterLayer.emitterCells = [emitterCell]
}
执行效果如下:
看完了这个下雪的demo,再看看文章开头那个彩色的粒子效果的代码吧。
func makePointEmitter() {
// 创建一个粒子图层
let emitterLayer = CAEmitterLayer()
// 设置粒子图层的发射模式为从一点发射出来。
emitterLayer.emitterMode = .points
// 设置粒子图层发射源尺寸
emitterLayer.emitterSize = self.view.layer.bounds.size
// 设置粒子发射位置的中心点
emitterLayer.emitterPosition = CGPoint(x: self.view.layer.bounds.size.width - 30, y: 30)
// 设置发射源形状,此处设置为点。
emitterLayer.emitterShape = .point
// 设置渲染模式,无序模式。
emitterLayer.renderMode = .unordered
// 添加到图层。
self.view.layer.addSublayer(emitterLayer)
// 创建粒子
let emitterCell = CAEmitterCell()
// 设置粒子名称
emitterCell.name = "snowCell"
// 设置粒子图片
emitterCell.contents = UIImage(named: "circle_white")?.cgImage
// 设置粒子生命周期,10秒后消失。
emitterCell.lifetime = 10.0
// 设置粒子出生率,即每秒发射20个粒子。
emitterCell.birthRate = 20.0
// 设置粒子的初始速度为40.
emitterCell.velocity = 40.0
// 设置粒子的速度变化范围.
emitterCell.velocityRange = 100
// 设置粒子的放缩系数,在原基础上放缩到0.2倍。
emitterCell.scale = 0.2
// 设置粒子的放缩系数变化范围,即实际的放缩为0.1到0.3不等。
emitterCell.scaleRange = 0.1
// 设置在生命周期内的放缩速度。
emitterCell.scaleSpeed = 0.02
// 设置粒子在y轴方向的加速度为15.
emitterCell.yAcceleration = 15.0
// 设置粒子在x轴方向的加速度为3.
emitterCell.xAcceleration = 3.0
// 设置粒子的发射方向。
emitterCell.emissionLongitude = CGFloat(Double.pi)
// 设置粒子发射方向的偏转范围。
emitterCell.emissionRange = CGFloat(Double.pi/4)
//颜色
emitterCell.color = UIColor(red: 0.5, green: 0.0, blue: 0.5, alpha: 1.0).cgColor
// 粒子颜色red,green,blue,alpha能改变的范围,默认0
emitterCell.redRange = 1.0
emitterCell.greenRange = 1.0
emitterCell.alphaRange = 0.8
// 粒子颜色red,green,blue,alpha在生命周期内的改变速度,默认都是0
emitterCell.blueSpeed = 1.0
emitterCell.alphaSpeed = -0.1
// 添加粒子。
emitterLayer.emitterCells = [emitterCell]
}
5. 总结
本文主要介绍了粒子图层CAEmitterLayer和粒子CAEmitterCell的属性概念,属性比较多,用起来可能需要好好理解一下,文中随后又附上了两个demo的代码,使用了一些常用的属性,显示出来的效果也比较简单。
本篇文章是粒子效果的一个入门级文章,只有理解了本篇文章,后续更多关于粒子的文章介绍才能更好的理解。
以上内容如果不正确的地方,还请路过的朋友指正,谢谢!
本篇文章出自https://blog.csdn.net/guoyongming925的博客,如需转载,请标明出处。