-
Notifications
You must be signed in to change notification settings - Fork 78
Expand file tree
/
Copy pathGenericReserializer.h
More file actions
307 lines (257 loc) · 16.1 KB
/
Copy pathGenericReserializer.h
File metadata and controls
307 lines (257 loc) · 16.1 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
#ifndef MANA_SCRIPT_GENERICRESERIALIZER_HPP
#define MANA_SCRIPT_GENERICRESERIALIZER_HPP
#include <vector>
#include <map>
#include <stack>
#include <string>
#include <functional>
#include <typeindex>
#include <typeinfo>
#include <memory>
#include <climits>
#include <osg/ref_ptr>
#include <osg/Referenced>
#include "GenericInputStream.h"
extern "C"
{
typedef void (*WrapperLoadingFunction)(void);
}
namespace osgVerse
{
struct BaseSerializer;
struct WrappableSerializer;
struct ObjectSerializer;
struct ImageSerializer;
struct VectorSerializer;
struct UserSerializer;
struct BoolSerializer;
struct GLenumSerializer;
struct StringSerializer;
struct EnumSerializer;
template<typename T> struct ValueSerializer;
class RewrapperManager;
class SerializerVisitor
{
public:
template<typename T> void apply(ValueSerializer<T>& obj);
void apply(BaseSerializer& obj) { applyValue(obj); }
virtual void apply(ObjectSerializer& obj) {}
virtual void apply(ImageSerializer& obj) {}
virtual void apply(VectorSerializer& obj) {}
virtual void apply(UserSerializer& obj) {}
virtual void apply(BoolSerializer& obj) {}
virtual void apply(StringSerializer& obj) {}
virtual void apply(EnumSerializer& obj) {}
virtual void apply(GLenumSerializer& obj) {}
template<typename T>
void registerType(std::function<void(ValueSerializer<T>&)> func)
{
_registry[std::type_index(typeid(ValueSerializer<T>))] = [func](BaseSerializer& baseObj)
{ ValueSerializer<T>& obj = static_cast<ValueSerializer<T>&>(baseObj); func(obj); };
}
SerializerVisitor() : _manager(NULL), _inputVersion(INT_MAX) {}
void setManager(RewrapperManager* m, int v) { _manager = m; _inputVersion = v; }
void push(const std::string& n) { _propertyList.push(n); }
void pop() { _propertyList.pop(); }
const std::stack<std::string>& getPropertyList() const { return _propertyList; }
protected:
void traverse(WrappableSerializer& obj);
void applyValue(BaseSerializer& obj);
typedef std::map<std::type_index, std::function<void(BaseSerializer&)>> SerializerMap;
SerializerMap _registry; RewrapperManager* _manager; int _inputVersion;
std::stack<std::string> _propertyList;
};
#define META_VISITOR() virtual void accept(const std::string& n, SerializerVisitor& v) \
{ v.push(n); v.apply(*this); v.pop(); }
struct BaseSerializer : public osg::Referenced
{
typedef std::function<void(InputStream& is, InputUserData& ud)> ReadFunc;
BaseSerializer() : _firstVersion(0), _lastVersion(INT_MAX) {}
int _firstVersion, _lastVersion; META_VISITOR()
};
struct WrapperAssociate
{
WrapperAssociate(const std::string& name) : _firstVersion(0), _lastVersion(INT_MAX), _name(name) {}
int _firstVersion, _lastVersion; std::string _name;
};
struct WrappableSerializer : public BaseSerializer { std::string _type; };
struct ObjectSerializer : public WrappableSerializer { META_VISITOR() };
struct ImageSerializer : public WrappableSerializer { META_VISITOR() };
struct VectorSerializer : public BaseSerializer { std::string _type; META_VISITOR() };
struct UserSerializer : public BaseSerializer { ReadFunc _reader; META_VISITOR() };
struct BoolSerializer : public BaseSerializer { bool _v0; META_VISITOR() };
struct StringSerializer : public BaseSerializer { std::string _v0; META_VISITOR() };
struct GLenumSerializer : public BaseSerializer { std::string _type; unsigned int _v0; META_VISITOR() };
template<typename T> struct ValueSerializer : public BaseSerializer { T _v0; bool _hex; META_VISITOR() };
template<typename T> struct ListSerializer : public BaseSerializer { T _v0; META_VISITOR() };
struct EnumSerializer : public BaseSerializer
{ std::string _v0; std::set<std::string> _values; META_VISITOR() };
struct BitFlagSerializer : public BaseSerializer
{ bool _asInt; unsigned int _v0; std::map<std::string, unsigned int> _valueMap; META_VISITOR() };
template<typename T> void SerializerVisitor::apply(ValueSerializer<T>& obj)
{ applyValue(static_cast<BaseSerializer&>(obj)); }
class Rewrapper : public osg::Referenced
{
public:
template<typename T> void addValueSerializer(const std::string& prop, T def, bool hex = false)
{ ValueSerializer<T>* s = new ValueSerializer<T>(); s->_v0 = def; s->_hex = hex; add(prop, s); }
template<typename T> void addRefValueSerializer(const std::string& prop, const T& def, bool hex = false)
{ ValueSerializer<T>* s = new ValueSerializer<T>(); s->_v0 = def; s->_hex = hex; add(prop, s); }
template<typename T> void addListSerializer(const std::string& prop)
{ ListSerializer<T>* s = new ListSerializer<T>(); add(prop, s); }
void addObjectListSerializer(const std::string& prop, const std::string& t)
{ ListSerializer<ObjectTypeAndID>* s = new ListSerializer<ObjectTypeAndID>(); s->_v0 = ObjectTypeAndID(t, ""); add(prop, s); }
void addBoolSerializer(const std::string& prop, bool def)
{ BoolSerializer* s = new BoolSerializer; s->_v0 = def; add(prop, s); }
void addGLenumSerializer(const std::string& prop, const std::string& type, unsigned int def)
{ GLenumSerializer* s = new GLenumSerializer; s->_type = type; s->_v0 = def; add(prop, s); }
void addStringSerializer(const std::string& prop, const std::string& def)
{ StringSerializer* s = new StringSerializer; s->_v0 = def; add(prop, s); }
void addObjectSerializer(const std::string& prop, const std::string& type)
{ ObjectSerializer* s = new ObjectSerializer; s->_type = type; add(prop, s); }
void addImageSerializer(const std::string& prop, const std::string& type)
{ ImageSerializer* s = new ImageSerializer; s->_type = type; add(prop, s); }
void addVectorSerializer(const std::string& prop, const std::string& type)
{ VectorSerializer* s = new VectorSerializer; s->_type = type; add(prop, s); }
void addUserSerializer(const std::string& prop, BaseSerializer::ReadFunc f)
{ UserSerializer* s = new UserSerializer; s->_reader = f; add(prop, s); }
void beginEnumSerializer(const std::string& prop, const std::string& value)
{ _lastEnum = new EnumSerializer; _lastEnum->_v0 = value; add(prop, _lastEnum); }
void addEnumValue(const std::string & v) { if (_lastEnum) _lastEnum->_values.insert(v); }
void endEnumSerializer() { _lastEnum = NULL; }
void beginBitFlagSerializer(const std::string& prop, unsigned int v, bool i)
{ _lastBitFlags = new BitFlagSerializer; _lastBitFlags->_asInt = i; _lastBitFlags->_v0 = v; add(prop, _lastBitFlags); }
void addBitFlagValue(const std::string& v, unsigned int ui) { if (_lastBitFlags) { _lastBitFlags->_valueMap[v] = ui; } }
void endBitFlagSerializer() { _lastBitFlags = NULL; }
void setAssociates(const std::string& a) { splitAssociates(a); }
void add(const std::string& n, BaseSerializer* s);
void clear();
void setUpdatedVersion(int v) { _version = v; }
int getUpdatedVersion() const { return _version; }
void markSerializerAsRemoved(const std::string& name);
void markAssociateAsRemoved(const std::string& name);
void markAssociateAsAdded(const std::string& name);
Rewrapper() : _lastBitFlags(NULL), _lastEnum(NULL), _version(0) {}
void accept(RewrapperManager* manager, SerializerVisitor& v,
int inputVersion, bool includingAssociates = true);
protected:
virtual ~Rewrapper() {}
void splitAssociates(const std::string& associates);
typedef std::pair<std::string, osg::ref_ptr<BaseSerializer>> SerializerPair;
std::vector<SerializerPair> _serializers;
std::vector<WrapperAssociate> _associates;
BitFlagSerializer* _lastBitFlags;
EnumSerializer* _lastEnum; int _version;
};
class RewrapperManager
{
public:
static std::shared_ptr<RewrapperManager> instance();
virtual ~RewrapperManager();
void addRewrapper(const std::string& name, Rewrapper* r);
void removeRewrapper(const std::string& name);
Rewrapper* getRewrapper(const std::string& name);
typedef std::map<std::string, osg::ref_ptr<Rewrapper>> RewrapperMap;
const RewrapperMap& getRewrappers() const { return _rewrappers; }
protected:
RewrapperMap _rewrappers;
};
struct RegisterWrapperProxy
{
public:
typedef void (*AddPropFunc)(Rewrapper&);
RegisterWrapperProxy(const std::string& name, const std::string& associates, AddPropFunc func);
virtual ~RegisterWrapperProxy(); std::string _className;
};
struct RegisterWrapperFunctionProxy
{
RegisterWrapperFunctionProxy(WrapperLoadingFunction function) { (function)(); }
};
struct UpdateWrapperVersionProxy
{
UpdateWrapperVersionProxy(Rewrapper* w, int v) : _wrapper(w)
{ _lastVersion = w->getUpdatedVersion(); w->setUpdatedVersion(v); }
~UpdateWrapperVersionProxy() { _wrapper->setUpdatedVersion(_lastVersion); }
Rewrapper* _wrapper; int _lastVersion;
};
}
#define ADD_USER_SERIALIZER(PROP) wrapper.addUserSerializer(#PROP, &read##PROP)
#define ADD_BOOL_SERIALIZER(PROP, DEF) wrapper.addBoolSerializer(#PROP, DEF)
#define ADD_GLENUM_SERIALIZER(PROP, TYPE, DEF) wrapper.addGLenumSerializer(#PROP, #TYPE, DEF)
#define ADD_STRING_SERIALIZER(PROP, DEF) wrapper.addStringSerializer(#PROP, DEF)
#define ADD_OBJECT_SERIALIZER(PROP, TYPE, DEF) wrapper.addObjectSerializer(#PROP, #TYPE)
#define ADD_IMAGE_SERIALIZER(PROP, TYPE, DEF) wrapper.addImageSerializer(#PROP, #TYPE)
#define ADD_CHAR_SERIALIZER(PROP, DEF) wrapper.addValueSerializer<char>(#PROP, DEF)
#define ADD_UCHAR_SERIALIZER(PROP, DEF) wrapper.addValueSerializer<unsigned char>(#PROP, DEF)
#define ADD_SHORT_SERIALIZER(PROP, DEF) wrapper.addValueSerializer<short>(#PROP, DEF)
#define ADD_USHORT_SERIALIZER(PROP, DEF) wrapper.addValueSerializer<unsigned short>(#PROP, DEF)
#define ADD_HEXSHORT_SERIALIZER(PROP, DEF) wrapper.addValueSerializer<unsigned short>(#PROP, DEF, true)
#define ADD_INT_SERIALIZER(PROP, DEF) wrapper.addValueSerializer<int>(#PROP, DEF)
#define ADD_UINT_SERIALIZER(PROP, DEF) wrapper.addValueSerializer<unsigned int>(#PROP, DEF)
#define ADD_GLINT_SERIALIZER(PROP, DEF) wrapper.addValueSerializer<GLint>(#PROP, DEF)
#define ADD_HEXINT_SERIALIZER(PROP, DEF) wrapper.addValueSerializer<unsigned int>(#PROP, DEF, true)
#define ADD_FLOAT_SERIALIZER(PROP, DEF) wrapper.addValueSerializer<float>(#PROP, DEF)
#define ADD_DOUBLE_SERIALIZER(PROP, DEF) wrapper.addValueSerializer<double>(#PROP, DEF)
#define ADD_VEC2B_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec2b>(#PROP, DEF)
#define ADD_VEC2UB_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec2ub>(#PROP, DEF)
#define ADD_VEC2S_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec2s>(#PROP, DEF)
#define ADD_VEC2US_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec2us>(#PROP, DEF)
#define ADD_VEC2I_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec2i>(#PROP, DEF)
#define ADD_VEC2UI_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec2ui>(#PROP, DEF)
#define ADD_VEC2F_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec2f>(#PROP, DEF)
#define ADD_VEC2D_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec2d>(#PROP, DEF)
#define ADD_VEC2_SERIALIZER(PROP, DEF) ADD_VEC2F_SERIALIZER(PROP, DEF)
#define ADD_VEC3B_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec3b>(#PROP, DEF)
#define ADD_VEC3UB_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec3ub>(#PROP, DEF)
#define ADD_VEC3S_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec3s>(#PROP, DEF)
#define ADD_VEC3US_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec3us>(#PROP, DEF)
#define ADD_VEC3I_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec3i>(#PROP, DEF)
#define ADD_VEC3UI_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec3ui>(#PROP, DEF)
#define ADD_VEC3F_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec3f>(#PROP, DEF)
#define ADD_VEC3D_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec3d>(#PROP, DEF)
#define ADD_VEC3_SERIALIZER(PROP, DEF) ADD_VEC3F_SERIALIZER(PROP, DEF)
#define ADD_VEC4B_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec4b>(#PROP, DEF)
#define ADD_VEC4UB_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec4ub>(#PROP, DEF)
#define ADD_VEC4S_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec4s>(#PROP, DEF)
#define ADD_VEC4US_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec4us>(#PROP, DEF)
#define ADD_VEC4I_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec4i>(#PROP, DEF)
#define ADD_VEC4UI_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec4ui>(#PROP, DEF)
#define ADD_VEC4F_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec4f>(#PROP, DEF)
#define ADD_VEC4D_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Vec4d>(#PROP, DEF)
#define ADD_VEC4_SERIALIZER(PROP, DEF) ADD_VEC4F_SERIALIZER(PROP, DEF)
#define ADD_QUAT_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Quat>(#PROP, DEF)
#define ADD_PLANE_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Plane>(#PROP, DEF)
#define ADD_MATRIX_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Matrix>(#PROP, DEF)
#define ADD_MATRIXF_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Matrixf>(#PROP, DEF)
#define ADD_MATRIXD_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::Matrixd>(#PROP, DEF)
#define ADD_BOUNDINGBOXF_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::BoundingBoxf>(#PROP, DEF)
#define ADD_BOUNDINGBOXD_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::BoundingBoxd>(#PROP, DEF)
#define ADD_BOUNDINGSPHEREF_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::BoundingSpheref>(#PROP, DEF)
#define ADD_BOUNDINGSPHERED_SERIALIZER(PROP, DEF) wrapper.addRefValueSerializer<osg::BoundingSphered>(#PROP, DEF)
#define ADD_VECTOR_SERIALIZER(PROP, TYPE, ETYPE, NUMONROW) wrapper.addVectorSerializer(#PROP, #TYPE)
#define ADD_ISAVECTOR_SERIALIZER(PROP, ETYPE, NUMONROW) wrapper.addVectorSerializer(#PROP, #ETYPE)
#define ADD_LIST_SERIALIZER(PROP, TYPE) wrapper.addListSerializer<TYPE>(#PROP);
#define ADD_OBJECT_LIST_SERIALIZER(PROP, TYPE) wrapper.addObjectListSerializer(#PROP, #TYPE);
#define BEGIN_ENUM_SERIALIZER(PROP, DEF) wrapper.beginEnumSerializer(#PROP, #DEF);
#define BEGIN_ENUM_SERIALIZER2(PROP, TYPE, DEF) wrapper.beginEnumSerializer(#PROP, #DEF);
#define ADD_ENUM_VALUE(VALUE) wrapper.addEnumValue(#VALUE);
#define END_ENUM_SERIALIZER() wrapper.endEnumSerializer();
#define BEGIN_BITFLAGS_SERIALIZER(PROP, DEF) wrapper.beginBitFlagSerializer(#PROP, DEF, false);
#define BEGIN_UINT_BITFLAGS_SERIALIZER(PROP, DEF) wrapper.beginBitFlagSerializer(#PROP, DEF, false);
#define BEGIN_INT_BITFLAGS_SERIALIZER(PROP, DEF) wrapper.beginBitFlagSerializer(#PROP, DEF, true);
#define ADD_BITFLAG_VALUE(VALUE_NAME, VALUE) wrapper.addBitFlagValue(#VALUE_NAME, VALUE);
#define END_BITFLAGS_SERIALIZER() wrapper.endBitFlagSerializer();
#define UPDATE_TO_VERSION(VER) wrapper.setUpdatedVersion((VER));
#define UPDATE_TO_VERSION_SCOPED(VER) UpdateWrapperVersionProxy uwvp(&wrapper, (VER));
#define ADDED_ASSOCIATE(STR) wrapper.markAssociateAsAdded(STR);
#define REMOVED_ASSOCIATE(STR) wrapper.markAssociateAsRemoved(STR);
#define REMOVE_SERIALIZER(PROP) wrapper.markSerializerAsRemoved(#PROP);
#define REGISTER_OBJECT_WRAPPER(NAME, CREATEINSTANCE, CLASS, ASSOCIATES) \
extern "C" void rewrapper_serializer_##NAME(void) {} \
extern void rewrapper_propfunc_##NAME(Rewrapper& wrapper); \
static osgVerse::RegisterWrapperProxy rewrapper_proxy_##NAME(#CLASS, ASSOCIATES, &rewrapper_propfunc_##NAME); \
void rewrapper_propfunc_##NAME(Rewrapper& wrapper)
#define USE_OBJECT_WRAPPER(NAME) \
extern "C" void rewrapper_serializer_##NAME(void); \
static osgVerse::RegisterWrapperFunctionProxy rewrapperfunc_proxy_##NAME(rewrapper_serializer_##NAME);
#endif