Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: orxonox.OLD/trunk/src/lib/lang/class_list.cc @ 9013

Last change on this file since 9013 was 8783, checked in by patrick, 18 years ago

merged the script engine branche back to trunk

File size: 12.2 KB
Line 
1/*
2   orxonox - the future of 3D-vertical-scrollers
3
4   Copyright (C) 2004 orx
5
6   This program is free software; you can redistribute it and/or modify
7   it under the terms of the GNU General Public License as published by
8   the Free Software Foundation; either version 2, or (at your option)
9   any later version.
10
11   ### File Specific:
12   main-programmer: Benjamin Grauer
13   co-programmer: ...
14*/
15
16//#define DEBUG_SPECIAL_MODULE DEBUG_MODULE_
17
18#include "class_list.h"
19#include "base_object.h"
20
21#include "compiler.h"
22#include "debug.h"
23#include <cmath>
24
25using namespace std;
26
27/**
28 * @brief Creates a new ClassList
29*/
30ClassList::ClassList(ClassID classID, unsigned long classIDFull, const std::string& className)
31  : className(className)
32{
33  this->classID = classID;
34  this->classIDFull = classIDFull;
35}
36
37/**
38 * @brief standard deconstructor
39*/
40ClassList::~ClassList ()
41{
42//   ClassList::classList->clear());
43}
44
45//! a List of all known Classes.
46std::list<ClassList>* ClassList::classList = NULL;
47
48//! a List of all strings of all classes, that have registered so far.
49std::list<std::string> ClassList::classNames;
50
51/**
52 * @brief Adds a new Object to the ClassList (and if necessary a new Class)
53 * @param objectPointer Pointer to the Object at hand
54 * @param classID ID of the Given ObjectType \see ClassID
55 * @param className name of the Class to add
56 *
57 * !! FIRST YOU HAVE TO CALL THIS FUNCTION ONCE
58 * !! Before unsing the ClassList, as it creates the ClassLits
59 */
60ClassList* ClassList::addToClassList(BaseObject* objectPointer, ClassID classID, unsigned long classIDFull, const std::string& className)
61{
62  if (unlikely(classList == NULL))
63    ClassList::classList = new list<ClassList>();
64
65  PRINTF(5)("subscribe a '%s'\n", className.c_str() );
66
67  ClassList* regClass = ClassList::getClassList(classID);
68  if (regClass != NULL)
69  {
70    regClass->objectList.push_back(objectPointer);
71    return regClass;
72  }
73  else
74  {
75    ClassList::classList->push_back(ClassList(classID, classIDFull, className));
76    ClassList::classList->back().objectList.push_back(objectPointer);
77    return &ClassList::classList->back();
78  }
79}
80
81/**
82 * @brief removes an Object from a the ClassList
83 * @param objectPointer the Object to delete from the List
84 */
85void ClassList::removeFromClassList(BaseObject* objectPointer)
86{
87  list<ClassList>::iterator cl;
88  for(cl = ClassList::classList->begin(); cl != ClassList::classList->end(); cl++)
89  {
90    if (objectPointer->isA((*cl).classID))
91    {
92      std::list<BaseObject*>::iterator bo = std::find ((*cl).objectList.begin(), (*cl).objectList.end(), objectPointer);
93      if (bo != (*cl).objectList.end())
94          (*cl).objectList.erase(bo);
95    }
96  }
97}
98
99/**
100 * @brief grabs the names of all Classes, and injects it into a List of const chars
101 * @return the generated List
102 *
103 * This function first looks, if the List has been changed (by the ListSize)
104 * befor it changes anything.
105 */
106const std::list<std::string>* ClassList::getClassNames()
107{
108  if (ClassList::classNames.size() != ClassList::classList->size())
109  {
110      ClassList::classNames.clear();
111
112      list<ClassList>::const_iterator cl;
113      for (cl = ClassList::classList->begin(); cl != ClassList::classList->end(); cl++)
114        ClassList::classNames.push_back((*cl).className);
115  }
116
117  return &ClassList::classNames;
118}
119
120/**
121 * @brief searches for classID and returns the list of Entities
122 * @param classID the ID of the class to get the list from
123 * @return the List accessed by classID, or NULL if not found
124 */
125const std::list<BaseObject*>* ClassList::getList(ClassID classID)
126{
127  ClassList* fl;
128  return ((fl = ClassList::getClassList(classID)) != NULL)?
129       &(fl->objectList) : NULL;
130
131/*
132  std::list<ClassList>::iterator classIT = find (classList->begin(), classList->end(), classID);
133  return (likely(classIT != classList->end()))? &(*classIT).objectList : NULL;*/
134
135/*  for (classIT = ClassList::classList->begin(); classIT != ClassList::classList->end(); classIT++)
136  {
137    if ((*classIT) == classID )
138      return &(*classIT).objectList;
139  }
140  return NULL;*/
141}
142
143/**
144 * @brief searches for className and returns the list of Entities
145 * @param className the name of the class to get the list from
146 * @return the List accessed by classID, or NULL if not found
147 */
148const std::list<BaseObject*>* ClassList::getList(const std::string& className)
149{
150  ClassList* fl;
151  return ((fl = ClassList::getClassList(className)) != NULL)?
152      &(fl->objectList) : NULL;
153
154  /*
155  std::list<ClassList>::iterator classIT = find (classList->begin(), classList->end(), className);
156  return (likely(classIT != classList->end()))? &(*classIT).objectList : NULL;*/
157
158
159/*  for (classIT = ClassList::classList->begin(); classIT != ClassList::classList->end(); classIT++)
160  {
161    if ((*classIT) == className )
162      return &(*classIT).objectList;
163  }
164  return NULL;*/
165}
166
167/**
168 * !!PRIVATE!!
169 * @param classID the ClassID to search for
170 * @returns the ClassList with classID as specifyer, or NULL if not
171 */
172ClassList* ClassList::getClassList(ClassID classID)
173{
174  std::list<ClassList>::iterator classIT = find (ClassList::classList->begin(), ClassList::classList->end(), classID);
175  return (likely(classIT != classList->end()))? &(*classIT) : NULL;
176}
177
178
179/**
180 * !!PRIVATE!!
181 * @param className the ClassName to search for
182 * @returns the ClassList with className as specifyer, or NULL if not
183 */
184ClassList* ClassList::getClassList(const std::string& className)
185{
186  if (className.empty())
187    return NULL;
188  std::list<ClassList>::iterator classIT = find (classList->begin(), classList->end(), className);
189  return (likely(classIT != classList->end()))? &(*classIT) : NULL;
190}
191
192
193/**
194 * @brief checks if the BaseObject* object exists.
195 * @param objectName the name of the BaseObject to look for
196 * @param classID if not CL_NULL it will only search through a specific type of Objects. Otherwise it will be searched everywhere.
197 * @return true, if the Object Exists in the specified ClassID, false otherwise
198 * @todo: speed this up!!
199 */
200BaseObject* ClassList::getObject(const std::string& objectName, ClassID classID)
201{
202  if (classID != CL_NULL)
203  {
204    ClassList* cl = ClassList::getClassList(classID);
205    if (cl != NULL)
206    {
207      std::list<BaseObject*>::iterator bo;
208      for (bo = cl->objectList.begin(); bo != cl->objectList.end(); bo++)
209        if ((*bo)->getName() != NULL && objectName == (*bo)->getName())
210          return (*bo);
211    }
212  }
213  else
214  {
215    list<ClassList>::iterator cl;
216    for (cl = ClassList::classList->begin(); cl != ClassList::classList->end(); cl++)
217    {
218      std::list<BaseObject*>::iterator bo;
219      for (bo = (*cl).objectList.begin(); bo != (*cl).objectList.end(); bo++)
220        if ((*bo)->getName() != NULL && objectName == (*bo)->getName())
221          return (*bo);
222    }
223  }
224  return NULL;
225}
226
227
228/**
229 * @brief checks if the BaseObject* object exists.
230 * @param objectName the name of the BaseObject to look for
231 * @param classID if not CL_NULL it will only search through a specific type of Objects. Otherwise it will be searched everywhere.
232 * @return true, if the Object Exists in the specified ClassID, false otherwise
233 * @todo: speed this up!!
234 */
235BaseObject* ClassList::getObject(const std::string& objectName, const std::string& className)
236{
237
238  ClassList* cl = ClassList::getClassList(className);
239  if (cl != NULL)
240  {
241    std::list<BaseObject*>::iterator bo;
242    for (bo = cl->objectList.begin(); bo != cl->objectList.end(); bo++)
243      if ((*bo)->getName() != NULL && objectName == (*bo)->getName())
244        return (*bo);
245  }
246  return NULL;
247}
248
249
250/**
251 * @brief checks if the BaseObject* object exists.
252 * @param object the Pointer to a BaseObject to check if it exists
253 * @param classID if not CL_NULL it will only search through a specific type of Objects. Otherwise it will be searched everywhere.
254 * @return true, if the Object Exists in the specified ClassID, false otherwise
255 * @todo: speed this up!!
256 */
257bool ClassList::exists(const BaseObject* object, ClassID classID)
258{
259  if (classID != CL_NULL)
260  {
261    ClassList* cl = ClassList::getClassList(classID);
262    if (cl != NULL)
263    {
264      std::list<BaseObject*>::const_iterator bo = std::find (cl->objectList.begin(), cl->objectList.end(), object);
265      return (bo != cl->objectList.end());
266    }
267  }
268  else
269  {
270    list<ClassList>::iterator cl;
271    for (cl = ClassList::classList->begin(); cl != ClassList::classList->end(); cl++)
272    {
273      std::list<BaseObject*>::const_iterator bo = std::find ((*cl).objectList.begin(), (*cl).objectList.end(), object);
274      if (bo != (*cl).objectList.end())
275        return true;
276    }
277  }
278  return false;
279}
280
281bool ClassList::exists(const std::string& className, const std::string& objectName)
282{
283  ClassList* cl = ClassList::getClassList(className);
284  if (likely(cl != NULL))
285  {
286    std::list<BaseObject*>::iterator bo;
287    for (bo = cl->objectList.begin(); bo != cl->objectList.end(); bo++)
288      if ((*bo)->getName() != NULL && objectName == (*bo)->getName())
289        return true;
290  }
291  return false;
292}
293
294
295/**
296 * @brief prints out a string of all the types this Object matches
297 * @param object a Pointer to the object to analyze
298 */
299void ClassList::whatIs(const BaseObject* object)
300{
301  list<ClassList>::iterator cl;
302  for (cl = ClassList::classList->begin(); cl != ClassList::classList->end(); cl++)
303    if (object->isA((*cl).classID))
304  {
305    PRINT(0)("=%s::0x%.8X=-", (*cl).className.c_str(), (*cl).classID);
306  }
307}
308
309/**
310 * @brief converts a ClassID into a string
311 * @param classID the ClassID to search for
312 * @return a String containing the name of the Class, NULL if the Class was not found
313 */
314const std::string& ClassList::IDToString(ClassID classID)
315{
316  static const std::string empty("");
317
318  ClassList* cl = ClassList::getClassList(classID);
319  return (cl != NULL) ? cl->className : empty;
320}
321
322/**
323 * @brief converts a String into a ClassID
324 * @param className the name of the class to search for
325 * @return the ClassID. CL_NULL, if the class was not found.
326 */
327ClassID ClassList::StringToID(const std::string& className)
328{
329  ClassList* cl = ClassList::getClassList(className);
330  return (cl != NULL) ? cl->classID : CL_NULL;
331}
332
333/**
334 * @brief checks if this ClassList is named className
335 * @param className the Name to check this ClassList's ClassName against
336 * @returns true on match, false otherwise
337 */
338bool ClassList::operator==(const std::string& className)
339{
340  return (this->className == className);
341}
342
343
344
345/**
346 * @brief Print out some very nice debug information
347 * @param debugLevel the level of verbosity
348 * @param classID the class that should be displayed (if CL_NULL (default) all classes will be displayed)
349 */
350void ClassList::debug(unsigned int debugLevel, ClassID classID)
351{
352  if (debugLevel > 3)
353    debugLevel = 3;
354  PRINT(0)("==========================\n");
355  PRINT(0)("=  CLASS_LIST (level %d)  =\n", debugLevel);
356  PRINT(0)("==========================\n");
357  PRINT(0)("| knows %d Classes\n|\n", ClassList::classList->size());
358  char niceString[100];
359  int lenCount = 0;
360
361  list<ClassList>::iterator cl;
362  for (cl = ClassList::classList->begin(); cl != ClassList::classList->end(); cl++)
363  {
364    if ((debugLevel >= 1 || (*cl).objectList.size() > 0 ) &&
365         (classID == CL_NULL || unlikely (classID == (*cl).classID)))
366    {
367      lenCount = 1;
368      while (std::pow((float)10, (int)lenCount) <= (*cl).objectList.size())
369        ++lenCount;
370      for (unsigned int i=0; i < 30-(*cl).className.size() - lenCount; i++)
371        (niceString[i]) = ' ';
372      niceString[30-(*cl).className.size() - lenCount] = '\0';
373
374      PRINT(0)("| CLASS %s::%s %d\n", (*cl).className.c_str(), niceString, (*cl).objectList.size());
375
376      if (debugLevel >=2 && (*cl).objectList.size() > 0)
377      {
378        PRINT(0)("|  Listing Instances:\n");
379        list<BaseObject*>::const_iterator bo;
380        for (bo = (*cl).objectList.begin(); bo != (*cl).objectList.end(); bo++)
381        {
382          PRINT(0)("|   %s::%s::(0x%.8X->%p ", (*bo)->getClassName(), (*bo)->getName(), (*bo)->getClassID(), (*bo));
383          if (debugLevel == 3)
384            ClassList::whatIs(*bo);
385          PRINT(0)("\n");
386        }
387      }
388    }
389  }
390  PRINT(0)("=======================CL=\n");
391}
392
393/**
394 * @brief Print out some very nice debug information
395 * @param debugLevel the level of verbosity
396 * @param className the class that should be displayed.
397 * @see ClassList::debug
398 */
399void ClassList::debugS(const std::string& className, unsigned int debugLevel)
400{
401  ClassList::debug(debugLevel, ClassList::StringToID(className));
402}
Note: See TracBrowser for help on using the repository browser.