Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: code/trunk/src/modules/weapons/projectiles/MineProjectile.cc @ 12273

Last change on this file since 12273 was 11071, checked in by landauf, 9 years ago

merged branch cpp11_v3 back to trunk

  • Property svn:eol-style set to native
File size: 9.2 KB
RevLine 
[10836]1/*
2 *   ORXONOX - the hottest 3D action shooter ever to exist
3 *                    > www.orxonox.net <
4 *
5 *
6 *   License notice:
7 *
8 *   This program is free software; you can redistribute it and/or
9 *   modify it under the terms of the GNU General Public License
10 *   as published by the Free Software Foundation; either version 2
11 *   of the License, or (at your option) any later version.
12 *
13 *   This program is distributed in the hope that it will be useful,
14 *   but WITHOUT ANY WARRANTY; without even the implied warranty of
15 *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16 *   GNU General Public License for more details.
17 *
18 *   You should have received a copy of the GNU General Public License
19 *   along with this program; if not, write to the Free Software
20 *   Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
21 *
22 *   Author:
[10908]23 *      Jannis Holzer
[10836]24 *      Fabien Vultier
25 *   Co-authors:
26 *      ...
27 *
28 */
29
30/**
31    @file MineProjectile.h
32    @brief Implementation of the MineProjectile class.
33*/
34
35#include "MineProjectile.h"
36
37#include "core/CoreIncludes.h"
[10908]38#include "graphics/Model.h"
[10897]39#include "core/command/Executor.h"
[10908]40#include "graphics/ParticleSpawner.h"
41#include "worldentities/pawns/Pawn.h"
[10897]42#include "core/EventIncludes.h"
[10908]43#include "sound/WorldSound.h"
[10836]44
45namespace orxonox
46{
47    RegisterClass(MineProjectile);
48
[10908]49    const float MineProjectile::collisionShapeRadius_ = 15.0f;
50    const float MineProjectile::damageRadius_ = 200.0f;
51    const float MineProjectile::triggerRadius_ = 100.0f;
52
[10889]53    MineProjectile::MineProjectile(Context* context) : MovableEntity(context), BasicProjectile()
[10836]54    {
55        RegisterObject(MineProjectile);
56
[10908]57        this->bAllowExplosion_ = false;
[10889]58        this->maxTimeUntilExplosion_ = 10.0f;
59        this->timeUntilActivation_ = 1.0f;
[10836]60
[10908]61        //Create movable entities
62        rings1_ = new MovableEntity(this->getContext());
63        this->attach(rings1_);
64        rings1_->setPosition(Vector3(0.0,0.0,0.0));
65        rings1_->setAngularVelocity(Vector3(0.0,5.0,0.0));
[10889]66
[10908]67        rings2_ = new MovableEntity(this->getContext());
68        this->attach(rings2_);
69        rings2_->setPosition(Vector3(0.0,0.0,0.0));
70        rings2_->setAngularVelocity(Vector3(0.0,0.0,5.0));
71
72        core_ = new MovableEntity(this->getContext());
73        this->attach(core_);
74        core_->setPosition(Vector3(0.0,0.0,0.0));
75        core_->setAngularVelocity(Vector3(2.5,2.5,0.0));
76
77        //Create Models
78        //Core
[10889]79        modelCore_ = new Model(this->getContext());
80        modelCore_->setMeshSource("Mine_Core.mesh");
81        modelCore_->setScale(15.0);
[10908]82        core_->attach(modelCore_);
[10889]83        modelCore_->setPosition(Vector3(0,0,0));
84
[10908]85        //Ring 1
[10889]86        modelRing1_ = new Model(this->getContext());
87        modelRing1_->setMeshSource("Mine_Ring.mesh");
88        modelRing1_->setScale(15.0);
[10908]89        rings1_->attach(modelRing1_);
[10889]90        modelRing1_->setPosition(Vector3(0,0,0));
91        modelRing1_->yaw(Degree(0));
[10908]92        //Ring 2
[10889]93        modelRing2_ = new Model(this->getContext());
94        modelRing2_->setMeshSource("Mine_Ring.mesh");
95        modelRing2_->setScale(15.0);
[10908]96        rings1_->attach(modelRing2_);
[10889]97        modelRing2_->setPosition(Vector3(0,0,0));
98        modelRing2_->yaw(Degree(180));
[10908]99        //Ring 3
100        modelRing3_ = new Model(this->getContext());
101        modelRing3_->setMeshSource("Mine_Ring.mesh");
102        modelRing3_->setScale(15.0);
103        rings2_->attach(modelRing3_);
104        modelRing3_->setPosition(Vector3(0,0,0));
105        modelRing3_->yaw(Degree(90));
106        //Ring 4
107        modelRing4_ = new Model(this->getContext());
108        modelRing4_->setMeshSource("Mine_Ring.mesh");
109        modelRing4_->setScale(15.0);
110        rings2_->attach(modelRing4_);
111        modelRing4_->setPosition(Vector3(0,0,0));
112        modelRing4_->yaw(Degree(270));
[10889]113
[11071]114        emitter_ = nullptr;
[10908]115
[10889]116        if (GameMode::isMaster())
117        {
118            this->setMass(10.0f);
[10911]119            this->setLinearDamping(0.5f);
120            this->setAngularDamping(0.1f);
[10889]121            this->enableCollisionCallback();
[10911]122            this->setCollisionResponse(true);
[11071]123            this->setCollisionType(CollisionType::Dynamic);
[10889]124
125            // Create a sphere collision shape and attach it to the projectile.
126            collisionShape_ = new SphereCollisionShape(this->getContext());
[10908]127            collisionShape_->setRadius(collisionShapeRadius_);
[10889]128            this->attachCollisionShape(collisionShape_);
[10908]129            collisionShape_->setPosition(Vector3(0,0,0));
[10889]130
131            // Create a distance trigger and attach it to the projectile.
132            distanceTrigger_ = new DistanceTrigger(this->getContext());
133            this->attach(distanceTrigger_);
134            distanceTrigger_->setPosition(Vector3(0,0,0));
[10908]135            distanceTrigger_->setDistance(triggerRadius_);
[10889]136            distanceTrigger_->addTarget("Pawn");
[10908]137            distanceTrigger_->setStayActive(false);
[10897]138
139            this->addEventSource(distanceTrigger_, "explode");
[10889]140        }
[10836]141    }
142
[10889]143    MineProjectile::~MineProjectile()
144    {
[10897]145        if (this->isInitialized())
[10889]146        {
[10908]147            modelCore_->destroy();
148            modelRing1_->destroy();
149            modelRing2_->destroy();
150            modelRing3_->destroy();
151            modelRing4_->destroy();
152
[10911]153            if (distanceTrigger_)
154            {
155                distanceTrigger_->destroy();
156            }
[10908]157            if (emitter_)
[10897]158            {
[10908]159                emitter_->destroy();
160            }
[10897]161        }
[10889]162    }
163
[10908]164    /**
165    @brief
[10944]166        XMLPort for MineProjectile.
[10908]167    */
[10897]168    void MineProjectile::XMLEventPort(Element& xmlelement, XMLPort::Mode mode)
169    {
170        SUPER(MineProjectile, XMLEventPort, xmlelement, mode);
[10908]171        XMLPortEventState(MineProjectile, BaseObject, "explode", explode, xmlelement, mode);
[10897]172    }
173
[10836]174    /**
175    @brief
[10944]176        Max Time; after this time runs out,the Mine explodes.
[10836]177    */
[10889]178    void MineProjectile::setMaxTimeUntilExplosion(float maxTimeUntilExplosion)
[10836]179    {
[10889]180        if (maxTimeUntilExplosion >= 0)
[10836]181        {
[10889]182            this->maxTimeUntilExplosion_ = maxTimeUntilExplosion;
183            if (GameMode::isMaster())
184            {
[10908]185                this->explodeTimer_.setTimer(this->maxTimeUntilExplosion_, false, createExecutor(createFunctor(&MineProjectile::explode, this)));
[10889]186            }
[10836]187        }
188        else
189        {
[10889]190            this->maxTimeUntilExplosion_ = 0;
[10836]191        }
192    }
193
194    /**
195    @brief
[10944]196        The mine can only explode when the activation time has run out.
[10836]197    */
[10889]198    void MineProjectile::setTimeUntilActivation(float timeUntilActivation)
199    {
200        timeUntilActivation_ = timeUntilActivation;
[10836]201
[10889]202        if (GameMode::isMaster())
203        {
[10908]204            this->activationTimer_.setTimer(this->timeUntilActivation_, false, createExecutor(createFunctor(&MineProjectile::allowExplosion, this)));
[10889]205        }
206    }
[10836]207
208    /**
209    @brief
[10944]210        Mine explodes, deals damage to pawn within range and destroys itself.
[10836]211    */
[10908]212    void MineProjectile::explode()
[10836]213    {
[10908]214        if (bAllowExplosion_)
215        {
216            if (GameMode::isMaster())
217            {
218                // Damage all pawns within the damage radius
[11071]219                for (Pawn* pawn : ObjectList<Pawn>())
[10908]220                {
[11071]221                    Vector3 distanceVector = pawn->getWorldPosition()-this->getWorldPosition();
[10908]222                    if(distanceVector.length()< damageRadius_)
223                    {
[11071]224                        pawn->hit(this->getShooter(), pawn->getWorldPosition(), nullptr, this->getDamage(), this->getHealthDamage(), this->getShieldDamage());
[10908]225                    }
226                }
227            }
[10836]228
[10908]229            this->destructionEffect();
230            this->destroyLater();
231        }
232    }
[10836]233
[10908]234    /**
235    @brief
[10944]236        Mine is ready to explode.
[10908]237    */
238    void MineProjectile::allowExplosion()
239    {
240        // Allow explosion
241        bAllowExplosion_ = true;
242        // Add particle effect
243        emitter_ = new ParticleEmitter(this->getContext());
244        this->attach(emitter_);
245        emitter_->setOrientation(this->getOrientation());
246        emitter_->setSource("Orxonox/mineparticle"); 
[10836]247    }
[10889]248
[10908]249    void MineProjectile::destructionEffect()
[10889]250    {
[10908]251        ParticleSpawner *effect1, *effect2, *effect3;
252       
253        effect1 = new ParticleSpawner(this->getContext());
254        effect2 = new ParticleSpawner(this->getContext());
255        effect3 = new ParticleSpawner(this->getContext());
[10889]256
[10908]257        effect1->setPosition(this->getPosition());
258        effect1->setOrientation(this->getOrientation());
259        effect1->setDestroyAfterLife(true);
260        effect1->setSource("Orxonox/MineExpl");
261        effect1->setLifetime(2.5f);
262
263        effect2->setPosition(this->getPosition());
264        effect2->setOrientation(this->getOrientation());
265        effect2->setDestroyAfterLife(true);
266        effect2->setSource("Orxonox/MineExpl1");
267        effect2->setLifetime(2.5f);
268
269        effect3->setPosition(this->getPosition());
270        effect3->setOrientation(this->getOrientation());
271        effect3->setDestroyAfterLife(true);
272        effect3->setSource("Orxonox/MineExpl2");
273        effect3->setLifetime(2.5f);
274
275        // Explosion sound effect.
276        WeakPtr<WorldSound> explosionSound_ = new WorldSound(getContext());
[10944]277        explosionSound_->setSource("sounds/minesound.ogg");
[10948]278        explosionSound_->setVolume(1.0);
[10908]279        explosionSound_->play();
[10889]280    }
[10836]281}
Note: See TracBrowser for help on using the repository browser.