
Particle systems
I always say that video games are comparable to films, differences aside, because they tell stories, have an argument, different scenes, a soundtrack, and special effects. Yes, you read correctly, you can add special effects, or particle systems as they're commonly known in computer games, to your games.
In computer graphics, this technique is commonly used because it simulates several natural and meteorological phenomena such as snow, sun, rain, fire, meteors, and smoke. It also simulates other special effects such as spirals, explosions, fireworks, and other lighting effects by using a large amount of small images. If you think about natural phenomena, like rain for example, it is composed of hundreds of water droplets and so that's what we need to replicate if we want to simulate a particle system in Cocos2d.
You might be thinking that this task must be hard and offers little possibilities, but in this section, you will learn to create and customize your own particle effects easily.
CCParticleSystem
The class responsible for creating and managing particle effects is CCParticleSystem
, a subclass of CCParticleSystemBase
, which inherits from CCNode
. It offers some features that its parent class doesn't, such as:
- Floating-point numbers in particle sizes
- Subrectangles
- Batched rendering to improve performance
- Rotation
- Scalation
This class allows you to configure several attributes to achieve the effect you're looking for, but before customizing a particle system, let's create a simple one.
We will need a private CCParticleSystem
instance variable, so in GameScene.m
, add the following line after CGSize _screenSize;
:
// Declare a private CCParticleSystem instance variable CCParticleSystem *_fire;
Then add the following lines to the init
method, just after [self configureParallaxEffect];
:
// Init the fire particle _fire = [CCParticleFire node]; // Place the fire _fire.position = CGPointMake(_scientist.position.x, _scientist.position.y); // Add the particle system to the scene [self addChild:_fire z:1];
As you can see, creating a particle system is as easy as creating a common sprite. We declared a CCParticleSystem
instance and then initialized it by sending the node
message to CCParticleFire
so we have a fire particle. Then we place the fire in the middle of the scientist's back and we add it to the scene with a z-order of 1
to be above the parallax node. Pretty short and simple, isn't it? Run the project and let's see what happens.
Where is the fire? Don't worry, I introduced this issue deliberately to expose a particularity of CCParticleSystem
. If you take a look at Target Output at the bottom of the Xcode screen, you will see the following log:
2014-05-29 23:12:18.760 ExplosionsAndUFOs[13561:60b] -[CCFileUtils fullPathForFilename:contentScale:] : cocos2d: Warning: File not found: fire.png 2014-05-29 23:12:18.761 ExplosionsAndUFOs[13561:60b] cocos2d: Couldn't find file:fire.png 2014-05-29 23:14:17.359 ExplosionsAndUFOs[13561:60b] cocos2d: animation stopped 2014-05-29 23:14:17.385 ExplosionsAndUFOs[13561:60b] cocos2d: animation started with frame interval: 4.00 2014-05-29 23:14:17.405 ExplosionsAndUFOs[13561:60b] cocos2d: animation stopped
Okay it is important to notice that our particle system is looking for a file named fire.png
and is not finding it; that's why there is no visual representation. This means that we must provide the texture to be used to represent the particles.
You can solve this issue by following these steps:
- In the project navigator, select the Resources group.
- Right-click and select Add Files to "ExplosionsAndUFOs"….
- Select the
fire.png
file (which I downloaded from http://misteraibo.deviantart.com/art/Fire-311421529) in theResources
folder you unzipped and click on Add.
Run your game and you will see something like the following screenshot:

You just created your first particle system by adding the fire.png
file into your project. It's the default file the particle system will look for, but you can choose a different file to create the effect. The next line shows how to apply a texture created with a custom file to our fire particle system:
_fire.texture = [CCTexture textureWithFile:@"flame.png"];
If you think about it, this feature allows you to create a large variety of particle systems. What should happen if you use the image of a bubble as a particle? Let's check it.
Again in the project navigator:
- Right-click on the Resources group and select Add Files to "ExplosionsAndUFOs"….
- Select
bubble.png
in theResources
folder and click on Add.
Then go back to GameScene.m
and add the following line in the init
method, before [self addChild:_fire z:1];
:
// Create particle from a texture _fire.texture = [CCTexture textureWithFile:@"bubble.png"];
Run the project and you will see what happens:

I just wanted to show you how powerful particle systems are in Cocos2d, but it doesn't stop there. Before proceeding, undo the last changes:
- Delete
bubble.png
from the project, making sure that you choose the Move to Trash option. - Delete the line
_fire.texture = [CCTexture textureWithFile:@"bubble.png"];
.
CCParticleSystem modes
There are two modes of particle systems that depend on which way they emit particles:
- Gravity Mode
- Radius Mode
You can set the mode by assigning CCParticleSystemModeGravity
or CCParticleSystemModeRadius
to the emitterMode
property of the particle system. These modes can be customized thanks to a broad set of properties, some of which are exclusive to each mode; that's why you need to pay attention or you will encounter NSInternalInconsistencyException
.
This is the default mode and it creates particles that flow from a source point or that converge at a target point. You can set up a gravity particle, setting values for the following attributes:
gravity
: This indicates the acceleration of the particles in the x and y axesspeed
: This indicates the speed that each particle will havespeedVar
: This is the speed variance that each particle will havetangentialAccel
: This indicates the velocity of the particles moving in a curved pathtangentialAccelVar
: This is the variance of the tangential accelerationradialAccel
: This indicates the acceleration of a particle that moves at a constant speed along a circular pathradialAccelVar
: This is the variance of the radial acceleration
Better than reading, let's play a little with these attributes. Add the following lines to the init
method, just before return self;
:
_fire.emitterMode = CCParticleSystemModeGravity; _fire.gravity = CGPointMake(0, -160); _fire.speed = 50.0; _fire.speedVar = 200.0; _fire.tangentialAccel = 70.0; _fire.tangentialAccelVar = 150.0; _fire.radialAccel = 80.0; _fire.radialAccelVar = 30.0;
Run the game and discover how these values affect the fire's behavior. I recommend you try your own setups to obtain your desired results.
This mode creates particles that move around a central point. The particular attributes for this mode are:
startRadius
: This determines the starting radius of the particles. In other words, the distance to the node's position.startRadiusVar
: This is the starting radius variance of the particles.endRadius
: This determines the final radius of the particles. It can be made equal to the starting radius by specifyingCCParticleSystemStartRadiusEqualToEndRadius
.endRadiusVar
: This is the end radius variance of the particles.rotatePerSecond
: This indicates the number of degrees the particles will rotate around the source.rotatePerSecondVar
: This is the variance in degrees for each rotation per second.
Let's play a little with these attributes too. Replace the lines added in the gravity mode section with these ones:
_fire.emitterMode = CCParticleSystemModeRadius; _fire.startRadius = 200.0; _fire.startRadiusVar = 5.0; _fire.endRadius = 30.0; _fire.endRadiusVar = 3.0; _fire.rotatePerSecond = 100.0; _fire.rotatePerSecondVar = 12.0;
You can see the results in the following screenshots:

Besides these specific attributes, CCParticleSystem
objects have some common attributes among which I would like to stress the most interesting that you may want to know about:
totalParticles
: This is the maximum number of particles that will be on the screen at the same time.life
/lifeVar
: This is the time that each particle will take to move from the start to the end point. If this value is low enough, there will be more and more particles on the screen, but this will never exceed thetotalParticles
value.emissionRate
: This indicates the number of particles that will be created per second. Usually, this value corresponds tototalParticles
/life
.startSpin
/startSpinVar
: This determines the initial spin value of each particle.endSpin
/endSpinVar
: This determines the final spin value of each particle.startSize
/startSizeVar
: This indicates the initial size of each particle.endSize
/endSizeVar
: This indicates the final size of each particle. You can keep the initial size at the end by using theCCParticleSystemStartSizeEqualToEndSize
constant.startColor
/startColorVar
: This sets up the initial color of the particles. For example, you can tint your particles in green using_fire.startColor = [CCColor greenColor]
.endColor
/endColorVar
: This sets the final color of each particle.texture
: This specifies the texture used to render each particle.angle
/angleVar
: This determines the direction the particles will follow once emitted, where0
means right,90
means up,180
means left, and270
means down.duration
: This is the time the emitter will run, not to be confused with thelife
attribute, where-1
andCCParticleSystemDurationInfinity
means forever.posVar
: This is the position variance of the emitter.sourcePosition
: This indicates the offset position of the particles from the emitter.
However, you must be wondering how these properties affect our project visually. Replace the lines added during the Radius Mode section with these ones:
_fire.totalParticles = 200; _fire.life = 3.3; _fire.lifeVar = 0.5; _fire.emissionRate = _fire.totalParticles/_fire.life; _fire.startSpin = 13.0; _fire.startSpinVar = 0.5; _fire.endSpin = 50.0; _fire.endSpinVar = 0.3; _fire.startSize = 60.0; _fire.startSizeVar = 5.0; _fire.endSize = 10.0; _fire.endSizeVar = 2.0; _fire.startColor = [CCColor greenColor]; _fire.startColorVar = [CCColor blueColor]; _fire.endColor = [CCColor redColor]; _fire.endColorVar = [CCColor purpleColor]; _fire.angle = 270.0; _fire.duration = CCParticleSystemDurationInfinity; _fire.posVar = CGPointMake(10, 10); _fire.sourcePosition = CGPointMake(0, 50);
Run the project again and look at the results.
Do you realize the potential these particles have thanks to these attributes? There are only a few changes required to achieve the result we are looking for in the backpack-reactor.
Replace the following properties from the previous block with the following ones:
// Configure the particle system _fire.startSize = 50.0; _fire.startSizeVar = 1.0; _fire.posVar = CGPointMake(10, 0); _fire.sourcePosition = CGPointMake(0, -10);
Add these new ones:
_fire.speed = 50.0; _fire.speedVar = 1.0;
By modifying startSize
and its variance, the position variance, and the source position, we have customized the particle node to behave as we want. Also, by setting its speed and speed variance, we made it look like a reactor, but we want the fire to follow the scientist so add these lines at the end of the update
method:
// Make the fire follow the scientist _fire.position = CGPointMake(_scientist.position.x, _scientist.position.y);
Run the game and you will see the brand new invention of Dr. Fringe in action, the super BPR-200!

Particle Designer
It's important that as game developers we know as many tools as possible so in this section, I would like to introduce you to a very useful one: Particle Designer (http://71squared.com/en/particledesigner).
This editor, which has a trial and a paid version, allows us to customize our particle systems in real time without needing to run the Xcode project each time to see the resultant effect.

Particle Designer has a main view where you can see your particles (in the current version, you can work with multiple particle systems) in different screen modes: from iPhone SD Portrait to iPad HD Landscape and from Android Normal Portrait to Android X-Large Landscape. There you can change the stage color too, which will help you to reproduce your game's colors so you can achieve the proper effect.
On the left, you have your particle systems where you can edit its particlePositionType
attribute (grouped or relative) and select other visual properties of the editor to show or hide the particle system.
On the right side, you will find four panel settings: Emitter Settings, Particle Settings, Color Settings, and Texture Settings. In these panels, you will be able to edit all the attributes of the particles while you see how this affects the visual result.
There is an interesting button with a cloud shape at the top-right corner of the editor. Clicking this shows the particles other users have shared, which you can export or just take a look at to get ideas.
Once you have set up your particles, if you have a licensed version, you can export them in the PEX, LAP, Plist, or JSON format. We won't cover how to integrate these files into Cocos2d in this book, but you will find a lot of documentation on the official website at http://71squared.com/particledesigner.