Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: code/branches/pickup2/src/modules/pickup/PickupSpawner.cc @ 6405

Last change on this file since 6405 was 6405, checked in by dafrick, 14 years ago

Commit changes in pickup before merge.

  • Property svn:eol-style set to native
File size: 8.9 KB
RevLine 
[2917]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:
23 *      Daniel 'Huty' Haggenmueller
24 *   Co-authors:
[6405]25 *      Damian 'Mozork' Frick
[2917]26 *
27 */
28
29/**
30    @file
31    @brief Implementation of PickupSpawner.
32*/
33
34#include "PickupSpawner.h"
[3196]35
[2917]36#include "core/CoreIncludes.h"
[6405]37//#include "core/GUIManager.h"     // HACK; see below
[3196]38#include "core/Template.h"
[2917]39#include "core/XMLPort.h"
[5735]40#include "worldentities/pawns/Pawn.h"
[6405]41//#include "PickupInventory.h"    // HACK; Only for hack, remove later
[2917]42
[3196]43
[2917]44namespace orxonox
45{
[5953]46
[6405]47//     const float PickupSpawner::bounceSpeed_s = 6.0f;
48//     const float PickupSpawner::rotationSpeed_s = 1.0f;
49//     const float PickupSpawner::bounceDistance_s = 4.0f;
[3046]50
[2917]51    CreateFactory(PickupSpawner);
52
53    /**
[5947]54    @brief
55        Constructor. Registers the PickupSpawner.
56    @param creator
57        Pointer to the object which created this item.
[2917]58    */
59    PickupSpawner::PickupSpawner(BaseObject* creator) : StaticEntity(creator)
60    {
[5953]61        this->initialize();
62    }
63
[6405]64    PickupSpawner::PickupSpawner(BaseObject* creator, Pickupable* pickup, float triggerDistance, float respawnTime, int maxSpawnedItems) : StaticEntity(creator)
[5953]65    {
66        this->initialize();
67 
[6405]68        this->pickup_ = pickup;
[5953]69
70        this->triggerDistance_ = triggerDistance;
71        this->respawnTime_ = respawnTime;
72        this->setMaxSpawnedItems(maxSpawnedItems);
73    }
74
75    void PickupSpawner::initialize(void)
76    {
[2917]77        RegisterObject(PickupSpawner);
78
[6405]79        this->pickup_ = NULL;
80       
[2917]81        this->triggerDistance_ = 20;
[6405]82        this->respawnTime_ = 0;
83        this->tickSum_ = 0;
[5953]84        this->maxSpawnedItems_ = INF;
85        this->spawnsRemaining_ = INF;
[2917]86    }
[5947]87
88    /**
89    @brief
90        Destructor.
91    */
[2917]92    PickupSpawner::~PickupSpawner()
93    {
[5947]94       
[2917]95    }
[5947]96
[2917]97    /**
[5947]98    @brief
99        Method for creating a PickupSpawner through XML.
100    @param xmlelement
101        XML element which contains the PickupSpawner.
102    @param mode
103        XMLPort mode.
[2917]104    */
105    void PickupSpawner::XMLPort(Element& xmlelement, XMLPort::Mode mode)
106    {
107        SUPER(PickupSpawner, XMLPort, xmlelement, mode);
108
[6405]109        XMLPortObject(PickupSpawner, Pickupable, "pickup", addPickupable, getPickupable, xmlelement, mode);
110       
[2917]111        XMLPortParam(PickupSpawner, "triggerDistance", setTriggerDistance, getTriggerDistance, xmlelement, mode);
112        XMLPortParam(PickupSpawner, "respawnTime", setRespawnTime, getRespawnTime, xmlelement, mode);
[5953]113        XMLPortParam(PickupSpawner, "maxSpawnedItems", setMaxSpawnedItems, getMaxSpawnedItems, xmlelement, mode);
[3063]114
[5947]115        //TODO: Kill hack.
[3063]116        // HACKs
117        // Load the GUI image as soon as the PickupSpawner gets loaded
118        //  = less delays while running
[6405]119//         BaseObject* newObject = this->itemTemplate_->getBaseclassIdentifier()->fabricate(this);
120//         BaseItem* asItem = orxonox_cast<BaseItem*>(newObject);
121//         if (asItem)
122//         {
123//             asItem->addTemplate(this->itemTemplate_);
124//             PickupInventory::getImageForItem(asItem);
125//             newObject->destroy();
126//         }
[3063]127
128        //  & load the GUI itself too, along with some empty windows
129        //   = even less delays
[6405]130//         GUIManager::getInstance().showGUI("PickupInventory");
131//         GUIManager::getInstance().executeCode("hideGUI(\"PickupInventory\")");
132//         PickupInventory::getSingleton();
[2917]133    }
[6405]134   
135    void PickupSpawner::addPickupable(Pickupable* pickup)
[2917]136    {
[6405]137        if(this->pickup_ != NULL)
138        {
139            COUT(1) << "addPickupable called, with this->pickup_ already set." << std::endl;
140            return;
141        }
142        if(pickup == NULL)
143        {
144            COUT(1) << "Argument of addPickupable is NULL." << std::endl;
145            return;
146        }
147       
148        this->pickup_ = pickup;
[2917]149    }
[6405]150   
151    Pickupable* PickupSpawner::getPickupable(void)
152    {
153        return this->pickup_;
154    }
[5947]155
[2917]156    /**
[5947]157    @brief
[6405]158        Invoked when the activity has changed. Sets visibility of attached objects.
[2917]159    */
[6405]160//     void PickupSpawner::changedActivity()
161//     {
162//         SUPER(PickupSpawner, changedActivity);
163//
164//         for (std::set<WorldEntity*>::const_iterator it = this->getAttachedObjects().begin(); it != this->getAttachedObjects().end(); it++)
165//             (*it)->setVisible(this->isActive());
166//     }
[5947]167
[5953]168    void PickupSpawner::setMaxSpawnedItems(int items)
169    {
170        this->maxSpawnedItems_ = items;
171        this->spawnsRemaining_ = items;
172    }
173
[2917]174    /**
[5947]175    @brief
176        Tick, checks if any Pawn is close enough to trigger.
177    @param dt
178        Time since last tick.
[2917]179    */
[6405]180    //TODO: Replace this with a real DistanceTrigger?
[2917]181    void PickupSpawner::tick(float dt)
182    {
[6405]183        //! If the PickupSpawner is active.
[2917]184        if (this->isActive())
185        {
[6405]186            //! Iterate trough all Pawns.
[5929]187            for (ObjectList<Pawn>::iterator it = ObjectList<Pawn>::begin(); it != ObjectList<Pawn>::end(); ++it)
[2917]188            {
189                Vector3 distance = it->getWorldPosition() - this->getWorldPosition();
[6405]190                //! If a Pawn, that fits the target-range of the item spawned by this Pickup, is in trigger-distance.
191                if (distance.length() < this->triggerDistance_ && this->pickup_->isTarget(*it))
192                {
[2917]193                    this->trigger(*it);
[6405]194                }
[2917]195            }
[5953]196
197            //! Animation.
[6405]198//             this->yaw(Radian(rotationSpeed_s*dt));
199//             this->tickSum_ += bounceSpeed_s*dt;
200//             this->translate(Vector3(0,bounceDistance_s*dt*sin(this->tickSum_),0));
201//             if (this->tickSum_ > 2*Ogre::Math::PI)
202//                 this->tickSum_ -= 2*Ogre::Math::PI;
[2917]203        }
204    }
[5947]205
[2917]206    /**
[5947]207    @brief
208        Trigger the PickupSpawner.
[2917]209
[5947]210        Adds the pickup to the Pawn that triggered,
211        sets the timer to re-activate and deactives the PickupSpawner.
[2917]212
[5947]213    @param pawn
214        Pawn which triggered the PickupSpawner.
[2917]215    */
216    void PickupSpawner::trigger(Pawn* pawn)
217    {
[6405]218        //TODO: If private, isActive doesn't need to be tested anymore.
219        if (this->isActive()) //!< Checks whether PickupItem is active.
[2917]220        {
[6405]221            Pickupable* pickup = this->getPickup();
222            if (pickup != NULL) //!< If everything went ok, and pickup is not NULL.
[2917]223            {
[6405]224                PickupCarrier* carrier = dynamic_cast<PickupCarrier*>(pawn);
225                if(carrier == NULL)
[2917]226                {
[6405]227                    COUT(1) << "This is bad. Pawn isn't PickupCarrier." << std::endl;
228                    return;
229                }
230               
231                if(pickup->pickup(carrier))
232                {
233                    COUT(3) << "Pickup got picked up." << std::endl;
[2917]234
[6405]235                    this->decrementSpawnsRemaining();
[2917]236                }
237                else
[5953]238                {
[6405]239                    pickup->destroy();
[5953]240                }
[2917]241            }
242        }
[6405]243    }
244   
245    void PickupSpawner::decrementSpawnsRemaining(void)
246    {
247        if(this->spawnsRemaining_ != INF)
248        {
249            this->spawnsRemaining_--;
250        }
251        if(this->spawnsRemaining_ != 0 && this->respawnTime_ > 0)
252        {
253            //TODO: Nicer?
254            this->respawnTimer_.setTimer(this->respawnTime_, false, createExecutor(createFunctor(&PickupSpawner::respawnTimerCallback, this)));
[5953]255
[6405]256            this->setActive(false);
257            this->fireEvent();
258        }
259        else
[5953]260        {
261            COUT(3) << "PickupSpawner empty, selfdistruct initialized." << std::endl;
262            this->setActive(false);
[6405]263            this->destroy(); //TODO: Implement destroy().
[5953]264        }
[2917]265    }
[5947]266
[2917]267    /**
[5947]268    @brief
[6405]269        Creates a new Pickupable.
[5953]270    @return
[6405]271        The Pickupable created.
[5953]272    */   
[6405]273    Pickupable* PickupSpawner::getPickup(void)
[5953]274    {
[6405]275        if(this->spawnsRemaining_ == 0)
276        {
277            COUT(1) << "Massive Error: PickupSpawner still alive until having spawned last item." << std::endl;
278            return NULL;
279        }
280       
281        Pickupable* pickup = this->pickup_->clone();
282        return pickup;
[5953]283    }
284
285    /**
286    @brief
[5947]287        Invoked by the timer, re-activates the PickupSpawner.
[2917]288    */
289    void PickupSpawner::respawnTimerCallback()
290    {
291        COUT(3) << "PickupSpawner reactivated." << std::endl;
292
293        this->setActive(true);
294    }
295}
Note: See TracBrowser for help on using the repository browser.