Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: code/branches/pickups2/src/orxonox/objects/pickup/PickupCollection.cc @ 2972

Last change on this file since 2972 was 2972, checked in by danielh, 15 years ago

Update

  • Minor changes in BaseItem
  • Updated to NotificationQueue from trunk (compile error with old)
  • Added PickupInventory for GUI handling
  • Added basic support for toLua++ methods
  • Property svn:eol-style set to native
File size: 12.3 KB
Line 
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:
25 *      ...
26 *
27 */
28
29/**
30    @file
31    @brief Implementation of PickupCollection.
32*/
33
34#include "PickupCollection.h"
35
36#include "BaseItem.h"
37#include "EquipmentItem.h"
38#include "PassiveItem.h"
39#include "UsableItem.h"
40
41#include "core/CoreIncludes.h"
42
43#include "objects/worldentities/pawns/Pawn.h"
44
45namespace orxonox
46{
47    //! Constructor
48    PickupCollection::PickupCollection()
49    {
50        this->bBlockRemovals_ = false;
51    }
52
53    /**
54        @brief
55            Add an item to the collection.
56           
57            Only adds the item if there's a free slot for it.
58
59        @param item Item to add to the collection.
60        @return Returns whether the item has been added to the collection.
61    */
62    bool PickupCollection::add(BaseItem* item)
63    {
64        if (this->checkSlot(item))
65        {
66            this->items_.insert( std::pair<std::string, BaseItem*> (item->getPickupIdentifier(), item) );
67            return true;
68        }
69        else
70            return false;
71    }
72    /**
73        @brief
74            Check if there's a free slot for an item.
75
76            Compares the amount of the item-type in the collection
77            against the maximal amount of the item that can be carried.
78
79        @param item Item to check for a slot.
80        @return Returns if there's a free slot for the item.
81    */
82    bool PickupCollection::checkSlot(BaseItem* item)
83    {
84        return (this->items_.count(item->getPickupIdentifier()) < item->getMaxCarryAmount());
85    }
86    /**
87        @brief
88            Empty the collection.
89
90            Calls dropped() on all the items in the collection,
91            then clears the collection.
92    */
93    void PickupCollection::clear()
94    {
95        this->bBlockRemovals_ = true;
96        for (std::multimap<std::string, BaseItem*>::iterator it = this->items_.begin(); it != this->items_.end(); it++)
97        {
98            if((*it).second && (*it).second->getOwner())
99                (*it).second->dropped((*it).second->getOwner());
100        }
101        this->items_.clear();
102        this->bBlockRemovals_ = false;
103    }
104    /**
105        @brief Check if an item/type of item is in the collection.
106        @param item Item to check.
107        @param anyOfType If it should look for any item of the item's type (default: false).
108        @return Whether the collection contains the item/type of item.
109    */
110    bool PickupCollection::contains(BaseItem* item, bool anyOfType)
111    {
112        if (anyOfType)
113        {
114            return (this->items_.count(item->getPickupIdentifier()) > 0);
115        }
116        else
117        {
118            std::multimap<std::string, BaseItem*>::_Pairii bounds = this->items_.equal_range(item->getPickupIdentifier());
119            for (std::multimap<std::string, BaseItem*>::iterator it = bounds.first; it != bounds.second && it != this->items_.end(); it++)
120            {
121                if ((*it).second == item)
122                {
123                    return true;
124                }
125            }
126            return false;
127        }
128    }
129    //! Uses the first usable item in the collection on the owner.
130    void PickupCollection::useItem()
131    {
132        Identifier* ident = Class(UsableItem);
133        for (std::multimap<std::string, BaseItem*>::iterator it = this->items_.begin(); it != this->items_.end(); it++)
134        {
135            if ((*it).second->isA(ident))
136            {
137                UsableItem* asUsable = dynamic_cast<UsableItem*>((*it).second);
138                asUsable->used(this->owner_);
139                return;
140            }
141        }
142    }
143    /**
144        @brief Uses a usable item on the owner of the collection.
145        @param item Item to use.
146    */
147    void PickupCollection::useItem(UsableItem* item)
148    {
149        if (item && this->owner_)
150            item->used(this->owner_);
151    }
152    /**
153        @brief Remove an item/all of a type from the collection.
154        @param item Item to remove.
155        @param removeAllOfType Whether to remove all the items with the item's type (default: false).
156    */
157    void PickupCollection::remove(BaseItem* item, bool removeAllOfType)
158    {
159        if (!item || !this->contains(item, removeAllOfType) || this->bBlockRemovals_)
160            return;
161
162        if (removeAllOfType)
163        {
164            std::multimap<std::string, BaseItem*>::iterator it;
165            while ((it = this->items_.find(item->getPickupIdentifier())) != this->items_.end())
166            {
167                this->items_.erase(it);
168            }
169        }
170        else
171        {
172            std::multimap<std::string, BaseItem*>::_Pairii bounds = this->items_.equal_range(item->getPickupIdentifier());
173            for (std::multimap<std::string, BaseItem*>::iterator it = bounds.first; it != bounds.second && it != this->items_.end(); it++)
174            {
175                if ((*it).second == item)
176                {
177                    this->items_.erase(it);
178                    return;
179                }
180            }
181        }
182    }
183    /**
184        @brief Add an additive modifier.
185        @param type ModifierType to add.
186        @param value Value for the modifier.
187    */
188    void PickupCollection::addAdditiveModifier(ModifierType::Enum type, float value)
189    {
190        this->additiveModifiers_.insert( std::pair<ModifierType::Enum, float>(type, value) );
191    }
192    /**
193        @brief Get the total amount of an additive modifier.
194        @param type Type for which to get the total.
195        @return Returns the sum of the additive modifiers of the type.
196    */
197    float PickupCollection::getAdditiveModifier(ModifierType::Enum type)
198    {
199        float v = 0.0f;
200
201        std::multimap<ModifierType::Enum, float>::_Pairii range = this->additiveModifiers_.equal_range(type);
202
203        for (std::multimap<ModifierType::Enum, float>::iterator it = range.first; it != range.second && it != this->additiveModifiers_.end(); it++)
204        {
205            v += (*it).second;
206        }
207
208        return v;
209    }
210    /**
211        @brief Remove an additive modifier.
212        @param type Type of modifier.
213        @param value Value which is to be removed.
214    */
215    void PickupCollection::removeAdditiveModifier(ModifierType::Enum type, float value)
216    {
217        std::multimap<ModifierType::Enum, float>::_Pairii range = this->additiveModifiers_.equal_range(type);
218        for (std::multimap<ModifierType::Enum, float>::iterator it = range.first; it != range.second && it != this->additiveModifiers_.end(); it++)
219        {
220            if ((*it).second == value)
221            {
222                this->additiveModifiers_.erase(it);
223                return;
224            }
225        }
226    }
227    /**
228        @brief Add a multiplicative modifier.
229        @param type ModifierType to add.
230        @param value Value for the modifier.
231    */
232    void PickupCollection::addMultiplicativeModifier(ModifierType::Enum type, float value)
233    {
234        this->multiplicativeModifiers_.insert( std::pair<ModifierType::Enum, float>(type, value) );
235    }
236    /**
237        @brief Get the total amount of a multiplicative modifier.
238        @param type Type for which to get the total.
239        @return Returns the product of the multiplicative modifiers of the type.
240    */
241    float PickupCollection::getMultiplicativeModifier(ModifierType::Enum type)
242    {
243        float v = 1.0f;
244
245        std::multimap<ModifierType::Enum, float>::_Pairii range = this->multiplicativeModifiers_.equal_range(type);
246        for (std::multimap<ModifierType::Enum, float>::iterator it = range.first; it != range.second && it != this->multiplicativeModifiers_.end(); it++)
247        {
248            v *= (*it).second;
249        }
250
251        return v;
252    }
253    /**
254        @brief Remove a multiplicative modifier.
255        @param type Type of modifier.
256        @param value Value which is to be removed.
257    */
258    void PickupCollection::removeMultiplicativeModifier(ModifierType::Enum type, float value)
259    {
260        std::multimap<ModifierType::Enum, float>::_Pairii range = this->multiplicativeModifiers_.equal_range(type);
261        for (std::multimap<ModifierType::Enum, float>::iterator it = range.first; it != range.second && it != this->multiplicativeModifiers_.end(); it++)
262        {
263            if ((*it).second == value)
264            {
265                this->multiplicativeModifiers_.erase(it);
266                return;
267            }
268        }
269    }
270    /**
271        @brief Applies modifiers to a float.
272        @param type Type of modifier tp apply.
273        @param inputValue Value which is to be processed.
274        @param addBeforeMultiplication Whether to apply the additive modifier before the multiplicative one (default: false).
275        @return Returns the value after being processed.
276    */
277    float PickupCollection::processModifiers(ModifierType::Enum type, float inputValue, bool addBeforeMultiplication)
278    {
279        float outputValue = inputValue;
280
281        if (addBeforeMultiplication)
282            outputValue += this->getAdditiveModifier(type);
283
284        outputValue *= this->getMultiplicativeModifier(type);
285
286        if (!addBeforeMultiplication)
287            outputValue += this->getAdditiveModifier(type);
288
289        return outputValue;
290    }
291    /**
292        @brief Applies modifiers to a Vector3.
293        @param type Type of modifier tp apply.
294        @param inputValue Value which is to be processed.
295        @param addBeforeMultiplication Whether to apply the additive modifier before the multiplicative one (default: false).
296        @return Returns the value after being processed.
297    */
298    Vector3 PickupCollection::processModifiers(ModifierType::Enum type, Vector3 inputValue, bool addBeforeMultiplication)
299    {
300        Vector3 outputValue = inputValue;
301
302        if (addBeforeMultiplication)
303            outputValue += Vector3(this->getAdditiveModifier(type));
304
305        outputValue *= this->getMultiplicativeModifier(type);
306
307        if (!addBeforeMultiplication)
308            outputValue += Vector3(this->getAdditiveModifier(type));
309
310        return outputValue;
311    }
312    /**
313        @brief Get a list of equipment-type items.
314        @return Returns a list of all the equipment-type items in the collection.
315    */
316    std::deque<EquipmentItem*> PickupCollection::getEquipmentItems()
317    {
318        std::deque<EquipmentItem*> ret;
319        Identifier* ident = Class(EquipmentItem);
320
321        for (std::multimap<std::string, BaseItem*>::iterator it = this->items_.begin(); it != this->items_.end(); it++)
322        {
323            if ((*it).second->isA(ident))
324                ret.push_back(dynamic_cast<EquipmentItem*>((*it).second));
325        }
326
327        return ret;
328    }
329    /**
330        @brief Get a list of passive items.
331        @return Returns a list of all the passive items in the collection.
332    */
333    std::deque<PassiveItem*> PickupCollection::getPassiveItems()
334    {
335        std::deque<PassiveItem*> ret;
336        Identifier* ident = Class(PassiveItem);
337
338        for (std::multimap<std::string, BaseItem*>::iterator it = this->items_.begin(); it != this->items_.end(); it++)
339        {
340            if ((*it).second->isA(ident))
341                ret.push_back(dynamic_cast<PassiveItem*>((*it).second));
342        }
343
344        return ret;
345    }
346    /**
347        @brief Get a list of usable items.
348        @return Returns a list of all the usable items in the collection.
349    */
350    std::deque<UsableItem*> PickupCollection::getUsableItems()
351    {
352        std::deque<UsableItem*> ret;
353        Identifier* ident = Class(UsableItem);
354
355        for (std::multimap<std::string, BaseItem*>::iterator it = this->items_.begin(); it != this->items_.end(); it++)
356        {
357            if ((*it).second->isA(ident))
358                ret.push_back(dynamic_cast<UsableItem*>((*it).second));
359        }
360
361        return ret;
362    }
363}
Note: See TracBrowser for help on using the repository browser.