Blender  V3.3
serialize.cc
Go to the documentation of this file.
1 /* SPDX-License-Identifier: GPL-2.0-or-later */
2 
3 #include "BLI_serialize.hh"
4 
5 #include "json.hpp"
6 
7 namespace blender::io::serialize {
8 
10 {
11  if (type_ != eValueType::String) {
12  return nullptr;
13  }
14  return static_cast<const StringValue *>(this);
15 }
16 
18 {
19  if (type_ != eValueType::Int) {
20  return nullptr;
21  }
22  return static_cast<const IntValue *>(this);
23 }
24 
26 {
27  if (type_ != eValueType::Double) {
28  return nullptr;
29  }
30  return static_cast<const DoubleValue *>(this);
31 }
32 
34 {
35  if (type_ != eValueType::Boolean) {
36  return nullptr;
37  }
38  return static_cast<const BooleanValue *>(this);
39 }
40 
42 {
43  if (type_ != eValueType::Array) {
44  return nullptr;
45  }
46  return static_cast<const ArrayValue *>(this);
47 }
48 
50 {
51  if (type_ != eValueType::Dictionary) {
52  return nullptr;
53  }
54  return static_cast<const DictionaryValue *>(this);
55 }
56 
57 static void convert_to_json(nlohmann::ordered_json &j, const Value &value);
58 static void convert_to_json(nlohmann::ordered_json &j, const ArrayValue &value)
59 {
60  const ArrayValue::Items &items = value.elements();
61  /* Create a json array to store the elements. If this isn't done and items is empty it would
62  * return use a null value, in stead of an empty array. */
63  j = "[]"_json;
64  for (const ArrayValue::Item &item_value : items) {
65  nlohmann::ordered_json json_item;
66  convert_to_json(json_item, *item_value);
67  j.push_back(json_item);
68  }
69 }
70 
71 static void convert_to_json(nlohmann::ordered_json &j, const DictionaryValue &value)
72 {
73  const DictionaryValue::Items &attributes = value.elements();
74  /* Create a json object to store the attributes. If this isn't done and attributes is empty it
75  * would return use a null value, in stead of an empty object. */
76  j = "{}"_json;
77  for (const DictionaryValue::Item &attribute : attributes) {
78  nlohmann::ordered_json json_item;
79  convert_to_json(json_item, *attribute.second);
80  j[attribute.first] = json_item;
81  }
82 }
83 
84 static void convert_to_json(nlohmann::ordered_json &j, const Value &value)
85 {
86  switch (value.type()) {
87  case eValueType::String: {
88  j = value.as_string_value()->value();
89  break;
90  }
91 
92  case eValueType::Int: {
93  j = value.as_int_value()->value();
94  break;
95  }
96 
97  case eValueType::Array: {
98  const ArrayValue &array = *value.as_array_value();
100  break;
101  }
102 
103  case eValueType::Dictionary: {
104  const DictionaryValue &object = *value.as_dictionary_value();
105  convert_to_json(j, object);
106  break;
107  }
108 
109  case eValueType::Null: {
110  j = nullptr;
111  break;
112  }
113 
114  case eValueType::Boolean: {
115  j = value.as_boolean_value()->value();
116  break;
117  }
118 
119  case eValueType::Double: {
120  j = value.as_double_value()->value();
121  }
122  }
123 }
124 
125 static std::unique_ptr<Value> convert_from_json(const nlohmann::ordered_json &j);
126 static std::unique_ptr<ArrayValue> convert_from_json_to_array(const nlohmann::ordered_json &j)
127 {
128  std::unique_ptr<ArrayValue> array = std::make_unique<ArrayValue>();
129  ArrayValue::Items &elements = array->elements();
130  for (auto element : j.items()) {
131  nlohmann::ordered_json element_json = element.value();
132  std::unique_ptr<Value> value = convert_from_json(element_json);
133  elements.append_as(value.release());
134  }
135  return array;
136 }
137 
138 static std::unique_ptr<DictionaryValue> convert_from_json_to_object(
139  const nlohmann::ordered_json &j)
140 {
141  std::unique_ptr<DictionaryValue> object = std::make_unique<DictionaryValue>();
142  DictionaryValue::Items &elements = object->elements();
143  for (auto element : j.items()) {
144  std::string key = element.key();
145  nlohmann::ordered_json element_json = element.value();
146  std::unique_ptr<Value> value = convert_from_json(element_json);
147  elements.append_as(std::pair(key, value.release()));
148  }
149  return object;
150 }
151 
152 static std::unique_ptr<Value> convert_from_json(const nlohmann::ordered_json &j)
153 {
154  switch (j.type()) {
155  case nlohmann::json::value_t::array: {
156  return convert_from_json_to_array(j);
157  }
158 
159  case nlohmann::json::value_t::object: {
160  return convert_from_json_to_object(j);
161  }
162 
163  case nlohmann::json::value_t::string: {
164  std::string value = j;
165  return std::make_unique<StringValue>(value);
166  }
167 
168  case nlohmann::json::value_t::null: {
169  return std::make_unique<NullValue>();
170  }
171 
172  case nlohmann::json::value_t::boolean: {
173  return std::make_unique<BooleanValue>(j);
174  }
175  case nlohmann::json::value_t::number_integer:
176  case nlohmann::json::value_t::number_unsigned: {
177  return std::make_unique<IntValue>(j);
178  }
179 
180  case nlohmann::json::value_t::number_float: {
181  return std::make_unique<DoubleValue>(j);
182  }
183 
184  case nlohmann::json::value_t::binary:
185  case nlohmann::json::value_t::discarded:
186  /*
187  * Binary data isn't supported.
188  * Discarded is an internal type of nlohmann.
189  *
190  * Assert in case we need to parse them.
191  */
193  return std::make_unique<NullValue>();
194  }
195 
197  return std::make_unique<NullValue>();
198 }
199 
200 void JsonFormatter::serialize(std::ostream &os, const Value &value)
201 {
202  nlohmann::ordered_json j;
203  convert_to_json(j, value);
204  if (indentation_len) {
205  os << j.dump(indentation_len);
206  }
207  else {
208  os << j.dump();
209  }
210 }
211 
212 std::unique_ptr<Value> JsonFormatter::deserialize(std::istream &is)
213 {
214  nlohmann::ordered_json j;
215  is >> j;
216  return convert_from_json(j);
217 }
218 
219 } // namespace blender::io::serialize
#define BLI_assert_unreachable()
Definition: BLI_assert.h:93
in reality light always falls off quadratically Particle Retrieve the data of the particle that spawned the object for example to give variation to multiple instances of an object Point Retrieve information about points in a point cloud Retrieve the edges of an object as it appears to Cycles topology will always appear triangulated Convert a blackbody temperature to an RGB value Normal Generate a perturbed normal from an RGB normal map image Typically used for faking highly detailed surfaces Generate an OSL shader from a file or text data block Image Sample an image file as a texture Sky Generate a procedural sky texture Noise Generate fractal Perlin noise Wave Generate procedural bands or rings with noise Voronoi Generate Worley noise based on the distance to random points Typically used to generate textures such as or biological cells Brick Generate a procedural texture producing bricks Texture Retrieve multiple types of texture coordinates nTypically used as inputs for texture nodes Vector Convert a or normal between and object coordinate space Combine Create a color from its and value channels Color Retrieve a color attribute
ATTR_WARN_UNUSED_RESULT const void * element
void append_as(ForwardValue &&...value)
Definition: BLI_vector.hh:442
const Container & elements() const
std::unique_ptr< Value > deserialize(std::istream &is) override
Definition: serialize.cc:212
void serialize(std::ostream &os, const Value &value) override
Definition: serialize.cc:200
const std::string & value() const
const BooleanValue * as_boolean_value() const
Definition: serialize.cc:33
const ArrayValue * as_array_value() const
Definition: serialize.cc:41
const StringValue * as_string_value() const
Definition: serialize.cc:9
const IntValue * as_int_value() const
Definition: serialize.cc:17
const DoubleValue * as_double_value() const
Definition: serialize.cc:25
const DictionaryValue * as_dictionary_value() const
Definition: serialize.cc:49
static std::unique_ptr< ArrayValue > convert_from_json_to_array(const nlohmann::ordered_json &j)
Definition: serialize.cc:126
static std::unique_ptr< Value > convert_from_json(const nlohmann::ordered_json &j)
Definition: serialize.cc:152
static std::unique_ptr< DictionaryValue > convert_from_json_to_object(const nlohmann::ordered_json &j)
Definition: serialize.cc:138
static void convert_to_json(nlohmann::ordered_json &j, const Value &value)
Definition: serialize.cc:84