gstack/docs/howto-diagrams-and-formats.md

4.9 KiB

How to put diagrams in your documents (and export beyond PDF)

This guide covers the diagram + multi-format engine that ships with /make-pdf and /diagram (v1.58.0.0+). Everything here runs fully offline: the mermaid and excalidraw runtimes are vendored in lib/diagram-render/, loaded into the browse daemon's Chromium. No CDN, no network at render time.

Render a mermaid diagram inside a PDF

Put a fence in your markdown. That's it.

```mermaid title="Render pipeline"
graph LR
  A[markdown] --> B[prepass]
  B --> C[Chromium]
  C --> D[PDF]
```
make-pdf generate doc.md out.pdf

The fence renders as a vector diagram (crisp at any zoom, selectable text), with the title as caption and accessibility label. The raw mermaid source is preserved in an HTML comment inside the document for debugging.

Fence options (space-separated in the info string):

Option Effect
title="..." caption below the diagram + aria-label
render=false keep the fence as a plain code block
page=landscape force this diagram onto its own landscape page
page=portrait veto auto-landscape for this diagram

A fence that fails to parse renders as a loud red diagnostic block with the parse error and source excerpt — your document still builds, and the error is impossible to miss.

```excalidraw fences work the same way; the body is a full .excalidraw scene file (what excalidraw.com saves with File → Save).

Control image size and orientation

Local images are inlined automatically (relative paths resolve against the markdown file) and never truncate — every image caps at the content box. Oversized photos downscale to print resolution (300dpi at the content width), so a phone photo doesn't bloat the document.

Per-image directives go immediately after the image:

![quarterly chart](chart.png){width=full}
![logo](logo.png){width=2in}
![wide architecture](arch.png){page=landscape}
![wide screenshot](shot.png){page=portrait}

width= accepts full, a percentage (50%), or a dimension (3in, 8cm, 200px). page= forces or vetoes a dedicated landscape page.

Auto-landscape: a wide, small-text, diagram-like image gets its own vertically-centered landscape page automatically — inside an otherwise portrait document. The heuristic is deliberately conservative (aspect ratio ≥ 1.8, intrinsic width over ~2.5x the content box, and a diagram-ish alt word: diagram / architecture / flowchart / chart / graph). If it doesn't fire when you want it, add {page=landscape}; if it fires when you don't, add {page=portrait}.

Export single-file HTML or Word

make-pdf generate doc.md out.html --to html
make-pdf generate doc.md out.docx --to docx
  • --to html writes ONE self-contained file: diagrams as inline SVG, images as data URIs, zero network references, plus a screen-reading layer (centered measure, padding). Email it, attach it, open it anywhere.
  • --to docx is a content-fidelity export: headings, tables, code blocks, lists, and diagrams (embedded as 300dpi PNGs with alt text) carry over. Page-perfect layout does not — that's Word's job once it's open.

Heads-up: --to is the output format. --format is an old alias for --page-size — different thing.

Generate a diagram from English

/diagram make a flowchart of our deploy pipeline: build, test, canary, promote

The skill authors mermaid and emits a triplet:

File Use it for
<slug>.mmd the source of truth — edit and re-render
<slug>.excalidraw open at excalidraw.com (File → Open), move boxes, hand back
<slug>.svg / <slug>.png docs, issues, READMEs, chat

Flowcharts convert to fully editable excalidraw scenes. Other mermaid types (sequence, state, gantt) render to SVG/PNG fine but skip the .excalidraw artifact — an upstream converter limitation the skill will tell you about.

For documents, embed the .mmd source in your markdown instead of the PNG — /make-pdf renders it as vector and the diagram stays editable forever.

CI: fail loud instead of shipping placeholders

make-pdf generate docs.md --strict

Missing local images and unfetched remote images exit non-zero instead of rendering a placeholder — for docs pipelines where a broken image should break the build.

Troubleshooting

  • "diagram-render bundle not found" → run bun run build:diagram-render in the gstack repo, or re-run ./setup.
  • Diagram renders but looks squished inline → it's wide; give it room with page=landscape on the fence.
  • A two-row "racetrack" loop instead of one long line: mermaid subgraph trick — top-level flowchart TB, two subgraphs with direction LR and direction RL, connect the subgraphs (node-level edges across subgraph boundaries silently disable direction).
  • Remote images → not fetched by default (offline posture). Pass --allow-network to opt in.