Planet
navi homePPSaboutscreenshotsdownloaddevelopmentforum

source: orxonox.OLD/trunk/src/lib/util/multi_type.cc @ 7200

Last change on this file since 7200 was 7200, checked in by bensch, 18 years ago

orxonox/truink: minor cleanup

File size: 10.4 KB
RevLine 
[4744]1/*
[1853]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.
[1855]10
11   ### File Specific:
[5643]12   main-programmer: Benjamin Grauer
[1855]13   co-programmer: ...
[1853]14*/
15
[3955]16//#define DEBUG_SPECIAL_MODULE DEBUG_MODULE_
[1853]17
[5536]18#include "multi_type.h"
[1853]19
[5659]20//#include "stdincl.h"
21#include <stddef.h>
22#include <stdlib.h>
23#include <string.h>
24#include <stdio.h>
[7199]25#include <sstream>
[5659]26
27#ifdef DEBUG
28#include "debug.h"
29#endif
30
[1856]31using namespace std;
[1853]32
[5545]33/**
[7199]34 * @brief creates a multiType without any stored value at all.
[5545]35 */
[7197]36MultiType::MultiType(MT_Type type)
[5540]37{
[7197]38  this->type = type;
[7200]39  switch (this->type)
40  {
41    case MT_BOOL:
42      this->value.Bool = false;
43      break;
44    case MT_INT:
45      this->value.Int = 0;
46      break;
47    case MT_FLOAT:
48      this->value.Float = 0.0f;
49      break;
50    case MT_CHAR:
51      this->value.Char = '\0';
52      break;
53  }
[5540]54}
[5545]55/**
[7199]56 * @brief creates a multiType out of a boolean
[5545]57 * @param value the Value of this MulitType
58 */
[5537]59MultiType::MultiType(bool value)
60{
[5540]61  this->setBool(value);
[5537]62}
63
[5545]64/**
[7199]65 * @brief creates a multiType out of an integer
[5545]66 * @param value the Value of this MulitType
67 */
[5536]68MultiType::MultiType(int value)
69{
[5540]70  this->setInt(value);
[5536]71}
[1856]72
[5545]73/**
[7199]74 * @brief creates a multiType out of a float (double)
[5545]75 * @param value the Value of this MulitType
76 */
[5539]77MultiType::MultiType(double value)
[3365]78{
[5540]79  this->setFloat(value);
[5536]80}
[4320]81
[5545]82/**
[7199]83 * @brief creates a multiType out of a char
[5545]84 * @param value the Value of this MulitType
85 */
[5536]86MultiType::MultiType(char value)
87{
[5540]88  this->setChar(value);
[3365]89}
[1853]90
[5545]91/**
[7199]92 * @brief creates a multiType out of a C-String
[5545]93 * @param value the Value of this MulitType
94 */
[5536]95MultiType::MultiType(const char* value)
96{
[5540]97  this->setString(value);
[5536]98}
99
[7199]100/**
101 * @brief creates a multiType out of a String
102 * @param value the Value of this MulitType
103 */
104MultiType::MultiType(const std::string& value)
105{
106  this->setString(value);
107}
108
109/**
110 * @brief constructs a new MultiType from another one (copy)
111 */
[5659]112MultiType::MultiType(const MultiType& multiType)
113{
114  *this = multiType;
115}
116
[3245]117/**
[7199]118 * @brief standard deconstructor
[3245]119*/
[5536]120MultiType::~MultiType ()
[7199]121{ }
[5537]122
[5540]123/**
[7199]124 * @brief copy operator
[5540]125 * @param mt: the entity to copy
[7199]126 * @returns A Copy of itself. (strings inside are copied as well)
[5540]127 */
[5659]128MultiType& MultiType::operator= (const MultiType& mt)
129{
130  this->type = mt.type;
131  this->value = mt.value;
[7199]132  this->storedString = mt.storedString;
133
[5659]134  return *this;
135}
136
[5545]137/**
[6643]138 * @brief checks if the two Multitypes match
139 * @param mt MultiType to check against this one
140 * @returns true on match. false otherwise
141 *
142 * Two MultiType match if and only if
143 *  1. the internal Type is the same
144 *  2. the stored values match
145 */
146bool MultiType::operator==(const MultiType& mt) const
147{
148  if (this->type != mt.type)
149    return false;
150
151  switch (this->type)
152  {
153    case MT_NULL:
154      return true;
155    case MT_BOOL:
156      return (this->value.Bool == mt.value.Bool);
157    case MT_INT:
158      return (this->value.Int == mt.value.Int);
159    case MT_CHAR:
160      return (this->value.Char == mt.value.Char);
161    case MT_FLOAT:
162      return (this->value.Float == mt.value.Float);
163    case MT_STRING:
[7199]164      return (this->storedString == mt.storedString);
[6643]165  }
166}
167
168
169/**
[7199]170 * @brief sets the type of this MultiType and resets to the default value
[5643]171 * @param type the new Type
172 */
[6645]173void MultiType::setType(MT_Type type)
[5540]174{
[7199]175  if (this->type == type)
176    return;
177
178  switch (type)
179  {
180    case MT_BOOL:
181      this->setBool(this->getBool());
182      break;
183    case MT_INT:
184      this->setInt(this->getInt());
185      break;
186    case MT_FLOAT:
187      this->setFloat(this->getFloat());
188      break;
189    case MT_CHAR:
190      this->setChar(this->getChar());
191      break;
192    case MT_STRING:
193      this->setString(this->getString());
194      break;
195  }
[5540]196}
197
[5545]198/**
[7199]199 * @brief sets the Value of mt without changing the type of this MultiType
200 * @param mt: the MultiType to get the value from
201 *
202 * This is a pure Value copy. The current type will be preserved.
203 *
204 * @TODO speedup
205 */
206void MultiType::setValueOf(const MultiType& mt)
207{
208  MT_Type prevType = this->type;
209
210  *this = mt;
211  this->setType(prevType);
212}
213
214
215/**
216 * @brief sets a new Value to the MultiType
[5545]217 * @param value the new Value as a bool
218 */
[5540]219void MultiType::setBool(bool value)
220{
221  this->type = MT_BOOL;
222  this->value.Bool = value;
223}
224
[5545]225/**
[7199]226 * @brief sets a new Value to the MultiType
[5545]227 * @param value the new Value as an int
228 */
[5540]229void MultiType::setInt(int value)
230{
231  this->type = MT_INT;
232  this->value.Int = value;
233}
234
[5545]235/**
[7199]236 * @brief sets a new Value to the MultiType
[5545]237 * @param value the new Value as a float
238 */
[5540]239void MultiType::setFloat(float value)
240{
241  this->type = MT_FLOAT;
242  this->value.Float = value;
243}
244
[5545]245/**
[7199]246 * @brief sets a new Value to the MultiType
[5545]247 * @param value the new Value as a char
248 */
[5540]249void MultiType::setChar(char value)
250{
251  this->type = MT_CHAR;
252  this->value.Char = value;
253}
254
[5545]255/**
[7199]256 * @brief sets a new Value to the MultiType
[5545]257 * @param value the new Value as a String
258 */
[7199]259void MultiType::setString(const std::string& value)
[5540]260{
261  this->type = MT_STRING;
[7199]262  this->storedString = value;
[5540]263}
264
265
[7199]266/**************************
267*** RETRIEVAL FUNCTIONS ***
268**************************/
[5545]269/**
270 * @returns the Value of this MultiType as a int
271 */
[5544]272bool MultiType::getBool() const
[5537]273{
274  // default case:
275  if (this->type & MT_BOOL)
276    return this->value.Bool;
277  // Special Cases:
278  else if (this->type & MT_INT) return (this->value.Int == 0)? false : true;
279  else if (this->type & MT_FLOAT) return (this->value.Float == 0.0f)? false : true;
280  else if (this->type & MT_CHAR) return (this->value.Char == '\0')? false : true;
[7199]281  else if (this->type & MT_STRING) return (this->storedString == "true" ||
282                                            this->storedString == "TRUE" ||
283                                            this->storedString != "0"); //! @TODO make this better...
[5538]284
285  return false;
[5537]286}
287
[5545]288/**
289 * @returns the Value of this MultiType as a int
290 */
[5544]291int MultiType::getInt() const
[5537]292{
293  // default case:
294  if (this->type & MT_INT)
295    return this->value.Int;
296  if (this->type & MT_BOOL) return (this->value.Bool)? 1 : 0;
297  else if (this->type & MT_FLOAT) return (int) this->value.Float;
298  else if (this->type & MT_CHAR) return (int) this->value.Char;
[7199]299  else if (this->type & MT_STRING)
300  {
[5538]301    char* endPtr = NULL;
[7199]302    int result = strtol(this->storedString.c_str(), &endPtr, 10);
303    if ( endPtr >= this->storedString.c_str() && endPtr < this->storedString.c_str() + strlen(this->storedString.c_str()))
[5538]304      return 0;
305    else
306      return result;
307  }
308  return 0;
[5537]309}
310
[7199]311
[5545]312/**
313 * @returns the Value of this MultiType as a float
314 */
[5544]315float MultiType::getFloat() const
[5537]316{
[7199]317  // default case:
[5539]318  if (this->type & MT_FLOAT)
319    return this->value.Float;
320  if (this->type & MT_BOOL) return (this->value.Bool == true)? 1.0f : 0.0f;
[5537]321  else if (this->type & MT_INT) return (float) this->value.Int;
322  else if (this->type & MT_CHAR) return (float) this->value.Char;
[7199]323  else if (this->type & MT_STRING)
324  {
[5538]325    char* endPtr = NULL;
[7199]326    double result = strtod(this->storedString.c_str(), &endPtr);
327    if ( endPtr >= this->storedString.c_str() && endPtr < this->storedString.c_str() + strlen(this->storedString.c_str()))
[5538]328      return 0.0f;
329    else
330      return result;
331  }
332  return 0.0f;
[5537]333}
334
335
[5545]336/**
337 * @returns the Value of this MultiType as a char
338 */
[5544]339char MultiType::getChar() const
[5537]340{
[7199]341  // default case:
[5537]342  if (this->type & MT_INT)
343    return this->value.Int;
344  if (this->type & MT_BOOL) return (this->value.Bool)? 'y' : 'n';
345  else if (this->type & MT_INT) return (int) this->value.Int;
346  else if (this->type & MT_FLOAT) return (char) this->value.Float;
[7199]347  else if (this->type & MT_STRING) return this->storedString[0];
[5538]348
349  return '\0';
[5537]350}
351
[7199]352
[5545]353/**
354 * @returns the Value of this MultiType as a String
355 */
[7199]356std::string MultiType::getString() const
[5537]357{
[7199]358  // default case:
[5537]359  if (this->type & MT_STRING)
[7199]360    return this->storedString;
[5538]361  else
362  {
363    if (this->type & MT_BOOL) return (this->value.Bool)? "true" : "false";
[7199]364
[5641]365    else if (this->type & MT_INT)
366    {
[7199]367      char tmpString[32];
[5538]368      sprintf(tmpString, "%d", this->value.Int);
[7199]369      return tmpString;
[5538]370    }
[7199]371    else if (this->type & MT_FLOAT)
[5538]372    {
[7199]373      char tmpString[64];
[5538]374      sprintf(tmpString, "%f", this->value.Float);
[7199]375      return tmpString;
[5538]376    }
[7200]377    else if (this->type & MT_CHAR)
378    {
379      char tmpString[2];
380      tmpString[0] = this->value.Char;
381      tmpString[1] = '\0';
382      return tmpString;
383    }
[5538]384  }
385  return "";
[5537]386}
387
[5545]388/**
[7199]389 * @returns a formated c-string of the held value
[5545]390 */
[7199]391const char* MultiType::getCString()
[5544]392{
[7199]393  if (this->type & MT_STRING) return this->storedString.c_str();
394  else
395  {
396    this->storedString = this->getString();
397    return this->storedString.c_str();
398  }
399}
400
401/**
402 * @brief prints out some nice debug output
403 */
404void MultiType::debug() const
405{
[5659]406#ifdef DEBUG
407  PRINT(0)
408#else
409  printf
410#endif
[7199]411  ("MultiType of Type '%s' :: Values: BOOL: '%d', INT: '%d', FLOAT: '%f', CHAR: '%c', STRING '%s'\n",
412   MultiType::MultiTypeToString(this->type),
413   this->getBool(),
414   this->getInt(),
415   this->getFloat(),
416   this->getChar(),
417   this->getString().c_str()
418  );
419}
[5544]420
421
[5545]422/**
[7199]423 * @brief Resets the MultiType to default values.
[5643]424 */
425void MultiType::reset()
426{
[5659]427  switch ( this->type )
[5643]428  {
429    case MT_BOOL:
430      this->setBool(false);
[7200]431      break;
[5643]432    case MT_INT:
433      this->setInt(0);
434      break;
435    case MT_FLOAT:
436      this->setFloat(0.0f);
437      break;
438    case MT_CHAR:
439      this->setChar('\0');
440      break;
441    case MT_STRING:
442      this->setString("");
443      break;
[5659]444    default:
445#ifdef DEBUG
446      PRINTF(2)("Unknown Type not reseting\n");
447#endif
448      break;
[5643]449  }
450}
451
452/**
[7199]453 * @brief converts a MT_Type into a String
[5545]454 * @param type: the MT_Type
455 * @returns: the Type as a constant String (do not delete)
456 */
[5544]457const char* MultiType::MultiTypeToString(MT_Type type)
458{
[5659]459  switch ( type )
[5544]460  {
[7199]461    case MT_BOOL:
462      return "bool";
463    case MT_INT:
464      return "int";
465    case MT_FLOAT:
466      return "float";
467    case MT_CHAR:
468      return "char";
469    case MT_STRING:
470      return "string";
[5544]471  }
[7200]472  return "NONE";
[5544]473}
474
[5545]475/**
[7199]476 * @brief converts a String into a MT_Type
[5545]477 * @param type: the Type as a String
478 * @returns: the Type as MT_Type
479 */
[5544]480MT_Type MultiType::StringToMultiType(const char* type)
481{
482  if (!strncmp(type, "bool", 4))
483    return MT_BOOL;
484  if (!strncmp(type, "int", 3))
485    return MT_INT;
486  if (!strncmp(type, "float", 5))
487    return MT_FLOAT;
488  if (!strncmp(type, "char", 4))
489    return MT_CHAR;
490  if (!strncmp(type, "string", 6))
491    return MT_STRING;
[7200]492
493  return MT_NULL;
[5544]494}
Note: See TracBrowser for help on using the repository browser.