- attempt to cleanup particles when a unit is deleted

This commit is contained in:
Mark Vejvoda 2010-09-06 17:52:33 +00:00
parent 58ab55a6aa
commit ca30612c9c
6 changed files with 120 additions and 49 deletions

View File

@ -477,6 +477,14 @@ void Renderer::manageParticleSystem(ParticleSystem *particleSystem, ResourceScop
particleManager[rs]->manage(particleSystem);
}
void Renderer::cleanupParticleSystems(vector<ParticleSystem *> &particleSystems, ResourceScope rs) {
particleManager[rs]->cleanupParticleSystems(particleSystems);
}
void Renderer::cleanupUnitParticleSystems(vector<UnitParticleSystem *> &particleSystems, ResourceScope rs) {
particleManager[rs]->cleanupUnitParticleSystems(particleSystems);
}
void Renderer::updateParticleManager(ResourceScope rs, int renderFps) {
particleManager[rs]->update(renderFps);
}

View File

@ -290,6 +290,8 @@ public:
Font2D *newFont(ResourceScope rs);
TextRenderer2D *getTextRenderer() const {return textRenderer;}
void manageParticleSystem(ParticleSystem *particleSystem, ResourceScope rs);
void cleanupParticleSystems(vector<ParticleSystem *> &particleSystems,ResourceScope rs);
void cleanupUnitParticleSystems(vector<UnitParticleSystem *> &particleSystems,ResourceScope rs);
void updateParticleManager(ResourceScope rs,int renderFps=-1);
void renderParticleManager(ResourceScope rs);
void swapBuffers();

View File

