![]() |
CUGL 3.0
Cornell University Game Library
|
#include <CUParticleSystem.h>
Public Member Functions | |
ParticleSystem () | |
~ParticleSystem () | |
void | dispose () |
bool | init (size_t capacity) |
bool | initWithMesh (size_t capacity, const Mesh< ParticleVertex > &mesh) |
bool | initWithMesh (size_t capacity, Mesh< ParticleVertex > &&mesh) |
bool | initWithData (const std::shared_ptr< JsonValue > data, bool buffer=true) |
const Particle3 * | getParticles () const |
const ParticleInstance * | getInstances () const |
const Mesh< ParticleVertex > & | getMesh () const |
void | setMesh (const Mesh< ParticleVertex > &mesh) |
void | setMesh (Mesh< ParticleVertex > &&mesh) |
const std::unordered_map< std::string, ParticleEmitter > & | getEmitters () const |
void | addEmitter (const std::string key, const ParticleEmitter &data) |
void | removeEmitter (const std::string key) |
const std::shared_ptr< InstanceBuffer > | getInstanceBuffer () const |
size_t | getCapacity () const |
size_t | getAllocated () const |
bool | is2d () const |
void | set2d (bool value) |
ParticleAllocator | getAllocator () const |
void | setAllocator (ParticleAllocator func) |
ParticleDeallocator | getDeallocator () const |
void | setDeallocator (ParticleDeallocator func) |
ParticleUpdater | getUpdater () const |
void | setUpdater (ParticleUpdater func) |
void | update (float delta, const Vec3 camera) |
void | draw (const std::shared_ptr< Shader > &shader) |
Static Public Member Functions | |
static std::shared_ptr< ParticleSystem > | alloc (size_t capacity) |
static std::shared_ptr< ParticleSystem > | allocWithMesh (size_t capacity, const Mesh< ParticleVertex > &mesh) |
static std::shared_ptr< ParticleSystem > | allocWithMesh (size_t capacity, Mesh< ParticleVertex > &&mesh) |
static std::shared_ptr< ParticleSystem > | allocWithData (const std::shared_ptr< JsonValue > data, bool buffer=true) |
Friends | |
class | ParticleLoader |
This class implements a (3d) particle system.
A particle system is a graphics::Mesh
instanced many times to display a large collection of images. Instances are particles, which are represented the Particle3
class.
Particle simulation is defined via a user-defined ParticleUpdater
function. Without this function, no instance data will be created for the particles, so nothing can be rendered to the screen.
While we do not support user-defined particles, it is possible to add user data to a particle object with the function types ParticleAllocator
and ParticleDeallocator
. In fact, ParticleAllocator
is required to emit any particles. Without it, no particles will be created. On the other hand, ParticleDeallocator
is optional and only required to prevent possible memory leaks.
Each particle system has its own InstanceBuffer
. This is done for performance reasons. This is different that a SpriteBatch
which has a single buffer that would be used for all objects of the same time. This particle system and its internal buffer should be combined with a particle shader to display this particles.
While particle systems are designed for 3d particles, they work perfectly well in 2d scene graphs. In that case, the particle classes should always set the z-value for the particle instances to 0. In addition, you should call set2d
to prevent unnecessary z-sorting.
cugl::graphics::ParticleSystem::ParticleSystem | ( | ) |
Creates a new unitialized particle system.
This particle system has degenerate values for all attributes. No particles will be generated until it is initialized.
|
inline |
Deletes this particle system, disposing all of the resources.
void cugl::graphics::ParticleSystem::addEmitter | ( | const std::string | key, |
const ParticleEmitter & | data | ||
) |
Adds an emitter to the particle system.
This method will do nothing if the key is already in use by another emitter. The emitter will be immediately integrated into the simulation.
key | The key identifing this emitter |
data | The emitter data |
|
inlinestatic |
Returns a newly allocated particle system with the given capacity.
The particle system will have an empty template and no emitters. It will also have no user-defined update or allocation functions. It will not generate any particles until all of these are set.
capacity | The particle capacity |
|
inlinestatic |
Returns a newly allocated particle system from the given JsonValue
The JsonValue should either be an array or an JSON object. If it is an array, the elements should all be float arrays of length four, representing the individual ParticleVertex
vertices. These vertices will be interpretted as a triangle fan.
On the other hand, if it is a JSON object, it supports the following attributes:
"capacity": An int with the maximum capacity "mesh": An array or JSON object representing the mesh (see below) "emitters": An object with key/emitter pairs
All attributes except "capacity" are optional. If "emitters" is missing or empty, there are no emitters. The values in the key/value pairs for the emitter are per the specification for ParticleEmitter
.
If the "mesh" is missing, the mesh template is empty. If it is an array, the elements should all be float arrays of length four, representing the individual ParticleVertex
vertices. Otherwise, it should have the following attributes:
"vertices": An array of float arrays of length four "indices": An intenger list of triangle indices (in multiples of 3) "triangulator": One of 'monotone', 'earclip', 'delaunay', 'fan', or 'strip'
All attributes are optional. If "vertices" are missing, the mesh will be empty. If both "indices" and "triangulator" are missing, the mesh will use a triangle fan. The "triangulator" choice will only be applied if the "indices" are missing.
The particle system will only create a graphics buffer if buffer is true. This is to handle cases where the sprite mesh is created in a separate thread (as OpenGL only allows graphics buffers to be made on the main thread).
Note that the JSON does not a provide a way to specify the user-defined allocation and update functions. No particles will be generated until these are set.
data | The JSON object specifying the particle system |
buffer | Whether to create a graphics buffer |
|
inlinestatic |
Returns a newly allocated particle system with the given capacity and mesh.
The particle system will have no emitters. It will also have no user-defined update or allocation functions. It will not generate any particles until all of these are set.
This version of the initializer will acquire the resources of the original mesh. Use std::move to use this initializer.
capacity | The particle capacity |
mesh | The template mesh to copy |
|
inlinestatic |
Returns a newly allocated particle system with the given capacity and mesh.
The particle system will have no emitters. It will also have no user-defined update or allocation functions. It will not generate any particles until all of these are set.
This version of the initializer will acquire the resources of the original mesh. Use std::move to use this initializer.
capacity | The particle capacity |
mesh | The template mesh to acquire |
void cugl::graphics::ParticleSystem::dispose | ( | ) |
Disposes the emitters and allocation lists for this particle system.
You must reinitialize the particle system to use it.
void cugl::graphics::ParticleSystem::draw | ( | const std::shared_ptr< Shader > & | shader | ) |
Draws the render buffer with the given shader.
shader | The shader to draw with |
|
inline |
Returns the number of particles currently allocated.
|
inline |
Returns the allocation function associated with this system.
If this function pointer is null, no particles will be allocated from any of the emitters.
|
inline |
Returns the capacity of this particle system.
The capacity the maximum number of particles that can be allocated at any given time.
|
inline |
Returns the deallocation function associated with this system.
This function pointer is optional. It is only needed to clean up particles where memory was previously allocated. If there is no chance of a memory leak, it can be omitted.
|
inline |
Returns the emitters for this particle system.
Each emitter is identified by a user-specified key. It is safe to change the attributes of an emitter mid-simulation, but any changes will only be applied to new particles, not existing ones.
|
inline |
Returns the instance buffer for this particle system.
This buffer is used to render the particles. It should be combined with the particle shader.
|
inline |
Returns the array of instance data.
This array should be passed to the shader for drawing. This array will have getCapacity
length. However, only the first getAllocated
elements will be in use.
|
inline |
Returns the mesh template associated with this particle system.
This mesh can be safely changed mid-simulation. It only affects how particles are rendered, not their state. However, changing the mesh affects the getInstanceBuffer
. Therefore, the mesh should never be modified directly. Changes should go through setMesh
.
|
inline |
Returns the array of particles.
This array will have getCapacity
length. However, only the first getAllocated
elements will be in use.
|
inline |
Returns the update function associated with this system.
If this function pointer is null, no instance data will be created for the particles, so nothing can be rendered to the screen. Indeed, the result of getInstances
is undefined if this value is null.
bool cugl::graphics::ParticleSystem::init | ( | size_t | capacity | ) |
Initializes this particle system to have the given capacity.
The particle system will have an empty mesh and no emitters. It will also have no user-defined update or allocation functions. It will not generate any particles until all of these are set.
capacity | The particle capacity |
bool cugl::graphics::ParticleSystem::initWithData | ( | const std::shared_ptr< JsonValue > | data, |
bool | buffer = true |
||
) |
Initializes a particle template from the given JsonValue
The JsonValue should either be an array or an JSON object. If it is an array, the elements should all be float arrays of length four, representing the individual ParticleVertex
vertices. These vertices will be interpretted as a triangle fan.
On the other hand, if it is a JSON object, it supports the following attributes:
"capacity": An int with the maximum capacity "mesh": An array or JSON object representing the mesh (see below) "emitters": An object with key/emitter pairs
All attributes except "capacity" are optional. If "emitters" is missing or empty, there are no emitters. The values in the key/value pairs for the emitter are per the specification for ParticleEmitter
.
If the "mesh" is missing, the mesh template is empty. If it is an array, the elements should all be float arrays of length four, representing the individual ParticleVertex
vertices. Otherwise, it should have the following attributes:
"vertices": An array of float arrays of length four "indices": An intenger list of triangle indices (in multiples of 3) "triangulator": One of 'monotone', 'earclip', 'delaunay', 'fan', or 'strip'
All attributes are optional. If "vertices" are missing, the mesh will be empty. If both "indices" and "triangulator" are missing, the mesh will use a triangle fan. The "triangulator" choice will only be applied if the "indices" are missing.
The particle system will only create a graphics buffer if buffer is true. This is to handle cases where the sprite mesh is created in a separate thread (as OpenGL only allows graphics buffers to be made on the main thread).
Note that the JSON does not a provide a way to specify the user-defined allocation and update functions. No particles will be generated until these are set.
data | The JSON object specifying the particle system |
buffer | Whether to create a graphics buffer |
bool cugl::graphics::ParticleSystem::initWithMesh | ( | size_t | capacity, |
const Mesh< ParticleVertex > & | mesh | ||
) |
Initializes this particle system with the given capacity and mesh.
The particle system will have no emitters. It will also have no user-defined update or allocation functions. It will not generate any particles until all of these are set.
This version of the initializer will copy the original mesh.
capacity | The particle capacity |
mesh | The template mesh to copy |
bool cugl::graphics::ParticleSystem::initWithMesh | ( | size_t | capacity, |
Mesh< ParticleVertex > && | mesh | ||
) |
Initializes this particle system with the given capacity and mesh.
The particle system will have no emitters. It will also have no user-defined update or allocation functions. It will not generate any particles until all of these are set.
This version of the initializer will acquire the resources of the original mesh. Use std::move to use this initializer.
capacity | The particle capacity |
mesh | The template mesh to acquire |
|
inline |
Returns whether this particle system is optimized for 2d.
A 2d particle system has no z-value and does not require z-sorting.
void cugl::graphics::ParticleSystem::removeEmitter | ( | const std::string | key | ) |
Removes the emitter with the given key.
Any particles previously created by the emitter will remain part of the simultation until their life value reaches 0. This method will have no effect if there is no emitter with the given key.
key | The key identifing the emitter |
|
inline |
Sets whether this particle system is optimized for 2d.
A 2d particle system has no z-value and does not require z-sorting.
value | Whether this particle system is optimized for 2d |
|
inline |
Sets the allocation function associated with this system.
If this function pointer is null, no particles will be allocated from any of the emitters.
func | The allocation function associated with this system. |
|
inline |
Sets the desllocation function associated with this system.
This function pointer is optional. It is only needed to clean up particles where memory was previously allocated. If there is no chance of a memory leak, it can be omitted.
func | The deallocation function associated with this system. |
void cugl::graphics::ParticleSystem::setMesh | ( | const Mesh< ParticleVertex > & | mesh | ) |
Sets the mesh template associated with this particle system.
This mesh can be safely changed mid-simulation. It only affects how particles are rendered, not their state. However, changing the mesh affects the getInstanceBuffer
. Therefore, the mesh should never be modified directly. Changes should go through setMesh
.
mesh | The particle mesh template |
void cugl::graphics::ParticleSystem::setMesh | ( | Mesh< ParticleVertex > && | mesh | ) |
Sets the mesh template associated with this particle system.
This mesh can be safely changed mid-simulation. It only affects how particles are rendered, not their state. However, changing the mesh affects the getInstanceBuffer
. Therefore, the mesh should never be modified directly. Changes should go through setMesh
.
mesh | The particle mesh template |
|
inline |
Sets the update function associated with this system.
If this function pointer is null, no instance data will be created for the particles, so nothing can be rendered to the screen. Indeed, the result of getInstances
is undefined if this value is null.
func | The update function associated with this system. |
void cugl::graphics::ParticleSystem::update | ( | float | delta, |
const Vec3 | camera | ||
) |
Updates the simulation by the given amount of time.
Most of the work of this method is implemented by the particle class. This method manages particle emission (with delay) and camera distance.
delta | The time passed in the simulation |
camera | The camera position in world space |