ResidualVM logo ResidualVM website - Forums - Contact us BuildBot - Doxygen - Wiki curved edge

pool.h

Go to the documentation of this file.
00001 /* ResidualVM - A 3D game interpreter
00002  *
00003  * ResidualVM is the legal property of its developers, whose names
00004  * are too numerous to list here. Please refer to the AUTHORS
00005  * file distributed with this source distribution.
00006  *
00007  * This program is free software; you can redistribute it and/or
00008  * modify it under the terms of the GNU General Public License
00009  * as published by the Free Software Foundation; either version 2
00010  * of the License, or (at your option) any later version.
00011  *
00012  * This program is distributed in the hope that it will be useful,
00013  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00014  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00015  * GNU General Public License for more details.
00016  *
00017  * You should have received a copy of the GNU General Public License
00018  * along with this program; if not, write to the Free Software
00019  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
00020  *
00021  */
00022 
00023 #ifndef GRIM_POOL_H
00024 #define GRIM_POOL_H
00025 
00026 #include "common/hashmap.h"
00027 #include "common/list.h"
00028 
00029 #include "engines/grim/savegame.h"
00030 
00031 namespace Grim {
00032 
00033 template<class T> class Pool;
00034 
00035 class PoolObjectBase {
00036 public:
00037     virtual ~PoolObjectBase() { };
00038     virtual int getId() const = 0;
00039     virtual int32 getTag() const = 0;
00040 };
00041 
00042 template<class T>
00043 class PoolObject : public PoolObjectBase {
00044 public:
00045     class Pool {
00046     public:
00047         template<class it, class Type>
00048         class Iterator {
00049         public:
00050             Iterator(const Iterator &i) : _i(i._i) { }
00051             Iterator(const it &i) : _i(i) { }
00052 
00053             int32 getId() const { return _i->_key; }
00054             Type &getValue() const { return _i->_value; }
00055 
00056             Type &operator*() const { return _i->_value; }
00057 
00058             Iterator &operator=(const Iterator &i) { _i = i._i; return *this; }
00059 
00060             bool operator==(const Iterator i) const { return _i == i._i; }
00061             bool operator!=(const Iterator i) const { return _i != i._i; }
00062 
00063             Iterator &operator++() { ++_i; return *this; }
00064             Iterator operator++(int) { Iterator iter = *this; ++_i; return iter; }
00065 
00066             Iterator &operator--() { --_i; return *this; }
00067             Iterator operator--(int) { Iterator iter = *this; --_i; return iter; }
00068 
00069         private:
00070             it _i;
00071         };
00072 
00073         typedef Iterator<typename Common::HashMap<int32, T *>::iterator, T *> iterator;
00074         typedef Iterator<typename Common::HashMap<int32, T *>::const_iterator, T *const> const_iterator;
00075 
00076         Pool();
00077         ~Pool();
00078 
00079         void addObject(T *obj);
00080         void removeObject(int32 id);
00081 
00082         T *getObject(int32 id);
00083         iterator begin();
00084         const_iterator begin() const;
00085         iterator end();
00086         const_iterator end() const;
00087         int getSize() const;
00088         void deleteObjects();
00089         void saveObjects(SaveGame *save);
00090         void restoreObjects(SaveGame *save);
00091 
00092     private:
00093         bool _restoring;
00094         Common::HashMap<int32, T*> _map;
00095     };
00096 
00103     class Ptr {
00104     public:
00105         Ptr() : _obj(NULL) { }
00106         Ptr(T *obj) : _obj(obj) {
00107             if (_obj)
00108                 _obj->addPointer(this);
00109         }
00110         Ptr(const Ptr &ptr) : _obj(ptr._obj) {
00111             if (_obj)
00112                 _obj->addPointer(this);
00113         }
00114         ~Ptr() {
00115             if (_obj)
00116                 _obj->removePointer(this);
00117         }
00118 
00119         Ptr &operator=(T *obj);
00120         Ptr &operator=(const Ptr &ptr);
00121 
00122         inline operator bool() const { return _obj; }
00123         inline bool operator!() const { return !_obj; }
00124         inline bool operator==(T *obj) const { return _obj == obj; }
00125         inline bool operator!=(T *obj) const { return _obj != obj; }
00126 
00127         inline T *operator->() const { return _obj; }
00128         inline T &operator*() const { return *_obj; }
00129         inline operator T*() const { return _obj; }
00130 
00131     private:
00132         inline void reset() { _obj = NULL; }
00133 
00134         T *_obj;
00135 
00136         friend class PoolObject;
00137     };
00138 
00139     virtual ~PoolObject();
00140 
00141     void setId(int id);
00142 
00143     int getId() const override;
00144     virtual int32 getTag() const override { return T::getStaticTag(); }
00145 
00146     static Pool &getPool();
00147 
00148 protected:
00149     PoolObject();
00150 
00151     static void saveStaticState(SaveGame *state) {}
00152     static void restoreStaticState(SaveGame *state) {}
00153 
00154 private:
00155     void addPointer(Ptr *pointer) { _pointers.push_back(pointer); }
00156     void removePointer(Ptr *pointer) { _pointers.remove(pointer); }
00157 
00158     int _id;
00159     static int s_id;
00160     static Pool *s_pool;
00161 
00162     Common::List<Ptr *> _pointers;
00163 
00164     friend class Pool;
00165     friend class Ptr;
00166 };
00167 
00168 template <class T>
00169 bool operator==(T *obj, const typename PoolObject<T>::Ptr &ptr) {
00170     return obj == ptr._obj;
00171 }
00172 
00173 template <class T>
00174 bool operator!=(T *obj, const typename PoolObject<T>::Ptr &ptr) {
00175     return obj != ptr._obj;
00176 }
00177 
00178 template <class T>
00179 int PoolObject<T>::s_id = 0;
00180 
00181 template <class T>
00182 typename PoolObject<T>::Pool *PoolObject<T>::s_pool = NULL;
00183 
00184 template <class T>
00185 PoolObject<T>::PoolObject() {
00186     ++s_id;
00187     _id = s_id;
00188 
00189     if (!s_pool) {
00190         s_pool = new Pool();
00191     }
00192     s_pool->addObject(static_cast<T *>(this));
00193 }
00194 
00195 template <class T>
00196 PoolObject<T>::~PoolObject() {
00197     s_pool->removeObject(_id);
00198 
00199     for (typename Common::List<Ptr *>::iterator i = _pointers.begin(); i != _pointers.end(); ++i) {
00200         (*i)->reset();
00201     }
00202 }
00203 
00204 template <class T>
00205 void PoolObject<T>::setId(int id) {
00206     _id = id;
00207     if (id > s_id) {
00208         s_id = id;
00209     }
00210 }
00211 
00212 template <class T>
00213 int PoolObject<T>::getId() const {
00214     return _id;
00215 }
00216 
00217 template <class T>
00218 typename PoolObject<T>::Pool &PoolObject<T>::getPool() {
00219     if (!s_pool) {
00220         s_pool = new Pool();
00221     }
00222     return *s_pool;
00223 }
00224 
00229 template <class T>
00230 PoolObject<T>::Pool::Pool() :
00231     _restoring(false) {
00232 }
00233 
00234 template <class T>
00235 PoolObject<T>::Pool::~Pool() {
00236     PoolObject<T>::s_pool = NULL;
00237 }
00238 
00239 template <class T>
00240 void PoolObject<T>::Pool::addObject(T *obj) {
00241     if (!_restoring) {
00242         _map.setVal(obj->_id, obj);
00243     }
00244 }
00245 
00246 template <class T>
00247 void PoolObject<T>::Pool::removeObject(int32 id) {
00248     _map.erase(id);
00249 }
00250 
00251 template <class T>
00252 T *PoolObject<T>::Pool::getObject(int32 id) {
00253     return _map.getVal(id, NULL);
00254 }
00255 
00256 template <class T>
00257 typename PoolObject<T>::Pool::iterator PoolObject<T>::Pool::begin() {
00258     return iterator(_map.begin());
00259 }
00260 
00261 template <class T>
00262 typename PoolObject<T>::Pool::const_iterator PoolObject<T>::Pool::begin() const {
00263     return const_iterator(_map.begin());
00264 }
00265 
00266 template <class T>
00267 typename PoolObject<T>::Pool::iterator PoolObject<T>::Pool::end() {
00268     return iterator(_map.end());
00269 }
00270 
00271 template <class T>
00272 typename PoolObject<T>::Pool::const_iterator PoolObject<T>::Pool::end() const {
00273     return const_iterator(_map.end());
00274 }
00275 
00276 template <class T>
00277 int PoolObject<T>::Pool::getSize() const {
00278     return _map.size();
00279 }
00280 
00281 template <class T>
00282 void PoolObject<T>::Pool::deleteObjects() {
00283     while (!_map.empty()) {
00284         delete *begin();
00285     }
00286     delete this;
00287 }
00288 
00289 template <class T>
00290 void PoolObject<T>::Pool::saveObjects(SaveGame *state) {
00291     state->beginSection(T::getStaticTag());
00292 
00293     T::saveStaticState(state);
00294 
00295     state->writeLEUint32(_map.size());
00296     for (iterator i = begin(); i != end(); ++i) {
00297         T *a = *i;
00298         state->writeLESint32(i.getId());
00299 
00300         a->saveState(state);
00301     }
00302 
00303     state->endSection();
00304 }
00305 
00306 template <class T>
00307 void PoolObject<T>::Pool::restoreObjects(SaveGame *state) {
00308     state->beginSection(T::getStaticTag());
00309 
00310     T::restoreStaticState(state);
00311 
00312     int32 size = state->readLEUint32();
00313     _restoring = true;
00314     Common::HashMap<int32, T *> tempMap;
00315     for (int32 i = 0; i < size; ++i) {
00316         int32 id = state->readLESint32();
00317         T *t = _map.getVal(id);
00318         _map.erase(id);
00319         if (!t) {
00320             t = new T();
00321             t->setId(id);
00322         }
00323         tempMap[id] = t;
00324         t->restoreState(state);
00325     }
00326     for (iterator i = begin(); i != end(); ++i) {
00327         delete *i;
00328     }
00329     _map = tempMap;
00330     _restoring = false;
00331 
00332     state->endSection();
00333 }
00334 
00335 template<class T>
00336 typename PoolObject<T>::Ptr &PoolObject<T>::Ptr::operator=(T *obj) {
00337     if (_obj) {
00338         _obj->removePointer(this);
00339     }
00340     _obj = obj;
00341     if (obj) {
00342         obj->addPointer(this);
00343     }
00344 
00345     return *this;
00346 }
00347 
00348 template<class T>
00349 typename PoolObject<T>::Ptr &PoolObject<T>::Ptr::operator=(const Ptr &ptr) {
00350     if (_obj) {
00351         _obj->removePointer(this);
00352     }
00353     _obj = ptr._obj;
00354     if (_obj) {
00355         _obj->addPointer(this);
00356     }
00357 
00358     return *this;
00359 }
00360 
00361 }
00362 
00363 #endif


Generated on Sat May 18 2019 05:01:12 for ResidualVM by doxygen 1.7.1
curved edge   curved edge