MNX Document Model
Loading...
Searching...
No Matches
ContentArray.h
1/*
2 * Copyright (C) 2025, Robert Patterson
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a copy
5 * of this software and associated documentation files (the "Software"), to deal
6 * in the Software without restriction, including without limitation the rights
7 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
8 * copies of the Software, and to permit persons to whom the Software is
9 * furnished to do so, subject to the following conditions:
10 *
11 * The above copyright notice and this permission notice shall be included in
12 * all copies or substantial portions of the Software.
13 *
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
17 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
18 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
19 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
20 * THE SOFTWARE.
21 */
22#pragma once
23
24#include "BaseTypes.h"
25
26namespace mnx {
27
47template <typename BaseContentT>
48class ContentArray : public Array<BaseContentT>
49{
50public:
52 using BaseArray::BaseArray; // Inherit constructors
53
55 template <typename T, std::enable_if_t<std::is_base_of_v<BaseContentT, T>, int> = 0>
56 [[nodiscard]] T get(size_t index) const
57 {
58 this->checkIndex(index);
59 return this->operator[](index).template get<T>();
60 }
61
62 // Prevent inherited Array::append(...) overloads from being used on content arrays.
63 BaseContentT append(...) = delete;
64
65protected:
66 template <typename T, typename... Args>
67 T appendWithType(Args&&... args)
68 {
69 static_assert(std::is_base_of_v<BaseContentT, T>,
70 "ContentArray::appendWithType requires a compatible content base type.");
71 auto result = BaseArray::template append<T>(std::forward<Args>(args)...);
72 const BaseContentT& contentObject = result;
73 if (T::ContentTypeValue != contentObject.defaultType()) {
74 result.set_type(std::string(T::ContentTypeValue));
75 }
76 return result;
77 }
78
81 template <typename T, std::enable_if_t<std::is_base_of_v<BaseContentT, T>, int> = 0>
82 [[nodiscard]] T getTypedObject(size_t index) const
83 {
84 this->checkIndex(index);
85 auto element = (*this)[index];
86 if (element.type() != T::ContentTypeValue) {
87 throw std::invalid_argument("Type mismatch: expected " + std::string(T::ContentTypeValue) +
88 ", got " + element.type());
89 }
90 return T(this->root(), this->pointer() / std::to_string(index));
91 }
92};
93
94} // namespace mnx
Represents an MNX array, encapsulating property access.
Definition BaseTypes.h:531
void checkIndex(size_t index) const
validates that an index is not out of range
Definition BaseTypes.h:688
auto operator[](size_t index) const
const operator[]
Definition BaseTypes.h:609
json_pointer pointer() const
Returns the json_pointer for this node.
Definition BaseTypes.h:274
const std::shared_ptr< json > & root() const
Returns the root.
Definition BaseTypes.h:297
Class for content arrays.
Definition ContentArray.h:49
T get(size_t index) const
Retrieve an element from the array as a specific type.
Definition ContentArray.h:56
T getTypedObject(size_t index) const
Constructs an object of type T if its type matches the JSON type.
Definition ContentArray.h:82
object model for MNX format