1
0
Fork 0
mirror of https://github.com/AquariaOSE/Aquaria.git synced 2025-02-15 09:05:52 +00:00

cleanup the partcile system a bit, and use new randomness

This commit is contained in:
fgenesis 2025-02-01 07:32:54 +01:00
parent 26e1da131d
commit 3a40506ddb
7 changed files with 126 additions and 241 deletions

View file

@ -209,10 +209,9 @@ void Avatar::onAnimationKeyPassed(int key)
Entity::onAnimationKeyPassed(key);
}
Vector randCirclePos(Vector position, int radius)
static Vector randCirclePos(const Vector& position, float radius)
{
float a = ((rand()%360)*(2*PI))/360.0f;
return position + Vector(sinf(a), cosf(a))*radius;
return position + randVector(radius);
}
SongIconParticle::SongIconParticle(Vector color, Vector pos, size_t note)
@ -224,7 +223,7 @@ SongIconParticle::SongIconParticle(Vector color, Vector pos, size_t note)
setWidthHeight(32);
float life = 1.0;
const float life = 1;
toIcon = 0;
this->color = color;

View file

@ -192,6 +192,11 @@ enum LerpType
#define DOUBLE_CLICK_DELAY 0.5f
inline float lerp(float v1, float v2, float t)
{
return (v2-v1)*t+v1;
}
float lerp(float v1, float v2, float dt, int lerpType);

View file

