Index: code/trunk/src/modules/pickup/CMakeLists.txt
===================================================================
--- code/trunk/src/modules/pickup/CMakeLists.txt	(revision 6901)
+++ code/trunk/src/modules/pickup/CMakeLists.txt	(revision 7163)
@@ -1,3 +1,4 @@
 SET_SOURCE_FILES(PICKUP_SRC_FILES
+  CollectiblePickup.cc
   DroppedPickup.cc
   Pickup.cc
@@ -17,6 +18,4 @@
     PickupManager.h
     PickupRepresentation.h
-  DEFINE_SYMBOL
-    "PICKUP_SHARED_BUILD"
   PCH_FILE
     PickupPrecompiledHeaders.h
Index: code/trunk/src/modules/pickup/CollectiblePickup.cc
===================================================================
--- code/trunk/src/modules/pickup/CollectiblePickup.cc	(revision 7163)
+++ code/trunk/src/modules/pickup/CollectiblePickup.cc	(revision 7163)
@@ -0,0 +1,164 @@
+/*
+ *   ORXONOX - the hottest 3D action shooter ever to exist
+ *                    > www.orxonox.net <
+ *
+ *
+ *   License notice:
+ *
+ *   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 2
+ *   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., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ *
+ *   Author:
+ *      Damian 'Mozork' Frick
+ *   Co-authors:
+ *      ...
+ *
+ */
+
+/**
+    @file CollectiblePickup.cc
+    @brief Implementation of the CollectiblePickup class.
+*/
+
+#include "CollectiblePickup.h"
+
+#include "core/CoreIncludes.h"
+#include "PickupCollection.h"
+
+namespace orxonox {
+
+    /**
+    @brief
+        Constructor.
+        Registers the object and initializes variables.
+    */
+    CollectiblePickup::CollectiblePickup() : isInCollection_(false)
+    {
+        RegisterObject(CollectiblePickup);
+
+        this->collection_ = NULL;
+    }
+
+    /**
+    @brief
+        Destructor.
+    */
+    CollectiblePickup::~CollectiblePickup()
+    {
+
+    }
+
+    /**
+    @brief
+        Is called by OrxonoxClass::destroy() before the object is actually destroyed.
+    */
+    void CollectiblePickup::preDestroy(void)
+    {
+        this->Pickupable::preDestroy();
+
+        // The PickupCollection has to be destroyed as well.
+        if(this->isInCollection())
+            this->collection_->Pickupable::destroy();
+    }
+
+    /**
+    @brief
+        Destroys a Pickupable.
+    */
+    void CollectiblePickup::destroyPickup(void)
+    {
+        if(!this->isInCollection()) // If the CollectiblePickup is not in a PickupCollection the destroyPickup method of Pickupable is called.
+            this->Pickupable::destroyPickup();
+        else // Else the ColectiblePickup is dropped and disabled,
+        {
+            this->drop(false);
+            if(this->isInCollection() && this->isEnabled()) // It is only disabled if it is enabled and still ina PickupCollection after having been dropped.
+            {
+                this->setDisabled();
+                this->collection_->pickupDisabled();
+            }
+        }
+    }
+
+    /**
+    @brief
+        Is called by the PickupCarrier when it is being destroyed.
+    */
+    void CollectiblePickup::carrierDestroyed(void)
+    {
+        if(!this->isInCollection())
+            this->Pickupable::destroy();
+        else // If the CollectiblePickup is part of a PickupCollection it is just dropped instead of destroyed.
+            this->drop(false);
+    }
+
+    /**
+    @brief
+        Is called when the pickup has transited from used to unused or the other way around.
+    */
+    void CollectiblePickup::changedUsed(void)
+    {
+        SUPER(CollectiblePickup, changedUsed);
+
+        if(this->isInCollection())
+            this->collection_->pickupChangedUsed(this->isUsed());
+    }
+
+    /**
+    @brief
+        Is called when the pickup has transited from picked up to dropped or the other way around.
+    */
+    void CollectiblePickup::changedPickedUp(void)
+    {
+        SUPER(CollectiblePickup, changedPickedUp);
+
+        if(this->isInCollection())
+            this->collection_->pickupChangedPickedUp(this->isPickedUp());
+    }
+
+    /**
+    @brief
+        Adds this CollectiblePickup to the input PickupCollection.
+    @param collection
+        A pointer to the PickupCollection to which the CollectiblePickup should be added.
+    @return
+        Returns true if the CollectiblePickup was successfully added to the PickupCollection.
+    */
+    bool CollectiblePickup::addToCollection(PickupCollection* collection)
+    {
+        if(this->isInCollection() || collection == NULL) //If the CollectiblePickup already is in a PickupCollection or if the input pointer is NULL.
+            return false;
+
+        this->isInCollection_ = true;
+        this->collection_ = collection;
+        return true;
+    }
+
+    /**
+    @brief
+        Removes this CollectiblePickup from its PickupCollection.
+    @return
+        Returns true if the CollectiblePickup was succcessfully removed.
+    */
+    bool CollectiblePickup::removeFromCollection(void)
+    {
+        if(!this->isInCollection()) //If the CollectiblePickup is not in a PickupCollection.
+            return false;
+
+        this->isInCollection_ = false;
+        this->collection_ = NULL;
+        return true;
+    }
+
+}
Index: code/trunk/src/modules/pickup/CollectiblePickup.h
===================================================================
--- code/trunk/src/modules/pickup/CollectiblePickup.h	(revision 7163)
+++ code/trunk/src/modules/pickup/CollectiblePickup.h	(revision 7163)
@@ -0,0 +1,82 @@
+/*
+ *   ORXONOX - the hottest 3D action shooter ever to exist
+ *                    > www.orxonox.net <
+ *
+ *
+ *   License notice:
+ *
+ *   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 2
+ *   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., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ *
+ *   Author:
+ *      Damian 'Mozork' Frick
+ *   Co-authors:
+ *      ...
+ *
+ */
+
+/**
+    @file CollectiblePickup.h
+    @brief Definition of the CollectiblePickup class.
+*/
+
+#ifndef _CollectiblePickup_H__
+#define _CollectiblePickup_H__
+
+#include "pickup/PickupPrereqs.h"
+
+#include "interfaces/Pickupable.h"
+
+namespace orxonox {
+
+    /**
+    @brief
+        Collectible Pickup class. Any pickup inheriting from this class can be added to a PickupCollection and thus be part uf such.
+    @author
+        Damian 'Mozork' Frick
+    */
+    class _PickupExport CollectiblePickup : public Pickupable
+    {
+
+        public:
+            CollectiblePickup(); //!< Constructor.
+            virtual ~CollectiblePickup(); //! Destructor.
+
+            virtual void changedUsed(void); //!< Is called when the pickup has transited from used to unused or the other way around.
+            virtual void changedPickedUp(void); //!< Is called when the pickup has transited from picked up to dropped or the other way around.
+
+            /**
+            @brief Check whether the given CollectiblePickup is par of a PickupCollection.
+            @return Returns true if the ColelctiblePickup is part of a PickupCollection.
+            */
+            bool isInCollection(void)
+                { return this->isInCollection_; }
+            
+            bool addToCollection(PickupCollection* collection); //!< Adds this CollectiblePickup to the input PickupCollection.
+            bool removeFromCollection(void); //!< Removes this CollectiblePickup from its PickupCollection.
+
+            void carrierDestroyed(void); //!< Is called by the PickupCarrier when it is being destroyed.
+
+        protected:
+            virtual void preDestroy(void); //!< Is called by OrxonoxClass::destroy() before the object is actually destroyed.
+            virtual void destroyPickup(void); //!< //!< Destroys a Pickupable.
+
+        private:
+            bool isInCollection_; //!< True if the CollectiblePickup is in a PickupCollection.
+            PickupCollection* collection_; //!< A pointer to the PickupCollection this CollectiblePickup is in.
+
+    };
+}
+
+#endif // _CollectiblePickup_H__
Index: code/trunk/src/modules/pickup/DroppedPickup.cc
===================================================================
--- code/trunk/src/modules/pickup/DroppedPickup.cc	(revision 6901)
+++ code/trunk/src/modules/pickup/DroppedPickup.cc	(revision 7163)
@@ -41,7 +41,7 @@
 namespace orxonox
 {
-    
+
     CreateFactory(DroppedPickup);
-    
+
     /**
     @brief
@@ -51,5 +51,5 @@
     {
         RegisterObject(DroppedPickup);
-        
+
     }
 
@@ -67,10 +67,10 @@
     */
     DroppedPickup::DroppedPickup(BaseObject* creator, Pickupable* pickup, PickupCarrier* carrier, float triggerDistance) : PickupSpawner(creator, pickup, triggerDistance, 5, 1)
-    {   
+    {
         RegisterObject(DroppedPickup);
 
         this->setPosition(carrier->getCarrierPosition());
         this->setActive(false);
-        
+
         //TODO: Do more elegantly.
         this->startRespawnTimer();
Index: code/trunk/src/modules/pickup/DroppedPickup.h
===================================================================
--- code/trunk/src/modules/pickup/DroppedPickup.h	(revision 6901)
+++ code/trunk/src/modules/pickup/DroppedPickup.h	(revision 7163)
@@ -41,5 +41,5 @@
 namespace orxonox
 {
-    
+
     /**
     @brief
Index: code/trunk/src/modules/pickup/Pickup.cc
===================================================================
--- code/trunk/src/modules/pickup/Pickup.cc	(revision 6901)
+++ code/trunk/src/modules/pickup/Pickup.cc	(revision 7163)
@@ -48,4 +48,6 @@
     /*static*/ const std::string Pickup::durationTypeOnce_s = "once";
     /*static*/ const std::string Pickup::durationTypeContinuous_s = "continuous";
+
+    CreateUnloadableFactory(Pickup);
 
     Pickup::Pickup(BaseObject* creator) : BaseObject(creator)
@@ -146,9 +148,9 @@
     void Pickup::setActivationType(const std::string& type)
     {
-        if(type == activationTypeImmediate_s)
+        if(Pickup::activationTypeImmediate_s.compare(type) == 0)
         {
             this->activationType_ = pickupActivationType::immediate;
         }
-        else if(type == activationTypeOnUse_s)
+        else if(Pickup::activationTypeOnUse_s.compare(type) == 0)
         {
             this->activationType_ = pickupActivationType::onUse;
@@ -168,9 +170,9 @@
     void Pickup::setDurationType(const std::string& type)
     {
-        if(type == durationTypeOnce_s)
+        if(Pickup::durationTypeOnce_s.compare(type) == 0)
         {
             this->durationType_ = pickupDurationType::once;
         }
-        else if(type == durationTypeContinuous_s)
+        else if(Pickup::durationTypeContinuous_s.compare(type) == 0)
         {
             this->durationType_ = pickupDurationType::continuous;
@@ -192,5 +194,5 @@
 
         //! Sets the Pickup to used if the Pickup has activation type 'immediate' and gets picked up.
-        if(this->getCarrier() != NULL && this->isPickedUp() && this->isImmediate())
+        if(this->isPickedUp() && this->isImmediate())
         {
             this->setUsed(true);
Index: code/trunk/src/modules/pickup/Pickup.h
===================================================================
--- code/trunk/src/modules/pickup/Pickup.h	(revision 6901)
+++ code/trunk/src/modules/pickup/Pickup.h	(revision 7163)
@@ -40,5 +40,5 @@
 #include "core/XMLPort.h"
 
-#include "interfaces/Pickupable.h"
+#include "CollectiblePickup.h"
 
 #include "tools/Timer.h"
@@ -74,11 +74,9 @@
         Damian 'Mozork' Frick
     */
-    class _PickupExport Pickup : public Pickupable, public BaseObject
+    class _PickupExport Pickup : public CollectiblePickup, public BaseObject
     {
 
-        protected:
+        public:
             Pickup(BaseObject* creator); //!< Constructor.
-
-        public:
             virtual ~Pickup(); //!< Destructor.
 
@@ -167,5 +165,5 @@
         private:
             void initialize(void); //!< Initializes the member variables.
-            
+
             //TODO: Problems, when there are more Timers needed? Solutions?
             Timer durationTimer_; //!< Timer at the disposal of each Class implementing Pickup.
Index: code/trunk/src/modules/pickup/PickupCollection.cc
===================================================================
--- code/trunk/src/modules/pickup/PickupCollection.cc	(revision 6901)
+++ code/trunk/src/modules/pickup/PickupCollection.cc	(revision 7163)
@@ -35,4 +35,5 @@
 #include "core/XMLPort.h"
 #include "interfaces/PickupCarrier.h"
+#include "CollectiblePickup.h"
 #include "DroppedPickup.h"
 #include "PickupCollectionIdentifier.h"
@@ -42,5 +43,5 @@
 namespace orxonox
 {
- 
+
     CreateFactory(PickupCollection);
 
@@ -52,8 +53,13 @@
     {
         RegisterObject(PickupCollection);
-        
+
         this->pickupCollectionIdentifier_ = new PickupCollectionIdentifier(this);
-    }
-    
+        this->usedCounter_ = 0;
+        this->pickedUpCounter_ = 0;
+        this->disabledCounter_ = 0;
+        this->processingUsed_ = false;
+        this->processingPickedUp_ = false;
+    }
+
     /**
     @brief
@@ -62,12 +68,13 @@
     PickupCollection::~PickupCollection()
     {
-        //! Destroy all Pickupables constructing this PickupCollection.
-        for(std::vector<WeakPtr<Pickupable> >::iterator it = this->pickups_.begin(); it != this->pickups_.end(); it++)
-        {
-            if((*it).get() != NULL)
-                (*it).get()->destroy();
-        }
-    }
-    
+        // Destroy all Pickupables constructing this PickupCollection.
+        for(std::vector<CollectiblePickup*>::iterator it = this->pickups_.begin(); it != this->pickups_.end(); it++)
+        {
+            (*it)->removeFromCollection();
+            (*it)->destroy();
+        }
+        this->pickups_.clear();
+    }
+
     /**
     @brief
@@ -77,10 +84,10 @@
     {
         SUPER(PickupCollection, XMLPort, xmlelement, mode);
-        
-        XMLPortObject(PickupCollection, Pickupable, "pickupables", addPickupable, getPickupable, xmlelement, mode);
-        
+
+        XMLPortObject(PickupCollection, CollectiblePickup, "pickupables", addPickupable, getPickupable, xmlelement, mode);
+
         this->initializeIdentifier();
     }
-    
+
     /**
     @brief
@@ -89,10 +96,10 @@
     void PickupCollection::initializeIdentifier(void)
     {
-        for(std::vector<WeakPtr<Pickupable> >::iterator it = this->pickups_.begin(); it != this->pickups_.end(); it++)
-        {
-            this->pickupCollectionIdentifier_->addPickup((*it).get()->getPickupIdentifier());
-        }
-    }
-    
+        for(std::vector<CollectiblePickup*>::iterator it = this->pickups_.begin(); it != this->pickups_.end(); it++)
+        {
+            this->pickupCollectionIdentifier_->addPickup((*it)->getPickupIdentifier());
+        }
+    }
+
     /**
     @brief
@@ -103,12 +110,35 @@
     {
         SUPER(PickupCollection, changedUsed);
-        
-        //! Change used for all Pickupables this PickupCollection consists of.
-        for(std::vector<WeakPtr<Pickupable> >::iterator it = this->pickups_.begin(); it != this->pickups_.end(); it++)
-        {
-            (*it).get()->setUsed(this->isUsed());
-        }
-    }
-    
+
+        this->processingUsed_ = true;
+        // Change used for all Pickupables this PickupCollection consists of.
+        for(std::vector<CollectiblePickup*>::iterator it = this->pickups_.begin(); it != this->pickups_.end(); it++)
+        {
+            (*it)->setUsed(this->isUsed());
+        }
+        this->processingUsed_ = false;
+
+        this->changedUsedAction();
+    }
+
+    /**
+    @brief
+        Helper method.
+        Checks whether due to changes in the used status of the pickups of this PickupCollection the used status of this PickupCollection has to change as well.
+    */
+    void PickupCollection::changedUsedAction(void)
+    {
+        if(this->processingUsed_)
+            return;
+
+        // If all the pickups are not in use but the PickupCollection is.
+        if(this->usedCounter_ == 0 && this->isUsed())
+            this->setUsed(false);
+
+        // If all the enabled pickups are in use but the PickupCollection is not.
+        if(this->usedCounter_ != 0 && this->usedCounter_ == this->pickups_.size()-this->disabledCounter_ && !this->isUsed())
+            this->setUsed(true);
+    }
+
     /**
     @brief
@@ -119,12 +149,15 @@
     {
         SUPER(PickupCollection, changedCarrier);
-        
-        //! Change the PickupCarrier for all Pickupables this PickupCollection consists of.
-        for(std::vector<WeakPtr<Pickupable> >::iterator it = this->pickups_.begin(); it != this->pickups_.end(); it++)
-        {
-            (*it).get()->setCarrier(this->getCarrier()->getTarget(*it));
-        }
-    }
-    
+
+        // Change the PickupCarrier for all Pickupables this PickupCollection consists of.
+        for(std::vector<CollectiblePickup*>::iterator it = this->pickups_.begin(); it != this->pickups_.end(); it++)
+        {
+            if(this->getCarrier() == NULL)
+                (*it)->setCarrier(NULL);
+            else
+                (*it)->setCarrier(this->getCarrier()->getTarget(*it));
+        }
+    }
+
     /**
     @brief
@@ -135,12 +168,35 @@
     {
         SUPER(PickupCollection, changedPickedUp);
-        
-        //! Change the pickedUp status for all Pickupables this PickupCollection consists of.
-        for(std::vector<WeakPtr<Pickupable> >::iterator it = this->pickups_.begin(); it != this->pickups_.end(); it++)
-        {
-            (*it).get()->setPickedUp(this->isPickedUp());
-        }
-    }
-    
+
+        this->processingPickedUp_ = true;
+        // Change the pickedUp status for all Pickupables this PickupCollection consists of.
+        for(std::vector<CollectiblePickup*>::iterator it = this->pickups_.begin(); it != this->pickups_.end(); it++)
+        {
+            (*it)->setPickedUp(this->isPickedUp());
+        }
+        this->processingPickedUp_ = false;
+
+        this->changedPickedUpAction();
+    }
+
+    /**
+    @brief
+        Helper method.
+        Checks whether due to changes in the picked up status of the pickups of this PickupCollection the picked up status of this PickupCollection has to change as well.
+    */
+    void PickupCollection::changedPickedUpAction(void)
+    {
+        if(this->processingPickedUp_)
+            return;
+
+        // If at least all the enabled pickups of this PickupCollection are no longer picked up. 
+        if(this->pickedUpCounter_ <= this->disabledCounter_ && this->isPickedUp())
+            this->Pickupable::destroy();
+
+        // If the PickupCollection is no longer picked up.
+        if(!this->isPickedUp())
+            this->pickedUpCounter_ = 0;
+    }
+
     /**
     @brief
@@ -154,18 +210,19 @@
         if(item == NULL)
             item = new PickupCollection(this);
-        
+
         SUPER(PickupCollection, clone, item);
-        
+
         PickupCollection* pickup = dynamic_cast<PickupCollection*>(item);
-        //! Clone all Pickupables this PickupCollection consist of.
-        for(std::vector<WeakPtr<Pickupable> >::iterator it = this->pickups_.begin(); it != this->pickups_.end(); it++)
-        {
-            Pickupable* newPickup = (*it).get()->clone();
-            pickup->addPickupable(newPickup);
+        // Clone all Pickupables this PickupCollection consist of.
+        for(std::vector<CollectiblePickup*>::iterator it = this->pickups_.begin(); it != this->pickups_.end(); it++)
+        {
+            Pickupable* newPickup = (*it)->clone();
+            CollectiblePickup* collectible = static_cast<CollectiblePickup*>(newPickup);
+            pickup->addPickupable(collectible);
         }
 
         pickup->initializeIdentifier();
     }
-    
+
     /**
     @brief
@@ -178,13 +235,13 @@
     bool PickupCollection::isTarget(PickupCarrier* carrier) const
     {
-        for(std::vector<WeakPtr<Pickupable> >::const_iterator it = this->pickups_.begin(); it != this->pickups_.end(); it++)
-        {
-            if(!carrier->isTarget((*it).get()))
+        for(std::vector<CollectiblePickup*>::const_iterator it = this->pickups_.begin(); it != this->pickups_.end(); it++)
+        {
+            if(!carrier->isTarget(*it))
                 return false;
         }
-        
+
         return true;
     }
-    
+
     /**
     @brief
@@ -198,5 +255,5 @@
         return this->pickupCollectionIdentifier_;
     }
-    
+
     /**
     @brief
@@ -207,14 +264,14 @@
         Returns true if successful,
     */
-    bool PickupCollection::addPickupable(Pickupable* pickup)
+    bool PickupCollection::addPickupable(CollectiblePickup* pickup)
     {
         if(pickup == NULL)
             return false;
-        
-        WeakPtr<Pickupable> ptr = pickup; //!< Create a weak pointer to be able to test in the constructor if the Pointer is still valid.
-        this->pickups_.push_back(ptr);
+
+        pickup->addToCollection(this);
+        this->pickups_.push_back(pickup);
         return true;
     }
-    
+
     /**
     @brief
@@ -227,7 +284,51 @@
     const Pickupable* PickupCollection::getPickupable(unsigned int index)
     {
-        return this->pickups_[index].get();
-    }
-        
+        return this->pickups_[index];
+    }
+
+    /**
+    @brief
+        Informs the PickupCollection, that one of its pickups has changed its used status to the input value.
+        This is used internally by the CollectiblePickup class.
+    @param changed
+        The value the used status has changed to. 
+    */
+    void PickupCollection::pickupChangedUsed(bool changed)
+    {
+        if(changed)
+            this->usedCounter_++;
+        else
+            this->usedCounter_--;
+
+        this->changedUsedAction();
+    }
+
+    /**
+    @brief
+        Informs the PickupCollection, that one of its pickups has changed its picked up status to the input value.
+        This is used internally by the CollectiblePickup class.
+    @param changed
+        The value the picked up status has changed to.
+    */
+    void PickupCollection::pickupChangedPickedUp(bool changed)
+    {
+        if(changed)
+            this->pickedUpCounter_++;
+        else
+            this->pickedUpCounter_--;
+
+        this->changedPickedUpAction();
+    }
+
+    /**
+    @brief
+        Informs the PickupCollection, that one of its pickups has been disabled.
+        This is used internally by the CollectiblePickup class.
+    */
+    void PickupCollection::pickupDisabled(void)
+    {
+        this->disabledCounter_++;
+    }
+
     /**
     @brief
@@ -245,4 +346,4 @@
         return true;
     }
-    
+
 }
Index: code/trunk/src/modules/pickup/PickupCollection.h
===================================================================
--- code/trunk/src/modules/pickup/PickupCollection.h	(revision 6901)
+++ code/trunk/src/modules/pickup/PickupCollection.h	(revision 7163)
@@ -37,6 +37,6 @@
 #include "PickupPrereqs.h"
 
-#include "interfaces/Pickupable.h"
 #include "core/BaseObject.h"
+#include "CollectiblePickup.h"
 
 #include <list>
@@ -47,16 +47,15 @@
     /**
     @brief
-        The PickupCollection combines different Pickupables to a coherent, single pickup and makes the seem (from the outside looking in) just as if they were just one Pickupable.
+        The PickupCollection combines different Pickupables to a coherent, single pickup and makes them seem (from the outside looking in) just as if they were just one Pickupable.
     @author
         Damian 'Mozork' Frick
     */
-    class _PickupExport PickupCollection : public Pickupable, public BaseObject
+    class _PickupExport PickupCollection : public CollectiblePickup, public BaseObject
     {
-        
+
         public:
-            
             PickupCollection(BaseObject* creator); //!< Default Constructor.
             virtual ~PickupCollection(); //!< Destructor.
-            
+
             virtual void XMLPort(Element& xmlelement, XMLPort::Mode mode); //!< Creates an instance of this Class through XML.
 
@@ -64,27 +63,40 @@
             virtual void changedCarrier(void); //!< Is called when the pickup has changed its PickupCarrier.
             virtual void changedPickedUp(void); //!< Is called when the pickup has transited from picked up to dropped or the other way around.
-            
+
             virtual void clone(OrxonoxClass*& item); //!< Creates a duplicate of the input OrxonoxClass.
-            
+
             virtual bool isTarget(PickupCarrier* carrier) const; //!< Get whether a given class, represented by the input Identifier, is a target of this PickupCollection.
-            
+
             virtual const PickupIdentifier* getPickupIdentifier(void); //!< Get the PickupIdentifier of this PickupCollection.
-            
-            bool addPickupable(Pickupable* pickup); //!< Add the input Pickupable to list of Pickupables combined by this PickupCollection.
+
+            bool addPickupable(CollectiblePickup* pickup); //!< Add the input Pickupable to list of Pickupables combined by this PickupCollection.
             const Pickupable* getPickupable(unsigned int index); //!< Get the Pickupable at the given index.
-            
+
+            void pickupChangedUsed(bool changed); //!< Informs the PickupCollection, that one of its pickups has changed its used status to the input value.
+            void pickupChangedPickedUp(bool changed); //!< Informs the PickupCollection, that one of its pickups has changed its picked up status to the input value.
+            void pickupDisabled(void); //!< Informs the PickupCollection, that one of its pickups has been disabled.
+
         protected:
             void initializeIdentifier(void); //!< Initializes the PickupIdentifier for this pickup.
+
+            virtual bool createSpawner(void); //!< Facilitates the creation of a PickupSpawner upon dropping of the Pickupable.
+
+            PickupCollectionIdentifier* pickupCollectionIdentifier_; //!< The PickupCollectionIdentifier of this PickupCollection. Is used to distinguish different PickupCollections amongst themselves.
+
+        private:
+            void changedUsedAction(void); //!< Helper method.
+            void changedPickedUpAction(void); //!< Helper method.
             
-            virtual bool createSpawner(void); //!< Facilitates the creation of a PickupSpawner upon dropping of the Pickupable.
-            
-            PickupCollectionIdentifier* pickupCollectionIdentifier_; //!< The PickupCollectionIdentifier of this PickupCollection. Is used to distinguish different PickupCollections amongst themselves.
-            
-        private:
-            
-            std::vector<WeakPtr<Pickupable> > pickups_; //!< The list of the pointers of all the Pickupables this PickupCollection consists of. They are weak pointers to facilitate testing, whether the pointers are still valid.
-        
+            std::vector<CollectiblePickup*> pickups_; //!< The list of the pointers of all the Pickupables this PickupCollection consists of. They are weak pointers to facilitate testing, whether the pointers are still valid.
+
+            unsigned int usedCounter_; //!< Keeps track of the number of pickups of this PickupCollection, that are in use.
+            unsigned int pickedUpCounter_; //!< Keeps track of the number of pickups of this PickupCollection, that are picked up.
+            unsigned int disabledCounter_; //!< Keeps track of the number of pickups of this PickupCollection, that are disabled.
+
+            bool processingUsed_; //!< Boolean to ensure, that the PickupCollection doesn't update its used status while its internal state is inconsistent.
+            bool processingPickedUp_; //!< Boolean to ensure, that the PickupCollection doesn't update its picked upp status while its internal state is inconsistent.
+
     };
-    
+
 }
 
Index: code/trunk/src/modules/pickup/PickupCollectionIdentifier.cc
===================================================================
--- code/trunk/src/modules/pickup/PickupCollectionIdentifier.cc	(revision 6901)
+++ code/trunk/src/modules/pickup/PickupCollectionIdentifier.cc	(revision 7163)
@@ -38,5 +38,5 @@
 namespace orxonox
 {
-    
+
     /**
     @brief
@@ -47,5 +47,5 @@
         RegisterObject(PickupCollectionIdentifier);
     }
-    
+
     /**
     @brief
@@ -54,5 +54,5 @@
     PickupCollectionIdentifier::~PickupCollectionIdentifier()
     {
-        
+
     }
 
@@ -67,23 +67,23 @@
     int PickupCollectionIdentifier::compare(const PickupIdentifier* identifier) const
     {
-        //! Slight un-niceity to cast the PickupIdentifier to a PickupCollectionIdentifier.
+        // Slight un-niceity to cast the PickupIdentifier to a PickupCollectionIdentifier.
         PickupIdentifier* temp = const_cast<PickupIdentifier*>(identifier);
         const PickupCollectionIdentifier* collectionIdentifier = dynamic_cast<PickupCollectionIdentifier*>(temp);
-        
-        //! If the input PickupIdentifier 'identifier' is no PickupCollectionIdentifier then just the two PickupIdentifiers are compared.
+
+        // If the input PickupIdentifier 'identifier' is no PickupCollectionIdentifier then just the two PickupIdentifiers are compared.
         if(collectionIdentifier == NULL)
         {
             return this->PickupIdentifier::compare(identifier);
         }
-        
-        //! If the number of Pickupables each of the two PickupCollectionIdentifiers contain differ, the one with less is considered smaller.
+
+        // If the number of Pickupables each of the two PickupCollectionIdentifiers contain differ, the one with less is considered smaller.
         if(this->identifiers_.size() != collectionIdentifier->identifiers_.size())
             return this->identifiers_.size()-collectionIdentifier->identifiers_.size();
-        
-        //! Compare the Pickupables of the two PickupCollectionIdentifiers one after the other. the one with the first 'smaller' one is considered smaller.
+
+        // Compare the Pickupables of the two PickupCollectionIdentifiers one after the other. the one with the first 'smaller' one is considered smaller.
         std::set<const PickupIdentifier*, PickupIdentifierCompare>::const_iterator it2 = collectionIdentifier->identifiers_.begin();
         for(std::set<const PickupIdentifier*, PickupIdentifierCompare>::const_iterator it = this->identifiers_.begin(); it != this->identifiers_.end(); it++)
         {
-            
+
             if((*it)->compare(*it2) < 0)
                 return -1;
@@ -91,9 +91,9 @@
                 return 1;
         }
-        
+
         //! Means they are equal.
         return 0;
     }
-    
+
     /**
     @brief
@@ -106,5 +106,5 @@
         this->identifiers_.insert(identifier);
     }
-    
+
 }
 
Index: code/trunk/src/modules/pickup/PickupCollectionIdentifier.h
===================================================================
--- code/trunk/src/modules/pickup/PickupCollectionIdentifier.h	(revision 6901)
+++ code/trunk/src/modules/pickup/PickupCollectionIdentifier.h	(revision 7163)
@@ -54,18 +54,18 @@
     class _PickupExport PickupCollectionIdentifier : public PickupIdentifier
     {
-        
+
         public:
             PickupCollectionIdentifier(Pickupable* pickup); //!< Constructor.
             ~PickupCollectionIdentifier(); //!< Destructor.
-            
+
             virtual int compare(const PickupIdentifier* identifier) const; //!< Compares a PickupCollectionIdentifier with a PickupIdentifier.
-            
+
             void addPickup(const PickupIdentifier* identifier); //!< Add a Pickupable to the PickupCollectionIdentifier.
-            
+
         private:
             std::set<const PickupIdentifier*, PickupIdentifierCompare> identifiers_; //!< The set of PickupIdentifiers of the Pickupables the PickupCollection with this PickupCollectionIdentifier consists of, ordered by the rule set by PickupIdentifierCompare.
-            
+
     };
-    
+
 }
 
Index: code/trunk/src/modules/pickup/PickupManager.cc
===================================================================
--- code/trunk/src/modules/pickup/PickupManager.cc	(revision 6901)
+++ code/trunk/src/modules/pickup/PickupManager.cc	(revision 7163)
@@ -39,7 +39,9 @@
 #include "core/ScopedSingletonManager.h"
 #include "core/Identifier.h"
+#include "util/Convert.h"
 #include "interfaces/PickupCarrier.h"
 #include "infos/PlayerInfo.h"
 #include "worldentities/pawns/Pawn.h"
+#include "CollectiblePickup.h"
 #include "PickupRepresentation.h"
 
@@ -50,9 +52,9 @@
     // Register tolua_open function when loading the library
     DeclareToluaInterface(Pickup);
-    
-    ManageScopedSingleton(PickupManager, ScopeID::Graphics, false);
-    
+
+    ManageScopedSingleton(PickupManager, ScopeID::Root, false);
+
     /*static*/ const std::string PickupManager::guiName_s = "PickupInventory";
-    
+
     /**
     @brief
@@ -62,10 +64,15 @@
     {
         RegisterRootObject(PickupManager);
-        
+
+        //TODO: This doesn't work, yet.
+        if( GameMode::showsGraphics() )
+        {
+            GUIManager::getInstance().loadGUI(PickupManager::guiName_s);
+        }
         this->defaultRepresentation_ = new PickupRepresentation();
-        
+
         COUT(3) << "PickupManager created." << std::endl;
     }
-    
+
     /**
     @brief
@@ -77,10 +84,10 @@
         if(this->defaultRepresentation_ != NULL)
             this->defaultRepresentation_->destroy();
-        
+
         this->representations_.clear();
-        
+
         COUT(3) << "PickupManager destroyed." << std::endl;
     }
-    
+
     /**
     @brief
@@ -95,14 +102,14 @@
     */
     bool PickupManager::registerRepresentation(const PickupIdentifier* identifier, PickupRepresentation* representation)
-    {       
+    {
         if(identifier == NULL || representation == NULL || this->representations_.find(identifier) != this->representations_.end()) //!< If the Pickupable already has a Representation registered.
             return false;
-        
+
         this->representations_[identifier] = representation;
-        
+
         COUT(4) << "PickupRepresentation " << representation << " registered with the PickupManager." << std::endl;
         return true;
     }
-    
+
     /**
     @brief
@@ -116,18 +123,18 @@
     */
     bool PickupManager::unregisterRepresentation(const PickupIdentifier* identifier, PickupRepresentation* representation)
-    {       
+    {
         if(identifier == NULL || representation == NULL)
             return false;
-        
+
         std::map<const PickupIdentifier*, PickupRepresentation*, PickupIdentifierCompare>::iterator it = this->representations_.find(identifier);
         if(it == this->representations_.end()) //!< If the Pickupable is not registered in the first place.
             return false;
-        
+
         this->representations_.erase(it);
-        
+
         COUT(4) << "PickupRepresentation " << representation << " unregistered with the PickupManager." << std::endl;
         return true;
     }
-    
+
     /**
     @brief
@@ -146,67 +153,84 @@
             return this->defaultRepresentation_;
         }
-        
+
         return it->second;
     }
-    
-    PickupCarrier* PickupManager::getPawn(void)
-    {
+
+    int PickupManager::getNumPickups(void)
+    {
+        this->pickupsList_.clear();
+
         PlayerInfo* player = GUIManager::getInstance().getPlayer(PickupManager::guiName_s);
+        PickupCarrier* carrier = NULL;
         if (player != NULL)
-            return dynamic_cast<PickupCarrier*>(player->getControllableEntity());
+            carrier =  dynamic_cast<PickupCarrier*>(player->getControllableEntity());
         else
-            return NULL;
-    }
-    
-    int PickupManager::getNumCarrierChildren(PickupCarrier* carrier)
-    {
-        if(carrier == NULL)
             return 0;
-        return carrier->getNumCarrierChildren();
-    }
-            
-    PickupCarrier* PickupManager::getCarrierChild(int index, PickupCarrier* carrier)
-    {
-        if(carrier == NULL)
-            return NULL;
-        return carrier->getCarrierChild(index);
-    }
-    
-    const std::string& PickupManager::getCarrierName(orxonox::PickupCarrier* carrier)
-    {
-        if(carrier == NULL)
-            return BLANKSTRING;
-        return carrier->getCarrierName();
-    }
-    
-    PickupRepresentation* PickupManager::getPickupRepresentation(int index, PickupCarrier* carrier)
-    {
-        Pickupable* pickup = carrier->getPickup(index);
-        if(pickup == NULL)
-            return NULL;
-        
-        return this->getRepresentation(pickup->getPickupIdentifier());
-    }
-    
-    int PickupManager::getNumPickups(PickupCarrier* carrier)
-    {
-        if(carrier == NULL)
-            return 0;
-        return carrier->getNumPickups();
-    }
-    
-    void PickupManager::dropPickup(int index, PickupCarrier* carrier)
-    {
-        Pickupable* pickup = carrier->getPickup(index);
-        if(pickup != NULL)
-            carrier->drop(pickup);
-    }
-    
-    void PickupManager::usePickup(int index, PickupCarrier* carrier, bool use)
-    {
-        Pickupable* pickup = carrier->getPickup(index);
-        if(pickup != NULL)
+
+        std::vector<PickupCarrier*>* carriers = this->getAllCarriers(carrier);
+        for(std::vector<PickupCarrier*>::iterator it = carriers->begin(); it != carriers->end(); it++)
+        {
+            std::set<Pickupable*> pickups = (*it)->getPickups();
+            for(std::set<Pickupable*>::iterator pickup = pickups.begin(); pickup != pickups.end(); pickup++)
+            {
+                CollectiblePickup* collectible = orxonox_cast<CollectiblePickup*>(*pickup);
+                if(collectible == NULL || !collectible->isInCollection())
+                    this->pickupsList_.insert(std::pair<Pickupable*, WeakPtr<Pickupable> >(*pickup, WeakPtr<Pickupable>(*pickup)));
+            }
+        }
+        delete carriers;
+
+        this->pickupsIterator_ = this->pickupsList_.begin();
+        return this->pickupsList_.size();
+    }
+
+    std::vector<PickupCarrier*>* PickupManager::getAllCarriers(PickupCarrier* carrier)
+    {
+        //TODO: More efficiently.
+        std::vector<PickupCarrier*>* carriers = new std::vector<PickupCarrier*>();
+        carriers->insert(carriers->end(), carrier);
+        std::vector<PickupCarrier*>* children = carrier->getCarrierChildren();
+        for(std::vector<PickupCarrier*>::iterator it = children->begin(); it != children->end(); it++)
+        {
+            std::vector<PickupCarrier*>* childrensChildren = this->getAllCarriers(*it);
+            for(std::vector<PickupCarrier*>::iterator it2 = childrensChildren->begin(); it2 != childrensChildren->end(); it2++)
+            {
+                carriers->insert(carriers->end(), *it2);
+            }
+            delete childrensChildren;
+        }
+        delete children;
+        return carriers;
+    }
+
+    void PickupManager::dropPickup(orxonox::Pickupable* pickup)
+    {
+        std::map<Pickupable*, WeakPtr<Pickupable> >::iterator it = this->pickupsList_.find(pickup);
+        if(pickup == NULL || it == this->pickupsList_.end() || it->second.get() == NULL)
+            return;
+
+        if(!pickup->isPickedUp())
+            return;
+
+        PickupCarrier* carrier = pickup->getCarrier();
+        if(pickup != NULL && carrier != NULL)
+        {
+            pickup->drop(carrier);
+        }
+    }
+
+    void PickupManager::usePickup(orxonox::Pickupable* pickup, bool use)
+    {
+        std::map<Pickupable*, WeakPtr<Pickupable> >::iterator it = this->pickupsList_.find(pickup);
+        if(pickup == NULL || it == this->pickupsList_.end() || it->second.get() == NULL)
+            return;
+
+        if(!pickup->isPickedUp())
+            return;
+
+        PickupCarrier* carrier = pickup->getCarrier();
+        if(pickup != NULL && carrier != NULL)
             pickup->setUsed(use);
     }
-    
+
 }
Index: code/trunk/src/modules/pickup/PickupManager.h
===================================================================
--- code/trunk/src/modules/pickup/PickupManager.h	(revision 6901)
+++ code/trunk/src/modules/pickup/PickupManager.h	(revision 7163)
@@ -39,4 +39,5 @@
 #include <map>
 #include "util/Singleton.h"
+#include "core/WeakPtr.h"
 #include "pickup/PickupIdentifier.h"
 #include "PickupRepresentation.h"
@@ -59,38 +60,39 @@
     { // tolua_export
         friend class Singleton<PickupManager>;
-        
+
         public:
             PickupManager();
             virtual ~PickupManager();
-            
+
             static PickupManager& getInstance() { return Singleton<PickupManager>::getInstance(); } // tolua_export
-            
+
             bool registerRepresentation(const PickupIdentifier* identifier, PickupRepresentation* representation); //!< Registers a PickupRepresentation together with the PickupIdentifier of the Pickupable the PickupRepresentation represents.
             bool unregisterRepresentation(const PickupIdentifier* identifier, PickupRepresentation* representation); //!< Unegisters a PickupRepresentation together with the PickupIdentifier of the Pickupable the PickupRepresentation represents.
             PickupRepresentation* getRepresentation(const PickupIdentifier* identifier); //!< Get the PickupRepresentation representing the Pickupable with the input PickupIdentifier.
-            
+
             // tolua_begin
-            orxonox::PickupCarrier* getPawn(void);
-            
-            int getNumCarrierChildren(orxonox::PickupCarrier* carrier);
-            orxonox::PickupCarrier* getCarrierChild(int index, orxonox::PickupCarrier* carrier);
-            
-            const std::string& getCarrierName(orxonox::PickupCarrier* carrier);
-            
-            int getNumPickups(orxonox::PickupCarrier* carrier);
-            PickupRepresentation* getPickupRepresentation(int index, orxonox::PickupCarrier* carrier);
-            void dropPickup(int index, orxonox::PickupCarrier* carrier);
-            void usePickup(int index, orxonox::PickupCarrier* carrier, bool use);
+            int getNumPickups(void);
+            orxonox::Pickupable* popPickup(void) { return (this->pickupsIterator_++)->first; }
+            orxonox::PickupRepresentation* getPickupRepresentation(orxonox::Pickupable* pickup) { if(pickup != NULL) return this->getRepresentation(pickup->getPickupIdentifier()); return NULL; }
+
+            void dropPickup(orxonox::Pickupable* pickup);
+            void usePickup(orxonox::Pickupable* pickup, bool use);
+            bool isValidPickup(orxonox::Pickupable* pickup) { std::map<Pickupable*, WeakPtr<Pickupable> >::iterator it = this->pickupsList_.find(pickup); if(it == this->pickupsList_.end()) return false; return it->second.get() != NULL; }
             // tolua_end
-            
+
         private:
             static PickupManager* singletonPtr_s;
             static const std::string guiName_s;
-            
+
             PickupRepresentation* defaultRepresentation_; //!< The default PickupRepresentation.
             std::map<const PickupIdentifier*, PickupRepresentation*, PickupIdentifierCompare> representations_; //!< Map linking PickupIdentifiers (representing types if Pickupables) and PickupRepresentations.
-        
+
+            std::map<Pickupable*, WeakPtr<Pickupable> > pickupsList_;
+            std::map<Pickupable*, WeakPtr<Pickupable> >::iterator pickupsIterator_;
+
+            std::vector<PickupCarrier*>* getAllCarriers(PickupCarrier* carrier);
+
     }; // tolua_export
-    
+
 } // tolua_export
 
Index: code/trunk/src/modules/pickup/PickupPrereqs.h
===================================================================
--- code/trunk/src/modules/pickup/PickupPrereqs.h	(revision 6901)
+++ code/trunk/src/modules/pickup/PickupPrereqs.h	(revision 7163)
@@ -43,5 +43,5 @@
 //-----------------------------------------------------------------------
 
-#if defined(ORXONOX_PLATFORM_WINDOWS) && !defined(ORXONOX_STATIC_BUILD)
+#if defined(ORXONOX_PLATFORM_WINDOWS) && !defined(PICKUP_STATIC_BUILD)
 #  ifdef PICKUP_SHARED_BUILD
 #    define _PickupExport __declspec(dllexport)
@@ -65,5 +65,6 @@
 namespace orxonox
 {
-    
+
+    class CollectiblePickup;
     class DroppedPickup;
     class Pickup;
@@ -75,8 +76,10 @@
 
     //items
+    class DronePickup;
     class HealthPickup;
     class InvisiblePickup;
     class MetaPickup;
     class SpeedPickup;
+    class ShieldPickup;
 
 }
Index: code/trunk/src/modules/pickup/PickupRepresentation.cc
===================================================================
--- code/trunk/src/modules/pickup/PickupRepresentation.cc	(revision 6901)
+++ code/trunk/src/modules/pickup/PickupRepresentation.cc	(revision 7163)
@@ -41,7 +41,7 @@
 namespace orxonox
 {
-    
+
     CreateFactory(PickupRepresentation);
-    
+
     /**
     @brief
@@ -52,8 +52,8 @@
     {
         RegisterObject(PickupRepresentation);
-        
+
         this->initialize();
     }
-    
+
     /**
     @brief
@@ -63,8 +63,8 @@
     {
         RegisterObject(PickupRepresentation);
-        
+
         this->initialize();
     }
-    
+
     /**
     @brief
@@ -75,9 +75,9 @@
         if(this->spawnerRepresentation_ != NULL)
             this->spawnerRepresentation_->destroy();
-        
+
         if(this->pickup_ != NULL)
             PickupManager::getInstance().unregisterRepresentation(this->pickup_->getPickupIdentifier(), this);
     }
-    
+
     /**
     @brief
@@ -91,5 +91,5 @@
         this->inventoryRepresentation_ = "Default";
     }
-    
+
     /**
     @brief
@@ -99,5 +99,5 @@
     {
         SUPER(PickupRepresentation, XMLPort, xmlelement, mode);
-        
+
         XMLPortParam(PickupRepresentation, "pickupName", setPickupName, getPickupName, xmlelement, mode);
         XMLPortParam(PickupRepresentation, "pickupDescription", setPickupDescription, getPickupDescription, xmlelement, mode);
@@ -106,13 +106,13 @@
         XMLPortObject(PickupRepresentation, Pickupable, "pickup", setPickup, getPickup, xmlelement, mode);
         XMLPortObject(PickupRepresentation, StaticEntity, "spawner-representation", setSpawnerRepresentation, getSpawnerRepresentationIndex, xmlelement, mode);
-        
+
         PickupManager::getInstance().registerRepresentation(this->pickup_->getPickupIdentifier(), this); //!< Registers the PickupRepresentation with the PickupManager through the PickupIdentifier of the Pickupable it represents.
-        
+
         if(this->spawnerRepresentation_ != NULL)
             this->spawnerRepresentation_->setVisible(false);
-        
+
         COUT(4) << "PickupRepresentation created: name: '" << this->name_ << "', description: '" << this->description_ << "', spawnerTemplate: '" << this->spawnerTemplate_ << "'." << std::endl;
     }
-    
+
     /**
     @brief
@@ -136,14 +136,14 @@
             this->addTemplate(this->spawnerTemplate_);
         }
-        
+
         StaticEntity* representation = this->spawnerRepresentation_;
         representation->setVisible(true);
-        
+
         this->addTemplate(this->spawnerTemplate_);
         this->spawnerRepresentation_->setVisible(false);
-        
+
         return representation;
     }
-    
+
     /**
     @brief
@@ -171,4 +171,4 @@
         return representation;
     }
-    
+
 }
Index: code/trunk/src/modules/pickup/PickupRepresentation.h
===================================================================
--- code/trunk/src/modules/pickup/PickupRepresentation.h	(revision 6901)
+++ code/trunk/src/modules/pickup/PickupRepresentation.h	(revision 7163)
@@ -56,12 +56,12 @@
         : public BaseObject
     { // tolua_export
-        
+
         public:
             PickupRepresentation(); //!< Constructor
             PickupRepresentation(BaseObject* creator); //!< Default constructor.
             virtual ~PickupRepresentation(); //!< Destructor.
-            
+
             virtual void XMLPort(Element& xmlelement, XMLPort::Mode mode);
-            
+
             /**
             @brief Set the name of the Pickupable represented by this PickupRepresentation.
@@ -102,5 +102,5 @@
             inline void setPickup(Pickupable* pickup)
                 { this->pickup_ = pickup; }
-                
+
             /**
             @brief Get the name of the Pickupable represented by this PickupRepresentation.
@@ -138,22 +138,22 @@
             inline const Pickupable* getPickup(unsigned int index)
                 { if(index == 0) return this->pickup_; return NULL; }
-                
+
             StaticEntity* getSpawnerRepresentation(PickupSpawner* spawner); //!< Get a spawnerRepresentation for a specific PickupSpawner.
-        
+
         private:
             void initialize(void); //!< Initializes the member variables of this PickupRepresentation.
             StaticEntity* getDefaultSpawnerRepresentation(PickupSpawner* spawner); //!< Get the default spawnerRepresentation for a specific PickupSpawner.
-            
+
             std::string name_; //!< The name of the Pickupable represented by this PickupRepresentation.
             std::string description_; //!< The description of the Pickupable represented by this PickupRepresentation.
             std::string spawnerTemplate_; //!<  The name of the template of this PickupRepresentation.
             StaticEntity* spawnerRepresentation_; //!< The spawnerRepresentation of this PickupRepresentation.
-            std::string inventoryRepresentation_; //!< The name of an image representing the pickup in the PickupInventory. TODO: Exact format and placement of image?
-            
+            std::string inventoryRepresentation_; //!< The name of an image representing the pickup in the PickupInventory.
+
             Pickupable* pickup_; //!< The Pickupable that is represented by this PickupRepresentation.
-            
+
     }; // tolua_export
 
 } // tolua_export
-    
+
 #endif // _PickupRepresentation_H__
Index: code/trunk/src/modules/pickup/PickupSpawner.cc
===================================================================
--- code/trunk/src/modules/pickup/PickupSpawner.cc	(revision 6901)
+++ code/trunk/src/modules/pickup/PickupSpawner.cc	(revision 7163)
@@ -55,5 +55,5 @@
     {
         RegisterObject(PickupSpawner);
-        
+
         this->initialize();
     }
@@ -76,7 +76,7 @@
     {
         RegisterObject(PickupSpawner);
-        
+
         this->initialize();
-  
+
         this->pickup_ = pickup;
 
@@ -84,5 +84,5 @@
         this->respawnTime_ = respawnTime;
         this->setMaxSpawnedItems(maxSpawnedItems);
-        
+
         if(this->pickup_ == NULL)
         {
@@ -107,4 +107,5 @@
         this->maxSpawnedItems_ = INF;
         this->spawnsRemaining_ = INF;
+        this->selfDestruct_ = false;
     }
 
@@ -115,5 +116,5 @@
     PickupSpawner::~PickupSpawner()
     {
-        if(this->pickup_ != NULL)
+        if(this->selfDestruct_ && this->pickup_ != NULL)
             this->pickup_->destroy();
     }
@@ -132,9 +133,9 @@
 
         XMLPortObject(PickupSpawner, Pickupable, "pickup", setPickupable, getPickupable, xmlelement, mode);
-        
+
         XMLPortParam(PickupSpawner, "triggerDistance", setTriggerDistance, getTriggerDistance, xmlelement, mode);
         XMLPortParam(PickupSpawner, "respawnTime", setRespawnTime, getRespawnTime, xmlelement, mode);
         XMLPortParam(PickupSpawner, "maxSpawnedItems", setMaxSpawnedItems, getMaxSpawnedItems, xmlelement, mode);
-        
+
         if(this->pickup_ == NULL)
         {
@@ -150,5 +151,5 @@
         }
     }
-    
+
     /**
     @brief
@@ -161,5 +162,5 @@
         this->setVisible(this->isActive());
     }
-     
+
     /**
     @brief
@@ -172,8 +173,10 @@
     {
         SUPER(PickupSpawner, tick, dt);
-        
+
         //! If the PickupSpawner is active.
         if (this->isActive())
         {
+            SmartPtr<PickupSpawner> temp = this; //Create a smart pointer to keep the PickupSpawner alive until we iterated through all Pawns (in case a Pawn takes the last pickup)
+
             //! Iterate trough all Pawns.
             for (ObjectList<Pawn>::iterator it = ObjectList<Pawn>::begin(); it != ObjectList<Pawn>::end(); ++it)
@@ -189,5 +192,5 @@
         }
     }
-    
+
     /**
     @brief
@@ -201,5 +204,5 @@
         this->spawnsRemaining_ = items;
     }
-    
+
     /**
     @brief
@@ -223,10 +226,10 @@
         else
         {
-            COUT(3) << "PickupSpawner empty, selfdestruct initialized." << std::endl;
+            COUT(4) << "PickupSpawner (&" << this << ") empty, selfdestruct initialized." << std::endl;
             this->setActive(false);
             this->destroy();
         }
     }
-    
+
     /**
     @brief
@@ -237,5 +240,5 @@
         this->respawnTimer_.setTimer(this->respawnTime_, false, createExecutor(createFunctor(&PickupSpawner::respawnTimerCallback, this)));
     }
-    
+
     /**
     @brief
@@ -248,16 +251,16 @@
         if(this->pickup_ != NULL)
         {
-            COUT(1) << "In PickupSpawner: setPickupable called, with this->pickup_ already set." << std::endl;
+            COUT(1) << "In PickupSpawner (&" << this << "): setPickupable called, with this->pickup_ already set." << std::endl;
             return;
         }
         if(pickup == NULL)
         {
-            COUT(1) << "In PickupSpawner: Argument of setPickupable is NULL." << std::endl;
+            COUT(1) << "In PickupSpawner (&" << this << "): Argument of setPickupable is NULL." << std::endl;
             return;
         }
-        
+
         this->pickup_ = pickup;
     }
-    
+
     /**
     @brief
@@ -282,6 +285,6 @@
         if (this->isActive()) //!< Checks whether PickupSpawner is active.
         {
-            COUT(3) << "PickupSpawner triggered and active." << std::endl;
-            
+            COUT(4) << "PickupSpawner (&" << this << ") triggered and active." << std::endl;
+
             PickupCarrier* carrier = dynamic_cast<PickupCarrier*>(pawn);
             if(carrier == NULL)
@@ -290,22 +293,21 @@
                 return;
             }
-            
+
             if(!carrier->isTarget(this->pickup_))
             {
-                COUT(4) << "PickupSpawner triggered but Pawn wasn't a target of the Pickupable." << std::endl;
+                COUT(4) << "PickupSpawner (&" << this << ") triggered but Pawn wasn't a target of the Pickupable." << std::endl;
                 return;
             }
-            
+
             PickupCarrier* target = carrier->getTarget(this->pickup_);
             Pickupable* pickup = this->getPickup();
-            
+
             if(target != NULL && pickup != NULL)
             {
-                if(target->pickup(pickup))
-                {
+                if(pickup->pickup(target))
                     this->decrementSpawnsRemaining();
-                }
                 else
                 {
+                    this->selfDestruct_ = true;
                     pickup->destroy();
                 }
@@ -314,12 +316,11 @@
             {
                 if(target == NULL)
-                    COUT(1) << "PickupSpawner: Pickupable has no target." << std::endl;
-                
+                    COUT(1) << "PickupSpawner (&" << this << "): Pickupable has no target." << std::endl;
+
                 if(pickup == NULL)
-                {
-                    COUT(1) << "PickupSpawner: getPickup produced an error, no Pickupable created." << std::endl;
-                }
+                    COUT(1) << "PickupSpawner (&" << this << "): getPickup produced an error, no Pickupable created." << std::endl;
                 else
                 {
+                    this->selfDestruct_ = true;
                     pickup->destroy();
                 }
@@ -333,5 +334,5 @@
     @return
         The Pickupable created.
-    */    
+    */
     Pickupable* PickupSpawner::getPickup(void)
     {
@@ -341,5 +342,5 @@
             return NULL;
         }
-        
+
         Pickupable* pickup = this->pickup_->clone();
         return pickup;
@@ -352,5 +353,5 @@
     void PickupSpawner::respawnTimerCallback()
     {
-        COUT(3) << "PickupSpawner reactivated." << std::endl;
+        COUT(4) << "PickupSpawner (&" << this << ") reactivated." << std::endl;
 
         this->setActive(true);
Index: code/trunk/src/modules/pickup/PickupSpawner.h
===================================================================
--- code/trunk/src/modules/pickup/PickupSpawner.h	(revision 6901)
+++ code/trunk/src/modules/pickup/PickupSpawner.h	(revision 7163)
@@ -101,17 +101,17 @@
         protected:
             void decrementSpawnsRemaining(void); //!< Decrements the number of remaining spawns.
-                        
+
             void startRespawnTimer(void);
-            
+
             virtual Pickupable* getPickup(void); //!< Creates a new Pickupable.
-            
+
             void setPickupable(Pickupable* pickup); //!< Sets a Pickupable for the PickupSpawner to spawn.
             const Pickupable* getPickupable(void); //!< Get the Pickupable that is spawned by this PickupSpawner.
-            
+
             Pickupable* pickup_; //!< The pickup to be spawned.
 
         private:
             void initialize(void);
-            
+
             void trigger(Pawn* pawn); //!< Method called when a Pawn is close enough.
             void respawnTimerCallback(); //!< Method called when the timer runs out.
@@ -125,4 +125,6 @@
             Timer respawnTimer_; //!< Timer used for re-activating.
 
+            bool selfDestruct_; //!< True if the PickupSpawner is selfdestructing.
+
             static const int INF = -1; //!< Constant for infinity.
     };
Index: code/trunk/src/modules/pickup/items/CMakeLists.txt
===================================================================
--- code/trunk/src/modules/pickup/items/CMakeLists.txt	(revision 6901)
+++ code/trunk/src/modules/pickup/items/CMakeLists.txt	(revision 7163)
@@ -3,4 +3,6 @@
   InvisiblePickup.cc
   MetaPickup.cc
+  DronePickup.cc
   SpeedPickup.cc
+  ShieldPickup.cc
 )
Index: code/trunk/src/modules/pickup/items/DronePickup.cc
===================================================================
--- code/trunk/src/modules/pickup/items/DronePickup.cc	(revision 7163)
+++ code/trunk/src/modules/pickup/items/DronePickup.cc	(revision 7163)
@@ -0,0 +1,199 @@
+/*
+ *   ORXONOX - the hottest 3D action shooter ever to exist
+ *                    > www.orxonox.net <
+ *
+ *
+ *   License notice:
+ *
+ *   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 2
+ *   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., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ *
+ *   Author:
+ *      Lukas Gasser
+ *   Co-authors:
+ *      ...
+ *
+ */
+
+/**
+    @file DronePickup.cc
+    @brief Implementation of the DronePickup class.
+*/
+
+#include "DronePickup.h"
+#include "worldentities/Drone.h"
+#include "controllers/DroneController.h"
+
+#include "core/CoreIncludes.h"
+#include "core/XMLPort.h"
+#include "util/StringUtils.h"
+
+#include "worldentities/pawns/Pawn.h"
+#include "pickup/PickupIdentifier.h"
+
+#include <sstream>
+
+namespace orxonox
+{
+
+    CreateFactory(DronePickup);
+
+    /**
+    @brief
+        Constructor. Registers the object and initializes the member variables.
+    */
+    DronePickup::DronePickup(BaseObject* creator) : Pickup(creator)
+    {
+        RegisterObject(DronePickup);
+
+        this->initialize();
+    }
+
+    /**
+    @brief
+        Destructor.
+    */
+    DronePickup::~DronePickup()
+    {
+
+    }
+
+    /**
+    @brief
+        Initializes the member variables.
+    */
+    void DronePickup::initialize(void)
+    {
+        this->addTarget(ClassIdentifier<Pawn>::getIdentifier());
+        this->setDurationTypeDirect(pickupDurationType::once);
+        this->droneTemplate_ = "";
+    }
+
+    /**
+    @brief
+        Initializes the PickupIdentifier of this pickup.
+    */
+    void DronePickup::initializeIdentifier(void)
+    {
+        std::string val = this->getDroneTemplate();
+        std::string type = "droneTemplate";
+        this->pickupIdentifier_->addParameter(type, val);
+    }
+
+    /**
+    @brief
+        Method for creating a DronePickup object through XML.
+    */
+    void DronePickup::XMLPort(Element& xmlelement, orxonox::XMLPort::Mode mode)
+    {
+        SUPER(DronePickup, XMLPort, xmlelement, mode);
+        XMLPortParam(DronePickup, "droneTemplate", setDroneTemplate, getDroneTemplate, xmlelement, mode);
+
+        this->initializeIdentifier();
+    }
+
+    void DronePickup::setDroneTemplate(std::string templatename){
+        droneTemplate_ = templatename;
+    }
+
+    const std::string& DronePickup::getDroneTemplate() const
+    {
+        return droneTemplate_;
+    }
+
+    /**
+    @brief
+        Is called when the pickup has transited from used to unused or the other way around.
+    */
+    void DronePickup::changedUsed(void)
+    {
+        SUPER(DronePickup, changedUsed);
+
+        //! If the pickup is not picked up nothing must be done.
+        if(!this->isPickedUp())
+            return;
+
+        //! If the pickup has transited to used.
+        if(this->isUsed())
+        {
+
+                Pawn* pawn = this->carrierToPawnHelper();
+                if(pawn == NULL) //!< If the PickupCarrier is no Pawn, then this pickup is useless and therefore is destroyed.
+                    this->Pickupable::destroy();
+
+                //Attach to pawn
+                Drone* drone = new Drone(pawn->getCreator()); // this is neccessary because the projectiles fired need a valid creator for the particlespawner (when colliding against something)
+                drone->addTemplate(this->getDroneTemplate());
+
+                Controller* controller = drone->getController();
+                DroneController* droneController = dynamic_cast<DroneController*>(controller);
+                if(droneController != NULL)
+                {
+                    droneController->setOwner(pawn);
+                }
+
+                Vector3 spawnPosition = pawn->getWorldPosition() + Vector3(30,0,-30);
+                drone->setPosition(spawnPosition);
+
+                //! The pickup has been used up.
+                this->setUsed(false);
+        }
+        else
+        {
+            //! If either the pickup can only be used once or it is continuous and used up, it is destroyed upon setting it to unused.
+            if(this->isOnce() || (this->isContinuous() ))
+            {
+                this->Pickupable::destroy();
+            }
+        }
+    }
+
+    /**
+    @brief
+        Helper to transform the PickupCarrier to a Pawn, and throw an error message if the conversion fails.
+    @return
+        A pointer to the Pawn, or NULL if the conversion failed.
+    */
+    Pawn* DronePickup::carrierToPawnHelper(void)
+    {
+        PickupCarrier* carrier = this->getCarrier();
+        Pawn* pawn = dynamic_cast<Pawn*>(carrier);
+
+        if(pawn == NULL)
+        {
+            COUT(1) << "Invalid PickupCarrier in DronePickup." << std::endl;
+        }
+
+        return pawn;
+    }
+
+    /**
+    @brief
+        Creates a duplicate of the input OrxonoxClass.
+    @param item
+        A pointer to the Orxonox class.
+    */
+    void DronePickup::clone(OrxonoxClass*& item)
+    {
+        if(item == NULL)
+            item = new DronePickup(this);
+
+        SUPER(DronePickup, clone, item);
+
+        DronePickup* pickup = dynamic_cast<DronePickup*>(item);
+        pickup->setDroneTemplate(this->getDroneTemplate());
+
+        pickup->initializeIdentifier();
+    }
+}
Index: code/trunk/src/modules/pickup/items/DronePickup.h
===================================================================
--- code/trunk/src/modules/pickup/items/DronePickup.h	(revision 7163)
+++ code/trunk/src/modules/pickup/items/DronePickup.h	(revision 7163)
@@ -0,0 +1,79 @@
+/*
+ *   ORXONOX - the hottest 3D action shooter ever to exist
+ *                    > www.orxonox.net <
+ *
+ *
+ *   License notice:
+ *
+ *   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 2
+ *   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., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ *
+ *   Author:
+ *      Lukas Gasser
+ *   Co-authors:
+ *      ...
+ *
+ */
+
+/**
+    @file DronePickup.h
+    @brief Declaration of the DronePickup class.
+*/
+
+#ifndef _DronePickup_H__
+#define _DronePickup_H__
+
+#include "pickup/PickupPrereqs.h"
+
+#include <string>
+#include <worldentities/pawns/Pawn.h>
+#include <worldentities/Drone.h>
+
+#include "worldentities/StaticEntity.h"
+
+#include "pickup/Pickup.h"
+#include "tools/interfaces/Tickable.h"
+
+namespace orxonox {
+
+
+    class _PickupExport DronePickup : public Pickup, public Tickable
+    {
+        public:
+
+            DronePickup(BaseObject* creator); //!< Constructor.
+            virtual ~DronePickup(); //!< Destructor.
+
+            virtual void XMLPort(Element& xmlelement, orxonox::XMLPort::Mode mode); //!< Method for creating a DronePickup object through XML.
+
+            virtual void changedUsed(void); //!< Is called when the pickup has transited from used to unused or the other way around.
+            virtual void clone(OrxonoxClass*& item); //!< Creates a duplicate of the input OrxonoxClass.
+
+            void setDroneTemplate(std::string templatename);
+            const std::string& getDroneTemplate() const;
+
+        protected:
+            void initializeIdentifier(void); //!< Initializes the PickupIdentifier of this pickup.
+
+        private:
+            void initialize(void); //!< Initializes the member variables.
+            std::string droneTemplate_;
+            Pawn* carrierToPawnHelper(void); //!< Helper to transform the PickupCarrier to a Pawn, and throw an error message if the conversion fails.
+
+
+
+    };
+}
+
+#endif // _DronePickup_H__
Index: code/trunk/src/modules/pickup/items/HealthPickup.cc
===================================================================
--- code/trunk/src/modules/pickup/items/HealthPickup.cc	(revision 6901)
+++ code/trunk/src/modules/pickup/items/HealthPickup.cc	(revision 7163)
@@ -45,11 +45,11 @@
 namespace orxonox
 {
-    
+
     /*static*/ const std::string HealthPickup::healthTypeLimited_s = "limited";
     /*static*/ const std::string HealthPickup::healthTypeTemporary_s = "temporary";
     /*static*/ const std::string HealthPickup::healthTypePermanent_s = "permanent";
-    
+
     CreateFactory(HealthPickup);
-    
+
     /**
     @brief
@@ -59,8 +59,8 @@
     {
         RegisterObject(HealthPickup);
-        
+
         this->initialize();
     }
-    
+
     /**
     @brief
@@ -69,13 +69,13 @@
     HealthPickup::~HealthPickup()
     {
-        
-    }
-    
-    /**
-    @brief 
+
+    }
+
+    /**
+    @brief
         Initializes the member variables.
     */
     void HealthPickup::initialize(void)
-    {        
+    {
         this->health_ = 0;
         this->healthRate_ = 0;
@@ -83,8 +83,8 @@
         this->maxHealthSave_ = 0;
         this->maxHealthOverwrite_ = 0;
-        
+
         this->addTarget(ClassIdentifier<Pawn>::getIdentifier());
     }
-    
+
     /**
     @brief
@@ -98,9 +98,9 @@
         std::string val1 = stream.str();
         this->pickupIdentifier_->addParameter(type1, val1);
-        
+
         std::string val2 = this->getHealthType();
         std::string type2 = "healthType";
         this->pickupIdentifier_->addParameter(type2, val2);
-        
+
         stream.clear();
         stream << this->getHealthRate();
@@ -109,5 +109,5 @@
         this->pickupIdentifier_->addParameter(type3, val3);
     }
-    
+
     /**
     @brief
@@ -117,15 +117,15 @@
     {
         SUPER(HealthPickup, XMLPort, xmlelement, mode);
-        
+
         XMLPortParam(HealthPickup, "health", setHealth, getHealth, xmlelement, mode);
         XMLPortParam(HealthPickup, "healthRate", setHealthRate, getHealthRate, xmlelement, mode);
         XMLPortParam(HealthPickup, "healthType", setHealthType, getHealthType, xmlelement, mode);
-        
+
         if(!this->isContinuous())
             this->healthRate_ = 0.0;
-        
+
         this->initializeIdentifier();
     }
-    
+
     /**
     @brief
@@ -138,11 +138,11 @@
     {
         SUPER(HealthPickup, tick, dt);
-        
+
         if(this->isContinuous() && this->isUsed())
         {
             Pawn* pawn = this->carrierToPawnHelper();
             if(pawn == NULL) //!< If the PickupCarrier is no Pawn, then this pickup is useless and therefore is destroyed.
-                this->destroy();
-            
+                this->Pickupable::destroy();
+
             //! Calculate the health that is added this tick.
             float health = dt*this->getHealthRate();
@@ -152,5 +152,5 @@
             float fullHealth = pawn->getHealth() + health;
             this->setHealth(this->getHealth()-health);
-                    
+
             switch(this->getHealthTypeDirect())
             {
@@ -173,5 +173,5 @@
                     COUT(1) << "Invalid healthType in HealthPickup." << std::endl;
             }
-            
+
             //! If all health has been transfered.
             if(this->getHealth() == 0)
@@ -181,5 +181,5 @@
         }
     }
-    
+
     /**
     @brief
@@ -189,9 +189,9 @@
     {
         SUPER(HealthPickup, changedUsed);
-        
+
         //! If the pickup is not picked up nothing must be done.
-        if(!this->isPickedUp())
+        if(!this->isPickedUp()) //TODO: Needed?
             return;
-        
+
         //! If the pickup has transited to used.
         if(this->isUsed())
@@ -201,6 +201,6 @@
                 Pawn* pawn = this->carrierToPawnHelper();
                 if(pawn == NULL) //!< If the PickupCarrier is no Pawn, then this pickup is useless and therefore is destroyed.
-                    this->destroy();
-                
+                    this->Pickupable::destroy();
+
                 float health = 0;
                 switch(this->getHealthTypeDirect())
@@ -226,5 +226,5 @@
                         COUT(1) << "Invalid healthType in HealthPickup." << std::endl;
                 }
-                
+
                 //! The pickup has been used up.
                 this->setUsed(false);
@@ -237,12 +237,12 @@
                 PickupCarrier* carrier = this->getCarrier();
                 Pawn* pawn = dynamic_cast<Pawn*>(carrier);
-                
+
                 if(pawn == NULL)
                 {
                     COUT(1) << "Something went horribly wrong in Health Pickup. PickupCarrier is no Pawn." << std::endl;
-                    this->destroy();
+                    this->Pickupable::destroy();
                     return;
                 }
-                
+
                 if(pawn->getMaxHealth() == this->maxHealthOverwrite_)
                 {
@@ -252,13 +252,13 @@
                 }
             }
-            
+
             //! If either the pickup can only be used once or it is continuous and used up, it is destroyed upon setting it to unused.
             if(this->isOnce() || (this->isContinuous() && this->getHealth() == 0))
             {
-                this->destroy();
-            }
-        }
-    }
-    
+                this->Pickupable::destroy();
+            }
+        }
+    }
+
     /**
     @brief
@@ -271,13 +271,13 @@
         PickupCarrier* carrier = this->getCarrier();
         Pawn* pawn = dynamic_cast<Pawn*>(carrier);
-        
+
         if(pawn == NULL)
         {
             COUT(1) << "Invalid PickupCarrier in HealthPickup." << std::endl;
         }
-        
+
         return pawn;
     }
-    
+
     /**
     @brief
@@ -290,15 +290,15 @@
         if(item == NULL)
             item = new HealthPickup(this);
-        
+
         SUPER(HealthPickup, clone, item);
-        
+
         HealthPickup* pickup = dynamic_cast<HealthPickup*>(item);
         pickup->setHealth(this->getHealth());
         pickup->setHealthRate(this->getHealthRate());
         pickup->setHealthTypeDirect(this->getHealthTypeDirect());
-        
+
         pickup->initializeIdentifier();
     }
-    
+
     /**
     @brief
@@ -322,5 +322,5 @@
         }
     }
-    
+
     /**
     @brief
@@ -341,5 +341,5 @@
         }
     }
-    
+
     /**
     @brief
@@ -356,8 +356,8 @@
         else
         {
-            COUT(1) << "Invalid healthSpeed in HealthPickup." << std::endl; 
-        }
-    }
-    
+            COUT(1) << "Invalid healthSpeed in HealthPickup." << std::endl;
+        }
+    }
+
     /**
     @brief
Index: code/trunk/src/modules/pickup/items/HealthPickup.h
===================================================================
--- code/trunk/src/modules/pickup/items/HealthPickup.h	(revision 6901)
+++ code/trunk/src/modules/pickup/items/HealthPickup.h	(revision 7163)
@@ -45,5 +45,5 @@
 
 namespace orxonox {
-    
+
     //! Enum for the type of the HealthPickup
     namespace pickupHealthType
@@ -56,5 +56,5 @@
         };
     }
-    
+
     /**
     @brief
@@ -71,14 +71,14 @@
     {
         public:
-        
+
             HealthPickup(BaseObject* creator); //!< Constructor.
             virtual ~HealthPickup(); //!< Destructor.
-            
+
             virtual void XMLPort(Element& xmlelement, orxonox::XMLPort::Mode mode); //!< Method for creating a HealthPickup object through XML.
             virtual void tick(float dt); //!< Is called every tick.
-            
+
             virtual void changedUsed(void); //!< Is called when the pickup has transited from used to unused or the other way around.
             virtual void clone(OrxonoxClass*& item); //!< Creates a duplicate of the input OrxonoxClass.
-            
+
             /**
             @brief Get the health that is transfered to the Pawn upon usage of this pickup.
@@ -93,13 +93,13 @@
             inline float getHealthRate(void)
                 { return this->healthRate_; }
-                
+
             /**
             @brief Get the type of HealthPickup, this pickup is.
-            @return Returns the health type as an enum. 
+            @return Returns the health type as an enum.
             */
             inline pickupHealthType::Value getHealthTypeDirect(void)
                 { return this->healthType_; }
             const std::string& getHealthType(void); //!< Get the health type of this pickup.
-            
+
         protected:
             void initializeIdentifier(void); //!< Initializes the PickupIdentifier of this pickup.
@@ -107,5 +107,5 @@
             void setHealth(float health); //!< Sets the health.
             void setHealthRate(float speed); //!< Set the rate at which health is transferred if the pickup is continuous.
-            
+
             /**
             @brief Set the health type of this pickup.
@@ -115,9 +115,9 @@
                 { this->healthType_ = type; }
             void setHealthType(std::string type); //!< Set the type of the HealthPickup.
-        
+
         private:
             void initialize(void); //!< Initializes the member variables.
             Pawn* carrierToPawnHelper(void); //!< Helper to transform the PickupCarrier to a Pawn, and throw an error message if the conversion fails.
-            
+
             float health_; //!< The health that is transferred to the Pawn.
             float healthRate_; //!< The rate at which the health is transferred.
@@ -125,10 +125,10 @@
             float maxHealthOverwrite_; //!< Helper to remember with which value we overwrote the maxHealh, to detect if someone else changed it as well.
             pickupHealthType::Value healthType_; //!< The type of the HealthPickup.
-            
+
             //! Strings for the health types.
             static const std::string healthTypeLimited_s;
             static const std::string healthTypeTemporary_s;
             static const std::string healthTypePermanent_s;
-        
+
     };
 }
Index: code/trunk/src/modules/pickup/items/InvisiblePickup.cc
===================================================================
--- code/trunk/src/modules/pickup/items/InvisiblePickup.cc	(revision 6901)
+++ code/trunk/src/modules/pickup/items/InvisiblePickup.cc	(revision 7163)
@@ -34,18 +34,20 @@
 #include "InvisiblePickup.h"
 
+#include <sstream>
+#include <OgreEntity.h>
+#include <OgreAnimationState.h>
+
+#include "util/StringUtils.h"
 #include "core/CoreIncludes.h"
 #include "core/XMLPort.h"
-#include "util/StringUtils.h"
 
 #include "worldentities/pawns/Pawn.h"
 #include "pickup/PickupIdentifier.h"
 
-#include <sstream>
-
 namespace orxonox
 {
 
     CreateFactory(InvisiblePickup);
-    
+
     /**
     @brief
@@ -56,7 +58,7 @@
         RegisterObject(InvisiblePickup);
         //! Defines who is allowed to pick up the pickup.
-        this->initialize(); 
-    }
-    
+        this->initialize();
+    }
+
     /**
     @brief
@@ -64,8 +66,8 @@
     */
     InvisiblePickup::~InvisiblePickup()
-    {        
-    }
-    
-    
+    {
+    }
+
+
     void InvisiblePickup::initializeIdentifier(void)
     {
@@ -76,5 +78,5 @@
         this->pickupIdentifier_->addParameter(type1, val1);
     }
-    
+
     /**
     @brief
@@ -93,10 +95,10 @@
     void InvisiblePickup::XMLPort(Element& xmlelement, orxonox::XMLPort::Mode mode)
     {
-        SUPER(InvisiblePickup, XMLPort, xmlelement, mode);    
+        SUPER(InvisiblePickup, XMLPort, xmlelement, mode);
         XMLPortParam(InvisiblePickup, "duration", setDuration, getDuration, xmlelement, mode);
-        
+
         this->initializeIdentifier();
     }
-    
+
     /**
     @brief
@@ -106,9 +108,9 @@
     {
         SUPER(InvisiblePickup, changedUsed);
-        
+
         //! If the pickup is not picked up nothing must be done.
         if(!this->isPickedUp())
             return;
-        
+
         if (this->isUsed())
         {
@@ -121,13 +123,15 @@
                 this->startPickupTimer(this->getDuration());
             }
+
             this->setInvisible(true);
+
         }
         else
         {
             this->setInvisible(false);
-        
+
             if(!this->getTimer()->isActive() && this->getTimer()->getRemainingTime() == this->getDuration())
             {
-                this->destroy();
+                this->Pickupable::destroy();
             }
             else
@@ -136,7 +140,7 @@
             }
         }
-        
-    }
-    
+
+    }
+
     /**
     @brief
@@ -149,5 +153,5 @@
         PickupCarrier* carrier = this->getCarrier();
         Pawn* pawn = dynamic_cast<Pawn*>(carrier);
-        
+
         if(pawn == NULL)
         {
@@ -156,5 +160,5 @@
         return pawn;
     }
-    
+
     /**
     @brief
@@ -167,12 +171,12 @@
         if(item == NULL)
             item = new InvisiblePickup(this);
-        
+
         SUPER(InvisiblePickup, clone, item);
-        
+
         InvisiblePickup* pickup = dynamic_cast<InvisiblePickup*>(item);
         pickup->setDuration(this->getDuration());
         pickup->initializeIdentifier();
     }
-    
+
     /**
     @brief
@@ -186,9 +190,21 @@
         if(pawn == NULL)
             return false;
-        
+
         pawn->setVisible(!invisibility);
+        pawn->setRadarVisibility(!invisibility);
+
+// Test to change Material at runtime!
+
+//      Ogre::MaterialPtr mat = this->mesh_.getEntity()->getSubEntity(0)->getMaterial();
+//      mat->setDiffuse(0.4, 0.3, 0.1, 0.1);
+//      mat->setAmbient(0.3, 0.7, 0.8);
+//      mat->setSpecular(0.5, 0.5, 0.5, 0.1);
+//      Ogre::SceneBlendType sbt = Ogre::SBT_ADD;
+//
+//      mat->setSceneBlending(sbt);
+
         return true;
     }
-    
+
     /**
     @brief
@@ -209,5 +225,5 @@
         }
     }
-    
+
     void InvisiblePickup::pickupTimerCallback(void)
     {
Index: code/trunk/src/modules/pickup/items/InvisiblePickup.h
===================================================================
--- code/trunk/src/modules/pickup/items/InvisiblePickup.h	(revision 6901)
+++ code/trunk/src/modules/pickup/items/InvisiblePickup.h	(revision 7163)
@@ -38,11 +38,11 @@
 
 #include <string>
+
 #include <worldentities/pawns/Pawn.h>
 #include "worldentities/StaticEntity.h"
-
 #include "pickup/Pickup.h"
 
 namespace orxonox {
-        
+
     /**
     @brief
@@ -57,5 +57,5 @@
     {
         public:
-        
+
             InvisiblePickup(BaseObject* creator); //!< Constructor.
             virtual ~InvisiblePickup(); //!< Destructor.
@@ -63,5 +63,5 @@
             virtual void changedUsed(void); //!< Is called when the pickup has transited from used to unused or the other way around.
             virtual void clone(OrxonoxClass*& item); //!< Creates a duplicate of the input OrxonoxClass.
-            
+
             /**
             @brief Checks whether the Pawn is invisible.
@@ -72,5 +72,5 @@
             inline float getDuration()
                 { return this->duration_; }
- 
+
         protected:
             bool setInvisible(bool invisibility); //!< Set the Pawn to be invisible or visible again.
@@ -78,5 +78,5 @@
             void initializeIdentifier(void);
             virtual void pickupTimerCallback(void); //!< Function that gets called when the timer ends.
-        
+
         private:
             void initialize(void); //!< Initializes the member variables.
Index: code/trunk/src/modules/pickup/items/MetaPickup.cc
===================================================================
--- code/trunk/src/modules/pickup/items/MetaPickup.cc	(revision 6901)
+++ code/trunk/src/modules/pickup/items/MetaPickup.cc	(revision 7163)
@@ -34,4 +34,5 @@
 #include "core/CoreIncludes.h"
 #include "core/XMLPort.h"
+#include "worldentities/pawns/Pawn.h"
 #include "interfaces/PickupCarrier.h"
 #include "pickup/PickupIdentifier.h"
@@ -40,12 +41,14 @@
 
 namespace orxonox {
- 
+
     CreateFactory(MetaPickup);
-    
+
     //! Setting the static variables to their values.
     /*static*/ const std::string MetaPickup::metaTypeNone_s = "none";
     /*static*/ const std::string MetaPickup::metaTypeUse_s = "use";
     /*static*/ const std::string MetaPickup::metaTypeDrop_s = "drop";
-    
+    /*static*/ const std::string MetaPickup::metaTypeDestroy_s = "destroy";
+    /*static*/ const std::string MetaPickup::metaTypeDestroyCarrier_s = "destroyCarrier";
+
     /**
     @brief
@@ -55,8 +58,8 @@
     {
         RegisterObject(MetaPickup);
-        
+
         this->initialize();
     }
-    
+
     /**
     @brief
@@ -65,7 +68,7 @@
     MetaPickup::~MetaPickup()
     {
-        
-    }
-    
+
+    }
+
     /**
     @brief
@@ -75,10 +78,10 @@
     {
         this->addTarget(ClassIdentifier<PickupCarrier>::getIdentifier());
-        
+
         this->setActivationTypeDirect(pickupActivationType::immediate);
         this->setDurationTypeDirect(pickupDurationType::once);
         this->metaType_ = pickupMetaType::none;
     }
-    
+
     /**
     @brief
@@ -91,5 +94,5 @@
         this->pickupIdentifier_->addParameter(type, val);
     }
-    
+
     /**
     @brief
@@ -99,10 +102,10 @@
     {
         SUPER(MetaPickup, XMLPort, xmlelement, mode);
-        
+
         XMLPortParam(MetaPickup, "metaType", setMetaType, getMetaType, xmlelement, mode);
-        
+
         this->initializeIdentifier();
     }
-    
+
     /**
     @brief
@@ -113,5 +116,5 @@
     {
         SUPER(MetaPickup, changedUsed);
-        
+
         //! If the MetaPickup transited to used.
         if(this->isUsed())
@@ -120,6 +123,12 @@
             if(this->getMetaTypeDirect() != pickupMetaType::none && carrier != NULL)
             {
+                if(this->getMetaTypeDirect() == pickupMetaType::destroyCarrier)
+                {
+                    Pawn* pawn = orxonox_cast<Pawn*>(carrier);
+                    pawn->kill();
+                    return;
+                }
                 std::set<Pickupable*> pickups = carrier->getPickups();
-                //! Set all Pickupables carried by the PickupCarrier either to used or drop them, depending o the meta type.
+                //! Set all Pickupables carried by the PickupCarrier either to used or drop them, depending on the meta type.
                 for(std::set<Pickupable*>::iterator it = pickups.begin(); it != pickups.end(); it++)
                 {
@@ -136,13 +145,20 @@
                         if(pickup != NULL && pickup != this)
                         {
-                            carrier->drop(pickup);
+                            pickup->drop();
+                        }
+                    }
+                    if(this->getMetaTypeDirect() == pickupMetaType::destroy)
+                    {
+                        if(pickup != NULL && pickup != this)
+                        {
+                            pickup->Pickupable::destroy();
                         }
                     }
                 }
             }
-            this->destroy();
-        }
-    }
-        
+            this->Pickupable::destroy();
+        }
+    }
+
     /**
     @brief
@@ -155,13 +171,13 @@
         if(item == NULL)
             item = new MetaPickup(this);
-        
+
         SUPER(MetaPickup, clone, item);
-        
+
         MetaPickup* pickup = dynamic_cast<MetaPickup*>(item);
         pickup->setMetaTypeDirect(this->getMetaTypeDirect());
-        
+
         pickup->initializeIdentifier();
     }
-    
+
     /**
     @brief
@@ -180,9 +196,13 @@
             case pickupMetaType::drop:
                 return MetaPickup::metaTypeDrop_s;
+            case pickupMetaType::destroy:
+                return MetaPickup::metaTypeDestroy_s;
+            case pickupMetaType::destroyCarrier:
+                return MetaPickup::metaTypeDestroyCarrier_s;
             default:
                 return BLANKSTRING;
         }
     }
-    
+
     /**
     @brief
@@ -205,5 +225,15 @@
             this->setMetaTypeDirect(pickupMetaType::drop);
         }
-    }
-    
+        else if(type == MetaPickup::metaTypeDestroy_s)
+        {
+            this->setMetaTypeDirect(pickupMetaType::destroy);
+        }
+        else if(type == MetaPickup::metaTypeDestroyCarrier_s)
+        {
+            this->setMetaTypeDirect(pickupMetaType::destroyCarrier);
+        }
+        else
+            COUT(2) << "Invalid metaType '" << type << "' in MetaPickup." << std::endl;
+    }
+
 }
Index: code/trunk/src/modules/pickup/items/MetaPickup.h
===================================================================
--- code/trunk/src/modules/pickup/items/MetaPickup.h	(revision 6901)
+++ code/trunk/src/modules/pickup/items/MetaPickup.h	(revision 7163)
@@ -48,11 +48,17 @@
             none,
             use,
-            drop
+            drop,
+            destroy,
+            destroyCarrier
         };
     }
-    
+
     /**
     @brief
-        The MetaPickup is a pickup that can, depending on the parameters, either drop all pickups of the PickupCarrier that picks it up, or use all the unused pickups of the PickupCarrier, that picks it up. The parameter to set for this is the metaType and it can be used with the values 'none', 'drop' and 'use'.
+        The MetaPickup is a pickup that can, depending on the parameter 'metaType', do different things. If the 'metaType' is set to
+        1) 'use', all the pickups, the PickupCarrier has, are immediately set to used upon pickup of the MetaPickup.
+        2) 'drop', all the pickups, the PickupCarrier has, are immediately dropped upon pickup of the MetaPickup.
+        3) 'destroy', all the pickups, the PickupCarrier has, are immediately destroyed upon pickup of the MetaPickup.
+        4) 'destroyCarrier', the PickupCarrier is immediately destroyed upon pickup of the MetaPickup.
     @author
         Damian 'Mozork' Frick
@@ -60,14 +66,14 @@
     class _PickupExport MetaPickup : public Pickup
     {
-        
+
         public:
             MetaPickup(BaseObject* creator); //!< Constructor. Registers and initializes the object.
             virtual ~MetaPickup(); //!< Destructor.
-            
+
             virtual void XMLPort(Element& xmlelement, orxonox::XMLPort::Mode mode); //!< Method for creating a MetaPickup object through XML.
-            
+
             virtual void changedUsed(void); //!< Is called when the pickup has transited from used to unused or the other way around.
             virtual void clone(OrxonoxClass*& item); //!< Creates a duplicate of the input OrxonoxClass.
-            
+
             /**
             @brief Returns the meta type of the MetaPickup.
@@ -77,8 +83,8 @@
                 { return this->metaType_; }
             const std::string& getMetaType(void); //!< Get the meta type of this MetaPickup.
-            
+
         protected:
             void initializeIdentifier(void); //!< Initializes the PickupIdentifier of this pickup.
-            
+
             /**
             @brief Set the meta type of the MetaPickup.
@@ -88,16 +94,18 @@
                 { this->metaType_ =  type; }
             void setMetaType(const std::string& type); //!< Set the meta type of this MetaPickup.
-            
+
         private:
             void initialize(void); //!< Initializes the member variables.
-            
+
             pickupMetaType::Value metaType_; //!< The meta type of the MetaPickup, determines which actions are taken.
-            
+
             //! Static strings for the meta types.
             static const std::string metaTypeNone_s;
             static const std::string metaTypeUse_s;
             static const std::string metaTypeDrop_s;
-            
-        
+            static const std::string metaTypeDestroy_s;
+            static const std::string metaTypeDestroyCarrier_s;
+
+
     };
 
Index: code/trunk/src/modules/pickup/items/ShieldPickup.cc
===================================================================
--- code/trunk/src/modules/pickup/items/ShieldPickup.cc	(revision 7163)
+++ code/trunk/src/modules/pickup/items/ShieldPickup.cc	(revision 7163)
@@ -0,0 +1,274 @@
+/*
+ *   ORXONOX - the hottest 3D action shooter ever to exist
+ *                    > www.orxonox.net <
+ *
+ *
+ *   License notice:
+ *
+ *   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 2
+ *   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., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ *
+ *   Author:
+ *      Eric Beier
+ *   Co-authors:
+ *      ...
+ *
+ */
+
+/**
+    @file ShieldPickup.cc
+    @brief Implementation of the ShieldPickup class.
+*/
+
+#include "ShieldPickup.h"
+
+#include "core/CoreIncludes.h"
+#include "core/XMLPort.h"
+#include "util/StringUtils.h"
+
+#include "worldentities/pawns/SpaceShip.h"
+#include "items/Engine.h"
+#include "pickup/PickupIdentifier.h"
+
+#include <sstream>
+
+
+namespace orxonox
+{
+    CreateFactory(ShieldPickup);
+
+    /**
+    @brief
+        Constructor. Registers the object and initializes the member variables.
+    */
+    ShieldPickup::ShieldPickup(BaseObject* creator) : Pickup(creator)
+    {
+        RegisterObject(ShieldPickup);
+
+        this->initialize();
+    }
+
+    /**
+    @brief
+        Destructor.
+    */
+    ShieldPickup::~ShieldPickup()
+    {
+
+    }
+
+    /**
+    @brief
+    Helper to transform the PickupCarrier to a Pawn, and throw an error message if the conversion fails.
+    @return
+    A pointer to the Pawn, or NULL if the conversion failed.
+    */
+    Pawn* ShieldPickup::carrierToPawnHelper(void)
+    {
+        PickupCarrier* carrier = this->getCarrier();
+        Pawn* pawn = dynamic_cast<Pawn*>(carrier);
+
+        if(pawn == NULL)
+        {
+            COUT(1) << "Invalid PickupCarrier in ShieldPickup." << std::endl;
+        }
+        return pawn;
+    }
+
+    /**
+    @brief
+        Initializes the member variables.
+    */
+    void ShieldPickup::initialize(void)
+    {
+        this->duration_ = 0.0f;
+        this->shieldAbsorption_ = 0.0f;
+        this->shieldHealth_ = 0.0f;
+
+        this->addTarget(ClassIdentifier<Pawn>::getIdentifier());
+    }
+
+    /**
+    @brief
+        Initializes the PickupIdentifier of this pickup.
+    */
+    void ShieldPickup::initializeIdentifier(void)
+    {
+        std::stringstream stream;
+        stream << this->getDuration();
+        std::string type1 = "duration";
+        std::string val1 = stream.str();
+        this->pickupIdentifier_->addParameter(type1, val1);
+
+        stream.clear();
+        stream << this->getShieldHealth();
+        std::string type2 = "ShieldHealth";
+        std::string val2 = stream.str();
+        this->pickupIdentifier_->addParameter(type2, val2);
+
+        stream.clear();
+        stream << this->getShieldAbsorption();
+        std::string type3 = "ShieldAbsorption";
+        std::string val3 = stream.str();
+        this->pickupIdentifier_->addParameter(type3, val3);
+
+    }
+
+    /**
+    @brief
+        Method for creating a ShieldPickup object through XML.
+    */
+    void ShieldPickup::XMLPort(Element& xmlelement, orxonox::XMLPort::Mode mode)
+    {
+        SUPER(ShieldPickup, XMLPort, xmlelement, mode);
+
+        XMLPortParam(ShieldPickup, "duration", setDuration, getDuration, xmlelement, mode);
+        XMLPortParam(ShieldPickup, "shieldhealth", setShieldHealth, getShieldHealth, xmlelement, mode);
+        XMLPortParam(ShieldPickup, "shieldabsorption", setShieldAbsorption, getShieldAbsorption, xmlelement, mode);
+
+        this->initializeIdentifier();
+    }
+
+    /**
+    @brief
+        Is called when the pickup has transited from used to unused or the other way around.
+    */
+    void ShieldPickup::changedUsed(void)
+    {
+        SUPER(ShieldPickup, changedUsed);
+
+        //! If the pickup is not picked up nothing must be done.
+        if(!this->isPickedUp())
+            return;
+
+        Pawn* pawn = this->carrierToPawnHelper();
+        if(pawn == NULL)
+            this->Pickupable::destroy();
+
+        //! If the pickup has transited to used.
+        if(this->isUsed())
+        {
+            if(!this->getTimer()->isActive() && this->getTimer()->getRemainingTime() > 0.0f)
+            {
+                this->getTimer()->unpauseTimer();
+            }
+            else
+            {
+                this->startPickupTimer(this->getDuration());
+            }
+            pawn->setShieldAbsorption(this->getShieldAbsorption());
+            pawn->setShieldHealth(this->getShieldHealth());
+        }
+        else
+        {
+            pawn->setShieldAbsorption(0.0f);
+            this->setShieldHealth(pawn->getShieldHealth());
+            pawn->setShieldHealth(0.0f);
+
+            if(this->isOnce())
+            {
+                if(!this->getTimer()->isActive() && this->getTimer()->getRemainingTime() == this->getDuration())
+                {
+                    this->Pickupable::destroy();
+                }
+                else
+                {
+                    this->getTimer()->pauseTimer();
+                }
+            }
+        }
+    }
+
+    /**
+    @brief
+        Creates a duplicate of the input OrxonoxClass.
+    @param item
+        A pointer to the Orxonox class.
+    */
+    void ShieldPickup::clone(OrxonoxClass*& item)
+    {
+        if(item == NULL)
+            item = new ShieldPickup(this);
+
+        SUPER(ShieldPickup, clone, item);
+
+        ShieldPickup* pickup = dynamic_cast<ShieldPickup*>(item);
+        pickup->setDuration(this->getDuration());
+        pickup->setShieldAbsorption(this->getShieldAbsorption());
+        pickup->setShieldHealth(this->getShieldHealth());
+        pickup->initializeIdentifier();
+    }
+
+    /**
+    @brief
+    Sets the percentage the shield absorbs of the dealt damage.
+    @param shieldAbsorption
+    The shieldAbsorption. Has to be between 0 and 1
+    */
+    void ShieldPickup::setShieldAbsorption(float shieldAbsorption)
+    {
+        if (shieldAbsorption>=0 && shieldAbsorption<=1)
+        {
+            this->shieldAbsorption_=shieldAbsorption;
+        }
+        else
+        {
+            COUT(1) << "Invalid Absorption in ShieldPickup." << std::endl;
+            this->shieldAbsorption_=0;
+        }
+    }
+
+    /**
+    @brief
+    Sets the health of the shield.
+    @param shieldHealth
+    The shieldHealth
+    */
+    void ShieldPickup::setShieldHealth(float shieldHealth)
+    {
+        if (shieldHealth>=0)
+        {
+            this->shieldHealth_=shieldHealth;
+        }
+        else
+        {
+            COUT(1) << "Invalid Shieldhealth in ShieldPickup." << std::endl;
+            this->shieldHealth_=0;
+        }
+    }
+
+    /**
+    @brief
+        Sets the duration.
+    @param duration
+        The duration
+    */
+    void ShieldPickup::setDuration(float duration)
+    {
+        if(duration >= 0.0f)
+        {
+            this->duration_ = duration;
+        }
+        else
+        {
+            COUT(1) << "Invalid duration in ShieldPickup." << std::endl;
+            this->duration_ = 0.0f;
+        }
+    }
+
+    void ShieldPickup::pickupTimerCallback(void)
+    {
+        this->setUsed(false);
+    }
+}
Index: code/trunk/src/modules/pickup/items/ShieldPickup.h
===================================================================
--- code/trunk/src/modules/pickup/items/ShieldPickup.h	(revision 7163)
+++ code/trunk/src/modules/pickup/items/ShieldPickup.h	(revision 7163)
@@ -0,0 +1,99 @@
+
+/*
+ *   ORXONOX - the hottest 3D action shooter ever to exist
+ *                    > www.orxonox.net <
+ *
+ *
+ *   License notice:
+ *
+ *   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 2
+ *   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., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
+ *
+ *   Author:
+ *      Eric Beier
+ *   Co-authors:
+ *      ...
+ *
+ */
+
+/**
+    @file ShieldPickup.h
+    @brief Declaration of the ShieldPickup class.
+*/
+
+#ifndef _ShieldPickup_H__
+#define _ShieldPickup_H__
+
+#include "pickup/PickupPrereqs.h"
+
+#include <string>
+#include "worldentities/pawns/Pawn.h"
+#include "worldentities/StaticEntity.h"
+
+#include "pickup/Pickup.h"
+
+namespace orxonox {
+
+    /**
+    @brief
+        A Pickup which can add a Shield to the Pawn.
+
+        1) The percentage: The percentage the shield takes from the damage dealt to a Pawn
+        2) The hit points: The amount of damage points a shield can teake before collapsing
+        3) The activation type: 'immediate' or 'onUse'. defines if the item is used when it's picked up or only after the player chooses to use it.
+        4) The duration: the activation time of the pickup.
+
+    @author
+        Eric Beier
+    */
+    class _PickupExport ShieldPickup : public Pickup
+    {
+        public:
+
+            ShieldPickup(BaseObject* creator); //!< Constructor.
+            virtual ~ShieldPickup(); //!< Destructor.
+
+            virtual void XMLPort(Element& xmlelement, orxonox::XMLPort::Mode mode); //!< Method for creating a HealthPickup object through XML.
+
+            virtual void changedUsed(void); //!< Is called when the pickup has transited from used to unused or the other way around.
+            virtual void clone(OrxonoxClass*& item); //!< Creates a duplicate of the input OrxonoxClass.
+
+            inline float getDuration(void)
+                { return this->duration_; }
+            inline float getShieldHealth()
+                { return this->shieldHealth_; }
+            inline float getShieldAbsorption()
+                { return this->shieldAbsorption_; }
+
+        protected:
+            void initializeIdentifier(void); //!< Initializes the PickupIdentifier of this pickup.
+
+            virtual void pickupTimerCallback(void); //!< Function that gets called when timer ends.
+
+            void setDuration(float duration);
+            void setShieldHealth(float shieldHealth);
+            void setShieldAbsorption(float shieldAbsorption);
+
+        private:
+            void initialize(void); //!< Initializes the member variables.
+            Pawn* carrierToPawnHelper(void); //!< Helper to transform the PickupCarrier to a Pawn, and throw an error message if the conversion fails.
+
+            float duration_; //!< The health that is transferred to the Pawn.
+            float shieldHealth_;
+            float shieldAbsorption_; // Has to be between 0 and 1
+
+    };
+}
+
+#endif // _ShieldPickup_H__
Index: code/trunk/src/modules/pickup/items/SpeedPickup.cc
===================================================================
--- code/trunk/src/modules/pickup/items/SpeedPickup.cc	(revision 6901)
+++ code/trunk/src/modules/pickup/items/SpeedPickup.cc	(revision 7163)
@@ -136,6 +136,6 @@
         Engine* engine = this->carrierToEngineHelper();
         if(engine == NULL) //!< If the PickupCarrier is no Engine, then this pickup is useless and therefore is destroyed.
-            this->destroy();
-        
+            this->Pickupable::destroy();
+
         //! If the pickup has transited to used.
         if(this->isUsed())
@@ -156,10 +156,10 @@
             engine->setSpeedAdd(0.0f);
             engine->setSpeedMultiply(1.0f);
-            
+
             if(this->isOnce())
             {
                 if(!this->getTimer()->isActive() && this->getTimer()->getRemainingTime() == this->getDuration())
                 {
-                    this->destroy();
+                    this->Pickupable::destroy();
                 }
                 else
@@ -186,5 +186,5 @@
             COUT(1) << "Invalid PickupCarrier in SpeedPickup." << std::endl;
         }
-        
+
         return engine;
     }
@@ -269,5 +269,5 @@
 
     void SpeedPickup::pickupTimerCallback(void)
-    {       
+    {
         this->setUsed(false);
     }
Index: code/trunk/src/modules/pickup/items/SpeedPickup.h
===================================================================
--- code/trunk/src/modules/pickup/items/SpeedPickup.h	(revision 6901)
+++ code/trunk/src/modules/pickup/items/SpeedPickup.h	(revision 7163)
@@ -78,5 +78,5 @@
         protected:
             void initializeIdentifier(void); //!< Initializes the PickupIdentifier of this pickup.
-            
+
             virtual void pickupTimerCallback(void); //!< Function that gets called when timer ends.
 
