我们来实现这种下雪的粒子效果
要创建粒子发射器的动画,需要用到一个新的layer:CAEmitterLayer
在viewDidLoad中创建emitter对象
let rect = CGRect(x: 0.0, y: 100.0, width: view.bounds.width, height: 50.0)
let emitter = CAEmitterLayer()
emitter.frame = rect
view.layer.addSublayer(emitter)
设置发射器的形状:
emitter.emitterShape = kCAEmitterLayerRectangle
这里简单介绍其中三种发射器的形状
kCAEmitterLayerPoint:点形状的发射器将在同一个位置创建所有的粒子,例如火焰效果
kCAEmitterLayerLine:线形状的发射器将沿发射器frame的坐标顶部创建所有粒子,例如瀑布
kCAEmitterLayerRectangle:矩形发射器通过给定的矩形区域随机创建粒子。
设置发射器的坐标:
emitter.emitterPosition = CGPoint(x: rect.width/2, y: rect.height/2)//发射器位置居中
emitter.emitterSize = rect.size
创建emitter cell
emitter cell是粒子源的数据模型,一个emitter layer可以包含多个emitter cell,例如每粒爆米花可能有多种形态,有未爆开的、已爆开的,半爆开的等。
let emitterCell = CAEmitterCell()
emitterCell.contents = UIImage(named: "flake.png")?.cgImage
emitter cell将在不同的位置创建很多的副本
emitterCell.birthRate = 20
emitterCell.lifetime = 3.5
emitter.emitterCells = [emitterCell]
以上代码表示你将每秒创建20个粒子,并让它们在屏幕上停留3.5秒,所以你的屏幕上将显示70个粒子,然后旧的逐渐消失,新的逐渐创建。最后将cell添加到emitter,当你设置完emitterCells,粒子即开始创建。运行效果:
然而现在的粒子只是依次创建和消失,并没有下落的效果,现在我们来对其进行一些设置,来达到理想的效果。添加y方向上的加速度,粒子将会向下落,3.5秒之后消失:
emitterCell.yAcceleration = 70.0
运行效果
雪很少直线下落的,所以我们为粒子添加水平方向上的加速度
emitterCell.xAcceleration = 10.0
雪将沿着对角线方向下落。
现在我们来设置粒子发射的初速度和发射角度,velocity表示初速度,emissionLongtitude表示x-y平面的发射角度,.pi * - 0.5表示方向逆时针旋转90度,即粒子延y轴发射;emissionLatitude表示z轴方向的角度。
emitterCell.velocity = 20.0
emitterCell.emissionLongitude = .pi * -0.5
运行效果
现在的所有粒子看起来效果都是一样的,有点太单调了,我们来为粒子添加随机初始速度:
emitterCell.velocityRange = 200.0
因为我们前面设置了velocity为20,设置velocityRange之后,粒子的初始速度将在(20-200)=-180和(20+200)=220之间随机选择,初速度为负值的粒子将不会有发射效果,一旦出现在屏幕上,将直接开始飘落。
我们来为粒子添加随机的发射方向:
emitterCell.emissionRange = .pi * 0.5
最初我们设置了粒子的发射方向为-π/2,设置emissionRange之后,粒子的初始方向将在(-π/2+π/2)=0到(-π/2-π/2)=-π之间随机选择,即粒子将以不同的角度向x轴上方发射,不再是直接向正上方发射。
运行效果
我们还可以为粒子设置tint Color
emitterCell.color = UIColor(red: 0.9, green: 1.0, blue: 1.0, alpha: 1.0).cgColor
现在所有的粒子都是淡蓝色效果,我们来为每个粒子设置不同的颜色值,因为所有的颜色都是由红绿蓝三原色组成,我们可以为粒子分别设置三原色的取值范围,以达到粒子随机颜色的效果
emitterCell.redRange = 0.3
emitterCell.greenRange = 0.3
emitterCell.blueRange = 0.3
之前我们设置了粒子的颜色color,在设置了Range之后,粒子的red取值将在(0.9+0.3)=1.2到(0.9-0.3)=0.6之间随机选择,green取值将在(1.0+0.3)=1.3到(1.0-0.3)=0.7之间随机选择,blue取值将在(1.0+0.3)=1.3到(1.0-0.3)=0.7之间随机选择,因为颜色值不会超过1.0,所以最后红色取值范围为0.6-1.0,绿色和蓝色的取值范围为0.7-1.0。我们将range均设置为0.1,看起来跟雪更像。
运行效果
现在粒子看起都是一样大小的,我们来为粒子的大小设置随机值
emitterCell.scale = 0.8
emitterCell.scaleRange = 0.8
当scale设置为0.8时,设置了scaleRange之后,粒子的放大倍数将在(0.8-0.8)=0到(0.8+0.8)=1.6之间随机选择,当放大倍数为0时,粒子创建后就会立即消失。
运行效果
我们不仅可以设置粒子的初始大小,还可以在下落时修改粒子的大小
emitterCell.scaleSpeed = -0.15
scaleSpeed表示粒子每秒缩小0.15倍。
将birthRate设置为150,让粒子更密集。我们还可以为粒子设置随机alpha值,让雪花效果更有层次感。
emitterCell.alphaRange = 0.75
emitterCell.alphaSpeed = -0.15
之前我们设置了粒子的alpha值为1,设置alphaRange之后,粒子的透明度将在(1.0-0.75)=0.25到(1.0+0.75)=1.75之间随机选择,因为alpha值不能超过1.0,所以最后透明度取值在0.25到1.0之间。
alphaSpeed表示粒子的透明度将每秒减少0.15,直到0为止。
修改emissionLongitude为-.pi,粒子将向y轴左侧随机发射,让粒子有被风向右吹落的感觉,修改rect将粒子发射器移除屏幕外:
let rect = CGRect(x: 0.0, y: -70.0, width: view.bounds.width, height: 50.0)
为粒子设置随机生命周期
emitterCell.lifetimeRange = 1.0
因为之前设置了lifetime为3.5,所以粒子的最终lifetime将在2.5到4.5之间随机选择。
运行效果