1 /////////////////////////////////////////////////////////////////////////////
3 // Purpose: Contrib. demo
4 // Author: Aleksandras Gluchovas
8 // Copyright: (c) Aleksandras Gluchovas
9 // Licence: wxWindows license
10 /////////////////////////////////////////////////////////////////////////////
12 #ifndef __OBJSTORE_G__
13 #define __OBJSTORE_G__
15 #include "wx/object.h"
16 #include "wx/string.h"
20 #include "wx/window.h"
21 #include "wx/button.h"
22 #include "wx/textctrl.h"
23 #include "wx/treectrl.h"
24 #include "wx/dynarray.h"
26 // abstract classes declared
28 class wxDataStreamBase
;
29 class wxSerializerBase
;
30 class wxObjectStorage
;
32 // classes which implement the above interfaces
34 class wxPointSerializer
;
35 class wxSizeSerializer
;
36 class wxRectSerializer
;
37 class wxPenSerializer
;
38 class wxBrushSerializer
;
40 class wxObjectListSerializer
;
42 class wxEvtHandlerSerializer
;
43 class wxWindowSerializer
;
44 class wxButtonSerializer
;
45 class wxScrollBarSerializer
;
46 class wxChoiceSerializer
;
47 class wxTextCtrlSerializer
;
48 class wxTreeCtrlSerializer
;
51 class wxIOStreamWrapper
;
53 // prototypes for serialzatoin/initialization functions
55 typedef void (*wxObjectSerializationFn
) (wxObject
*, wxObjectStorage
& );
56 typedef void (*wxObjectInitializationFn
)(wxObject
*);
58 #define NO_CLASS_VER NULL
59 #define NO_CLASS_INIT NULL
62 * class conceptually simiar to wxClassInfo, execpt that it's static
63 * instances hold information about class-serializers rather then
64 * about the classes themselves.
67 class wxSerializerInfo
72 wxClassInfo
* classInfo
; // link to corresponding class-info object,
73 // established upon invocation of InitializeSerializers()
75 wxObjectSerializationFn serFn
;
76 wxObjectInitializationFn initFn
;
80 static bool alreadyInitialized
;
81 static wxSerializerInfo
* first
;
82 static wxHashTable serInfoHash
; // classInfo <=> serializerInfo
84 wxSerializerInfo
* next
;
85 wxSerializerInfo
* nextByVersion
;
87 wxSerializerInfo( char* theClassName
,
88 wxObjectSerializationFn serializationFun
,
89 wxObjectInitializationFn initializationFun
,
90 char* classVersionName
93 // looks up for serializers of the base classes (base1 and base2)
94 // of the given object invokes them if present
96 void SerializeInherited ( wxObject
* pObj
, wxObjectStorage
& store
);
97 void InitializeInherited( wxObject
* pObj
);
99 bool HasVersion() { return classVersion
!= NO_CLASS_VER
; }
101 bool HasInitializer() { return initFn
!= NO_CLASS_INIT
; }
105 static void InitializeSerializers(void);
107 static wxSerializerInfo
* FindSerializer( char* className
);
111 * formal base class for all serializers, implemented as
112 * classes with static serialization/initialization methods
115 class wxSerializerBase
{};
117 // macros for declaring and implementing serializers both as
118 // classes and as a pair of (serialize/init) functions
120 #define DECLARE_SERIALIZER_CLASS(serializerName) \
122 static wxSerializerInfo info;;
124 #define IMPLEMENT_SERIALIZER_CLASS( name, serializerName, serFn, initFn) \
126 serializerName::info( #name, serFn, initFn, NO_CLASS_VER );
128 #define IMPLEMENT_SERIALIZER_FUNCTIONS( name, serFn, initFn) \
130 static __gSerFnInfoFor##name( #name, serFn, initFn, NO_CLASS_VER );
132 // for serializers, which are dedicated for specific versions of persistant classes
133 // (further referred as "versioned" serializers)
135 #define IMPLEMENT_SERIALIZER_CLASS_FOR_VERSION( name, serializerName, serFn, initFn, versionName) \
137 serializerName::info( #name, serFn, initFn, #versionName );
139 #define IMPLEMENT_SERIALIZER_FUNCTIONS_FOR_VERSION( name, serializerName, serFn, initFn, versionName) \
141 static __gSerFnInfoFor##name( #name, serFn, initFn, #versionName );
144 * defines abstract inferface for data-stream objects,
145 * can be implemented as a wrapper class for already
146 * existing stream classes
149 class wxDataStreamBase
: public wxObject
151 DECLARE_ABSTRACT_CLASS( wxDataStreamBase
)
156 virtual bool StoreChar ( char ch
) = 0;
157 virtual bool StoreInt ( int i
) = 0;
158 virtual bool StoreLong ( long l
) = 0;
159 virtual bool StoreDouble( double d
) = 0;
160 virtual bool StoreBytes ( void* bytes
, int count
) = 0;
162 virtual bool LoadChar ( char *pCh
) = 0;
163 virtual bool LoadInt ( int *pI
) = 0;
164 virtual bool LoadLong ( long *pL
) = 0;
165 virtual bool LoadDouble( double *pD
) = 0;
166 virtual bool LoadBytes ( void *pBytes
, int count
) = 0;
168 virtual bool Flush() = 0;
170 virtual long GetStreamPos() = 0;
172 bool IsForInput() { return mIsForInput
; }
176 * class provides stream-based persistance service for
177 * classes derivated from wxObject, which are declared
178 * as dynamic classes. Relies on the presence of appropriate
179 * serializers for objects, which are being stored/loaded.
182 class wxObjectStorage
: public wxObject
184 DECLARE_DYNAMIC_CLASS( wxObjectStorage
)
186 wxDataStreamBase
* mpStm
;
189 wxHashTable mRefHash
;
192 wxHashTable mInitialRefsHash
;
193 long mInitialRefsCnt
;
196 wxList mSerializersForNewObjs
;
198 bool mFinalizePending
;
201 wxSerializerBase
* FindSerializer( wxObject
* pForObj
);
203 void ClearHashesAndLists();
205 virtual bool VersionsMatch( char* v1
, char* v2
);
207 virtual wxSerializerInfo
* FindSrzInfoForClass( wxClassInfo
* pInfo
);
209 void DoExchangeObject( wxObject
* pInstance
, wxSerializerInfo
& srzInfo
);
211 bool ExchangeObjectInfo( wxClassInfo
** ppCInfo
, wxSerializerInfo
** ppSrz
);
213 wxSerializerInfo
* GetLatestSrzForObj( wxObject
* pWxObj
);
216 // can be changed (with countion!)
218 static char mVerSepartorCh
; // default: '#'
219 static char mMinorMajorSepartorCh
; // default: '-'
225 wxObjectStorage( wxDataStreamBase
& stm
);
227 virtual ~wxObjectStorage();
229 // adds initial reference, objects referred by such reference
230 // are not serialized when storing. When loading, pointers which
231 // refere to these "inital objects" are set up to refere to
232 // objects provided in by AddInitailRef() method.
234 // NOTE:: initial references should be added always in the
235 // same order, since the seq-# of the reference is used
236 // as an alias to the real object while storing/loading
238 void AddInitialRef( wxObject
* pObjRef
);
240 void ClearInitalRefs();
242 // init/reinit of object-storage
244 void SetDataStream( wxDataStreamBase
& stm
);
246 // performs linkng of in-memory references after loading, or
247 // links in-stream references after storing has proceeded
251 // storage methods for basic types
253 void XchgChar ( char& chObj
);
254 void XchgInt ( int& intObj
);
255 void XchgLong ( long& longObj
);
256 void XchgBool ( bool& boolObj
);
257 void XchgDouble ( double& doubleObj
);
258 void XchgCStr ( char* pCStrObj
);
259 void XchgUInt ( unsigned int& uI
);
260 void XchgSizeType( size_t& szObj
);
262 void XchgObjList ( wxList
& objList
);
263 void XchgObjArray ( wxBaseArray
& objArr
);
264 void XchgLongArray( wxBaseArray
& longArr
);
266 // storage methods for objects and pointers to objects
268 void XchgObj ( wxObject
* pWxObj
);
269 void XchgObjPtr( wxObject
** ppWxObj
);
271 bool IsLoading() { return mIsLoading
; }
273 // storage methods for common wxWindows classes,
274 // which may or may not be dymaic, therefor use the
275 // below methods instead of XchgObj(..)
277 void XchgWxStr ( wxString
& str
);
278 void XchgWxSize ( wxSize
& size
);
279 void XchgWxPoint( wxPoint
& point
);
280 void XchgWxRect ( wxRect
& rect
);
284 * The below classes provide "curde" serialization for most
285 * common wxWindows objects, i.e. they discard the information
286 * which may be contained in the subclassed versions of these classes
287 * However, more "fine-grainded" serializers could be written
288 * to match these subclasses exactly.
291 class wxColourSerializer
: public wxSerializerBase
293 DECLARE_SERIALIZER_CLASS( wxColourSerializer
);
295 static void Serialize( wxObject
* pObj
, wxObjectStorage
& store
);
298 // NOTE:: currently "stipple" and "dashes" properties of the pen
299 // are not serialized
301 class wxPenSerializer
: public wxSerializerBase
303 DECLARE_SERIALIZER_CLASS( wxPenSerializer
);
305 static void Serialize( wxObject
* pObj
, wxObjectStorage
& store
);
308 // NOTE:: currently "stipple" property of the brush is not serialized
310 class wxBrushSerializer
: public wxSerializerBase
312 DECLARE_SERIALIZER_CLASS( wxBrushSerializer
);
314 static void Serialize( wxObject
* pObj
, wxObjectStorage
& store
);
317 // serializer for wxList, assuming that the list
318 // holds derivatives of wxObject.
320 class wxObjectListSerializer
: public wxSerializerBase
322 DECLARE_SERIALIZER_CLASS( wxObjectListSerializer
);
324 static void Serialize( wxObject
* pObj
, wxObjectStorage
& store
);
327 // generic serializer for classes derived from wxEvtHandler handler,
328 // assuming that they do not add any new properties to wxEvtHandler
329 // or these properties are transient
331 class wxEvtHandlerSerializer
: public wxSerializerBase
333 DECLARE_SERIALIZER_CLASS( wxEvtHandlerSerializer
);
335 static void Serialize( wxObject
* pObj
, wxObjectStorage
& store
);
337 static void Initialize( wxObject
* pObj
);
340 // serializer for generic wxWindow. Serializes position, size, id,
341 // reference to parent, list of children, style flags and name string.
342 // Could be used for serializing wxWindow and generic wxPanel objects.
343 // Separate serializers have to be written for control classes.
345 class wxWindowSerializer
: public wxEvtHandlerSerializer
347 DECLARE_SERIALIZER_CLASS( wxWindowSerializer
);
350 static void Serialize( wxObject
* pObj
, wxObjectStorage
& store
);
352 // helpers, to ease the creation of serializers for derivatives of wxWindow
354 typedef (*wndCreationFn
)(wxWindow
*, wxWindow
*, const wxWindowID
,
355 const wxPoint
&, const wxSize
&, long, const wxString
& );
358 static void DoSerialize( wxObject
* pObj
, wxObjectStorage
& store
,
359 wndCreationFn creationFn
, bool refreshNow
= TRUE
363 static void CreateWindowFn( wxWindow
* wnd
, wxWindow
* parent
, const wxWindowID id
,
364 const wxPoint
& pos
, const wxSize
& size
, long style
,
365 const wxString
& name
);
369 class wxTextCtrlSerializer
: public wxWindowSerializer
371 DECLARE_SERIALIZER_CLASS( wxTextCtrlSerializer
);
373 static void Serialize( wxObject
* pObj
, wxObjectStorage
& store
);
375 static void CreateTextCtrlWindowFn( wxTextCtrl
* wnd
, wxWindow
* parent
, const wxWindowID id
,
376 const wxPoint
& pos
, const wxSize
& size
, long style
,
377 const wxString
& name
);
380 class wxButtonSerializer
: public wxWindowSerializer
382 DECLARE_SERIALIZER_CLASS( wxButtonSerializer
);
384 static void Serialize( wxObject
* pObj
, wxObjectStorage
& store
);
386 static void CreateButtonWindowFn( wxButton
* btn
, wxWindow
* parent
, const wxWindowID id
,
387 const wxPoint
& pos
, const wxSize
& size
, long style
,
388 const wxString
& name
);
391 class wxStaticTextSerializer
: public wxWindowSerializer
393 DECLARE_SERIALIZER_CLASS( wxStaticTextSerializer
);
395 static void Serialize( wxObject
* pObj
, wxObjectStorage
& store
);
397 static void CreateSTextWindowFn( wxStaticText
* pSTxt
, wxWindow
* parent
, const wxWindowID id
,
398 const wxPoint
& pos
, const wxSize
& size
, long style
,
399 const wxString
& name
);
403 class wxScrollBarSerializer
: public wxWindowSerializer
405 DECLARE_SERIALIZER_CLASS( wxScrollBarSerializer
);
407 static void Serialize( wxObject
* pObj
, wxObjectStorage
& store
);
409 static void CreateScollBarWindowFn( wxScrollBar
* sbar
, wxWindow
* parent
, const wxWindowID id
,
410 const wxPoint
& pos
, const wxSize
& size
, long style
,
411 const wxString
& name
);
414 class wxTreeCtrlSerializer
: public wxWindowSerializer
416 DECLARE_SERIALIZER_CLASS( wxTreeCtrlSerializer
);
419 static void SerializeBranch( wxTreeItemId parentId
, wxTreeCtrl
* pTree
,
420 wxObjectStorage
& store
, wxTreeItemId nextVisId
,
424 static void Serialize( wxObject
* pObj
, wxObjectStorage
& store
);
426 static void CreateTreeCtrlWindowFn( wxTreeCtrl
* tree
, wxWindow
* parent
, const wxWindowID id
,
427 const wxPoint
& pos
, const wxSize
& size
, long style
,
428 const wxString
& name
);
431 // default implementations of interfaces, used by wxObjectStorage class
433 // FOR NOW:: methods do not yet perform byte-swaps for outputting/reading words in
434 // machine-independent format. Better solution would be to write wrapper
435 // around the "promissed" protable-data-stream class of wxWindows
437 class wxIOStreamWrapper
: public wxDataStreamBase
439 DECLARE_DYNAMIC_CLASS( wxIOStreamWrapper
)
443 long mStreamPos
; // precalcualted stream postion,
444 // assuming that the actual stream object is not
445 // capable of telling postion of current get/put pointer
446 // (e.g. socket-stream)
451 // default constructor
454 // attach this wrapper to already exiting iostream object
456 wxIOStreamWrapper( iostream
& stm
, bool forInput
= TRUE
);
458 // creates "fstream" object with the given file name in binary mode,
459 // returns FALSE, if stream creation failed
461 // The created fstream object is "owned" by this wrapper,
462 // thus it is destored during destruction of this object
464 bool Create( const char* fileName
, bool forInput
= TRUE
);
466 inline bool CreateForInput( const char* fileName
)
468 { return Create( fileName
, TRUE
); }
470 inline bool CreateForOutput( const char* fileName
)
472 { return Create( fileName
, FALSE
); }
474 // the same as in the second constructor, previousely used
475 // stream object is flushed and destroyed (if owned).
476 // The attached stream is not "owned" by this wrapper object
478 void Attach( iostream
& stm
, bool forInput
= TRUE
);
480 virtual ~wxIOStreamWrapper();
482 virtual bool StoreChar ( char ch
);
483 virtual bool StoreInt ( int i
);
484 virtual bool StoreLong ( long l
);
485 virtual bool StoreDouble( double d
);
486 virtual bool StoreBytes ( void* bytes
, int count
);
488 virtual bool LoadChar ( char* pCh
);
489 virtual bool LoadInt ( int* pI
);
490 virtual bool LoadLong ( long* pL
);
491 virtual bool LoadDouble( double* pD
);
492 virtual bool LoadBytes ( void* pBytes
, int count
);
494 virtual bool Flush();
496 virtual long GetStreamPos();