Orxonox  0.0.5 Codename: Arcturus
Identifier.h
Go to the documentation of this file.
1 /*
2  * ORXONOX - the hottest 3D action shooter ever to exist
3  * > www.orxonox.net <
4  *
5  *
6  * License notice:
7  *
8  * This program is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU General Public License
10  * as published by the Free Software Foundation; either version 2
11  * of the License, or (at your option) any later version.
12  *
13  * This program is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16  * GNU General Public License for more details.
17  *
18  * You should have received a copy of the GNU General Public License
19  * along with this program; if not, write to the Free Software
20  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
21  *
22  * Author:
23  * Fabian 'x3n' Landau
24  * Co-authors:
25  * ...
26  *
27  */
28 
71 #ifndef _Identifier_H__
72 #define _Identifier_H__
73 
74 #include "core/CorePrereqs.h"
75 
76 #include <cassert>
77 #include <map>
78 #include <set>
79 #include <string>
80 #include <typeinfo>
81 #include <loki/TypeTraits.h>
82 
83 #include "util/Output.h"
84 #include "util/OrxAssert.h"
85 #include "core/object/ObjectList.h"
86 #include "core/object/Listable.h"
87 #include "core/object/Context.h"
89 #include "core/object/WeakPtr.h"
90 #include "IdentifierManager.h"
91 #include "Super.h"
92 
93 namespace orxonox
94 {
95  // ###############################
96  // ### Identifier ###
97  // ###############################
110  {
111  public:
112  struct InheritsFrom
113  {
114  virtual ~InheritsFrom() {}
115  virtual Identifier* getParent() const = 0;
116  };
117 
118  public:
119  Identifier(const std::string& name, Factory* factory, bool bLoadable);
120  virtual ~Identifier();
121 
122  // non-copyable:
123  Identifier(const Identifier&) = delete;
124  Identifier& operator=(const Identifier&) = delete;
125 
127  inline const std::string& getName() const { return this->name_; }
128 
130  virtual const std::type_info& getTypeInfo() = 0;
131 
133  inline uint32_t getNetworkID() const { return this->networkID_; }
134  void setNetworkID(uint32_t id);
135 
137  ORX_FORCEINLINE unsigned int getClassID() const { return this->classID_; }
138 
140  inline bool hasFactory() const { return (this->factory_ != nullptr); }
141 
142  Identifiable* fabricate(Context* context);
143 
145  inline bool isLoadable() const { return this->bLoadable_; }
146 
148  inline bool isVirtualBase() const { return this->bIsVirtualBase_; }
150  inline void setVirtualBase(bool bIsVirtualBase) { this->bIsVirtualBase_ = bIsVirtualBase; }
151 
153  inline bool isInitialized() const { return this->bInitialized_; }
154 
155  virtual void destroyObjects() = 0;
156 
157  virtual bool canDynamicCastObjectToIdentifierClass(Identifiable* object) const = 0;
158 
159  static bool initConfigValues_s; // TODO: this is a hack - remove it as soon as possible
160 
161 
165  Identifier& inheritsFrom(InheritsFrom* directParent);
166 
167  void initializeParents(const std::list<const Identifier*>& initializationTrace);
168  void finishInitialization();
169  void reset();
170 
171  bool isA(const Identifier* identifier) const;
172  bool isExactlyA(const Identifier* identifier) const;
173  bool isChildOf(const Identifier* identifier) const;
174  bool isDirectChildOf(const Identifier* identifier) const;
175  bool isParentOf(const Identifier* identifier) const;
176  bool isDirectParentOf(const Identifier* identifier) const;
177 
179  inline const std::list<const Identifier*>& getDirectParents() const { return this->directParents_; }
181  inline const std::list<const Identifier*>& getParents() const { return this->parents_; }
182 
184  inline const std::set<const Identifier*>& getDirectChildren() const { return this->directChildren_; }
186  inline const std::set<const Identifier*>& getChildren() const { return this->children_; }
187 
188 
192  virtual void updateConfigValues(bool updateChildren = true) const = 0;
193 
195  inline bool hasConfigValues() const { return this->bHasConfigValues_; }
196 
197  void addConfigValueContainer(const std::string& varname, ConfigValueContainer* container);
198  ConfigValueContainer* getConfigValueContainer(const std::string& varname);
199 
200 
205  inline const std::map<std::string, XMLPortParamContainer*>& getXMLPortParamMap() const { return this->xmlportParamContainers_; }
206 
208  inline const std::map<std::string, XMLPortObjectContainer*>& getXMLPortObjectMap() const { return this->xmlportObjectContainers_; }
209 
210  void addXMLPortParamContainer(const std::string& paramname, XMLPortParamContainer* container);
211  XMLPortParamContainer* getXMLPortParamContainer(const std::string& paramname);
212 
213  void addXMLPortObjectContainer(const std::string& sectionname, XMLPortObjectContainer* container);
214  XMLPortObjectContainer* getXMLPortObjectContainer(const std::string& sectionname);
215 
216  protected:
217  virtual void createSuperFunctionCaller() const = 0;
218 
219  private:
220  void verifyIdentifierTrace() const;
221  void addIfNotExists(std::list<const Identifier*>& list, const Identifier* identifierToAdd) const;
222 
223  std::list<const InheritsFrom*> manualDirectParents_;
224  std::list<const Identifier*> directParents_;
225  std::list<const Identifier*> parents_;
226 
227  std::set<const Identifier*> directChildren_;
228  std::set<const Identifier*> children_;
229 
231  bool bLoadable_;
235  uint32_t networkID_;
236  unsigned int classID_;
237 
239  std::map<std::string, ConfigValueContainer*> configValues_;
240 
241  std::map<std::string, XMLPortParamContainer*> xmlportParamContainers_;
242  std::map<std::string, XMLPortObjectContainer*> xmlportObjectContainers_;
243  };
244 
245  _CoreExport std::ostream& operator<<(std::ostream& out, const std::set<const Identifier*>& list);
246 
247 
248  // ###############################
249  // ### ClassIdentifier ###
250  // ###############################
261  template <class T>
263  {
264  static_assert(std::is_base_of<Identifiable, T>::value, "ClassIdentifier can only be used with Identifiables");
265 
266  #ifndef DOXYGEN_SHOULD_SKIP_THIS
267  #define SUPER_INTRUSIVE_DECLARATION_INCLUDE
268  #include "Super.h"
269  #endif
270 
271  public:
272  ClassIdentifier(const std::string& name, Factory* factory, bool bLoadable) : Identifier(name, factory, bLoadable)
273  {
274  OrxVerify(ClassIdentifier<T>::classIdentifier_s == nullptr, "Assertion failed in ClassIdentifier of type " << typeid(T).name());
276 
278  }
280  {
282  }
283 
284  bool initializeObject(T* object);
285 
286  virtual void updateConfigValues(bool updateChildren = true) const override;
287 
288  virtual const std::type_info& getTypeInfo() override
289  { return typeid(T); }
290 
291  virtual bool canDynamicCastObjectToIdentifierClass(Identifiable* object) const override
292  { return dynamic_cast<T*>(object) != nullptr; }
293 
294  virtual void destroyObjects() override;
295 
296  static ClassIdentifier<T>* getIdentifier();
297 
298  private:
299  // non-copyable:
300  ClassIdentifier(const ClassIdentifier<T>&) = delete;
301  ClassIdentifier& operator=(const ClassIdentifier<T>&) = delete;
302 
303  void setConfigValues(T* object, Configurable*) const;
304  void setConfigValues(T* object, Identifiable*) const;
305 
306  void addObjectToList(T* object, Listable*);
307  void addObjectToList(T* object, Identifiable*);
308 
309  void destroyObjects(Listable*);
310  void destroyObjects(void*);
311 
312  void destroyObject(Destroyable* object);
313  void destroyObject(void* object);
314 
315  void updateConfigValues(bool updateChildren, Listable*) const;
316  void updateConfigValues(bool updateChildren, Identifiable*) const;
317 
319  };
320 
321  template <class T>
323 
328  template <class T>
330  {
331  if (ClassIdentifier<T>::classIdentifier_s == nullptr)
332  ClassIdentifier<T>::classIdentifier_s = (ClassIdentifier<T>*) IdentifierManager::getInstance().getIdentifierByTypeInfo(typeid(T));
333 
334  OrxVerify(ClassIdentifier<T>::classIdentifier_s != nullptr, "Did you forget to register the class of type " << typeid(T).name() << "?");
335  return ClassIdentifier<T>::classIdentifier_s;
336  }
337 
342  template <class T>
344  {
345  orxout(verbose, context::object_list) << "Register Object: " << this->getName() << endl;
346 
347  object->identifier_ = this;
348  if (IdentifierManager::getInstance().isCreatingHierarchy())
349  {
351 
353  this->setConfigValues(object, object);
354 
355  return true;
356  }
357  else
358  {
359  this->addObjectToList(object, object);
360 
361  // Add pointer of type T to the map in the Identifiable instance that enables "dynamic_casts"
362  object->objectPointers_.emplace_back(this->getClassID(), static_cast<void*>(object));
363  return false;
364  }
365  }
366 
370  template <class T>
372  {
373  object->setConfigValues();
374  }
375 
376  template <class T>
378  {
379  // no action
380  }
381 
385  template <class T>
387  {
388  if (listable->getContext())
389  listable->getContext()->addObject(object);
390  }
391 
392  template <class T>
394  {
395  // no action
396  }
397 
402  template <class T>
404  {
405  this->destroyObjects((T*)nullptr);
406  }
407 
411  template <class T>
413  {
414  ObjectList<T> list(Context::getRootContext()->getObjectList(this));
415  for (typename ObjectList<T>::iterator it = list.begin(); it != list.end(); )
416  this->destroyObject(*(it++));
417  }
418 
419  template <class T>
421  {
422  // no action
423  }
424 
428  template <class T>
430  {
431  object->destroy();
432  }
433 
434  template <class T>
436  {
437  delete static_cast<Identifiable*>(object);
438  }
439 
443  template <class T>
444  void ClassIdentifier<T>::updateConfigValues(bool updateChildren) const
445  {
446  this->updateConfigValues(updateChildren, static_cast<T*>(nullptr));
447  }
448 
449  template <class T>
450  void ClassIdentifier<T>::updateConfigValues(bool updateChildren, Listable*) const
451  {
452  if (!this->hasConfigValues())
453  return;
454 
455  for (T* object : ObjectList<T>())
456  this->setConfigValues(object, object);
457 
458  if (updateChildren)
459  for (const Identifier* child : this->getChildren())
460  child->updateConfigValues(false);
461  }
462 
463  template <class T>
464  void ClassIdentifier<T>::updateConfigValues(bool updateChildren, Identifiable*) const
465  {
466  // no action
467  }
468 
469 
470  // ###############################
471  // ### orxonox_cast ###
472  // ###############################
484  template <class T, class U>
486  {
487 #ifdef ORXONOX_COMPILER_MSVC
488  typedef Loki::TypeTraits<typename Loki::TypeTraits<T>::PointeeType>::NonConstType ClassType;
489  if (source != nullptr)
490  return source->template getDerivedPointer<ClassType>(ClassIdentifier<ClassType>::getIdentifier()->getClassID());
491  else
492  return nullptr;
493 #else
494  return dynamic_cast<T>(source);
495 #endif
496  }
497 }
498 
499 #endif /* _Identifier_H__ */
static void destroy(ClassIdentifier< T > *)
Definition: Super.h:321
The ClassIdentifier is derived from Identifier and holds all class-specific functions and variables t...
Definition: Identifier.h:262
The ConfigValuecontainer contains all needed information about a configurable variable.
Definition: ConfigValueContainer.h:98
void source(const std::string &filename)
Reads the content of a file and executes the commands in it line by line.
Definition: ConsoleCommandCompilation.cc:167
Definition: XMLPort.h:323
bool bHasConfigValues_
True if this class has at least one assigned config value.
Definition: Identifier.h:238
static WeakPtr< ClassIdentifier< T > > classIdentifier_s
Definition: Identifier.h:318
static void initialize(ClassIdentifier< T > *)
Definition: Super.h:312
ObjectListIterator< T > begin()
Returns an Iterator to the first element in the list.
Definition: ObjectList.h:82
void destroyObject(Destroyable *object)
Call &#39;object->destroy()&#39; for Destroyables and &#39;delete object&#39; for all other types.
Definition: Identifier.h:429
std::map< std::string, ConfigValueContainer * > configValues_
A map to link the string of configurable variables with their ConfigValueContainer.
Definition: Identifier.h:239
Listable stores the entries of all object lists pointing to this instance.
Definition: Listable.h:50
ClassIdentifier(const std::string &name, Factory *factory, bool bLoadable)
Definition: Identifier.h:272
bool bIsVirtualBase_
If true, it is recommended to inherit virtually from this class. This changes the order of initializa...
Definition: Identifier.h:232
Shared library macros, enums, constants and forward declarations for the core library ...
::std::string string
Definition: gtest-port.h:756
bool isLoadable() const
Returns true if the class can be loaded through XML.
Definition: Identifier.h:145
uint32_t networkID_
The network ID to identify a class through the network.
Definition: Identifier.h:235
virtual bool canDynamicCastObjectToIdentifierClass(Identifiable *object) const override
Definition: Identifier.h:291
Output level, usually not visible, used for unimportant debug information.
Definition: OutputDefinitions.h:99
virtual const std::type_info & getTypeInfo() override
Returns the type_info of the class as it is returned by typeid(T)
Definition: Identifier.h:288
helper class to manually define inheritance
Definition: Identifier.h:112
void setConfigValues(T *object, Configurable *) const
Only configures the object if is a Configurable.
Definition: Identifier.h:371
void setVirtualBase(bool bIsVirtualBase)
Defines if child classes should inherit virtually from this class.
Definition: Identifier.h:150
Definition of WeakPtr<T>, wraps a pointer to an object.
virtual ~InheritsFrom()
Definition: Identifier.h:114
WeakPtr wraps a pointer to an object, which becomes nullptr if the object is deleted.
Definition: CorePrereqs.h:236
Identifiable is needed to create the class-hierarchy at startup and to store the Identifier.
Definition: Identifiable.h:50
This is the base class of all objects which may contain config values.
Definition: Configurable.h:47
unsigned int classID_
Uniquely identifies a class (might not be the same as the networkID_)
Definition: Identifier.h:236
std::map< std::string, XMLPortParamContainer * > xmlportParamContainers_
All loadable parameters.
Definition: Identifier.h:241
bool hasConfigValues() const
Returns true if this class has at least one config value.
Definition: Identifier.h:195
~ClassIdentifier()
Definition: Identifier.h:279
std::map< std::string, XMLPortObjectContainer * > xmlportObjectContainers_
All attachable objects.
Definition: Identifier.h:242
void createdObject(Identifiable *identifiable)
Notifies the IdentifierManager about a newly created object while creating the class hierarchy...
Definition: IdentifierManager.cc:194
std::list< const InheritsFrom * > manualDirectParents_
Manually defined direct parents.
Definition: Identifier.h:223
void addObjectToList(T *object, Listable *)
Only adds the object to the object list if is a Listable.
Definition: Identifier.h:386
static ClassIdentifier< T > * getIdentifier()
Returns the only instance of this class.
Definition: Identifier.h:329
Definition: XMLPort.h:504
std::list< const Identifier * > parents_
The parents of the class the Identifier belongs to (sorted by their order of initialization) ...
Definition: Identifier.h:225
static bool initConfigValues_s
Definition: Identifier.h:159
const std::map< std::string, XMLPortObjectContainer * > & getXMLPortObjectMap() const
Returns the map that stores all XMLPort objects.
Definition: Identifier.h:208
const std::map< std::string, XMLPortParamContainer * > & getXMLPortParamMap() const
Returns the map that stores all XMLPort params.
Definition: Identifier.h:205
const std::set< const Identifier * > & getChildren() const
Returns the children of the class the Identifier belongs to.
Definition: Identifier.h:186
Identifier * getIdentifierByTypeInfo(const std::type_info &typeInfo)
Returns the Identifier with a given typeid-name.
Definition: IdentifierManager.cc:260
static Context * getRootContext()
Definition: Context.cc:87
bool isVirtualBase() const
Returns true if child classes should inherit virtually from this class.
Definition: Identifier.h:148
bool hasFactory() const
Returns true if the Identifier has a Factory.
Definition: Identifier.h:140
Factory * factory_
The Factory, able to create new objects of the given class (if available)
Definition: Identifier.h:234
bool bLoadable_
False = it&#39;s not permitted to load the object through XML.
Definition: Identifier.h:231
Definition: TypeTraits.h:165
OutputStream & orxout(OutputLevel level=level::debug_output, const OutputContextContainer &context=context::undefined())
This helper function returns a reference to a commonly used instance of OutputStream.
Definition: Output.h:81
Die Wagnis Klasse hat die folgenden Aufgaben:
Definition: ApplicationPaths.cc:66
bool bInitialized_
Is true if the Identifier was completely initialized.
Definition: Identifier.h:230
const std::list< const Identifier * > & getDirectParents() const
Returns the direct parents of the class the Identifier belongs to.
Definition: Identifier.h:179
virtual void destroyObjects() override
Destroy all objects of this class (must be Listable).
Definition: Identifier.h:403
#define _CoreExport
Definition: CorePrereqs.h:61
const std::list< const Identifier * > & getParents() const
Returns the parents of the class the Identifier belongs to.
Definition: Identifier.h:181
std::string name_
The name of the class the Identifier belongs to.
Definition: Identifier.h:233
std::list< const Identifier * > directParents_
The direct parents of the class the Identifier belongs to (sorted by their order of initialization) ...
Definition: Identifier.h:224
The Identifier is used to identify the class of an object and to store information about the class...
Definition: Identifier.h:109
Declaration of Destroyable, the base class of all objects which can be used with StrongPtr and WeakPt...
Defines the helper function orxout() and includes all necessary headers to use the output system...
ORX_FORCEINLINE T orxonox_cast(U *source)
Casts on object of type Identifiable to any derived type that is registered in the class hierarchy...
Definition: Identifier.h:485
ObjectListIterator< T > end()
Returns an Iterator to the element after the last element in the list.
Definition: ObjectList.h:85
Definition: InputPrereqs.h:78
The ObjectList contains all objects of the given class.
Definition: CorePrereqs.h:204
Definition: Context.h:45
bool initializeObject(T *object)
Adds an object of the given type to the ObjectList.
Definition: Identifier.h:343
Definition of the ObjectList class, a wrapper of ObjectListBase.
Declaration of Listable, the base of all classes whose instances can be stored in object lists...
Context * getContext() const
Definition: Listable.h:62
std::set< const Identifier * > directChildren_
The direct children of the class the Identifier belongs to.
Definition: Identifier.h:227
std::set< const Identifier * > children_
The children of the class the Identifier belongs to.
Definition: Identifier.h:228
Classes must inherit from this class if they should be used with StrongPtr or WeakPtr.
Definition: Destroyable.h:47
uint32_t getNetworkID() const
Returns the network ID to identify a class through the network.
Definition: Identifier.h:133
virtual void updateConfigValues(bool updateChildren=true) const override
Updates the config-values of all existing objects of this class by calling their setConfigValues() fu...
Definition: Identifier.h:444
#define ORX_FORCEINLINE
Definition: OrxonoxConfig.h:95
const std::string & getName() const
Returns the name of the class the Identifier belongs to.
Definition: Identifier.h:127
Definition of all super-function related macros, used to call functions of the base class...
bool isInitialized() const
Returns true if the Identifier was completely initialized.
Definition: Identifier.h:153
#define OrxVerify(condition, errorMessage)
Works like OrxAssert in debug mode, but also checks the condition in release mode (no abort() trigger...
Definition: OrxAssert.h:78
internal::String name_
Definition: gtest.cc:2289
static IdentifierManager & getInstance()
Returns a reference to the singleton instance.
Definition: Singleton.h:118
Definition: InputPrereqs.h:80
Base-class of all factories.
Definition: ClassFactory.h:52
ORX_FORCEINLINE unsigned int getClassID() const
Returns the unique ID of the class.
Definition: Identifier.h:137
const std::set< const Identifier * > & getDirectChildren() const
Returns the direct children the class the Identifier belongs to.
Definition: Identifier.h:184
ObjectListIterator<T> allows to iterate through the ObjectList of class T.
Definition: CorePrereqs.h:210
Declaration of custom assertion facilities
void addObject(T *object)
Definition: Context.h:65