#include "Serialize.h" #include "tinyxml2.h" #include "XmlException.h" #include using alm::ImageView; using alm::XmlException; using tinyxml2::XMLElement; using tinyxml2::XMLDocument; using tinyxml2::XMLError; using tinyxml2::XMLNode; using tinyxml2::XML_SUCCESS; template<> alm::Gradient alm::deserialize(XMLElement* elem) { if (elem == nullptr) throw alm::XmlException{ "invalid root node" }; bool repeat = false; bool hasMax = false; float maxVal = 0.0f; repeat = elem->BoolAttribute("repeat", false); XMLError e = elem->QueryFloatAttribute("max", &maxVal); if (e == XML_SUCCESS) hasMax = true; std::vector> points; XMLElement* colorNode = elem->FirstChildElement("color"); while(colorNode != nullptr) { int r = colorNode->IntAttribute("r"); int g = colorNode->IntAttribute("g"); int b = colorNode->IntAttribute("b"); float p = colorNode->FloatAttribute("p"); uint8_t cr = uint8_t(std::clamp(r, 0, 255)); uint8_t cg = uint8_t(std::clamp(g, 0, 255)); uint8_t cb = uint8_t(std::clamp(b, 0, 255)); points.push_back(std::make_pair(RGBColor{ cr, cg, cb }, p)); colorNode = colorNode->NextSiblingElement("color"); } if (hasMax) return Gradient{ std::move(points), maxVal, repeat }; else return Gradient{ std::move(points), repeat }; } template<> tinyxml2::XMLElement* alm::serialize(tinyxml2::XMLDocument& doc, const alm::Gradient&) { return nullptr; } template<> alm::Gradient alm::fromXml(const std::string& xml) { XMLDocument xmlDoc; XMLError err = xmlDoc.Parse(xml.c_str()); if (err != XML_SUCCESS) throw alm::XmlException{ "error parsing gradient xml" }; return deserialize(xmlDoc.RootElement()); } template<> std::string alm::toXml(const alm::Gradient& g) { std::stringstream buf; std::string version = "1.0.0"; buf << "" << std::endl; for (const auto&[color, val] : g.getPoints()) { buf << " " << std::endl; } buf << "" << std::endl; return buf.str(); }