]> git.saurik.com Git - wxWidgets.git/blobdiff - include/wx/variantbase.h
adding new files for xti merge
[wxWidgets.git] / include / wx / variantbase.h
diff --git a/include/wx/variantbase.h b/include/wx/variantbase.h
new file mode 100644 (file)
index 0000000..5745c92
--- /dev/null
@@ -0,0 +1,279 @@
+/////////////////////////////////////////////////////////////////////////////\r
+// Name:        wx/variantbase.h\r
+// Purpose:     wxVariantBase class, a minimal version of wxVariant used by XTI\r
+// Author:      Julian Smart\r
+// Modified by: Francesco Montorsi\r
+// Created:     10/09/98\r
+// RCS-ID:      $Id: variant.h 44625 2007-03-07 11:35:04Z VZ $\r
+// Copyright:   (c) Julian Smart\r
+// Licence:     wxWindows licence\r
+/////////////////////////////////////////////////////////////////////////////\r
+\r
+#ifndef _WX_VARIANTBASE_H_\r
+#define _WX_VARIANTBASE_H_\r
+\r
+#include "wx/defs.h"\r
+\r
+#if wxUSE_VARIANT\r
+\r
+#include "wx/string.h"\r
+#include "wx/arrstr.h"\r
+#include "wx/cpp.h"\r
+#include <typeinfo>\r
+\r
+#if wxUSE_DATETIME\r
+    #include "wx/datetime.h"\r
+#endif // wxUSE_DATETIME\r
+\r
+#include "wx/iosfwrap.h"\r
+\r
+class wxTypeInfo;\r
+class wxObject;\r
+class wxClassInfo;\r
+\r
+/*\r
+ * wxVariantData stores the actual data in a wxVariant object,\r
+ * to allow it to store any type of data.\r
+ * Derive from this to provide custom data handling.\r
+ *\r
+ * NB: To prevent addition of extra vtbl pointer to wxVariantData,\r
+ *     we don't multiple-inherit from wxObjectRefData. Instead,\r
+ *     we simply replicate the wxObject ref-counting scheme.\r
+ *\r
+ * NB: When you construct a wxVariantData, it will have refcount\r
+ *     of one. Refcount will not be further increased when\r
+ *     it is passed to wxVariant. This simulates old common\r
+ *     scenario where wxVariant took ownership of wxVariantData\r
+ *     passed to it.\r
+ *     If you create wxVariantData for other reasons than passing\r
+ *     it to wxVariant, technically you are not required to call\r
+ *     DecRef() before deleting it.\r
+ *\r
+ * TODO: in order to replace wxPropertyValue, we would need\r
+ * to consider adding constructors that take pointers to C++ variables,\r
+ * or removing that functionality from the wxProperty library.\r
+ * Essentially wxPropertyValue takes on some of the wxValidator functionality\r
+ * by storing pointers and not just actual values, allowing update of C++ data\r
+ * to be handled automatically. Perhaps there's another way of doing this without\r
+ * overloading wxVariant with unnecessary functionality.\r
+ */\r
+\r
+class WXDLLIMPEXP_BASE wxVariantData\r
+{\r
+    friend class wxVariantBase;\r
+\r
+public:\r
+    wxVariantData()\r
+        : m_count(1)\r
+    { }\r
+\r
+#if wxUSE_STD_IOSTREAM\r
+    virtual bool Write(wxSTD ostream& WXUNUSED(str)) const { return false; }\r
+    virtual bool Read(wxSTD istream& WXUNUSED(str)) { return false; }\r
+#endif\r
+    virtual bool Write(wxString& WXUNUSED(str)) const { return false; }\r
+    virtual bool Read(wxString& WXUNUSED(str)) { return false; }\r
+\r
+    // Override these to provide common functionality\r
+    virtual bool Eq(wxVariantData& data) const = 0;\r
+\r
+    // What type is it? Return a string name.\r
+    virtual wxString GetType() const = 0;\r
+\r
+    // returns the type info of the content\r
+    virtual const wxTypeInfo* GetTypeInfo() const = 0;\r
+\r
+    // If it based on wxObject return the ClassInfo.\r
+    virtual wxClassInfo* GetValueClassInfo() { return NULL; }\r
+\r
+    int GetRefCount() const \r
+        { return m_count; }\r
+    void IncRef() \r
+        { m_count++; }\r
+    void DecRef()\r
+    {\r
+        if ( --m_count == 0 )\r
+            delete this;\r
+    }\r
+\r
+protected:\r
+    // Protected dtor should make some incompatible code\r
+    // break more louder. That is, they should do data->DecRef()\r
+    // instead of delete data.\r
+    virtual ~wxVariantData() {}\r
+\r
+private:\r
+    int m_count;\r
+};\r
+\r
+template<typename T> class wxVariantDataT : public wxVariantData\r
+{\r
+public:\r
+    wxVariantDataT(const T& d) : m_data(d) {}\r
+    virtual ~wxVariantDataT() {}\r
+\r
+    // get a ref to the stored data\r
+    T & Get() { return m_data; }\r
+\r
+    // get a const ref to the stored data\r
+    const T & Get() const { return m_data; }\r
+\r
+    // set the data\r
+    void Set(const T& d) { m_data =  d; }\r
+\r
+    // Override these to provide common functionality\r
+    virtual bool Eq(wxVariantData& WXUNUSED(data)) const\r
+        { return false; /* FIXME!! */    }\r
+\r
+    // What type is it? Return a string name.\r
+    virtual wxString GetType() const\r
+        { return GetTypeInfo()->GetTypeName(); }\r
+\r
+    // return a heap allocated duplicate\r
+    //virtual wxVariantData* Clone() const { return new wxVariantDataT<T>( Get() ); }\r
+\r
+    // returns the type info of the contentc\r
+    virtual const wxTypeInfo* GetTypeInfo() const { return wxGetTypeInfo( (T*) NULL ); }\r
+\r
+private:\r
+    T m_data;\r
+};\r
+\r
+\r
+/*\r
+ * wxVariantBase can store any kind of data, but has some basic types\r
+ * built in.\r
+ */\r
+\r
+class WXDLLIMPEXP_BASE wxVariantBase\r
+{\r
+public:\r
+    wxVariantBase();\r
+    wxVariantBase(const wxVariantBase& variant);\r
+    wxVariantBase(wxVariantData* data, const wxString& name = wxEmptyString);\r
+\r
+    template<typename T> \r
+        wxVariantBase(const T& data, const wxString& name = wxEmptyString) :\r
+            m_data(new wxVariantDataT<T>(data)), m_name(name) {}\r
+\r
+    virtual ~wxVariantBase();\r
+\r
+    // generic assignment\r
+    void operator= (const wxVariantBase& variant);\r
+\r
+    // Assignment using data, e.g.\r
+    // myVariant = new wxStringVariantData("hello");\r
+    void operator= (wxVariantData* variantData);\r
+\r
+    bool operator== (const wxVariantBase& variant) const;\r
+    bool operator!= (const wxVariantBase& variant) const;\r
+\r
+    // Sets/gets name\r
+    inline void SetName(const wxString& name) { m_name = name; }\r
+    inline const wxString& GetName() const { return m_name; }\r
+\r
+    // Tests whether there is data\r
+    bool IsNull() const;\r
+\r
+    // FIXME: used by wxVariantBase code but is nice wording...\r
+    bool IsEmpty() const { return IsNull(); }\r
+\r
+    // For compatibility with wxWidgets <= 2.6, this doesn't increase\r
+    // reference count.\r
+    wxVariantData* GetData() const { return m_data; }\r
+    void SetData(wxVariantData* data) ;\r
+\r
+    // make a 'clone' of the object\r
+    void Ref(const wxVariantBase& clone);\r
+\r
+    // destroy a reference\r
+    void UnRef();\r
+\r
+    // Make NULL (i.e. delete the data)\r
+    void MakeNull();\r
+\r
+    // write contents to a string (e.g. for debugging)\r
+    wxString MakeString() const;\r
+\r
+    // Delete data and name\r
+    void Clear();\r
+\r
+    // Returns a string representing the type of the variant,\r
+    // e.g. "string", "bool", "stringlist", "list", "double", "long"\r
+    wxString GetType() const;\r
+\r
+    bool IsType(const wxString& type) const;\r
+    bool IsValueKindOf(const wxClassInfo* type) const;\r
+\r
+    // FIXME wxXTI methods:\r
+\r
+    // get the typeinfo of the stored object\r
+    const wxTypeInfo* GetTypeInfo() const \r
+    { \r
+        if (!m_data)\r
+            return NULL;\r
+        return m_data->GetTypeInfo(); \r
+    }\r
+\r
+    // get a ref to the stored data\r
+    template<typename T> T& Get(wxTEMPLATED_MEMBER_FIX(T))\r
+    {\r
+        wxVariantDataT<T> *dataptr = \r
+            wx_dynamic_cast(wxVariantDataT<T>*, m_data);\r
+        wxASSERT_MSG( dataptr, \r
+            wxString::Format(wxT("Cast to %s not possible"), typeid(T).name()) );\r
+        return dataptr->Get();\r
+    }\r
+\r
+    // get a const ref to the stored data\r
+    template<typename T> const T& Get(wxTEMPLATED_MEMBER_FIX(T)) const\r
+    {\r
+        const wxVariantDataT<T> *dataptr = \r
+            wx_dynamic_cast(const wxVariantDataT<T>*, m_data);\r
+        wxASSERT_MSG( dataptr, \r
+            wxString::Format(wxT("Cast to %s not possible"), typeid(T).name()) );\r
+        return dataptr->Get();\r
+    }\r
+\r
+    template<typename T> bool HasData(wxTEMPLATED_MEMBER_FIX(T)) const\r
+    {\r
+        const wxVariantDataT<T> *dataptr = \r
+            wx_dynamic_cast(const wxVariantDataT<T>*, m_data);\r
+        return dataptr != NULL;\r
+    }\r
+\r
+    // returns this value as string\r
+    wxString GetAsString() const;\r
+\r
+    // gets the stored data casted to a wxObject*, \r
+    // returning NULL if cast is not possible\r
+    wxObject* GetAsObject();\r
+\r
+protected:\r
+    wxVariantData*  m_data;\r
+    wxString        m_name;\r
+};\r
+\r
+#include "wx/dynarray.h"\r
+WX_DECLARE_OBJARRAY_WITH_DECL(wxVariantBase, wxVariantBaseArray, class WXDLLIMPEXP_BASE);\r
+\r
+\r
+// templated streaming, every type must have their specialization for these methods\r
+\r
+template<typename T>\r
+void wxStringReadValue( const wxString &s, T &data );\r
+\r
+template<typename T>\r
+void wxStringWriteValue( wxString &s, const T &data);\r
+\r
+template<typename T>\r
+void wxToStringConverter( const wxVariantBase &v, wxString &s wxTEMPLATED_FUNCTION_FIX(T)) \\r
+    { wxStringWriteValue( s, v.wxTEMPLATED_MEMBER_CALL(Get, T) ); }\r
+\r
+template<typename T>\r
+void wxFromStringConverter( const wxString &s, wxVariantBase &v wxTEMPLATED_FUNCTION_FIX(T)) \\r
+    { T d; wxStringReadValue( s, d ); v = wxVariantBase(d); }\r
+\r
+\r
+#endif // wxUSE_VARIANT\r
+#endif // _WX_VARIANTBASE_H_\r