Mercurial > minori
view dep/pugixml/docs/samples/save_custom_writer.cpp @ 258:862d0d8619f6
*: HUUUGE changes
animia has been renamed to animone, so instead of thinking of a
health condition, you think of a beautiful flower :)
I've also edited some of the code for animone, but I have no idea
if it even works or not because I don't have a mac or windows
machine lying around. whoops!
... anyway, all of the changes divergent from Anisthesia are now
licensed under BSD. it's possible that I could even rewrite most
of the code to where I don't even have to keep the MIT license,
but that's thinking too far into the future
I've been slacking off on implementing the anime seasons page,
mostly out of laziness. I think I'd have to create another db file
specifically for the seasons
anyway, this code is being pushed *primarily* because the hard drive
it's on is failing! yay :)
author | Paper <paper@paper.us.eu.org> |
---|---|
date | Mon, 01 Apr 2024 02:43:44 -0400 |
parents | d10b6c6b432e |
children |
line wrap: on
line source
#include "pugixml.hpp" #include <string> #include <iostream> #include <cstring> // tag::code[] struct xml_string_writer: pugi::xml_writer { std::string result; virtual void write(const void* data, size_t size) { result.append(static_cast<const char*>(data), size); } }; // end::code[] struct xml_memory_writer: pugi::xml_writer { char* buffer; size_t capacity; size_t result; xml_memory_writer(): buffer(0), capacity(0), result(0) { } xml_memory_writer(char* buffer, size_t capacity): buffer(buffer), capacity(capacity), result(0) { } size_t written_size() const { return result < capacity ? result : capacity; } virtual void write(const void* data, size_t size) { if (result < capacity) { size_t chunk = (capacity - result < size) ? capacity - result : size; memcpy(buffer + result, data, chunk); } result += size; } }; std::string node_to_string(pugi::xml_node node) { xml_string_writer writer; node.print(writer); return writer.result; } char* node_to_buffer(pugi::xml_node node, char* buffer, size_t size) { if (size == 0) return buffer; // leave one character for null terminator xml_memory_writer writer(buffer, size - 1); node.print(writer); // null terminate buffer[writer.written_size()] = 0; return buffer; } char* node_to_buffer_heap(pugi::xml_node node) { // first pass: get required memory size xml_memory_writer counter; node.print(counter); // allocate necessary size (+1 for null termination) char* buffer = new char[counter.result + 1]; // second pass: actual printing xml_memory_writer writer(buffer, counter.result); node.print(writer); // null terminate buffer[writer.written_size()] = 0; return buffer; } int main() { // get a test document pugi::xml_document doc; doc.load_string("<foo bar='baz'>hey</foo>"); // get contents as std::string (single pass) std::cout << "contents: [" << node_to_string(doc) << "]\n"; // get contents into fixed-size buffer (single pass) char large_buf[128]; std::cout << "contents: [" << node_to_buffer(doc, large_buf, sizeof(large_buf)) << "]\n"; // get contents into fixed-size buffer (single pass, shows truncating behavior) char small_buf[22]; std::cout << "contents: [" << node_to_buffer(doc, small_buf, sizeof(small_buf)) << "]\n"; // get contents into heap-allocated buffer (two passes) char* heap_buf = node_to_buffer_heap(doc); std::cout << "contents: [" << heap_buf << "]\n"; delete[] heap_buf; } // vim:et