2 * Value.h: interface for the CValue class.
4 * Copyright (c) 1996-2000 Erwin Coumans <coockie@acm.org>
6 * Permission to use, copy, modify, distribute and sell this software
7 * and its documentation for any purpose is hereby granted without fee,
8 * provided that the above copyright notice appear in all copies and
9 * that both that copyright notice and this permission notice appear
10 * in supporting documentation. Erwin Coumans makes no
11 * representations about the suitability of this software for any
12 * purpose. It is provided "as is" without express or implied warranty.
16 #if defined(WIN32) && !defined(FREE_WINDOWS)
17 #pragma warning (disable:4786)
20 /////////////////////////////////////////////////////////////////////////////////////
22 //// Together with CExpression, CValue and it's derived classes can be used to
23 //// parse expressions into a parsetree with error detecting/correcting capabilities
24 //// also expandible by a CFactory pluginsystem
27 //// Reference Counting (AddRef() / Release())
28 //// Calculations (Calc() / CalcFinal())
29 //// Configuration (Configure())
30 //// Serialization (EdSerialize() / EdIdSerialize() / EdPtrSerialize() and macro PLUGIN_DECLARE_SERIAL
31 //// Property system (SetProperty() / GetProperty() / FindIdentifier())
32 //// Replication (GetReplica())
33 //// Flags (IsSelected() / IsModified() / SetSelected()...)
35 //// Some small editor-specific things added
36 //// A helperclass CompressorArchive handles the serialization
38 /////////////////////////////////////////////////////////////////////////////////////
42 #include <map> // array functionality for the propertylist
43 #include "STR_String.h" // STR_String class
45 #ifdef WITH_CXX_GUARDEDALLOC
46 #include "MEM_guardedalloc.h"
51 #define assert(exp) ((void)NULL)
57 #define trace(exp) ((void)NULL)
62 #define debug(exp) ((void)NULL)
65 #ifndef GEN_NO_ASSERTD
67 #define assertd(exp) ((void)NULL)
71 #ifndef USE_PRAGMA_ONCE
78 #define EDITOR_LEVEL_VERSION 0x06
82 VALUE_MOD_OPERATOR, // %
83 VALUE_ADD_OPERATOR, // +
84 VALUE_SUB_OPERATOR, // -
85 VALUE_MUL_OPERATOR, // *
86 VALUE_DIV_OPERATOR, // /
87 VALUE_NEG_OPERATOR, // -
88 VALUE_POS_OPERATOR, // +
89 VALUE_AND_OPERATOR, // &&
90 VALUE_OR_OPERATOR, // ||
91 VALUE_EQL_OPERATOR, // ==
92 VALUE_NEQ_OPERATOR, // !=
93 VALUE_GRE_OPERATOR, // >
94 VALUE_LES_OPERATOR, // <
95 VALUE_GEQ_OPERATOR, // >=
96 VALUE_LEQ_OPERATOR, // <=
97 VALUE_NOT_OPERATOR, // !
98 VALUE_NO_OPERATOR // no operation at all
101 enum VALUE_DATA_TYPE {
102 VALUE_NO_TYPE, // abstract baseclass
110 VALUE_COMBISOLID_TYPE,
114 VALUE_MAX_TYPE //only here to provide number of types
120 //extern int gRefCountValue; // debugonly variable to check if all CValue Refences are Dereferenced at programexit
125 HashableInt(int id) : mData(id) { }
127 unsigned long Hash() const { return 0;} ////}gHash(&mData, sizeof(int));}
129 bool operator==(HashableInt rhs) { return mData == rhs.mData; }
136 // Bitfield that stores the flags for each CValue derived class
143 ReleaseRequested(false),
145 RefCountDisabled(false),
146 HasProperties(false),
154 unsigned short Modified : 1;
155 unsigned short Selected : 1;
156 unsigned short Affected : 1;
157 unsigned short ReleaseRequested : 1;
158 unsigned short Error : 1;
159 unsigned short RefCountDisabled : 1;
160 unsigned short HasProperties : 1;
161 unsigned short HasName : 1;
162 unsigned short Visible : 1;
163 unsigned short CustomFlag1 : 1;
164 unsigned short CustomFlag2 : 1;
170 * Base Class for all Actions performed on CValue's. Can be extended for undo/redo system in future.
179 virtual void Execute() const =0;
182 #ifdef WITH_CXX_GUARDEDALLOC
184 void *operator new(size_t num_bytes) { return MEM_mallocN(num_bytes, "GE:CAction"); }
185 void operator delete( void *mem ) { MEM_freeN(mem); }
192 // Base class for all editor functionality, flexible object type that allows
193 // calculations and uses reference counting for memory management.
200 #include "PyObjectPlus.h"
201 #ifndef DISABLE_PYTHON
204 class CValue : public PyObjectPlus
209 enum AllocationTYPE {
221 // Construction / Destruction
224 #ifndef DISABLE_PYTHON
225 //static PyObject* PyMake(PyObject*,PyObject*);
226 virtual PyObject *py_repr(void)
228 return PyUnicode_FromString((const char*)GetText());
231 virtual PyObject* ConvertValueToPython() {
235 virtual CValue* ConvertPythonToValue(PyObject* pyobj, const char *error_prefix);
237 static PyObject * pyattr_get_name(void * self, const KX_PYATTRIBUTE_DEF * attrdef);
239 virtual PyObject* ConvertKeysToPython( void );
240 #endif // DISABLE_PYTHON
244 // Expression Calculation
245 virtual CValue* Calc(VALUE_OPERATOR op, CValue *val) = 0;
246 virtual CValue* CalcFinal(VALUE_DATA_TYPE dtype, VALUE_OPERATOR op, CValue *val) = 0;
247 virtual void SetOwnerExpression(class CExpression* expr);
251 void Execute(const CAction& a)
256 /// Reference Counting
262 // Add a reference to this value
265 // Increase global reference count, used to see at the end of the program
266 // if all CValue-derived classes have been dereferenced to 0
267 //debug(gRefCountValue++);
275 // Release a reference to this value (when reference count reaches 0, the value is removed from the heap)
278 // Decrease global reference count, used to see at the end of the program
279 // if all CValue-derived classes have been dereferenced to 0
280 //debug(gRefCountValue--);
284 // Decrease local reference count, if it reaches 0 the object should be freed
285 if (--m_refcount > 0)
287 // Reference count normal, return new reference count
292 // Reference count reached 0, delete ourselves and return 0
293 // MT_assert(m_refcount==0, "Reference count reached sub-zero, object released too much");
301 /// Property Management
302 virtual void SetProperty(const STR_String& name,CValue* ioProperty); // Set property <ioProperty>, overwrites and releases a previous property with the same name if needed
303 virtual void SetProperty(const char* name,CValue* ioProperty);
304 virtual CValue* GetProperty(const char* inName); // Get pointer to a property with name <inName>, returns NULL if there is no property named <inName>
305 virtual CValue* GetProperty(const STR_String & inName);
306 const STR_String& GetPropertyText(const STR_String & inName); // Get text description of property with name <inName>, returns an empty string if there is no property named <inName>
307 float GetPropertyNumber(const STR_String& inName,float defnumber);
308 virtual bool RemoveProperty(const char *inName); // Remove the property named <inName>, returns true if the property was succesfully removed, false if property was not found or could not be removed
309 virtual vector<STR_String> GetPropertyNames();
310 virtual void ClearProperties(); // Clear all properties
312 virtual void SetPropertiesModified(bool inModified); // Set all properties' modified flag to <inModified>
313 virtual bool IsAnyPropertyModified(); // Check if any of the properties in this value have been modified
315 virtual CValue* GetProperty(int inIndex); // Get property number <inIndex>
316 virtual int GetPropertyCount(); // Get the amount of properties assiocated with this value
318 virtual CValue* FindIdentifier(const STR_String& identifiername);
319 /** Set the wireframe color of this value depending on the CSG
321 * @attention: not implemented */
322 virtual void SetColorOperator(VALUE_OPERATOR op);
324 virtual const STR_String & GetText() = 0;
325 virtual double GetNumber() = 0;
326 double* ZeroVector() { return m_sZeroVec; };
327 virtual double* GetVector3(bool bGetTransformedVec = false);
329 virtual STR_String& GetName() = 0; // Retrieve the name of the value
330 virtual void SetName(const char *name) = 0; // Set the name of the value
331 /** Sets the value to this cvalue.
332 * @attention this particular function should never be called. Why not abstract? */
333 virtual void SetValue(CValue* newval);
334 virtual CValue* GetReplica() =0;
335 virtual void ProcessReplica();
336 //virtual CValue* Copy() = 0;
339 STR_String op2str(VALUE_OPERATOR op);
341 // setting / getting flags
342 inline void SetSelected(bool bSelected) { m_ValFlags.Selected = bSelected; }
343 virtual void SetModified(bool bModified) { m_ValFlags.Modified = bModified; }
344 virtual void SetAffected(bool bAffected=true) { m_ValFlags.Affected = bAffected; }
345 inline void SetReleaseRequested(bool bReleaseRequested) { m_ValFlags.ReleaseRequested=bReleaseRequested; }
346 inline void SetError(bool err) { m_ValFlags.Error=err; }
347 inline void SetVisible (bool vis) { m_ValFlags.Visible=vis; }
349 virtual bool IsModified() { return m_ValFlags.Modified; }
350 inline bool IsError() { return m_ValFlags.Error; }
351 virtual bool IsAffected() { return m_ValFlags.Affected || m_ValFlags.Modified; }
352 virtual bool IsSelected() { return m_ValFlags.Selected; }
353 inline bool IsReleaseRequested() { return m_ValFlags.ReleaseRequested; }
354 virtual bool IsVisible() { return m_ValFlags.Visible;}
355 virtual void SetCustomFlag1(bool bCustomFlag) { m_ValFlags.CustomFlag1 = bCustomFlag;};
356 virtual bool IsCustomFlag1() { return m_ValFlags.CustomFlag1;};
358 virtual void SetCustomFlag2(bool bCustomFlag) { m_ValFlags.CustomFlag2 = bCustomFlag;};
359 virtual bool IsCustomFlag2() { return m_ValFlags.CustomFlag2;};
362 virtual void DisableRefCount(); // Disable reference counting for this value
363 //virtual void AddDataToReplica(CValue* replica);
367 std::map<STR_String,CValue*>* m_pNamedPropertyArray; // Properties for user/game etc
368 ValueFlags m_ValFlags; // Frequently used flags in a bitfield (low memoryusage)
369 int m_refcount; // Reference Counter
370 static double m_sZeroVec[3];
377 // Declare a CValue or CExpression or CWhatever to be serialized by the editor.
379 // This macro introduces the EdSerialize() function (which must be implemented by
380 // the client) and the EdIdSerialize() function (which is implemented by this macro).
382 // The generated Copy() function returns a pointer to <root_base_class_name> type
383 // of object. So, for *any* CValue-derived object this should be set to CValue,
384 // for *any* CExpression-derived object this should be set to CExpression.
386 #define PLUGIN_DECLARE_SERIAL(class_name, root_base_class_name) \
388 virtual root_base_class_name * Copy() { return new class_name; } \
389 virtual bool EdSerialize(CompressorArchive& arch,class CFactoryManager* facmgr,bool bIsStoring); \
390 virtual bool EdIdSerialize(CompressorArchive& arch,class CFactoryManager* facmgr,bool bIsStoring) \
393 arch.StoreString(#class_name); \
399 ////////////////////////////////////////////////////////////////////////////////
400 ////////////////////////////////////////////////////////////////////////////////
401 ////////////////////////////////////////////////////////////////////////////////
403 // CPropValue is a CValue derived class, that implements the identification (String name)
404 // SetName() / GetName(),
405 // normal classes should derive from CPropValue, real lightweight classes straight from CValue
408 class CPropValue : public CValue
418 virtual ~CPropValue()
422 virtual void SetName(const char *name) {
426 virtual STR_String& GetName() {
427 //STR_String namefromprop = GetPropertyText("Name");
428 //if (namefromprop.Length() > 0)
429 // return namefromprop;
434 STR_String m_strNewName; // Identification
437 #ifdef WITH_CXX_GUARDEDALLOC
439 void *operator new(size_t num_bytes) { return MEM_mallocN(num_bytes, "GE:CPropValue"); }
440 void operator delete( void *mem ) { MEM_freeN(mem); }
444 #endif // !defined _VALUEBASECLASS_H