OpenVDB  12.0.0
Metadata.h
Go to the documentation of this file.
1 // Copyright Contributors to the OpenVDB Project
2 // SPDX-License-Identifier: Apache-2.0
3 
4 #ifndef OPENVDB_METADATA_HAS_BEEN_INCLUDED
5 #define OPENVDB_METADATA_HAS_BEEN_INCLUDED
6 
7 #include "version.h"
8 #include "Exceptions.h"
9 #include "Types.h"
10 #include "math/Math.h" // for math::isZero()
11 #include "util/Name.h"
12 #include "util/Assert.h"
13 #include <cstdint>
14 #include <iostream>
15 #include <string>
16 #include <vector>
17 
18 
19 namespace openvdb {
21 namespace OPENVDB_VERSION_NAME {
22 
23 /// @brief Base class for storing metadata information in a grid.
25 {
26 public:
29 
30  Metadata() {}
31  virtual ~Metadata() {}
32 
33  // Disallow copying of instances of this class.
34  Metadata(const Metadata&) = delete;
35  Metadata& operator=(const Metadata&) = delete;
36 
37  /// Return the type name of the metadata.
38  virtual Name typeName() const = 0;
39 
40  /// Return a copy of the metadata.
41  virtual Metadata::Ptr copy() const = 0;
42 
43  /// Copy the given metadata into this metadata.
44  virtual void copy(const Metadata& other) = 0;
45 
46  /// Return a textual representation of this metadata.
47  virtual std::string str() const = 0;
48 
49  /// Return the boolean representation of this metadata (empty strings
50  /// and zeroVals evaluate to false; most other values evaluate to true).
51  virtual bool asBool() const = 0;
52 
53  /// Return @c true if the given metadata is equivalent to this metadata.
54  bool operator==(const Metadata& other) const;
55  /// Return @c true if the given metadata is different from this metadata.
56  bool operator!=(const Metadata& other) const { return !(*this == other); }
57 
58  /// Return the size of this metadata in bytes.
59  virtual Index32 size() const = 0;
60 
61  /// Unserialize this metadata from a stream.
62  void read(std::istream&);
63  /// Serialize this metadata to a stream.
64  void write(std::ostream&) const;
65 
66  /// Create new metadata of the given type.
67  static Metadata::Ptr createMetadata(const Name& typeName);
68 
69  /// Return @c true if the given type is known by the metadata type registry.
70  static bool isRegisteredType(const Name& typeName);
71 
72  /// Clear out the metadata registry.
73  static void clearRegistry();
74 
75  /// Register the given metadata type along with a factory function.
76  static void registerType(const Name& typeName, Metadata::Ptr (*createMetadata)());
77  static void unregisterType(const Name& typeName);
78 
79 protected:
80  /// Read the size of the metadata from a stream.
81  static Index32 readSize(std::istream&);
82  /// Write the size of the metadata to a stream.
83  void writeSize(std::ostream&) const;
84 
85  /// Read the metadata from a stream.
86  virtual void readValue(std::istream&, Index32 numBytes) = 0;
87  /// Write the metadata to a stream.
88  virtual void writeValue(std::ostream&) const = 0;
89 };
90 
91 
92 /// @brief Subclass to hold raw data of an unregistered type
94 {
95 public:
96  using ByteVec = std::vector<uint8_t>;
97 
98  explicit UnknownMetadata(const Name& typ = "<unknown>"): mTypeName(typ) {}
99 
100  Name typeName() const override { return mTypeName; }
101  Metadata::Ptr copy() const override;
102  void copy(const Metadata&) override;
103  std::string str() const override { return (mBytes.empty() ? "" : "<binary data>"); }
104  bool asBool() const override { return !mBytes.empty(); }
105  Index32 size() const override { return static_cast<Index32>(mBytes.size()); }
106 
107  void setValue(const ByteVec& bytes) { mBytes = bytes; }
108  const ByteVec& value() const { return mBytes; }
109 
110 protected:
111  void readValue(std::istream&, Index32 numBytes) override;
112  void writeValue(std::ostream&) const override;
113 
114 private:
115  Name mTypeName;
116  ByteVec mBytes;
117 };
118 
119 
120 /// @brief Templated metadata class to hold specific types.
121 template<typename T>
122 class TypedMetadata: public Metadata
123 {
124 public:
127 
128  TypedMetadata();
129  TypedMetadata(const T& value);
130  TypedMetadata(const TypedMetadata<T>& other);
131  ~TypedMetadata() override;
132 
133  Name typeName() const override;
134  Metadata::Ptr copy() const override;
135  void copy(const Metadata& other) override;
136  std::string str() const override;
137  bool asBool() const override;
138  Index32 size() const override { return static_cast<Index32>(sizeof(T)); }
139 
140  /// Set this metadata's value.
141  void setValue(const T&);
142  /// Return this metadata's value.
143  T& value();
144  const T& value() const;
145 
146  // Static specialized function for the type name. This function must be
147  // template specialized for each type T.
148  static Name staticTypeName() { return typeNameAsString<T>(); }
149 
150  /// Create new metadata of this type.
151  static Metadata::Ptr createMetadata();
152 
153  static void registerType();
154  static void unregisterType();
155  static bool isRegisteredType();
156 
157 protected:
158  void readValue(std::istream&, Index32 numBytes) override;
159  void writeValue(std::ostream&) const override;
160 
161 private:
162  T mValue;
163 };
164 
165 /// Write a Metadata to an output stream
166 std::ostream& operator<<(std::ostream& ostr, const Metadata& metadata);
167 
168 
169 ////////////////////////////////////////
170 
171 
172 inline void
173 Metadata::writeSize(std::ostream& os) const
174 {
175  const Index32 n = this->size();
176  os.write(reinterpret_cast<const char*>(&n), sizeof(Index32));
177 }
178 
179 
180 inline Index32
181 Metadata::readSize(std::istream& is)
182 {
183  Index32 n = 0;
184  is.read(reinterpret_cast<char*>(&n), sizeof(Index32));
185  return n;
186 }
187 
188 
189 inline void
190 Metadata::read(std::istream& is)
191 {
192  const Index32 numBytes = this->readSize(is);
193  this->readValue(is, numBytes);
194 }
195 
196 
197 inline void
198 Metadata::write(std::ostream& os) const
199 {
200  this->writeSize(os);
201  this->writeValue(os);
202 }
203 
204 
205 ////////////////////////////////////////
206 
207 
208 template <typename T>
209 inline
211 {
212 }
213 
214 template <typename T>
215 inline
216 TypedMetadata<T>::TypedMetadata(const T &value) : mValue(value)
217 {
218 }
219 
220 template <typename T>
221 inline
223  Metadata(),
224  mValue(other.mValue)
225 {
226 }
227 
228 template <typename T>
229 inline
231 {
232 }
233 
234 template <typename T>
235 inline Name
237 {
239 }
240 
241 template <typename T>
242 inline void
244 {
245  mValue = val;
246 }
247 
248 template <typename T>
249 inline T&
251 {
252  return mValue;
253 }
254 
255 template <typename T>
256 inline const T&
258 {
259  return mValue;
260 }
261 
262 template <typename T>
263 inline Metadata::Ptr
265 {
266  Metadata::Ptr metadata(new TypedMetadata<T>());
267  metadata->copy(*this);
268  return metadata;
269 }
270 
271 template <typename T>
272 inline void
274 {
275  const TypedMetadata<T>* t = dynamic_cast<const TypedMetadata<T>*>(&other);
276  if (t == nullptr) OPENVDB_THROW(TypeError, "Incompatible type during copy");
277  mValue = t->mValue;
278 }
279 
280 
281 template<typename T>
282 inline void
283 TypedMetadata<T>::readValue(std::istream& is, [[maybe_unused]] Index32 numBytes)
284 {
285  OPENVDB_ASSERT(this->size() == numBytes);
286  is.read(reinterpret_cast<char*>(&mValue), this->size());
287 }
288 
289 template<typename T>
290 inline void
291 TypedMetadata<T>::writeValue(std::ostream& os) const
292 {
293  os.write(reinterpret_cast<const char*>(&mValue), this->size());
294 }
295 
296 template <typename T>
297 inline std::string
299 {
300  std::ostringstream ostr;
301  ostr << mValue;
302  return ostr.str();
303 }
304 
305 template<typename T>
306 inline bool
308 {
309  return !math::isZero(mValue);
310 }
311 
312 template <typename T>
313 inline Metadata::Ptr
315 {
316  Metadata::Ptr ret(new TypedMetadata<T>());
317  return ret;
318 }
319 
320 template <typename T>
321 inline void
323 {
326 }
327 
328 template <typename T>
329 inline void
331 {
333 }
334 
335 template <typename T>
336 inline bool
338 {
340 }
341 
342 
343 template<>
344 inline std::string
346 {
347  return (mValue ? "true" : "false");
348 }
349 
350 
351 inline std::ostream&
352 operator<<(std::ostream& ostr, const Metadata& metadata)
353 {
354  ostr << metadata.str();
355  return ostr;
356 }
357 
358 
376 
377 
378 ////////////////////////////////////////
379 
380 
381 template<>
382 inline Index32
383 StringMetadata::size() const
384 {
385  return static_cast<Index32>(mValue.size());
386 }
387 
388 
389 template<>
390 inline std::string
391 StringMetadata::str() const
392 {
393  return mValue;
394 }
395 
396 
397 template<>
398 inline void
399 StringMetadata::readValue(std::istream& is, Index32 size)
400 {
401  mValue.resize(size, '\0');
402  is.read(&mValue[0], size);
403 }
404 
405 template<>
406 inline void
407 StringMetadata::writeValue(std::ostream& os) const
408 {
409  os.write(reinterpret_cast<const char*>(&mValue[0]), this->size());
410 }
411 
412 } // namespace OPENVDB_VERSION_NAME
413 } // namespace openvdb
414 
415 #endif // OPENVDB_METADATA_HAS_BEEN_INCLUDED
bool operator!=(const Metadata &other) const
Return true if the given metadata is different from this metadata.
Definition: Metadata.h:56
static Name staticTypeName()
Definition: Metadata.h:148
#define OPENVDB_API
Definition: Platform.h:268
bool asBool() const override
Definition: Metadata.h:104
UnknownMetadata(const Name &typ="<unknown>")
Definition: Metadata.h:98
void write(std::ostream &) const
Serialize this metadata to a stream.
Definition: Metadata.h:198
#define OPENVDB_THROW(exception, message)
Definition: Exceptions.h:74
General-purpose arithmetic and comparison routines, most of which accept arbitrary value types (or at...
virtual std::string str() const =0
Return a textual representation of this metadata.
static Index32 readSize(std::istream &)
Read the size of the metadata from a stream.
Definition: Metadata.h:181
~TypedMetadata() override
Definition: Metadata.h:230
std::vector< uint8_t > ByteVec
Definition: Metadata.h:96
Name typeName() const override
Return the type name of the metadata.
Definition: Metadata.h:100
Subclass to hold raw data of an unregistered type.
Definition: Metadata.h:93
TypedMetadata()
Definition: Metadata.h:210
static Metadata::Ptr createMetadata()
Create new metadata of this type.
Definition: Metadata.h:314
const ByteVec & value() const
Definition: Metadata.h:108
std::string str() const override
Return a textual representation of this metadata.
Definition: Metadata.h:103
Base class for storing metadata information in a grid.
Definition: Metadata.h:24
bool operator==(const Vec3< T0 > &v0, const Vec3< T1 > &v1)
Equality operator, does exact floating point comparisons.
Definition: Vec3.h:474
bool asBool() const override
Definition: Metadata.h:307
Templated metadata class to hold specific types.
Definition: Metadata.h:122
std::shared_ptr< T > SharedPtr
Definition: Types.h:114
SharedPtr< const Metadata > ConstPtr
Definition: Metadata.h:28
static void registerType(const Name &typeName, Metadata::Ptr(*createMetadata)())
Register the given metadata type along with a factory function.
bool isZero(const Type &x)
Return true if x is exactly equal to zero.
Definition: Math.h:337
#define OPENVDB_ASSERT(X)
Definition: Assert.h:41
void readValue(std::istream &, Index32 numBytes) override
Read the metadata from a stream.
Definition: Metadata.h:283
static bool isRegisteredType(const Name &typeName)
Return true if the given type is known by the metadata type registry.
void read(std::istream &)
Unserialize this metadata from a stream.
Definition: Metadata.h:190
Definition: Exceptions.h:13
static bool isRegisteredType()
Definition: Metadata.h:337
static void registerType()
Definition: Metadata.h:322
void setValue(const ByteVec &bytes)
Definition: Metadata.h:107
void setValue(const T &)
Set this metadata&#39;s value.
Definition: Metadata.h:243
Name typeName() const override
Return the type name of the metadata.
Definition: Metadata.h:236
uint32_t Index32
Definition: Types.h:52
Index32 size() const override
Return the size of this metadata in bytes.
Definition: Metadata.h:138
void writeValue(std::ostream &) const override
Write the metadata to a stream.
Definition: Metadata.h:291
Metadata::Ptr copy() const override
Return a copy of the metadata.
Definition: Metadata.h:264
std::ostream & operator<<(std::ostream &ostr, const Metadata &metadata)
Write a Metadata to an output stream.
Definition: Metadata.h:352
Definition: Exceptions.h:64
std::string str() const override
Return a textual representation of this metadata.
Definition: Metadata.h:298
static void unregisterType()
Definition: Metadata.h:330
std::string Name
Definition: Name.h:19
void writeSize(std::ostream &) const
Write the size of the metadata to a stream.
Definition: Metadata.h:173
#define OPENVDB_VERSION_NAME
The version namespace name for this library version.
Definition: version.h.in:121
virtual ~Metadata()
Definition: Metadata.h:31
T & value()
Return this metadata&#39;s value.
Definition: Metadata.h:250
static void unregisterType(const Name &typeName)
Index32 size() const override
Return the size of this metadata in bytes.
Definition: Metadata.h:105
#define OPENVDB_USE_VERSION_NAMESPACE
Definition: version.h.in:218
Metadata()
Definition: Metadata.h:30
SharedPtr< Metadata > Ptr
Definition: Metadata.h:27