Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: code/branches/objecthierarchie/src/Identifier.h @ 218

Last change on this file since 218 was 218, checked in by landauf, 16 years ago

added factory

File size: 7.3 KB
Line 
1#ifndef _Identifier_H__
2#define _Identifier_H__
3
4#include "ClassHierarchy.h"
5#include "IdentifierList.h"
6#include "ObjectList.h"
7#include "OrxonoxClass.h"
8#include "Factory.h"
9
10namespace orxonox
11{
12    // ##### Identifier #####
13    class Identifier
14    {
15        template <class T>
16        friend class ClassIdentifier;
17
18        template <class T>
19        friend class BaseIdentifier;
20
21        public:
22            void addObject(OrxonoxClass* object);
23            void removeObject(OrxonoxClass* object);
24
25            virtual OrxonoxClass* fabricate() {};
26
27            bool isA(Identifier* identifier);
28            bool isDirectlyA(Identifier* identifier);
29            bool isChildOf(Identifier* identifier);
30            bool isDirectChildOf(Identifier* identifier);
31            bool isParentOf(Identifier* identifier);
32            bool isDirectParentOf(Identifier* identifier);
33
34            std::string getName() { return this->name_; }
35            IdentifierList* getDirectParents() { return this->directParents_; }
36            IdentifierList* getAllParents() { return this->allParents_; }
37            IdentifierList* getDirectChildren() { return this->directChildren_; }
38            IdentifierList* getAllChildren() { return this->allChildren_; }
39
40        private:
41            Identifier();
42            Identifier(const Identifier& identifier) {}
43            virtual ~Identifier();
44            void initialize(IdentifierList* parents);
45
46            IdentifierList* directParents_;
47            IdentifierList* allParents_;
48            IdentifierList* directChildren_;
49            IdentifierList* allChildren_;
50
51            ObjectList* objects_;
52            std::string name_;
53
54            bool bIsAbstractClass_;
55            bool bCreatedOneObject_;
56    };
57
58
59    // ##### ClassIdentifier #####
60    template <class T>
61    class ClassIdentifier : public Identifier
62    {
63        public:
64            static ClassIdentifier<T>* registerClass(IdentifierList* parents, std::string name, bool bRootClass, bool bIsAbstractClass);
65            static ClassIdentifier<T>* getIdentifier();
66            OrxonoxClass* fabricate();
67            T* fabricateClass();
68
69        private:
70            ClassIdentifier();
71            ClassIdentifier(const ClassIdentifier<T>& identifier) {}
72            ~ClassIdentifier();
73
74            static ClassIdentifier<T>* pointer_;
75
76    };
77
78    template <class T>
79    ClassIdentifier<T>* ClassIdentifier<T>::pointer_ = NULL;
80
81    template <class T>
82    ClassIdentifier<T>::ClassIdentifier()
83    {
84    }
85
86    template <class T>
87    ClassIdentifier<T>::~ClassIdentifier()
88    {
89        this->pointer_ = NULL;
90    }
91
92    template <class T>
93    OrxonoxClass* ClassIdentifier<T>::fabricate()
94    {
95        return this->fabricateClass();
96    }
97
98    template <class T>
99    T* ClassIdentifier<T>::fabricateClass()
100    {
101        return new T;
102    }
103
104    template <class T>
105    ClassIdentifier<T>* ClassIdentifier<T>::registerClass(IdentifierList* parents, std::string name, bool bRootClass, bool bIsAbstractClass)
106    {
107        std::cout << "*** Register Class in " << name << "-Singleton.\n";
108        if (!pointer_)
109        {
110            std::cout << "*** Register Class in " << name << "-Singleton -> Create Singleton.\n";
111            if (parents || bRootClass)
112            {
113                pointer_ = new ClassIdentifier();
114                pointer_->name_ = name;
115                pointer_->bIsAbstractClass_ = bIsAbstractClass;
116
117                ClassFactory::add(name, pointer_);
118
119                pointer_->initialize(parents);
120            }
121            else
122            {
123                pointer_ = getIdentifier();
124            }
125        }
126
127        return pointer_;
128    }
129
130    template <class T>
131    ClassIdentifier<T>* ClassIdentifier<T>::getIdentifier()
132    {
133//        std::cout << "*** Get Identifier.\n";
134        if (!pointer_)
135        {
136            std::cout << "*** Get Identifier -> Create Class\n";
137            ClassHierarchy::getSingleton()->startCreatingHierarchy();
138            T* temp = new T();
139            ClassHierarchy::getSingleton()->stopCreatingHierarchy();
140            delete temp;
141        }
142
143        return pointer_;
144    }
145
146    // ##### BaseIdentifier #####
147    template <class B>
148    class BaseIdentifier
149    {
150        public:
151            BaseIdentifier();
152
153            BaseIdentifier<B>& operator= (Identifier* identifier)
154            {
155                if (!identifier->isA(ClassIdentifier<B>::getIdentifier()))
156                {
157                    std::cout << "Error: Class " << identifier->getName() << " is not a " << ClassIdentifier<B>::getIdentifier()->getName() << "!\n";
158                    std::cout << "Error: BaseIdentifier<" << ClassIdentifier<B>::getIdentifier()->getName() << "> = Class(" << identifier->getName() << ") is forbidden.\n";
159                    std::cout << "Aborting...\n";
160                    abort();
161                }
162                this->identifier_ = identifier;
163                return *this;
164            }
165
166            Identifier* operator* ()
167            {
168                return this->identifier_;
169            }
170
171            Identifier* operator-> () const
172            {
173                return this->identifier_;
174            }
175
176            B* fabricate()
177            {
178                OrxonoxClass* newObject = this->identifier_->fabricate();
179                if (newObject)
180                {
181                    return dynamic_cast<B*>(newObject);
182                }
183                else
184                {
185                    if (this->identifier_)
186                    {
187                        std::cout << "Error: Class " << this->identifier_->getName() << " is not a " << ClassIdentifier<B>::getIdentifier()->getName() << "!\n";
188                        std::cout << "Error: Couldn't fabricate a new Object.\n";
189                        std::cout << "Aborting...\n";
190                    }
191                    else
192                    {
193                        std::cout << "Error: Couldn't fabricate a new Object - Identifier is undefined.\n";
194                        std::cout << "Aborting...\n";
195                    }
196
197                    abort();
198                }
199            }
200
201            inline Identifier* getIdentifier()
202                { return this->identifier_; }
203            inline bool isA(Identifier* identifier)
204                { return this->identifier_->isA(identifier); }
205            inline bool isDirectlyA(Identifier* identifier)
206                { return this->identifier_->isDirectlyA(identifier); }
207            inline bool isChildOf(Identifier* identifier)
208                { return this->identifier_->isChildOf(identifier); }
209            inline bool isDirectChildOf(Identifier* identifier)
210                { return this->identifier_->isDirectChildOf(identifier); }
211            inline bool isParentOf(Identifier* identifier)
212                { return this->identifier_->isParentOf(identifier); }
213            inline bool isDirectParentOf(Identifier* identifier)
214                { return this->identifier_->isDirectParentOf(identifier); }
215
216        private:
217            Identifier* identifier_;
218    };
219
220    template <class B>
221    BaseIdentifier<B>::BaseIdentifier()
222    {
223        this->identifier_ = ClassIdentifier<B>::getIdentifier();
224    }
225}
226
227#endif
Note: See TracBrowser for help on using the repository browser.