Die Lyx SVG-Bibliothek erzeugt SVG-Dateien direkt — kein externes Tool, keine Abhängigkeiten. 9 Sub-Units decken Grundformen, Pfade, Stile, Filter, Animationen, Text, Definitionen und Parsing ab.
import std.svg.builder; // Pflicht: Dokument-Lifecycle
import std.svg.elements; // Grundformen
import std.svg.style; // Farbe, Strich, Transformationen
svg/builder — SvgNew, SvgSave, SvgFree, SvgToString (Dokument-Lifecycle)
svg/elements — rect, circle, ellipse, line, polyline, polygon, SvgApply, Gruppen
svg/path — <path d="..."> Builder: M L H V C S Q T A Z
svg/style — fill, stroke, opacity, dash, linecap/join, Transformationen
svg/text — SvgTextAt, SvgTextBegin/SvgTspan, Schriftart, Anker
svg/image — SvgImage (eingebettetes Bild oder Verweis)
svg/filter — Blur, Drop-Shadow, Composite, ColorMatrix
svg/defs — Gradienten, Muster, clipPath, Symbol, Marker
svg/anim — SMIL-Animationen: SvgAnimate, SvgAnimateTransform, SvgAnimateMotion
svg/parser — SVG-Datei einlesen und traversieren
svg/xml — Low-Level XML-Ausgabe (intern)
import std.svg.builder;
import std.svg.elements;
import std.svg.style;
fn main(): int64 {
// Dokument anlegen (400×300 px):
var doc: int64 := SvgNew(400.0, 300.0);
// Hintergrund:
SvgSetFillHex(doc, "#ADD8E6"c);
SvgRect(doc, 0.0, 0.0, 400.0, 300.0);
SvgApply(doc);
// Roter Kreis:
SvgSetFillHex(doc, "#FF0000"c);
SvgSetStroke(doc, 0.545, 0.0, 0.0); // dunkelrot
SvgSetStrokeWidth(doc, 2.0);
SvgCircle(doc, 200.0, 150.0, 60.0);
SvgApply(doc);
// Speichern:
SvgSave(doc, "output.svg"c);
SvgFree(doc);
return 0;
}
import std.svg.elements;
// Rechteck:
SvgRect(doc, x, y, width, height);
// Abgerundetes Rechteck:
SvgSetRounding(doc, rx, ry); // vor SvgRoundRect setzen
SvgRoundRect(doc, x, y, w, h);
// Kreis:
SvgCircle(doc, cx, cy, radius);
// Ellipse:
SvgEllipse(doc, cx, cy, rx, ry);
// Linie:
SvgLine(doc, x1, y1, x2, y2);
// Polyline (Punkte als String "x1,y1 x2,y2 ..."):
SvgPolyline(doc, "10,20 30,40 50,20"c);
// Nach jeder Form: SvgApply() — überträgt Style und erzeugt das Element
SvgApply(doc);
import std.svg.path;
import std.svg.style;
SvgSetFillNone(doc);
SvgSetStroke(doc, 0.0, 0.0, 0.0); // schwarz
SvgPathBegin(doc);
SvgMoveTo(doc, 50.0, 100.0);
SvgLineTo(doc, 150.0, 100.0);
SvgLineTo(doc, 100.0, 50.0);
SvgClosePath(doc);
SvgApply(doc); // <path d="M50,100 L150,100 L100,50 Z" .../>
// Kubische Bézierkurve:
SvgPathBegin(doc);
SvgMoveTo(doc, 10.0, 80.0);
SvgCurveSetCP(doc, 40.0, 10.0, 65.0, 10.0); // Kontrollpunkte
SvgCurveTo2(doc, 95.0, 80.0); // C — SvgCurveTo stuerzt ab (#1688)
SvgApply(doc);
import std.svg.style;
// Füllung:
SvgSetFillHex(doc, "#4682B4"c); // Hex-Farbe
SvgSetFillAlpha(doc, 0.27, 0.51, 0.71, 0.8); // Farbe + fill-opacity
SvgSetFillNone(doc); // keine Füllung
// Kontur:
SvgSetStroke(doc, 1.0, 0.0, 0.0); // rot — Anteile 0.0 bis 1.0
SvgSetStrokeWidth(doc, 3.0);
SvgSetOpacity(doc, 0.5); // Gesamtdeckkraft des Elements
// Linienenden und -verbindungen:
SvgSetLineCap(doc, SVG_CAP_ROUND); // butt | round | square
SvgSetLineJoin(doc, SVG_JOIN_MITER); // miter | round | bevel
// Gestrichelte Linie:
SvgSetDashArray(doc, "5,3"c); // "5px Strich, 3px Pause"
SvgSetDashOffset(doc, 0.0);
// Transformation:
SvgTranslate(doc, 100.0, 50.0);
SvgRotate(doc, 45.0);
SvgScale(doc, 2.0, 2.0);
// Die Transformkette wird mit dem naechsten SvgApply verbraucht —
// ein SvgResetTransform gibt es nicht.
import std.svg.text;
import std.svg.style;
SvgSetFillHex(doc, "#000000"c);
SvgSetFont(doc, "DejaVu Sans"c, 16.0); // Schriftart + Größe
SvgTextAt(doc, 50.0, 50.0, "Hallo Lyx"c);
SvgApply(doc);
// Mehrzeiliger Text mit tspan — dy je Zeile, Abschluss mit SvgTextEnd:
SvgTextBegin(doc, 20.0, 30.0);
SvgTspan(doc, "Zeile 1"c, 0.0, 0.0);
SvgTspan(doc, "Zeile 2"c, 0.0, 20.0);
SvgTextEnd(doc);
import std.svg.elements;
// Gruppe mit ID — Stil und Transform vorher setzen, sie landen am <g>:
SvgGroupBeginId(doc, "layer1"c);
SvgCircle(doc, 100.0, 100.0, 30.0);
SvgApply(doc);
SvgRect(doc, 50.0, 50.0, 40.0, 40.0);
SvgApply(doc);
SvgGroupEnd(doc);
import std.svg.anim;
// Farb-Animation: elem = 0 merkt die Animation fuer das naechste
// abgeschlossene Element vor (SvgCircle liefert nichts zurueck):
SvgAnimRepeat(doc, 0); // 0 = indefinite
SvgAnimate(doc, 0, "fill"c, "red"c, "blue"c, 2.0);
SvgSetFillHex(doc, "#FF0000"c);
SvgCircle(doc, 200.0, 150.0, 50.0);
SvgApply(doc);
// Rotation (0° → 360°, endlos) auf demselben Weg:
SvgAnimateTransform(doc, 0, SVG_AT_ROTATE, "0 200 150"c, "360 200 150"c, 3.0);
| Transform-Typ | Konstante |
|---|---|
| Verschiebung | SVG_AT_TRANSLATE |
| Skalierung | SVG_AT_SCALE |
| Rotation | SVG_AT_ROTATE |
| Scherung X | SVG_AT_SKEWX |
| Scherung Y | SVG_AT_SKEWY |
import std.svg.filter;
// Unschärfe auf Rechteck — der fertige Effekt liefert die Filternummer:
var blur: int64 := SvgBlur(doc, 3.0);
SvgSetFilter(doc, blur);
SvgRect(doc, 50.0, 50.0, 200.0, 100.0);
SvgApply(doc);
// Drop-Shadow (schwarz, Deckkraft als letztes Argument):
var shadow: int64 := SvgDropShadow(doc, 4.0, 4.0, 2.0, 0.6);
SvgSetFilter(doc, shadow);
// Eigener Filter aus Primitiven:
var flt: int64 := SvgFilterBegin(doc, "eigen"c, 0.0, 0.0, 1.2, 1.2);
SvgFeGaussianBlur(doc, flt, "SourceGraphic"c, 2.0, 2.0);
SvgFilterEnd(doc);
import std.svg.builder;
// In Datei speichern:
SvgSave(doc, "chart.svg"c);
// Als String holen (z. B. für HTTP-Response):
var svgStr: pchar := SvgToString(doc);
// ... svgStr verwenden ...
// Pretty-Print aktivieren (Zeilenumbrüche + Einrückung):
SvgSetPrettyPrint(doc, 1);
// ViewBox setzen:
SvgSetViewBox(doc, 0.0, 0.0, 800.0, 600.0);
// Aufräumen:
SvgFree(doc);
import std.io;
import std.svg.builder;
import std.svg.elements;
import std.svg.style;
import std.svg.filter;
import std.svg.anim;
fn main(): int64 {
var doc: int64 := SvgNew(400.0, 300.0);
SvgSetPrettyPrint(doc, 1);
SvgGroupBeginId(doc, "layer1");
SvgSetFillHex(doc, "#4682B4");
SvgCircle(doc, 100.0, 100.0, 30.0);
SvgApply(doc);
SvgGroupEnd(doc);
var blur: int64 := SvgBlur(doc, 3.0);
SvgSetFilter(doc, blur);
SvgSetFillHex(doc, "#FF0000");
SvgRect(doc, 200.0, 50.0, 150.0, 80.0);
SvgApply(doc);
SvgAnimRepeat(doc, 0);
SvgAnimate(doc, 0, "fill", "red", "blue", 2.0);
SvgSetFillHex(doc, "red");
SvgCircle(doc, 200.0, 220.0, 40.0);
SvgApply(doc);
Print(SvgToString(doc)); Print("\n");
SvgFree(doc);
return 0;
}
<?xml version="1.0" encoding="UTF-8"?>
<svg xmlns="http://www.w3.org/2000/svg" width="400" height="300">
<defs>
<filter id="flt0">
<feGaussianBlur stdDeviation="3"/>
</filter>
</defs>
<g fill="#4682B4" id="layer1">
<circle cx="100" cy="100" r="30"/>
</g>
<rect x="200" y="50" width="150" height="80" fill="#FF0000" filter="url(#flt0)"/>
<circle cx="200" cy="220" r="40" fill="red" id="_a0">
<animate attributeName="fill" from="red" to="blue" dur="2s" repeatCount="indefinite"/>
</circle>
</svg>
SvgRoundRect verliert die Eckenradien (#1684).
Letzte Aktualisierung: 2026-08-19 — Alle Ausschnitte gegen die echten Signaturen berichtigt (SvgSetFont/SvgTextAt/SvgTspan, SvgGroupBeginId, SvgBlur/SvgDropShadow mit Filternummer, Animation über elem = 0, SvgCurveTo2); durchgehendes Beispiel mit lyxc 1.1.3I übersetzt und ausgeführt.
Vorherige Aktualisierung: 2026-06-08
Codebeispiele geprüft: gegen lyxc 1.2.5C übersetzt (Prüflauf 2026-09-08 über die gesamte Doku: 574 Vollprogramme, 0 echte Fehler; zusätzlich 5159 Aufrufe gegen die pub fn-Signaturen in aurum/std gehalten, 0 Abweichungen).