128 lines
4.2 KiB
C++
128 lines
4.2 KiB
C++
//
|
|
// SuperTuxKart - a fun racing game with go-kart
|
|
// Copyright (C) 2004-2015 Steve Baker <sjbaker1@airmail.net>
|
|
//
|
|
// This program 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 3
|
|
// 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 "graphics/explosion.hpp"
|
|
|
|
#include "audio/sfx_base.hpp"
|
|
#include "audio/sfx_manager.hpp"
|
|
#include "config/stk_config.hpp"
|
|
#include "config/user_config.hpp"
|
|
#include "graphics/irr_driver.hpp"
|
|
#include "graphics/material.hpp"
|
|
#include "graphics/material_manager.hpp"
|
|
#include "graphics/particle_emitter.hpp"
|
|
#include "graphics/particle_kind_manager.hpp"
|
|
#include "graphics/stk_particle.hpp"
|
|
#include "items/projectile_manager.hpp"
|
|
#include "race/race_manager.hpp"
|
|
#include "utils/vec3.hpp"
|
|
|
|
|
|
/** Creates an explosion effect. */
|
|
Explosion::Explosion(const Vec3& coord, const char* explosion_sound, const char * particle_file)
|
|
: HitSFX(coord, explosion_sound)
|
|
{
|
|
// short emision time, explosion, not constant flame
|
|
|
|
m_explosion_ticks = stk_config->time2Ticks(2.0f);
|
|
m_remaining_ticks = stk_config->time2Ticks(0.1f);
|
|
m_emission_frames = 0;
|
|
|
|
#ifndef SERVER_ONLY
|
|
std::string filename = particle_file;
|
|
|
|
#ifdef ANDROID
|
|
// Use a lower quality effect on Android for better performance
|
|
if (filename == "explosion.xml" ||
|
|
filename == "explosion_bomb.xml" ||
|
|
filename == "explosion_cake.xml")
|
|
{
|
|
filename = "explosion_low.xml";
|
|
}
|
|
#endif
|
|
|
|
ParticleKindManager* pkm = ParticleKindManager::get();
|
|
ParticleKind* particles = pkm->getParticles(filename);
|
|
m_emitter = NULL;
|
|
|
|
if (UserConfigParams::m_particles_effects > 1)
|
|
{
|
|
m_emitter = new ParticleEmitter(particles, coord, NULL);
|
|
m_emitter->getNode()->setPreGenerating(false);
|
|
}
|
|
#endif
|
|
} // Explosion
|
|
|
|
//-----------------------------------------------------------------------------
|
|
/** Destructor stops the explosion sfx from being played and frees its memory.
|
|
*/
|
|
Explosion::~Explosion()
|
|
{
|
|
#ifndef SERVER_ONLY
|
|
if(m_emitter)
|
|
{
|
|
delete m_emitter;
|
|
}
|
|
#endif
|
|
} // ~Explosion
|
|
|
|
//-----------------------------------------------------------------------------
|
|
/** Updates the explosion, called one per time step.
|
|
* \param dt Time step size.
|
|
* \return true If the explosion is finished.
|
|
*/
|
|
bool Explosion::updateAndDelete(int ticks)
|
|
{
|
|
// The explosion sfx is shorter than the particle effect,
|
|
// so no need to save the result of the update call.
|
|
HitSFX::updateAndDelete(ticks);
|
|
|
|
m_emission_frames++;
|
|
m_remaining_ticks -= ticks;
|
|
|
|
// Do nothing more if the animation is still playing
|
|
if (m_remaining_ticks>0) return false;
|
|
|
|
// Otherwise check that the sfx has finished, otherwise the
|
|
// sfx will get aborted 'in the middle' when this explosion
|
|
// object is removed.
|
|
if (m_remaining_ticks > -m_explosion_ticks)
|
|
{
|
|
#ifndef SERVER_ONLY
|
|
// if framerate is very low, emit for at least a few frames, in case
|
|
// burst time is lower than the time of 1 frame
|
|
if (m_emission_frames > 2 && m_emitter != NULL)
|
|
{
|
|
// Stop the emitter and wait a little while for all particles to have time to fade out
|
|
m_emitter->getNode()->getEmitter()->setMinParticlesPerSecond(0);
|
|
m_emitter->getNode()->getEmitter()->setMaxParticlesPerSecond(0);
|
|
}
|
|
#endif
|
|
}
|
|
else
|
|
{
|
|
// Sound and animation finished, node can be removed now.
|
|
// Returning true will cause this node to be deleted by
|
|
// the projectile manager.
|
|
return true; // finished
|
|
}
|
|
|
|
return false; // not finished
|
|
} // updateAndDelete
|
|
|