mirror of
https://github.com/AquariaOSE/Aquaria.git
synced 2025-02-14 16:55:28 +00:00
Less special cases for non-rotated and non-flipped particles, but since these are rare and the rest of the quad rendering code has already gotten improvements there's not really any reason to keep the specialized modes around. The gains in GL calls were negligible and the new quad render code avoids glVertex3f() entirely, which is a much better gain imho.
228 lines
4.6 KiB
C++
228 lines
4.6 KiB
C++
/*
|
|
Copyright (C) 2007, 2010 - Bit-Blot
|
|
|
|
This file is part of Aquaria.
|
|
|
|
Aquaria is free software; you can redistribute it and/or
|
|
modify it under the terms of the GNU General Public License
|
|
as published by the Free Software Foundation; either version 2
|
|
of the License, or (at your option) any later version.
|
|
|
|
This program is distributed in the hope that it will be useful,
|
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
|
|
|
See the GNU General Public License for more details.
|
|
|
|
You should have received a copy of the GNU General Public License
|
|
along with this program; if not, write to the Free Software
|
|
Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
|
|
*/
|
|
#ifndef __particles__
|
|
#define __particles__
|
|
|
|
#include "Core.h"
|
|
#include "Quad.h"
|
|
#include "Randomness.h"
|
|
|
|
class Emitter;
|
|
class ParticleEffect;
|
|
|
|
struct SpawnParticleData
|
|
{
|
|
SpawnParticleData();
|
|
|
|
float randomScale1, randomScale2;
|
|
float randomAlphaMod1, randomAlphaMod2; // both unused
|
|
|
|
int pauseLevel;
|
|
int flipH, flipV;
|
|
|
|
float randomVelocityMagnitude;
|
|
int randomRotationRange;
|
|
Vector initialVelocity, gravity;
|
|
float randomSpawnRadius;
|
|
Vector randomSpawnMod;
|
|
int randomSpawnRadiusRange;
|
|
int justOne;
|
|
|
|
int copyParentRotation, copyParentFlip;
|
|
int width, height;
|
|
InterpolatedVector number, scale, rotation, color, alpha;
|
|
float life;
|
|
std::string texture;
|
|
BlendType blendType;
|
|
float spawnTimeOffset;
|
|
bool spawnLocal;
|
|
bool inheritColor;
|
|
bool inheritAlpha;
|
|
|
|
int influenced;
|
|
std::string deathPrt;
|
|
|
|
int suckIndex, suckStr;
|
|
};
|
|
|
|
struct Particle
|
|
{
|
|
Particle()
|
|
{
|
|
reset();
|
|
}
|
|
void reset()
|
|
{
|
|
active = false;
|
|
life = 1;
|
|
emitter = 0;
|
|
color.stop();
|
|
scale.stop();
|
|
rot.stop();
|
|
alpha.stop();
|
|
pos = Vector(0,0);
|
|
vel = Vector(0,0);
|
|
gvy = Vector(0,0);
|
|
color = Vector(1,1,1);
|
|
alpha = 1;
|
|
scale = Vector(1,1);
|
|
rot = Vector(0,0,0);
|
|
emitter = 0;
|
|
index = -1;
|
|
}
|
|
float life;
|
|
bool active;
|
|
Vector pos, vel, gvy;
|
|
InterpolatedVector color, alpha, scale, rot;
|
|
Emitter *emitter;
|
|
int index;
|
|
};
|
|
|
|
typedef std::vector<Particle> Particles;
|
|
|
|
class Emitter : public Quad
|
|
{
|
|
public:
|
|
Emitter(ParticleEffect *pe);
|
|
void destroy() OVERRIDE;
|
|
void addParticle(Particle *p);
|
|
void removeParticle(Particle *p);
|
|
|
|
SpawnParticleData data;
|
|
|
|
void start();
|
|
void stop();
|
|
|
|
bool isEmpty() const {return particles.empty();}
|
|
|
|
|
|
Vector getSpawnPosition();
|
|
|
|
protected:
|
|
Vector lastSpawn;
|
|
float lastDTDifference;
|
|
bool didOne;
|
|
void onRender(const RenderState& rs) const OVERRIDE;
|
|
Particle *spawnParticle(const Vector& spawnpos);
|
|
void onUpdate(float dt) OVERRIDE;
|
|
float randAngle();
|
|
|
|
ParticleEffect *pe;
|
|
|
|
typedef std::list<Particle*> Particles;
|
|
Particles particles;
|
|
FastRand rng;
|
|
};
|
|
|
|
class ParticleEffect : public RenderObject
|
|
{
|
|
public:
|
|
ParticleEffect();
|
|
void load(const std::string &name);
|
|
void bankLoad(const std::string &name, const std::string &path);
|
|
void start();
|
|
void stop();
|
|
bool isRunning() const {return running;}
|
|
void killParticleEffect();
|
|
Emitter *addNewEmitter();
|
|
void clearEmitters();
|
|
void transfer(ParticleEffect *pe);
|
|
|
|
void setDie(bool v);
|
|
|
|
std::string name;
|
|
protected:
|
|
bool die;
|
|
bool waitForParticles;
|
|
|
|
void onUpdate(float dt);
|
|
|
|
float effectLife, effectLifeCounter;
|
|
bool running;
|
|
typedef std::list<Emitter*> Emitters;
|
|
Emitters emitters;
|
|
};
|
|
|
|
struct ParticleInfluence
|
|
{
|
|
ParticleInfluence(Vector pos, float spd, float size, bool pull)
|
|
: pos(pos), size(size), spd(spd), pull(pull)
|
|
{}
|
|
ParticleInfluence() : size(0), spd(0), pull(false) {}
|
|
Vector pos;
|
|
float size;
|
|
float spd;
|
|
bool pull;
|
|
};
|
|
|
|
class ParticleManager
|
|
{
|
|
public:
|
|
ParticleManager(int size);
|
|
void setSize(size_t size);
|
|
void loadParticleBank(const std::string &bank1, const std::string &bank2);
|
|
void clearParticleBank();
|
|
|
|
Particle *getFreeParticle(Emitter *emitter);
|
|
int getSize();
|
|
|
|
void update(float dt);
|
|
|
|
void loadParticleEffectFromBank(const std::string &name, ParticleEffect *load);
|
|
void updateParticle(Particle *p, float dt);
|
|
|
|
void clearInfluences();
|
|
void addInfluence(ParticleInfluence inf);
|
|
int (*collideFunction)(Vector pos);
|
|
|
|
void endParticle(Particle *p);
|
|
|
|
size_t getFree() { return free; }
|
|
size_t getNumActive() { return numActive; }
|
|
|
|
void setNumSuckPositions(size_t num);
|
|
void setSuckPosition(size_t idx, const Vector &pos);
|
|
|
|
Vector *getSuckPosition(size_t idx);
|
|
|
|
static std::string particleBankPath;
|
|
|
|
protected:
|
|
|
|
std::vector<Vector> suckPositions;
|
|
size_t numActive;
|
|
Particle* stomp();
|
|
|
|
void nextFree(size_t f=1);
|
|
|
|
typedef std::vector<ParticleInfluence> Influences;
|
|
Influences influences;
|
|
|
|
size_t size, used, free;
|
|
Particles particles;
|
|
|
|
|
|
};
|
|
|
|
extern ParticleManager *particleManager;
|
|
|
|
#endif
|
|
|