64 lines
2.0 KiB
C++
64 lines
2.0 KiB
C++
#ifndef DESTRUM_GLMJSON_H
|
|
#define DESTRUM_GLMJSON_H
|
|
|
|
#include <stdexcept>
|
|
#include <string>
|
|
|
|
#include <glm/glm.hpp>
|
|
#include <glm/gtc/quaternion.hpp>
|
|
#include <nlohmann/json.hpp>
|
|
|
|
namespace destrum::json_detail {
|
|
inline void RequireNumberArray(const nlohmann::json& j, std::size_t size) {
|
|
if (!j.is_array() || j.size() != size) {
|
|
throw std::runtime_error(
|
|
"expected an array of " + std::to_string(size) + " numbers, got " + j.dump());
|
|
}
|
|
for (const auto& element : j) {
|
|
if (!element.is_number()) {
|
|
throw std::runtime_error(
|
|
"expected an array of " + std::to_string(size) + " numbers, got " + j.dump());
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
namespace nlohmann {
|
|
template <glm::length_t L, typename T, glm::qualifier Q>
|
|
struct adl_serializer<glm::vec<L, T, Q>> {
|
|
static void to_json(json& j, const glm::vec<L, T, Q>& value) {
|
|
j = json::array();
|
|
for (glm::length_t i = 0; i < L; ++i) {
|
|
j.push_back(value[i]);
|
|
}
|
|
}
|
|
|
|
static void from_json(const json& j, glm::vec<L, T, Q>& value) {
|
|
destrum::json_detail::RequireNumberArray(j, static_cast<std::size_t>(L));
|
|
for (glm::length_t i = 0; i < L; ++i) {
|
|
value[i] = j.at(static_cast<std::size_t>(i)).get<T>();
|
|
}
|
|
}
|
|
};
|
|
|
|
// Stored as [x, y, z, w], the same order as scene transforms
|
|
template <typename T, glm::qualifier Q>
|
|
struct adl_serializer<glm::qua<T, Q>> {
|
|
static void to_json(json& j, const glm::qua<T, Q>& value) {
|
|
j = json::array({value.x, value.y, value.z, value.w});
|
|
}
|
|
|
|
static void from_json(const json& j, glm::qua<T, Q>& value) {
|
|
destrum::json_detail::RequireNumberArray(j, 4);
|
|
value = glm::qua<T, Q>{
|
|
j.at(3).get<T>(),
|
|
j.at(0).get<T>(),
|
|
j.at(1).get<T>(),
|
|
j.at(2).get<T>()
|
|
};
|
|
}
|
|
};
|
|
}
|
|
|
|
#endif // DESTRUM_GLMJSON_H
|