[![Actions](https://github.com/sammycage/lunasvg/actions/workflows/main.yml/badge.svg)](https://github.com/sammycage/lunasvg/actions) [![License](https://img.shields.io/github/license/sammycage/lunasvg)](https://github.com/sammycage/lunasvg/blob/master/LICENSE) [![Releases](https://img.shields.io/github/v/release/sammycage/lunasvg)](https://github.com/sammycage/lunasvg/releases) [![Donate](https://img.shields.io/badge/Donate-PayPal-blue.svg)](https://www.paypal.me/sammycage) > Interested in HTML rendering? Explore a related library, [PlutoBook](https://github.com/plutoprint/plutobook), built for paged HTML rendering. # LunaSVG LunaSVG is an SVG rendering library in C++, designed to be lightweight and portable, offering efficient rendering and manipulation of Scalable Vector Graphics (SVG) files. ## Basic Usage ```cpp #include using namespace lunasvg; int main() { auto document = Document::loadFromFile("tiger.svg"); if(document == nullptr) return -1; auto bitmap = document->renderToBitmap(); if(bitmap.isNull()) return -1; bitmap.writeToPng("tiger.png"); return 0; } ``` ![tiger.png](https://github.com/user-attachments/assets/b87bbf92-6dd1-4b29-a890-99cfffce66b8) --- ## Dynamic Styling ```cpp #include using namespace lunasvg; static const char kLandspaceContent[] = R"SVG( )SVG"; static const char kSummerStyle[] = R"CSS( .sky { fill: #4A90E2; } .sun { fill: #FF7F00; } .mountain { fill: #2E3A59; } .cloud { fill: #FFFFFF; opacity: 0.8; } .ground { fill: #2E8B57; } )CSS"; static const char kWinterStyle[] = R"CSS( .sky { fill: #87CEEB; } .sun { fill: #ADD8E6; } .mountain { fill: #2F4F4F; } .cloud { fill: #FFFFFF; opacity: 0.8; } .ground { fill: #FFFAFA; } )CSS"; int main() { auto document = Document::loadFromData(kLandspaceContent); document->applyStyleSheet(kSummerStyle); document->renderToBitmap().writeToPng("summer.png"); document->applyStyleSheet(kWinterStyle); document->renderToBitmap().writeToPng("winter.png"); return 0; } ``` | `summer.png` | `winter.png` | | --- | --- | | ![summer.png](https://github.com/user-attachments/assets/c7f16780-23f8-4acd-906a-2242f2d0d33b) | ![winter.png](https://github.com/user-attachments/assets/fdd65288-11c7-4e16-bb5a-2bf28de57145) | --- ## Hit Testing This example demonstrates SVG element hit testing using `elementFromPoint(x, y)` in LunaSVG. It loads an SVG containing three shapes, performs point-based hit detection, and applies a skew transform with a black stroke to each matched element. The results are saved as `original.png` and `modified.png` for visual comparison. ```cpp #include #include #include using namespace lunasvg; static const char kSVGContent[] = R"SVG( )SVG"; int main() { auto document = Document::loadFromData(kSVGContent); document->renderToBitmap().writeToPng("original.png"); const std::pair points[] = { {30, 30}, // inside red-rect {200, 70}, // center of blue-circle {310, 50}, // inside green-rect {0, 0}, // outside all shapes }; for(const auto& [x, y] : points) { if(auto element = document->elementFromPoint(x, y)) { std::cout << "Element at (" << x << ", " << y << "): " << element.getAttribute("id") << "\n"; element.setAttribute("stroke", "black"); element.setAttribute("stroke-width", "3"); element.setAttribute("transform", "skewX(9)"); } else { std::cout << "No element found at (" << x << ", " << y << ")\n"; } } document->renderToBitmap().writeToPng("modified.png"); return 0; } ``` | `original.png` | `modified.png` | | --- | --- | | ![original.png](https://github.com/user-attachments/assets/bbffbd84-6311-484b-bfe3-219d7aec055b) | ![modified.png](https://github.com/user-attachments/assets/a7f6e502-a64f-48d5-8a01-901ad15b108b) | ```log Element at (30, 30): red-rect Element at (200, 70): blue-circle Element at (310, 50): green-rect No element found at (0, 0) ``` ## Features LunaSVG supports nearly all graphical features outlined in the SVG 1.1 and SVG 1.2 Tiny specifications. The primary exceptions are animation, filters, and scripts. As LunaSVG is designed for static rendering, animation is unlikely to be supported in the future. However, support for filters may be added. It currently handles a wide variety of elements, including: `` `` `` `` `` `` `` `` `` `` `` `` `` `` `` `` `` `` `