This idea isn't really new. I already mentioned this topic a while ago but i decided to wait with the implementation until the new animation system is working so that it can be used for animated particles. To avoid any discussions about implementation details after the code is written i decided to document the whole system beforehand.
This article isn't finished. That is why it is in my personal directory. When i finished the article i will move it to Particle engine and link it from the front page in the RFC section.
What is a particle engine?
A particle engine is a system that allows to create beautiful dynamic special effects based on creating and managing a large number of small, independent, moving sprites. Flames, smoke, fountains and waterfalls are just some examples what can be done with such an engine. For more information about particle engines see the Wikipedia article about particle systems.
Why a particle engine?
A particle engine would allow us to create a large variety of beautiful special effects with minimal effort that would outclass those of most other sprite based rpgs. The areas where particle effects could be used include but are not limited to:
- Enviromental effects like waterfalls, fountains or smoke comming out of chimneys
- Visualisation of mystical phenomenons like teleporters or other points of interest
- Graphic effects for spells
- Visualisation of status effects
Implementation proposal
My idea would be to create two new classes named "ParticleEmitter" and "Particle". Both have a position in three dimensional space (in this case the two dimensional game world is threatet as a flat plane in a three dimensional space). The "PaticleEmitter"s purpose is to create new "Particle"s. I would suggest to implement the "ParticleEmitter" as a new class and the "Particle"s as a derived class from "Sprite" so that they can be added to the maps sprite list to be drawn together with the other sprites by the "map" class. But the logic of both should be called by the "engine" class because the particles do not interfere with the game mechanics.
Particle Emitter
The creation of particle emitters is either triggered when a map is loaded that contains particle emitters for esthetical purpose or by events like spellcasting. An emitter can have a large number of properties. Most of these are basically the initial properties of the created particles. I would suggest to predefine the properties of the emitter types in external xml files. These are the properties of the emitter:
- layer
- When the Action Layers concept is realized it would be good to define the map layer on which the particles are drawn.
- posX, posY, posZ
- The coordinates in 3 dimensional space where the newly created particles are spawned.
- particleAppearance
- Either the filename of an xml file that contains the animation definition for animated particles or the file name of a png file for not animated particles.
- particleLifetime
- Lifetime of the particles.
- particleAmmount
- Number of particles that are created every game tick.
- angelHorizontal, angelVertical, power
- Initiall vector of the created sprites.
- accelerationAngelHorizontal, accelerationAngelVertical, accelerationPower
- Acceleration vector of the particles. The particles vector is multiplied by this vector after every game tick. Useful for creating particles that obey gravity, slow down or accelerate after they are created.
- emitterLifetime
- The time in game ticks the emitter exists (useful for event triggered special effects)
All properties have the attribute "value" and 4 optional attributes "diffusion", "delta", "frequency" and "amplitude" that define the change of the value. When "frequency" or "amplitude" is defined, the other one must be defined, too.
- diffusion
- is the range in which the value fluctuates randomly.
- delta
- is how much the value changes with every game tick. This allows to create emitters whichs properties change over time.
- amplitude
- Defines the amplitude of a sine wave that is added to the "value". Allows to set values that change over time, but not linear like the delta property but in a sine rythm.
- frequency
- Defines the frequency of a sine wave that is added to the "value" (unit: ticks per oscilation).
TODO: member var description, method description, where and when they are called, description of data structure in which they are stored, implementation details.*
In contrast to an implementation proposal i made earlier i decided to abstain from an option to create particle emitters that explicitely follow a being. Instead i would like to provide an interface for beings to create emitters and move them to their current position themself.
Particle
These are the member variables of the particle class:
- Animation animation
- Animation class that controls the animation of the particle (NULL for unanimated particles).
- Image* image
- Pointer to the image class for unanimated particles (NULL for animated particles).
- float posX, posY, posZ
- The coordinates in 3 dimensional space of the particle.
- float vectorX, vectorY, vectorZ
- The movement vector of the sprites. For faster calculation already splitted up in its components.
- float accelX, accelY, accelZ
- Acceleration vector of the sprites. For faster calculation already splitted up in its components.
- int lifetime
- A counter for the remaining lifetime of the particle. It is decremented during every update. When it reaches 0 the dead flag is raised.
- bool dead
- a flag that signalizes the engine that the particle should be removed.
TODO: method description, where and when they are called, description of data structure in which they are stored, implementation details.
Necessary extensions of the map format
Mappers should be able to define special effects that are placed statically on their maps.
TODO:Explain another reason why Bjørn should add a feature to Tiled and the .tmx format that allows to place user defined special objects on the map