@ -96,7 +96,6 @@ set(BBGE_SRCS
Slider.h
SoundManager.cpp
SoundManager.h
SpawnParticleData.cpp
SplineGrid.cpp
SplineGrid.h
StateMachine.cpp

View file

@ -21,6 +21,46 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
#include "Particles.h"
#include "RenderBase.h"
SpawnParticleData::SpawnParticleData()
{
suckIndex = -1;
suckStr = 0;
randomScale1 = 1;
randomScale2 = 1;
randomAlphaMod1 = 1;
randomAlphaMod2 = 1;
influenced = 0;
spawnLocal = false;
life = 1;
blendType = BLEND_DEFAULT;
scale = Vector(1,1,1);
width = 64;
height = 64;
color = Vector(1,1,1);
alpha = 1;
randomSpawnRadius = 0;
lastDTDifference = 0;
randomRotationRange = 0;
number = 1;
randomSpawnRadiusRange = 0;
randomSpawnMod = Vector(1,1);
randomVelocityMagnitude = 0;
copyParentRotation = 0;
justOne = didOne = false;
flipH = flipV = 0;
spawnTimeOffset = 0;
pauseLevel = 0;
copyParentFlip = 0;
inheritColor = false;
inheritAlpha = false;
}
Emitter::Emitter(ParticleEffect *pe) : Quad(), pe(pe)
{
//HACK:
@ -63,52 +103,32 @@ void Emitter::spawnParticle(float perc)
p->pos = lastSpawn + ((currentSpawn - lastSpawn) * perc);
int finalRadius = data.randomSpawnRadius;
if (data.randomSpawnRadiusRange > 0)
finalRadius += rand()%data.randomSpawnRadiusRange;
float finalRadius = data.randomSpawnRadius + rng.f01() * data.randomSpawnRadiusRange;
switch (data.spawnArea)
{
case SpawnParticleData::SPAWN_CIRCLE:
{
float a = rand()%360;
float a = randAngle();
p->pos += Vector(sinf(a)*finalRadius * data.randomSpawnMod.x, cosf(a)*finalRadius * data.randomSpawnMod.y);
}
break;
case SpawnParticleData::SPAWN_LINE:
{
if (rand()%2 == 0)
p->pos.x += finalRadius;
else
p->pos.x -= finalRadius;
}
break;
}
if (data.randomScale1 == 1 && data.randomScale1 == data.randomScale2)
if (!(data.randomScale1 == 1 && data.randomScale1 == data.randomScale2))
{
}
else
{
int r = rand()%(int(data.randomScale2*100) - int(data.randomScale1*100));
float sz = data.randomScale1 + float(r)/100.0f;
// Legacy codepath -- breaks animated scaling
float sz = lerp(data.randomScale1, data.randomScale2, rng.f01());
p->scale = Vector(sz,sz);
}
if (data.randomRotationRange > 0)
{
p->rot.z = rand()%int(data.randomRotationRange);
p->rot.ensureData();
p->rot.data->target.z += p->rot.z;
p->rot.z = rng.f01() * data.randomRotationRange;
p->rot.ensureData()->target.z += p->rot.z;
}
if (data.randomVelocityMagnitude > 0)
{
float a = rand()%data.randomVelocityRange;
float a = randAngle();
Vector v = Vector(sinf(a)*data.randomVelocityMagnitude, cosf(a)*data.randomVelocityMagnitude);
p->vel += v;
}
@ -119,6 +139,11 @@ void Emitter::spawnParticle(float perc)
}
}
float Emitter::randAngle()
{
return 2 * PI * rng.f01();
}
Vector Emitter::getSpawnPosition()
{
if (!data.spawnLocal)
@ -130,70 +155,56 @@ void Emitter::onUpdate(float dt)
{
Quad::onUpdate(dt);
if(!(pe->isRunning() && core->particlesPaused <= data.pauseLevel))
return;
if (pe->isRunning() && core->particlesPaused <= data.pauseLevel)
if (data.spawnTimeOffset > 0)
{
data.spawnTimeOffset -= dt;
if (data.spawnTimeOffset > 0)
{
data.spawnTimeOffset -= dt;
if (data.spawnTimeOffset > 0)
return;
}
int spawnCount;
float spawnPerc;
if (data.justOne)
{
if (data.didOne)
spawnCount = 0;
else
spawnCount = data.justOne;
spawnPerc = 1;
data.didOne = 1;
}
else if (data.useSpawnRate)
{
spawnCount = 0;
spawnPerc = 1;
data.counter += dt;
while (data.counter > data.spawnRate.x) // Faster than division
{
data.counter -= data.spawnRate.x;
spawnCount++;
}
}
else
{
float num = data.number.x * dt;
num += data.lastDTDifference;
spawnCount = int(num);
data.lastDTDifference = num - float(spawnCount);
if (spawnCount > 0)
spawnPerc = 1.0f / float(spawnCount);
}
if (spawnCount > 0)
{
// Avoid calling this until we know we actually need it for
// generating a particle (it has to apply the matrix chain,
// which is slow).
currentSpawn = getSpawnPosition();
if (lastSpawn.isZero())
lastSpawn = currentSpawn;
for (; spawnCount > 0; spawnCount--)
{
spawnParticle(spawnPerc);
}
lastSpawn = currentSpawn;
}
data.number.update(dt);
data.velocityMagnitude.update(dt);
data.spawnOffset.update(dt);
return;
}
int spawnCount;
float spawnPerc;
if (data.justOne)
{
if (data.didOne)
spawnCount = 0;
else
spawnCount = data.justOne;
spawnPerc = 1;
data.didOne = 1;
}
else
{
float num = data.number.x * dt;
num += data.lastDTDifference;
spawnCount = int(num);
data.lastDTDifference = num - float(spawnCount);
if (spawnCount > 0)
spawnPerc = 1.0f / float(spawnCount);
}
if (spawnCount > 0)
{
// Avoid calling this until we know we actually need it for
// generating a particle (it has to apply the matrix chain,
// which is slow).
currentSpawn = getSpawnPosition();
if (lastSpawn.isZero())
lastSpawn = currentSpawn;
for (; spawnCount > 0; spawnCount--)
{
spawnParticle(spawnPerc);
}
lastSpawn = currentSpawn;
}
data.number.update(dt);
}
void Emitter::start()

View file

@ -27,17 +27,19 @@ ParticleBank particleBank;
std::string ParticleManager::particleBankPath = "";
static int dummy_collideParticle(Vector pos)
{
return 0;
}
ParticleManager::ParticleManager(int size)
{
particleManager = this;
particles.resize(size);
used = 0;
free = 0;
oldFree = 0;
collideFunction = 0;
specialFunction = 0;
collideFunction = dummy_collideParticle;
numActive = 0;
@ -61,9 +63,8 @@ void ParticleManager::setSize(size_t size)
particles.resize(size);
this->size = size;
this->halfSize = size*0.5f;
free = oldFree = 0;
free = 0;
}
void ParticleManager::setNumSuckPositions(size_t num)
@ -104,31 +105,14 @@ void ParticleManager::updateParticle(Particle *p, float dt)
{
ParticleInfluence *pinf=0;
if (collideFunction)
if (collideFunction(p->pos))
{
if (collideFunction(p->pos))
{
const bool bounce = false;
if (bounce)
{
p->pos = p->lpos;
p->vel = -p->vel;
}
else
{
// fade out
p->vel = 0;
endParticle(p);
return;
}
}
// fade out
p->vel = 0;
endParticle(p);
return;
}
if (specialFunction)
{
specialFunction(p);
}
p->lpos = p->pos;
Influences::iterator i = influences.begin();
for (; i != influences.end(); i++)
{
@ -166,9 +150,6 @@ void ParticleManager::updateParticle(Particle *p, float dt)
p->emitter->hasRot = true;
}
p->lpos = p->pos;
if (p->life <= 0)
{
endParticle(p);
@ -205,14 +186,6 @@ void ParticleManager::nextFree(size_t jump)
free -= size;
}
void ParticleManager::setFree(size_t free)
{
if (free != -1)
{
this->free = free;
}
}
static const size_t spread = 8;
static const size_t spreadCheck = 128;
@ -220,9 +193,7 @@ static const size_t spreadCheck = 128;
Particle *ParticleManager::stomp()
{
int c = 0, idx = -1;
//int bFree = free;
Particle *p = 0;
bool exceed = false;
nextFree();
@ -230,7 +201,6 @@ Particle *ParticleManager::stomp()
{
if (c >= spreadCheck)
{
exceed = true;
break;
}
@ -241,13 +211,6 @@ Particle *ParticleManager::stomp()
}
while (p->active);
if (exceed)
{
}
endParticle(p);
p->index = idx;
return p;

View file

@ -23,6 +23,7 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
#include "Core.h"
#include "Quad.h"
#include "Randomness.h"
class Emitter;
class ParticleEffect;
@ -32,24 +33,14 @@ struct SpawnParticleData
SpawnParticleData();
float randomScale1, randomScale2;
float randomAlphaMod1, randomAlphaMod2;
enum { NO_SPAWN = 999 };
enum SpawnArea { SPAWN_CIRCLE=0, SPAWN_LINE };
float randomAlphaMod1, randomAlphaMod2; // both unused
int pauseLevel;
int flipH, flipV;
SpawnArea spawnArea;
float updateMultiplier;
InterpolatedVector velocityMagnitude;
int randomParticleAngleRange;
int randomVelocityRange;
float randomVelocityMagnitude;
int randomRotationRange;
InterpolatedVector initialVelocity, number, gravity;
Vector initialVelocity, gravity;
float randomSpawnRadius;
Vector randomSpawnMod;
int randomSpawnRadiusRange;
@ -57,16 +48,11 @@ struct SpawnParticleData
int justOne;
int copyParentRotation, copyParentFlip;
bool useSpawnRate;
bool calculateVelocityToCenter;
bool fadeAlphaWithLife, addAsChild;
int width, height;
InterpolatedVector scale, rotation, color, alpha, spawnOffset;
InterpolatedVector number, scale, rotation, color, alpha;
float life;
InterpolatedVector spawnRate;
std::string texture;
BlendType blendType;
float counter;
float spawnTimeOffset;
bool spawnLocal;
bool inheritColor;
@ -97,7 +83,6 @@ struct Particle
pos = Vector(0,0);
vel = Vector(0,0);
gvy = Vector(0,0);
lpos = Vector(0,0);
color = Vector(1,1,1);
alpha = 1;
scale = Vector(1,1);
@ -107,7 +92,7 @@ struct Particle
}
float life;
bool active;
Vector pos, vel, gvy, lpos;
Vector pos, vel, gvy;
InterpolatedVector color, alpha, scale, rot;
Emitter *emitter;
int index;
@ -139,11 +124,13 @@ protected:
void onRender(const RenderState& rs) const OVERRIDE;
void spawnParticle(float perc=1);
void onUpdate(float dt) OVERRIDE;
float randAngle();
ParticleEffect *pe;
typedef std::list<Particle*> Particles;
Particles particles;
FastRand rng;
};
class ParticleEffect : public RenderObject
@ -206,12 +193,9 @@ public:
void clearInfluences();
void addInfluence(ParticleInfluence inf);
int (*collideFunction)(Vector pos);
void (*specialFunction)(Particle *me);
void endParticle(Particle *p);
void setFree(size_t free);
size_t getFree() { return free; }
size_t getNumActive() { return numActive; }
@ -224,20 +208,16 @@ public:
protected:
std::vector<Vector> suckPositions;
size_t numActive;
Particle* stomp();
void nextFree(size_t f=1);
size_t oldFree;
typedef std::vector<ParticleInfluence> Influences;
Influences influences;
size_t size, used, free, halfSize;
size_t size, used, free;
Particles particles;

View file

@ -1,72 +0,0 @@
/*
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.
*/
#include "Particles.h"
SpawnParticleData::SpawnParticleData()
{
suckIndex = -1;
suckStr = 0;
randomScale1 = 1;
randomScale2 = 1;
randomAlphaMod1 = 1;
randomAlphaMod2 = 1;
influenced = 0;
spawnLocal = false;
useSpawnRate = false;
counter = 0;
life = 1;
blendType = BLEND_DEFAULT;
spawnRate = 1;
scale = Vector(1,1,1);
width = 64;
height = 64;
fadeAlphaWithLife = false;
color = Vector(1,1,1);
alpha = 1;
randomSpawnRadius = 0;
lastDTDifference = 0;
addAsChild = false;
randomRotationRange = 0;
number = 1;
randomParticleAngleRange = 0;
velocityMagnitude = 1;
calculateVelocityToCenter = false;
randomSpawnRadiusRange = 0;
randomSpawnMod = Vector(1,1);
spawnArea = SPAWN_CIRCLE;
randomVelocityMagnitude = 0;
randomVelocityRange = 360;
copyParentRotation = 0;
justOne = didOne = false;
flipH = flipV = 0;
spawnTimeOffset = 0;
pauseLevel = 0;
copyParentFlip = 0;
inheritColor = false;
inheritAlpha = false;
}