Rundes Logo-Badge per SVG-Canvas
Komponiertes Logo, das Engine.createSVGCanvas im praktischsten Anwendungsfall zeigt: Disc mit Radial-Gradient, Akzentring, Tick-Mark-Kranz, Chevron-Crest und Text in zwei Schriften (Inter + JetBrains Mono). Output ist echtes SVG — beliebig skalierbar nach Figma / Illustrator / Web ohne Re-Rastern.
Badge
JavaScript
// Circular badge / logo composed into an SVGCanvas — gradients,
// concentric rings, a tick-mark wreath and centred text. Showcases
// the typical "build a logo in code" use case where SVG output is
// the natural target (scales cleanly, copies into Figma / web).
// demo_svg_badge.js
//!NOIMAGE
//!OUTPUT: OUTPUT
//!PARAM: SIZE:integer=600,min=200,max=1600
//!PARAM: TITLE:string=OPTICSCRIPT
//!PARAM: TAGLINE:string=vector engine
//!PARAM: ACCENT:string=#e94560
//!PARAM: TICKS:integer=48,min=12,max=120
const svg = Engine.createSVGCanvas(SIZE, SIZE);
const cx = SIZE / 2, cy = SIZE / 2;
const R = SIZE * 0.45;
// 1) Background — radial gradient disc
svg.radialGradient(px(cx, cy * 0.85), R * 1.2,
["#1e293b", "#0b1220"], [0, 1]);
svg.drawPath(Engine.createPath().rect(0, 0, SIZE, SIZE));
// 2) Outer accent ring
svg.pen(ACCENT, SIZE * 0.012)
.drawPath(Engine.createPath().circle(cx, cy, R), true);
// 3) Tick-mark wreath — N radial ticks just inside the ring
const tickPath = Engine.createPath();
const tickOuter = R - SIZE * 0.025;
const tickInner = R - SIZE * 0.06;
for (let i = 0; i < TICKS; i++) {
const a = (i / TICKS) * 2 * Math.PI - Math.PI / 2;
const x1 = cx + Math.cos(a) * tickInner;
const y1 = cy + Math.sin(a) * tickInner;
const x2 = cx + Math.cos(a) * tickOuter;
const y2 = cy + Math.sin(a) * tickOuter;
tickPath.moveTo(x1, y1).lineTo(x2, y2);
}
svg.pen([0.91, 0.27, 0.38, 0.55], SIZE * 0.004).drawPath(tickPath, true);
// 4) Inner badge field — filled disc with subtle gradient
svg.radialGradient(px(cx, cy - R * 0.15), R * 0.9,
["#334155", "#0f172a"], [0, 1]);
svg.drawPath(Engine.createPath().circle(cx, cy, R * 0.72));
// 5) Crest mark — three stacked chevrons (looks like ^^^)
const chevW = R * 0.4, chevH = R * 0.10, chevGap = R * 0.07;
svg.save().translate(cx, cy - R * 0.05);
for (let i = 0; i < 3; i++) {
const yy = -chevGap * (i - 1);
const chev = Engine.createPath()
.moveTo(-chevW / 2, yy + chevH)
.lineTo(0, yy)
.lineTo(chevW / 2, yy + chevH);
svg.pen(ACCENT, SIZE * 0.010 - i * SIZE * 0.002).drawPath(chev, true);
}
svg.restore();
// 6) Title + tagline
svg.drawText(TITLE, cx, cy + R * 0.32, {
font: "Inter", size: SIZE * 0.075, color: "#ffffff", anchor: "middle",
});
svg.drawText(TAGLINE, cx, cy + R * 0.50, {
font: "JetBrains Mono", size: SIZE * 0.030, color: "#94a3b8", anchor: "middle",
});
// 7) Established-year ribbon at the bottom of the inner field
svg.drawText("· EST. 2026 ·", cx, cy + R * 0.62, {
font: "JetBrains Mono", size: SIZE * 0.022, color: ACCENT, anchor: "middle",
});
// Serialise + rasterise for preview
const out = svg.toString();
const img = Engine.loadSVG(out, 1.0);
Engine.saveImage(img, "OUTPUT");
`badge ${SIZE}px · ${out.length} chars SVG`;
// © 2026 Michael Lechner · mlc OpticScript · https://mlcgo.eu · Elastic License 2.0