Чтение SVG в C++
При выборе формата хранения или обмена векторными 2D изображениями, SVG один из главных претендентов, благодаря открытости и распространенности. При всех его достоинствах, авторы, на мой взгляд, чрезмерно увлеклись удобством и гибкостью при создании документов, что привело к большой вариативности и избыточности, а, следовательно, и сложностью чтения. Кроме того, ради компактности были изобретены разные грамматики, встроенные внутрь XML, что тоже добавило головной боли программистам.Сейчас есть несколько C/C++ библиотек, которые могут загрузить SVG и отрисовать его в растр, но это только малая часть возможных применений SVG в приложениях.
Я разработал C++ библиотеку, которая должна взять на себя реализацию большинства нюансов спецификации, предоставляя данные SVG в удобном виде. При этом ставилась задача не навязывать программисту каких-то упрощений исходной информации из SVG. Например, разработчику часто не интересно, в каких единицах измерения была задана длина, ему удобнее работать со значениями, приведенными к одной размерности. Но в некоторых случаях (например, создание SVG DOM) информацию о единицах надо передавать в программу. Или прямоугольники, окружности и т. д. — в ряде случаев их удобно представлять путями (path) для однообразия, но иногда мы хотим знать, какая это была фигура.
Итак, встречайте, SVG++ 1.0!
Бесплатна для коммерческого и некоммерческого использования, лицензия — Boost. Header-only, кроссплатформенная, достаточно C++03. Из сторонних библиотек требует только Boost. Ах да, еще XML парсер на ваш вкус. Из коробки есть адаптеры для RapidXML NS, libxml2 и MSXML, но поддержка других добавляется несложно. Как принято, мотивирующий пример:
#include
using namespace svgpp;
class Context
{
public:
void on_enter_element (tag: element: any);
void on_exit_element ();
void transform_matrix (const boost: array
typedef boost: mpl: set< tag::element::circle, tag::element::ellipse, tag::element::line, tag::element::path, tag::element::polygon, tag::element::polyline, tag::element::rect, tag::element::svg, tag::element::g >:: type processed_elements_t;
typedef boost: mpl: insert< traits::shapes_attributes_by_element, tag::attribute::transform >:: type processed_attributes_t;
void loadSvg (rapidxml_ns: xml_node<> const * xml_root_element)
{
Context context;
document_traversal<
processed_elements
Библиотека не рисует и не будет рисовать ничего сама, однако включает демонстрационное приложение svgpp/src/demo/render, реализующее растеризацию SVG (некоторое подмножество спецификации), используя для отрисовки AGG или GDI+.
Для полноценного использования библиотеки очень желательно знакомство со спецификацией SVG.
Главная страница библиотеки с документацией — svgpp.org (документация готовится к переводу на английский, поэтому временный mishmash русского and english языков) Репозиторий на GitHub github.com/svgpp/svgpp Форум на Google Groups