From 6d36d3c430b57b23939c8c70925fccdc560155d3 Mon Sep 17 00:00:00 2001 From: tannevaled Date: Wed, 5 Aug 2026 22:31:50 +0200 Subject: [PATCH] docs: document the widget bridge and fix stale scope wording README lacked any mention of AddWidget/AddWidgetVector (shipped in v0.3.0, extended in v0.4.0), the Widget bridge Features bullet, and a compiling usage snippet; add both, verified against the real API in a throwaway program. Also drop the "out of scope for v0.2" version pin from the scope note (stale) and note the v0.4.0 TrueType-face selectable-text path in the doc.go package comment. Co-Authored-By: Claude Opus 4.8 --- README.md | 33 ++++++++++++++++++++++++++++++++- doc.go | 5 ++++- 2 files changed, 36 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 1534a8b..31f4e87 100644 --- a/README.md +++ b/README.md @@ -35,6 +35,12 @@ Go-idiomatic rather than a gem port. rasterised as XObjects (FlateDecode) with an `/SMask` for alpha. - **Pages** — standard sizes (A3/A4/A5/Letter/Legal/Tabloid), portrait/landscape, custom sizes; `Pt`/`Mm`/`In` unit helpers. +- **Widget bridge** — `Page.AddWidget` and `Page.AddWidgetVector` "print" a + [go-widgets/toolkit](https://github.com/go-widgets/toolkit) widget tree onto a + page. `AddWidget` rasterises the tree and places it as an image XObject — + pixel-identical to the screen. `AddWidgetVector` instead emits PDF vector + operators, so fills/strokes stay crisp and text stays selectable, including a + TrueType-font widget label's own face embedded as real Type0 text. - **Deterministic** — with the zero `Options`, output has no timestamps and a content-derived `/ID`, so identical inputs produce byte-identical PDFs. @@ -81,6 +87,31 @@ Shaped (complex-script) text uses `p.TextShaped(x, y, s, features...)`, which runs the go-opentype shaper so Arabic, Indic and CJK position correctly. The default `Text` path stays a simple left-to-right cmap mapping. +### Printing a widget tree + +```go +import "github.com/go-widgets/toolkit" + +root := toolkit.NewContainer(toolkit.NewBoxLayout()) +btn := toolkit.NewButton("Submit", nil) +btn.Style = toolkit.ButtonProminent +root.AddWidget(btn) +root.AddWidget(toolkit.NewLabel("Status: ready")) + +rect := pdfkit.Rect{X: pdfkit.Mm(20), Y: pdfkit.Mm(200), Width: pdfkit.Mm(80), Height: pdfkit.Mm(30)} + +// Raster: pixel-identical to the screen, not selectable. +_ = p.AddWidget(root, rect, nil) + +// Vector: crisp fills/strokes, selectable text (needs an embedded Font). +rect.Y -= pdfkit.Mm(40) +_ = p.AddWidgetVector(root, rect, &pdfkit.WidgetOptions{Font: font}) +``` + +`WidgetOptions.Scale` sets the layout-pixels-per-point ratio (default +`DefaultWidgetScale`, 2); `WidgetOptions.Theme` selects the toolkit theme +(default `toolkit.DefaultLight()`). + ## Testing `GOWORK=off CGO_ENABLED=0 go test ./...` runs the suite at **exact 100% @@ -103,7 +134,7 @@ TrueType font, a synthesised CFF2 font and a bundled OFL OpenType/CFF font. - A **CID-keyed CFF** or a **CFF2 (variable)** font cannot be charstring-subsetted by the preserve-numbering path, so it gracefully falls back to embedding the whole `CFF`/`CFF2` table. -- Encryption, tagged/PDF-A, forms and annotations are out of scope for v0.2. +- Encryption, tagged/PDF-A, forms and annotations are not yet implemented. ## License diff --git a/doc.go b/doc.go index 3b1e4de..729aeb3 100644 --- a/doc.go +++ b/doc.go @@ -53,7 +53,10 @@ // XObject — any UI, exactly as it draws on screen. AddWidgetVector runs the same // tree through a painter that emits PDF vector operators instead of pixels, so // fills and strokes stay crisp and text drawn through the toolkit's built-in -// font becomes real, selectable PDF text (it needs a WidgetOptions.Font). +// font becomes real, selectable PDF text (it needs a WidgetOptions.Font). A +// widget label set in a TrueType/OpenType toolkit font (a painter.Face) embeds +// that face's own bytes and is emitted as selectable Type0 text too, so vector +// output is not limited to the toolkit's built-in bitmap font. // // # Font embedding //