21 template<
bool HasChoices>
39 static auto test(T *) ->
typename T::is_schema_t;
42 static std::false_type
test(...);
46 inline constexpr
bool is_schema_v = decltype(is_schema::test<T>(
nullptr))::value;
54 template<
typename T,
typename Allocator>
66 if constexpr(is_std_vector_v<T>) {
return is_schema_v<typename T::value_type>; }
67 else {
return false; }
88 if constexpr(is_std_map_v<T>) {
return is_schema_v<typename T::value_type>; }
89 else {
return false; }
98 template<
typename Scalar,
int Rows,
int Options,
int MaxRows>
99 struct is_eigen_vector<Eigen::Matrix<Scalar, Rows, 1, Options, MaxRows, 1>> :
public std::true_type
106 template<
typename T,
bool IsRequired,
bool IsInteractive,
bool HasChoices = false,
bool IsStatic = false>
108 const std::string & description,
112 template<
bool IsRequired,
bool IsInteractive,
bool HasChoices,
typename... Args>
117 auto get_choice = [&](
size_t idx)
119 if constexpr(HasChoices)
127 (addValueToForm<Args, IsRequired, IsInteractive, false, true>(
Default<Args>::value, get_choice(i++), {}, form), ...);
130 template<
typename T,
bool IsRequired,
bool IsInteractive,
bool HasChoices,
bool IsStatic>
132 const std::string & description,
136 const auto & get_value = [&value]() -> decltype(
auto)
138 if constexpr(IsStatic) {
return value; }
141 return [&value]() ->
const T & {
return value; };
144 if constexpr(details::is_schema_v<T>)
147 value.buildForm(input);
150 else if constexpr(details::is_std_vector_v<T>)
153 using value_type =
typename T::value_type;
154 static value_type default_{};
155 addValueToForm<value_type, true, IsInteractive>(default_, description, {}, input);
158 else if constexpr(details::is_std_map_v<T>)
162 else if constexpr(gui::details::is_variant_v<T>)
165 variantToForm<IsRequired, IsInteractive>(value, input, choices);
168 else if constexpr(std::is_same_v<T, bool>)
170 form.
addElement(mc_rtc::gui::FormCheckbox(description, IsRequired, get_value));
172 else if constexpr(std::is_integral_v<T>)
174 form.
addElement(mc_rtc::gui::FormIntegerInput(description, IsRequired, get_value));
176 else if constexpr(std::is_floating_point_v<T>)
178 form.
addElement(mc_rtc::gui::FormNumberInput(description, IsRequired, get_value));
180 else if constexpr(std::is_same_v<T, std::string>)
182 if constexpr(HasChoices)
184 auto it = std::find(choices.
choices.begin(), choices.
choices.end(), value);
189 else { form.
addElement(mc_rtc::gui::FormStringInput(description, IsRequired, get_value)); }
191 else if constexpr(std::is_same_v<T, Eigen::Vector3d>)
193 form.
addElement(mc_rtc::gui::FormPoint3DInput(description, IsRequired, get_value, IsInteractive));
195 else if constexpr(std::is_same_v<T, sva::PTransformd>)
197 form.
addElement(mc_rtc::gui::FormTransformInput(description, IsRequired, get_value, IsInteractive));
199 else if constexpr(std::is_same_v<T, sva::ForceVecd> || details::is_eigen_vector_v<T>)
203 else { static_assert(!std::is_same_v<T, T>,
"addValueToForm must be implemented for this value type"); }
223 using int_t = std::underlying_type_t<ValueFlag>;
224 return static_cast<ValueFlag>(
static_cast<int_t
>(lhs) |
static_cast<int_t
>(rhs));
229 using int_t = std::underlying_type_t<ValueFlag>;
230 return static_cast<ValueFlag>(
static_cast<int_t
>(lhs) &
static_cast<int_t
>(rhs));
235 using int_t = std::underlying_type_t<ValueFlag>;
236 return (
static_cast<int_t
>(flag) &
static_cast<int_t
>(feature)) != 0;
278 std::function<bool(
const void * lhs,
const void * rhs)>
areEqual = [](
const void *,
const void *) {
return true; };
300 template<
typename T,
typename Schema, T Schema::*ptr, ValueFlag Flags = ValueFlag::All,
bool HasChoices = false>
302 const std::string & name,
303 const std::string & description,
304 const std::integral_constant<ValueFlag, Flags> & = {},
311 const T & value =
static_cast<const Schema *
>(
self)->*ptr;
312 out.add(name, value);
316 write(
self, builder);
317 const T & value =
static_cast<const Schema *
>(
self)->*ptr;
318 builder.write(description);
319 builder.write(value);
325 T & value =
static_cast<Schema *
>(
self)->*ptr;
326 if(in.has(name)) { value = in(name).operator T(); }
333 if(IsRequired || in.has(description))
335 if constexpr(details::is_schema_v<T>)
337 auto out_ = out.add(name);
338 T::formToStd(in(description), out_);
340 else if constexpr(details::is_std_vector_schema_v<T>)
342 using SchemaT =
typename T::value_type;
343 std::vector<Configuration> in_ = in(description);
344 auto out_ = out.array(name, in_.size());
345 for(
size_t i = 0; i < in_.size(); ++i)
347 auto out_i = out_.object();
348 SchemaT::formToStd(in_[i], out_i);
351 else if constexpr(details::is_std_map_schema_v<T>) {}
352 else { out.add(name, in(description)); }
360 const T & value =
static_cast<const Schema *
>(
self)->*ptr;
361 details::addValueToForm<T, IsRequired, IsInteractive>(value, description, choices, form);
365 const T & lhs_value =
static_cast<const Schema *
>(lhs)->*ptr;
366 const T & rhs_value =
static_cast<const Schema *
>(rhs)->*ptr;
367 return areEqual(lhs, rhs) && (lhs_value == rhs_value);
380 template<
typename T, ValueFlag Flags = ValueFlag::All,
bool HasChoices = false>
382 const std::integral_constant<ValueFlag, Flags> & = {},
386 if constexpr(IsRequired && HasChoices && std::is_same_v<T, std::string>)
416 struct Default<T,
std::enable_if_t<schema::details::is_schema_v<T>>>
418 inline static const T value = {};
422 struct Default<T,
std::enable_if_t<schema::details::is_std_vector_v<T>>>
424 inline static const T value = {};
428 struct Default<T, typename
std::enable_if_t<schema::details::is_std_map_v<T>>>
430 inline static const T value = {};