Files
Webcam/include/engine/core/emitter.h
2026-06-22 11:49:35 +02:00

225 lines
4.3 KiB
C++

/* -----------------------------------------------------------------------------
GSFramework
Copyright 2001-2013 Emmanuel Julien. All Rights Reserved.
----------------------------------------------------------------------------- */
#ifndef __NEMITTER__
#define __NEMITTER__
#include "core/item.h"
#include "core/renderable.h"
#include "geometry/curve.h"
#include "sort/sort.h"
namespace GS {
namespace Core {
/*!
@short Particle class.
@author Emmanuel Julien (ejulien@gsworks.fr)
*/
struct Particle
{
Time time;
Vector4 position,
velocity;
float size;
float angle;
Color color;
/*!
@name Parameter scaler.
@{
*/
float opacity_scale,
size_scale;
/// @}
/// Is the particle alive.
bool IsAlive() const { return time.toSec() < 0 ? false : true; }
Particle()
{ opacity_scale = 1; }
};
/*
@short Particle model.
Models the particle attributes over its lifetime.
@author Emmanuel Julien (ejulien@gsworks.fr)
*/
struct ParticleModel : public SharedObject
{
struct RenderData
{
Render::sMaterial material;
};
String name;
String material;
Time time_to_live; ///< Time to live.
float damping; ///< Particle velocity damping.
Vector4 gravity; ///< Particle gravity.
Curve angle_curve,
size_curve;
Curve red_curve,
green_curve,
blue_curve,
opacity_curve;
AutoPtr <RenderData> render_data;
/// Setup render data.
void RenderSetup(ResourceFactories * = 0);
/*!
@short Set template color.
This function does not clear the color and opacity curves.
It only set their default value member, curves with keys will animate
as usual.
*/
void SetColor(const Color &);
/// Add color curve point.
void AddColorPoint(const Time &t, const Color &);
/*!
@name Serialization.
@{
*/
bool FromMetaTag(NML::Tag &);
NML::Tag *AsMetaTag() const;
/// @}
ParticleModel();
};
typedef SharedPtr <ParticleModel> sParticleModel;
/*!
@short Emitter class.
Note: Emitters emit particle along the Z axis.
@author Emmanuel Julien (ejulien@gsworks.fr)
*/
class Emitter : public Item, public Renderable
{
public:
struct RenderData
{
sParticleModel particle_model;
};
enum Model
{
Model_Spray = 0
};
/*!
@name Emitter model.
@{
*/
protected:
Model model;
public:
/*!
@name Renderable interface.
@{
*/
/// Compute the renderable minmax.
virtual void ComputeRenderableMinMax(MinMax &mm) { ComputeMinMax(mm); }
/// Get the renderable primitive list for this renderable.
virtual uint GetRenderablePrimitiveList(const Camera &view, const Camera &default_view, Stack <Render::Primitive *> &list, Renderable::Context context = Renderable::Context_Default, bool cull = true);
/// @}
uint pool_size; ///< Particle pool size.
float birth_rate; ///< Rate in particle/second.
float birth_speed_min,
birth_speed_max; ///< Speed in m.s.
float spray_angle;
/*!
@name Model scale.
@{
*/
float birth_rate_scale,
birth_opacity_scale,
birth_speed_scale,
birth_size_scale;
/// @}
String particle_model;
/// Model particle.
void ModelParticle(Particle &, const Item &, const Time &emitter_time);
/// Get emitter model.
Model GetModel() const { return model; }
/// Set as spray emitter.
void SetSprayModel(float angle = Units::Deg(45.f));
/// @}
AutoPtr <RenderData> render_data;
protected:
Array <Particle> particle_pool;
uint alive_count;
bool is_seen;
Time time;
Time birth_time;
Array <Sort <float, uint>::Entry> sort_array;
public:
void RenderSetup(ResourceFactories * = 0);
bool Setup();
void Update(const Time &dt);
void Free();
void ComputeMinMax(MinMax &) const;
/// Sort emitter particles against a given view matrix.
void Sort(const Matrix4 &view_matrix);
/*!
@short Get alive particle count.
@note The emitter must have been sorted beforehand.
@see Sort().
*/
uint GetParticleCount() const { return alive_count; }
/*
@short Get alive particle.
@note Particles are returned back to front.
*/
Particle *GetParticle(uint n) const { return n < particle_pool.GetCount() ? &particle_pool[sort_array[alive_count - 1 - n].o] : 0; }
/*!
@name Serialization.
@{
*/
bool FromMetaTag(NML::Tag &);
NML::Tag *AsMetaTag() const;
/// @}
Emitter();
};
} // Core
} // GS
#endif // __NEMITTER__