FastLED 3.9.15
Loading...
Searching...
No Matches
json.h
Go to the documentation of this file.
1#pragma once
2
123
124// Implementation details - users should not rely on these directly
125#include "fl/stl/json/types.h"
126#include "fl/stl/noexcept.h"
127
128namespace fl {
129
130class json {
131private:
133
134public:
135 // Constructors
136 json() FL_NOEXCEPT : mValue() {} // Default initialize to nullptr
141 json(float f) FL_NOEXCEPT : mValue(fl::make_shared<json_value>(f)) {} // Use float directly
142 json(double d) FL_NOEXCEPT : mValue(fl::make_shared<json_value>(static_cast<float>(d))) {} // Convert double to float
144 json(const char* s) FL_NOEXCEPT : json(fl::string(s)) {}
147 // Constructor from shared_ptr<json_value>
150 // Factory method to create a json from a json_value
151 static json fromValue(const json_value& value) FL_NOEXCEPT {
152 json result;
154 return result;
155 }
157 // Constructor for fl::vector<float> - converts to JSON array
159 auto ptr = mValue->data.ptr<json_array>();
160 if (ptr) {
161 for (const auto& item : vec) {
162 ptr->push_back(fl::make_shared<json_value>(item)); // Use float directly
163 }
164 }
165 }
167 // Special constructor for char values
168 static json from_char(char c) FL_NOEXCEPT {
169 json result;
171 //FL_WARN("Created json_value with string: " << value->is_string() << ", int: " << value->is_int());
172 result.mValue = value;
173 //FL_WARN("json has string: " << result.is_string() << ", int: " << result.is_int());
174 return result;
175 }
177 // Copy constructor
178 json(const json& other) FL_NOEXCEPT : mValue(other.mValue) {}
180 // Assignment operator
181 json& operator=(const json& other) FL_NOEXCEPT {
182 //FL_WARN("json& operator=(const json& other): " << (other.mValue ? other.mValue.get() : 0));
183 if (this != &other) {
184 mValue = other.mValue;
185 }
186 return *this;
188
189 json& operator=(json&& other) FL_NOEXCEPT {
190 if (this != &other) {
191 mValue = fl::move(other.mValue);
192 }
193 return *this;
194 }
196 // Assignment operators for primitive types to avoid ambiguity
199 return *this;
204 return *this;
209 return *this;
211
213 mValue = fl::make_shared<json_value>(static_cast<float>(value));
214 return *this;
219 return *this;
224 return *this;
225 }
227 // Assignment operator for fl::vector<float>
230 auto ptr = mValue->data.ptr<json_array>();
231 if (ptr) {
232 for (const auto& item : vec) {
233 ptr->push_back(fl::make_shared<json_value>(item)); // Use float directly
234 }
235 }
236 return *this;
237 }
239 // Type queries
240 bool is_null() const FL_NOEXCEPT { return mValue ? mValue->is_null() : true; }
241 bool is_bool() const FL_NOEXCEPT { return mValue && mValue->is_bool(); }
242 bool is_int() const FL_NOEXCEPT { return mValue && (mValue->is_int() || mValue->is_bool()); }
243 bool is_float() const FL_NOEXCEPT { return mValue && mValue->is_float(); }
244 bool is_double() const FL_NOEXCEPT { return mValue && mValue->is_double(); }
245 // is_number() returns true if the value is any numeric type (int or float)
246 bool is_number() const FL_NOEXCEPT { return mValue && mValue->is_number(); }
247 bool is_string() const FL_NOEXCEPT { return mValue && mValue->is_string(); }
248 bool is_array() const FL_NOEXCEPT { return mValue && mValue->is_array(); }
249 bool is_generic_array() const FL_NOEXCEPT { return mValue && mValue->is_generic_array(); }
250 bool is_object() const FL_NOEXCEPT { return mValue && mValue->is_object(); }
251 bool is_audio() const FL_NOEXCEPT { return mValue && mValue->is_audio(); }
252 bool is_bytes() const FL_NOEXCEPT { return mValue && mValue->is_bytes(); }
253 bool is_floats() const FL_NOEXCEPT { return mValue && mValue->is_floats(); }
255 // Safe extractors
256 fl::optional<bool> as_bool() const FL_NOEXCEPT { return mValue ? mValue->as_bool() : fl::nullopt; }
258 if (!mValue) return fl::nullopt;
259 return mValue->as_int();
260 }
262 template<typename IntType>
264 if (!mValue) return fl::nullopt;
265 return mValue->template as_int<IntType>();
267
269 if (!mValue) return fl::nullopt;
270 return mValue->as_float();
272
274 if (!mValue) return fl::nullopt;
275 return mValue->as_double();
276 }
278 template<typename FloatType>
280 if (!mValue) return fl::nullopt;
281 return mValue->template as_float<FloatType>();
283
285 if (!mValue) return fl::nullopt;
286 return mValue->as_string();
288 // Zero-copy pointer accessors
289 const json_array* as_array() const FL_NOEXCEPT { return mValue ? mValue->as_array() : nullptr; }
290 const json_object* as_object() const FL_NOEXCEPT { return mValue ? mValue->as_object() : nullptr; }
292 // Explicit copy methods - use when you need an owned copy or type conversion
293 fl::optional<json_array> clone_array() const FL_NOEXCEPT { return mValue ? mValue->clone_array() : fl::nullopt; }
294 fl::optional<json_object> clone_object() const FL_NOEXCEPT { return mValue ? mValue->clone_object() : fl::nullopt; }
295
296 // Copy packed-array elements into a caller-owned span with type conversion.
297 // Returns number of elements copied (min of array size and span size).
298 // Returns 0 if not a numeric array or json is null.
299 template<typename T>
300 size_t copy_to(fl::span<T> out) const FL_NOEXCEPT {
301 return mValue ? mValue->copy_to(out) : 0;
302 }
303
304 // Stream packed-array elements into an output iterator with type conversion.
305 // Use with fl::back_inserter(container) to append to any container.
306 // Returns number of elements written. Returns 0 if not a numeric array.
307 template<typename T, typename OutputIt>
308 size_t copy_to_output_iterator(OutputIt out) const FL_NOEXCEPT {
309 return mValue ? mValue->template copy_to_output_iterator<T, OutputIt>(out) : 0;
310 }
311
312 // Overload for back_insert_iterator: T deduced from container's value_type
313 template<typename Container>
315 return mValue ? mValue->copy_to_output_iterator(out) : 0;
316 }
317
318 // NEW ERGONOMIC API: try_as<T>() - Explicit optional handling
319 // Use when you need to explicitly handle conversion failure
320 template<typename T>
322 if (!mValue) {
323 return fl::nullopt;
324 }
325 return as_impl<T>();
326 }
327
328 // BACKWARD COMPATIBILITY: Keep existing as<T>() that returns fl::optional<T>
329 // This maintains compatibility with existing code
330 template<typename T>
332 return try_as<T>();
333 }
334
335 // NEW ERGONOMIC API: value<T>() - Direct conversion with sensible defaults
336 // Use when you want a value immediately with reasonable defaults on failure
337 template<typename T>
338 T value() const FL_NOEXCEPT {
339 auto result = try_as<T>();
340 return result.has_value() ? *result : get_default_value<T>();
341 }
342
343private:
344 // Integer types (excluding bool)
348 return mValue->template as_int<T>();
349 }
350
351 // Boolean type
355 return mValue->as_bool();
356 }
357
358 // Floating point types
359 template<typename T>
361 as_impl() const FL_NOEXCEPT {
362 // Force template call by explicitly using the templated method
363 return mValue->template as_float<T>();
364 }
365
366 // String type
370 return mValue->as_string();
371 }
372
373 // Array type - clone_array() provides packed-array conversion for try_as
377 return mValue->clone_array();
378 }
379
380 // Object type
381 template<typename T>
383 as_impl() const FL_NOEXCEPT {
384 auto ptr = mValue->as_object();
385 return ptr ? fl::optional<T>(*ptr) : fl::nullopt;
386 }
387
388 // Specialized vector types - use copy_to_output_iterator for cross-type conversion
389 // e.g., try_as<vector<float>>() works on u8/i16/float packed arrays
390 template<typename T>
392 as_impl() const FL_NOEXCEPT {
393 if (!mValue->is_array()) return fl::nullopt;
394 T result;
395 size_t n = mValue->copy_to_output_iterator(fl::back_inserter(result));
396 return n > 0 ? fl::optional<T>(fl::move(result)) : fl::nullopt;
397 }
398
399 template<typename T>
401 as_impl() const FL_NOEXCEPT {
402 if (!mValue->is_array()) return fl::nullopt;
403 T result;
404 size_t n = mValue->copy_to_output_iterator(fl::back_inserter(result));
405 return n > 0 ? fl::optional<T>(fl::move(result)) : fl::nullopt;
406 }
407
408 template<typename T>
410 as_impl() const FL_NOEXCEPT {
411 if (!mValue->is_array()) return fl::nullopt;
412 T result;
413 size_t n = mValue->copy_to_output_iterator(fl::back_inserter(result));
414 return n > 0 ? fl::optional<T>(fl::move(result)) : fl::nullopt;
415 }
416
417 // Helper methods for getting default values for each type
421 return T(0); // All integer types default to 0
422 }
423
424 template<typename T>
427 return false; // Boolean defaults to false
428 }
429
430 template<typename T>
433 return T(0.0); // Floating point types default to 0.0
434 }
435
439 return fl::string(); // String defaults to empty string
440 }
441
445 return json_array(); // Array defaults to empty array
446 }
447
451 return json_object(); // Object defaults to empty object
452 }
453
457 return fl::vector<i16>(); // Audio vector defaults to empty
458 }
459
463 return fl::vector<u8>(); // Bytes vector defaults to empty
464 }
465
469 return fl::vector<float>(); // Float vector defaults to empty
470 }
471
472public:
474 // Iterator support for objects
477 return mValue->begin();
478 }
480 if (!mValue) return json_value::iterator(json_object().end());
490 }
491
492 // Iterator support for arrays with type conversion
493 template<typename T>
494 typename json_value::template array_iterator<T> begin_array() FL_NOEXCEPT {
495 if (!mValue) return typename json_value::template array_iterator<T>();
496 return mValue->template begin_array<T>();
497 }
499 template<typename T>
500 typename json_value::template array_iterator<T> end_array() FL_NOEXCEPT {
501 if (!mValue) return typename json_value::template array_iterator<T>();
502 return mValue->template end_array<T>();
503 }
505 template<typename T>
506 typename json_value::template array_iterator<T> begin_array() const FL_NOEXCEPT {
507 if (!mValue) return typename json_value::template array_iterator<T>();
508 return mValue->template begin_array<T>();
509 }
511 template<typename T>
512 typename json_value::template array_iterator<T> end_array() const FL_NOEXCEPT {
513 if (!mValue) return typename json_value::template array_iterator<T>();
514 return mValue->template end_array<T>();
515 }
517 // Free functions for range-based for loops
518 friend json_value::iterator begin(json& j) FL_NOEXCEPT { return j.begin(); }
519 friend json_value::iterator end(json& j) FL_NOEXCEPT { return j.end(); }
520 friend json_value::const_iterator begin(const json& j) FL_NOEXCEPT { return j.begin(); }
521 friend json_value::const_iterator end(const json& j) FL_NOEXCEPT { return j.end(); }
523 // Object iteration support (needed for screenmap conversion)
526 if (mValue && mValue->is_object()) {
527 for (auto it = begin(); it != end(); ++it) {
528 auto keyValue = *it;
529 result.push_back(keyValue.first);
530 }
531 }
532 return result;
533 }
535 // Backward compatibility methods
539 // Indexing for fluid chaining
540 json operator[](size_t idx) FL_NOEXCEPT {
541 if (!mValue) {
543 }
544 // If we're indexing into a specialized array, convert it to regular json_array first
545 if (mValue->data.is<fl::vector<i16>>() ||
546 mValue->data.is<fl::vector<u8>>() ||
547 mValue->data.is<fl::vector<float>>()) {
548 // Convert to regular json_array (needs a copy/conversion)
549 auto arr = mValue->clone_array();
550 if (arr) {
552 }
553 }
554 // Get pointer directly to avoid copying - fixes silent mutation bug
555 auto arrPtr = mValue->as_array();
556 if (arrPtr) {
557 // Ensure the array is large enough
558 if (idx >= arrPtr->size()) {
559 for (size_t i = arrPtr->size(); i <= idx; i++) {
560 arrPtr->push_back(fl::make_shared<json_value>(nullptr));
561 }
562 }
563 return json((*arrPtr)[idx]);
564 }
565 return json(nullptr);
567
568 const json operator[](size_t idx) const FL_NOEXCEPT {
569 if (!mValue) {
570 return json(nullptr);
571 }
572 // Handle regular json_array - zero-copy pointer access
573 auto arrPtr = mValue->as_array();
574 if (arrPtr) {
575 if (idx < arrPtr->size()) {
576 return json((*arrPtr)[idx]);
577 }
578 return json(nullptr);
579 }
580 // For packed arrays, extract element directly without converting the whole array
581 if (auto p = mValue->data.ptr<fl::vector<i16>>()) {
582 if (idx < p->size()) return json(static_cast<i64>((*p)[idx]));
583 } else if (auto p = mValue->data.ptr<fl::vector<u8>>()) {
584 if (idx < p->size()) return json(static_cast<i64>((*p)[idx]));
585 } else if (auto p = mValue->data.ptr<fl::vector<float>>()) {
586 if (idx < p->size()) return json((*p)[idx]);
587 }
588 return json(nullptr);
590
592 if (!mValue || !mValue->is_object()) {
594 }
595 // Get reference to the json_value
596 auto objPtr = mValue->data.ptr<json_object>();
597 if (objPtr) {
598 // If key doesn't exist, create a new json_value and insert it
599 if (objPtr->find(key) == objPtr->end()) {
600 (*objPtr)[key] = fl::make_shared<json_value>(nullptr);
601 }
602 // Return a new json object that wraps the shared_ptr to the json_value
603 return json((*objPtr)[key]);
604 }
605 // Should not happen if mValue is properly initialized as an object
606 //return *reinterpret_cast<json*>(&get_null_value());
607 return json(nullptr);
609
610 const json operator[](const fl::string &key) const FL_NOEXCEPT {
611 if (!mValue || !mValue->is_object()) {
612 return json(nullptr);
613 }
614 // Use ptr<> directly to avoid copying the entire map via as_object().
615 // The variant stores json_object (not const), so use ptr<json_object>().
616 // The const overload of ptr<T>() returns const T*, which is what we want.
617 auto objPtr = mValue->data.ptr<json_object>();
618 if (!objPtr) return json(nullptr);
619 auto it = objPtr->find(key);
620 if (it != objPtr->end()) {
621 return json(it->second);
622 }
623 return json(nullptr);
624 }
626 // Contains methods for checking existence
627 bool contains(size_t idx) const FL_NOEXCEPT {
628 return mValue && mValue->contains(idx);
629 }
630 bool contains(const fl::string &key) const FL_NOEXCEPT {
631 return mValue && mValue->contains(key);
632 }
634 // Size method
635 size_t size() const FL_NOEXCEPT {
636 return mValue ? mValue->size() : 0;
637 }
638
639 // Default-value operator (pipe)
640 template<typename T>
641 T operator|(const T& fallback) const FL_NOEXCEPT {
642 if (!mValue) return fallback;
643 return (*mValue) | fallback;
644 }
645
646 // NEW ERGONOMIC API: as_or<T>(default) - Conversion with custom defaults
647 // Use when you want to specify your own default value
648 // This method uses try_as<T>() for proper string-to-number conversion
649 template<typename T>
650 T as_or(const T& fallback) const FL_NOEXCEPT {
651 auto result = try_as<T>();
652 return result.has_value() ? *result : fallback;
653 }
655 // has_value method for compatibility
656 bool has_value() const FL_NOEXCEPT {
657 return mValue && !mValue->is_null();
658 }
659
660 // Get access to the internal json_value for direct variant visiting
661 // Returns nullptr if no value is set
662 const json_value* internal_value() const FL_NOEXCEPT { return mValue.get(); }
664 // Method to set the internal value (for json_value::to_string())
666 mValue = value;
667 }
669 // Public method to access to_string_native for json_value::to_string()
672 // Serialization - now delegates to native implementation
674
675 // Native serialization (without external libraries)
678 // Parsing factory method - uses native parser
679 static json parse(const fl::string &txt) FL_NOEXCEPT {
680 auto parsed = json_value::parse2(txt);
681 if (parsed) {
682 json result;
683 result.mValue = parsed;
684 return result;
685 }
686 return json(nullptr);
687 }
689 // Convenience methods for creating arrays and objects
690 static json array() FL_NOEXCEPT {
691 return json(json_array{});
693
694 static json object() FL_NOEXCEPT {
695 return json(json_object{});
696 }
698 // Compatibility with existing API for array/object access
699 size_t get_size() const FL_NOEXCEPT { return size(); }
700 size_t getSize() const FL_NOEXCEPT { return size(); }
702 // Set methods for building objects
703 void set(const fl::string& key, const json& value) FL_NOEXCEPT {
704 if (!mValue || !mValue->is_object()) {
706 }
707 // Directly assign the value to the object without going through json::operator[]
708 auto objPtr = mValue->data.ptr<json_object>();
709 if (objPtr) {
710 // Create or update the entry directly
711 if (value.mValue) {
712 (*objPtr)[key] = value.mValue;
713 } else {
714 // If value has null mValue, create a null json_value
715 (*objPtr)[key] = fl::make_shared<json_value>(nullptr);
716 }
717 }
720 void set(const fl::string& key, bool value) FL_NOEXCEPT { set(key, json(value)); }
721 void set(const fl::string& key, int value) FL_NOEXCEPT { set(key, json(value)); }
722 void set(const fl::string& key, i64 value) FL_NOEXCEPT { set(key, json(value)); }
723 void set(const fl::string& key, float value) FL_NOEXCEPT { set(key, json(value)); }
724 void set(const fl::string& key, double value) FL_NOEXCEPT { set(key, json(value)); }
725 void set(const fl::string& key, const fl::string& value) FL_NOEXCEPT { set(key, json(value)); }
726 void set(const fl::string& key, const char* value) FL_NOEXCEPT { set(key, json(value)); }
727 template<typename T, typename = fl::enable_if_t<fl::is_same<T, char>::value>>
728 void set(const fl::string& key, T value) FL_NOEXCEPT { set(key, json(value)); }
729
730 // Generic setter for all integer types (excluding bool, int, and i64 which have explicit overloads)
731 // Converts to i64 for internal storage
732 template<typename IntType>
733 typename fl::enable_if<
739 void
740 >::type
741 set(const fl::string& key, IntType value) FL_NOEXCEPT {
742 // Convert to i64 for storage
743 set(key, json(static_cast<i64>(value)));
744 }
746 // Array push_back methods
747 void push_back(const json& value) FL_NOEXCEPT {
748 if (!mValue || !mValue->is_array()) {
750 }
751 // If we're pushing to a packed array, convert it to regular json_array first
752 if (mValue->is_array() &&
753 (mValue->data.is<fl::vector<i16>>() ||
754 mValue->data.is<fl::vector<u8>>() ||
755 mValue->data.is<fl::vector<float>>())) {
756 // Convert to regular json_array (needs a copy/conversion)
757 auto arr = mValue->clone_array();
758 if (arr) {
760 }
761 }
762 // For arrays, we need to manually handle the insertion since our indexing
763 // mechanism auto-creates elements
764 auto ptr = mValue->data.ptr<json_array>();
765 if (ptr) {
766 ptr->push_back(value.mValue);
767 }
768 }
770 // Create methods for compatibility
773 static json createArray() FL_NOEXCEPT { return json::array(); }
774 static json createObject() FL_NOEXCEPT { return json::object(); }
776 // Serialize method for compatibility
777 fl::string serialize() const FL_NOEXCEPT { return to_string(); }
778
779 // Helper function to normalize JSON string (remove whitespace)
780 static fl::string normalize_json_string(const char* jsonStr) FL_NOEXCEPT;
781 static fl::string normalizeJsonString(const char* jsonStr) FL_NOEXCEPT { return normalize_json_string(jsonStr); }
782};
783
784// JSON memory profiling support - defined in json.cpp.hpp
785// Set g_json_stack_base to a stack address to enable stack depth tracking
786extern volatile size_t g_json_stack_base; // cast address to size_t
787extern volatile size_t g_json_max_stack_depth;
788
789
790} // namespace fl
Back insert iterator - an output iterator that inserts elements at the end of a container.
Definition iterator.h:75
static const_iterator from_object_iterator(const iterator &other) FL_NOEXCEPT
Definition types.h:1563
static const_iterator from_iterator(json_object::const_iterator iter) FL_NOEXCEPT
Definition types.h:1569
fl::enable_if< fl::is_integral< T >::value &&!fl::is_same< T, bool >::value, T >::type get_default_value() const FL_NOEXCEPT
Definition json.h:418
void push_back(const json &value) FL_NOEXCEPT
Definition json.h:745
json() FL_NOEXCEPT
Definition json.h:134
size_t copy_to_output_iterator(OutputIt out) const FL_NOEXCEPT
Definition json.h:306
friend json_value::const_iterator begin(const json &j) FL_NOEXCEPT
Definition json.h:518
void set(const fl::string &key, float value) FL_NOEXCEPT
Definition json.h:721
json(const fl::shared_ptr< json_value > &value) FL_NOEXCEPT
Definition json.h:146
json(float f) FL_NOEXCEPT
Definition json.h:139
fl::shared_ptr< json_value > mValue
Definition json.h:130
const json_array * as_array() const FL_NOEXCEPT
Definition json.h:287
fl::vector< fl::string > getObjectKeys() const FL_NOEXCEPT
Definition json.h:535
static fl::string normalize_json_string(const char *jsonStr) FL_NOEXCEPT
const json_value * internal_value() const FL_NOEXCEPT
Definition json.h:660
json(const char *s) FL_NOEXCEPT
Definition json.h:142
fl::optional< i64 > as_int() const FL_NOEXCEPT
Definition json.h:255
static json fromValue(const json_value &value) FL_NOEXCEPT
Definition json.h:149
json(json_object o) FL_NOEXCEPT
Definition json.h:144
fl::optional< T > as() const FL_NOEXCEPT
Definition json.h:329
static json create_array() FL_NOEXCEPT
Definition json.h:769
fl::string serialize() const FL_NOEXCEPT
Definition json.h:775
bool is_generic_array() const FL_NOEXCEPT
Definition json.h:247
json(const fl::string &s) FL_NOEXCEPT
Definition json.h:141
fl::optional< double > as_double() const FL_NOEXCEPT
Definition json.h:271
fl::string to_string_native() const FL_NOEXCEPT
bool is_array() const FL_NOEXCEPT
Definition json.h:246
friend json_value::const_iterator end(const json &j) FL_NOEXCEPT
Definition json.h:519
static json create_object() FL_NOEXCEPT
Definition json.h:770
const json_object * as_object() const FL_NOEXCEPT
Definition json.h:288
void set_value(const fl::shared_ptr< json_value > &value) FL_NOEXCEPT
Definition json.h:663
bool is_float() const FL_NOEXCEPT
Definition json.h:241
static json createArray() FL_NOEXCEPT
Definition json.h:771
bool is_null() const FL_NOEXCEPT
Definition json.h:238
void set(const fl::string &key, T value) FL_NOEXCEPT
Definition json.h:726
fl::optional< json_object > clone_object() const FL_NOEXCEPT
Definition json.h:292
bool is_bytes() const FL_NOEXCEPT
Definition json.h:250
fl::optional< bool > as_bool() const FL_NOEXCEPT
Definition json.h:254
T operator|(const T &fallback) const FL_NOEXCEPT
Definition json.h:639
bool is_int() const FL_NOEXCEPT
Definition json.h:240
fl::optional< float > as_float() const FL_NOEXCEPT
Definition json.h:266
void set(const fl::string &key, double value) FL_NOEXCEPT
Definition json.h:722
size_t get_size() const FL_NOEXCEPT
Definition json.h:697
fl::optional< json_array > clone_array() const FL_NOEXCEPT
Definition json.h:291
bool has_value() const FL_NOEXCEPT
Definition json.h:654
fl::optional< T > try_as() const FL_NOEXCEPT
Definition json.h:319
bool is_number() const FL_NOEXCEPT
Definition json.h:244
bool is_object() const FL_NOEXCEPT
Definition json.h:248
size_t size() const FL_NOEXCEPT
Definition json.h:633
void set(const fl::string &key, const char *value) FL_NOEXCEPT
Definition json.h:724
json(int i) FL_NOEXCEPT
Definition json.h:137
fl::string to_string() const FL_NOEXCEPT
Definition json.h:671
json(bool b) FL_NOEXCEPT
Definition json.h:136
json_value::iterator begin() FL_NOEXCEPT
Definition json.h:473
void set(const fl::string &key, const fl::string &value) FL_NOEXCEPT
Definition json.h:723
T as_or(const T &fallback) const FL_NOEXCEPT
Definition json.h:648
bool is_string() const FL_NOEXCEPT
Definition json.h:245
bool is_audio() const FL_NOEXCEPT
Definition json.h:249
fl::enable_if< fl::is_integral< T >::value &&!fl::is_same< T, bool >::value, fl::optional< T > >::type as_impl() const FL_NOEXCEPT
Definition json.h:345
bool is_bool() const FL_NOEXCEPT
Definition json.h:239
fl::vector< fl::string > keys() const FL_NOEXCEPT
Definition json.h:522
fl::string to_string_native_public() const FL_NOEXCEPT
Definition json.h:668
json & operator=(const json &other) FL_NOEXCEPT
Definition json.h:179
json(json_array a) FL_NOEXCEPT
Definition json.h:143
json operator[](size_t idx) FL_NOEXCEPT
Definition json.h:538
static json createObject() FL_NOEXCEPT
Definition json.h:772
size_t copy_to(fl::span< T > out) const FL_NOEXCEPT
Definition json.h:298
json_value::iterator end() FL_NOEXCEPT
Definition json.h:477
bool contains(size_t idx) const FL_NOEXCEPT
Definition json.h:625
size_t getSize() const FL_NOEXCEPT
Definition json.h:698
T value() const FL_NOEXCEPT
Definition json.h:336
bool is_floats() const FL_NOEXCEPT
Definition json.h:251
fl::vector< fl::string > get_object_keys() const FL_NOEXCEPT
Definition json.h:534
bool is_double() const FL_NOEXCEPT
Definition json.h:242
static json from_char(char c) FL_NOEXCEPT
Definition json.h:166
json(i64 i) FL_NOEXCEPT
Definition json.h:138
void set(const fl::string &key, i64 value) FL_NOEXCEPT
Definition json.h:720
fl::optional< fl::string > as_string() const FL_NOEXCEPT
Definition json.h:282
static fl::string normalizeJsonString(const char *jsonStr) FL_NOEXCEPT
Definition json.h:779
json_value::template array_iterator< T > end_array() FL_NOEXCEPT
Definition json.h:498
void set(const fl::string &key, const json &value) FL_NOEXCEPT
Definition json.h:701
json(double d) FL_NOEXCEPT
Definition json.h:140
static json parse(const fl::string &txt) FL_NOEXCEPT
Definition json.h:677
static json object() FL_NOEXCEPT
Definition json.h:692
json_value::template array_iterator< T > begin_array() FL_NOEXCEPT
Definition json.h:492
static json array() FL_NOEXCEPT
Definition json.h:688
decltype(nullptr) nullptr_t
Definition s16x16x4.h:13
constexpr remove_reference< T >::type && move(T &&t) FL_NOEXCEPT
Definition s16x16x4.h:28
volatile size_t g_json_stack_base
constexpr int type_rank< T >::value
volatile size_t g_json_max_stack_depth
back_insert_iterator< Container > back_inserter(Container &c) FL_NOEXCEPT
Helper function to create a back_insert_iterator.
Definition iterator.h:139
Optional< T > optional
Definition optional.h:16
fl::i64 i64
Definition s16x16x4.h:222
shared_ptr< T > make_shared(Args &&... args) FL_NOEXCEPT
Definition shared_ptr.h:414
fl::vector< fl::shared_ptr< json_value > > json_array
Definition types.h:33
expected< T, E > result
Alias for expected (Rust-style naming)
Definition result.h:31
constexpr nullopt_t nullopt
Definition optional.h:13
fl::flat_map< fl::string, fl::shared_ptr< json_value >, fl::StringFastLess > json_object
Definition types.h:34
Base definition for an LED controller.
Definition crgb.hpp:179
#define FL_NOEXCEPT
json_value::iterator iterator
Definition types.h:697
static fl::shared_ptr< json_value > parse2(const fl::string &txt) FL_NOEXCEPT
json_value::const_iterator const_iterator
Definition types.h:698