@ -200,7 +200,7 @@ Unit::Unit(int id, UnitPathInterface *unitpath, const Vec2i &pos, const UnitType
meetingPos= pos;
alive= true;
if (!type->hasSkillClass(scBeBuilt)) {
if (type->hasSkillClass(scBeBuilt) == false) {
float rot= 0.f;
random.init(id);
rot+= random.randRange(-5, 5);
@ -210,15 +210,19 @@ Unit::Unit(int id, UnitPathInterface *unitpath, const Vec2i &pos, const UnitType
}
// else it was set appropriately in setModelFacing()
if(getType()->getField(fAir)) currField=fAir;
if(getType()->getField(fLand)) currField=fLand;
if(getType()->getField(fAir)) {
currField = fAir;
}
if(getType()->getField(fLand)) {
currField = fLand;
}
fire= NULL;
computeTotalUpgrade();
//starting skill
this->currSkill=getType()->getFirstStOfClass(scStop);
this->currSkill = getType()->getFirstStOfClass(scStop);
SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",__FILE__,__FUNCTION__,__LINE__);
@ -246,13 +250,20 @@ Unit::~Unit(){
}
SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",__FILE__,__FUNCTION__,__LINE__);
//remove commands
while(!commands.empty()){
while(commands.empty() == false) {
delete commands.back();
commands.pop_back();
}
SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",__FILE__,__FUNCTION__,__LINE__);
// If the unit is not visible we better make sure we cleanup associated particles
if(this->getVisible() == false) {
Renderer::getInstance().cleanupUnitParticleSystems(unitParticleSystems,rsGame);
Renderer::getInstance().cleanupParticleSystems(fireParticleSystems,rsGame);
}
// fade(and by this remove) all unit particle systems
while(!unitParticleSystems.empty()){
while(unitParticleSystems.empty() == false) {
unitParticleSystems.back()->fade();
unitParticleSystems.pop_back();
}
@ -420,11 +431,11 @@ bool Unit::isBeingBuilt() const{
throw runtime_error(szBuf);
}
return currSkill->getClass()==scBeBuilt;
return (currSkill->getClass() == scBeBuilt);
}
bool Unit::isBuilt() const{
return !isBeingBuilt();
return (isBeingBuilt() == false);
}
bool Unit::isPutrefacting() const{
@ -485,7 +496,7 @@ bool Unit::isInteresting(InterestingUnitType iut) const {
// ====================================== set ======================================
void Unit::setCurrSkill(const SkillType *currSkill){
void Unit::setCurrSkill(const SkillType *currSkill) {
if(currSkill == NULL) {
char szBuf[4096]="";
sprintf(szBuf,"In [%s::%s Line: %d] ERROR: currSkill == NULL, Unit = [%s]\n",__FILE__,__FUNCTION__,__LINE__,this->toString().c_str());
@ -497,20 +508,19 @@ void Unit::setCurrSkill(const SkillType *currSkill){
throw runtime_error(szBuf);
}
if(currSkill->getClass()!=this->currSkill->getClass()){
if(currSkill->getClass() != this->currSkill->getClass()) {
animProgress= 0;
lastAnimProgress= 0;
while(!unitParticleSystems.empty()){
while(unitParticleSystems.empty() == false) {
unitParticleSystems.back()->fade();
unitParticleSystems.pop_back();
}
}
if(showUnitParticles && (!currSkill->unitParticleSystemTypes.empty()) &&
(unitParticleSystems.empty()) ){
for(UnitParticleSystemTypes::const_iterator it= currSkill->unitParticleSystemTypes.begin(); it!=currSkill->unitParticleSystemTypes.end(); ++it){
UnitParticleSystem *ups;
ups= new UnitParticleSystem(200);
if(showUnitParticles && (currSkill->unitParticleSystemTypes.empty() == false) &&
(unitParticleSystems.empty() == true) ) {
for(UnitParticleSystemTypes::const_iterator it= currSkill->unitParticleSystemTypes.begin(); it != currSkill->unitParticleSystemTypes.end(); ++it) {
UnitParticleSystem *ups = new UnitParticleSystem(200);
(*it)->setValues(ups);
ups->setPos(getCurrVector());
ups->setFactionColor(getFaction()->getTexture()->getPixmap()->getPixel3f(0,0));
@ -580,10 +590,10 @@ void Unit::setTargetPos(const Vec2i &targetPos){
void Unit::setVisible(const bool visible) {
this->visible = visible;
for(UnitParticleSystems::iterator it= unitParticleSystems.begin(); it!=unitParticleSystems.end(); ++it){
for(UnitParticleSystems::iterator it= unitParticleSystems.begin(); it != unitParticleSystems.end(); ++it) {
(*it)->setVisible(visible);
}
for(UnitParticleSystems::iterator it= damageParticleSystems.begin(); it!=damageParticleSystems.end(); ++it){
for(UnitParticleSystems::iterator it= damageParticleSystems.begin(); it != damageParticleSystems.end(); ++it) {
(*it)->setVisible(visible);
}
}
@ -975,31 +985,31 @@ bool Unit::update(){
if (fire!=NULL) {
fire->setPos(getCurrVector());
}
for(UnitParticleSystems::iterator it= unitParticleSystems.begin(); it!=unitParticleSystems.end(); ++it){
for(UnitParticleSystems::iterator it= unitParticleSystems.begin(); it != unitParticleSystems.end(); ++it) {
(*it)->setPos(getCurrVector());
(*it)->setRotation(getRotation());
}
for(UnitParticleSystems::iterator it= damageParticleSystems.begin(); it!=damageParticleSystems.end(); ++it){
for(UnitParticleSystems::iterator it= damageParticleSystems.begin(); it != damageParticleSystems.end(); ++it) {
(*it)->setPos(getCurrVector());
(*it)->setRotation(getRotation());
}
//checks
if(animProgress>1.f){
if(animProgress>1.f) {
animProgress= currSkill->getClass()==scDie? 1.f: 0.f;
}
bool return_value = false;
//checks
if(progress>=1.f){
if(progress>=1.f) {
lastRotation= targetRotation;
if(currSkill->getClass()!=scDie){
if(currSkill->getClass()!=scDie) {
progress= 0.f;
return_value = true;
}
else{
else {
progress= 1.f;
deadCount++;
if(deadCount>=maxDeadCount){
if(deadCount>=maxDeadCount) {
toBeUndertaken= true;
return_value = false;
}
@ -1483,14 +1493,14 @@ CommandResult Unit::undoCommand(Command *command){
void Unit::stopDamageParticles(){
// stop fire
if(fire!=NULL) {
if(fire != NULL) {
SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",__FILE__,__FUNCTION__,__LINE__);
fire->fade();
fire= NULL;
fire = NULL;
SystemFlags::OutputDebug(SystemFlags::debugSystem,"In [%s::%s Line: %d]\n",__FILE__,__FUNCTION__,__LINE__);
}
// stop additional particles
while(!damageParticleSystems.empty()) {
while(damageParticleSystems.empty() == false) {
damageParticleSystems.back()->fade();
damageParticleSystems.pop_back();
}
@ -1521,8 +1531,10 @@ void Unit::startDamageParticles(){
fps->setTexture(CoreData::getInstance().getFireTexture());
fps->setParticleSize(type->getSize()/3.f);
fire= fps;
fireParticleSystems.push_back(fps);
Renderer::getInstance().manageParticleSystem(fps, rsGame);
if(showUnitParticles){
if(showUnitParticles) {
// smoke
UnitParticleSystem *ups= new UnitParticleSystem(400);
ups->setColorNoEnergy(Vec4f(0.0f, 0.0f, 0.0f, 0.13f));

View File

@ -195,7 +195,7 @@ class Unit {
private:
typedef list<Command*> Commands;
typedef list<UnitObserver*> Observers;
typedef list<UnitParticleSystem*> UnitParticleSystems;
typedef vector<UnitParticleSystem*> UnitParticleSystems;
public:
static const float speedDivider;
@ -254,8 +254,9 @@ private:
Commands commands;
Observers observers;
UnitParticleSystems unitParticleSystems;
vector<UnitParticleSystem*> unitParticleSystems;
UnitParticleSystems damageParticleSystems;
vector<ParticleSystem*> fireParticleSystems;
CardinalDir modelFacing;

View File

@ -423,9 +423,9 @@ public:
// class ParticleManager
// =====================================================
class ParticleManager{
class ParticleManager {
private:
list<ParticleSystem*> particleSystems;
vector<ParticleSystem *> particleSystems;
public:
~ParticleManager();
@ -433,6 +433,10 @@ public:
void render(ParticleRenderer *pr, ModelRenderer *mr) const;
void manage(ParticleSystem *ps);
void end();
void cleanupParticleSystems(ParticleSystem *ps);
void cleanupParticleSystems(vector<ParticleSystem *> &particleSystems);
void cleanupUnitParticleSystems(vector<UnitParticleSystem *> &particleSystems);
int findParticleSystems(ParticleSystem *psFind, const vector<ParticleSystem *> &particleSystems) const;
};
}}//end namespace

View File

@ -905,11 +905,10 @@ ParticleManager::~ParticleManager(){
}
void ParticleManager::render(ParticleRenderer *pr, ModelRenderer *mr) const{
list<ParticleSystem*>::const_iterator it;
for (it=particleSystems.begin(); it!=particleSystems.end(); it++){
if((*it)->getVisible()){
(*it)->render(pr, mr);
for (int i = 0; i < particleSystems.size(); i++) {
ParticleSystem *ps = particleSystems[i];
if(ps != NULL && ps->getVisible()) {
ps->render(pr, mr);
}
}
}
@ -920,9 +919,10 @@ void ParticleManager::update(int renderFps) {
int particleSystemCount = particleSystems.size();
int particleCount = 0;
list<ParticleSystem *>::iterator it;
for (it = particleSystems.begin(); it != particleSystems.end(); it++) {
ParticleSystem *ps = *it;
vector<ParticleSystem *> cleanupParticleSystemsList;
for (int i = 0; i < particleSystems.size(); i++) {
ParticleSystem *ps = particleSystems[i];
if(ps != NULL) {
particleCount += ps->getAliveParticleCount();
@ -934,25 +934,69 @@ void ParticleManager::update(int renderFps) {
if(showParticle == true) {
ps->update();
if(ps->isEmpty()) {
delete ps;
*it= NULL;
//delete ps;
//*it= NULL;
cleanupParticleSystemsList.push_back(ps);
}
}
}
}
particleSystems.remove(NULL);
//particleSystems.remove(NULL);
cleanupParticleSystems(cleanupParticleSystemsList);
if(chrono.getMillis() > 0) SystemFlags::OutputDebug(SystemFlags::debugPerformance,"In [%s::%s] Line: %d took msecs: %lld, particleSystemCount = %d, particleCount = %d\n",__FILE__,__FUNCTION__,__LINE__,chrono.getMillis(),particleSystemCount,particleCount);
}
void ParticleManager::manage(ParticleSystem *ps){
int ParticleManager::findParticleSystems(ParticleSystem *psFind, const vector<ParticleSystem *> &particleSystems) const {
int result = -1;
for (int i = 0; i < particleSystems.size(); i++) {
ParticleSystem *ps = particleSystems[i];
if(ps != NULL && psFind != NULL && psFind == ps) {
result = i;
break;
}
}
return result;
}
void ParticleManager::cleanupParticleSystems(ParticleSystem *ps) {
int index = findParticleSystems(ps, this->particleSystems);
if(ps != NULL && index >= 0) {
delete ps;
this->particleSystems.erase(this->particleSystems.begin() + index);
}
}
void ParticleManager::cleanupParticleSystems(vector<ParticleSystem *> &particleSystems) {
for (int i = 0; i < particleSystems.size(); i++) {
ParticleSystem *ps = particleSystems[i];
cleanupParticleSystems(ps);
}
particleSystems.clear();
//this->particleSystems.remove(NULL);
}
void ParticleManager::cleanupUnitParticleSystems(vector<UnitParticleSystem *> &particleSystems) {
for (int i = 0; i < particleSystems.size(); i++) {
ParticleSystem *ps = particleSystems[i];
cleanupParticleSystems(ps);
}
particleSystems.clear();
//this->particleSystems.remove(NULL);
}
void ParticleManager::manage(ParticleSystem *ps) {
particleSystems.push_back(ps);
}
void ParticleManager::end(){
while(!particleSystems.empty()){
delete particleSystems.front();
particleSystems.pop_front();
void ParticleManager::end() {
while(particleSystems.empty() == false) {
delete particleSystems.back();
particleSystems.pop_back();
}
}