Plugin SDK
Paged's plugin platform lets external bundles contribute tools, panels, commands, and document behavior to the editor through a small, versioned contract — the same surface Paged's own first-party plugins are built on.
Paged is the engine; plugins are the instruments. The plugin SDK is the contract through which a bundle — a unit of manifest plus code — extends the Paged editor: new drawing tools, new panels, new commands, and eventually new content types, all registered at runtime and removable without a trace.
In short a plugin is a bundle — a serializable manifest plus one
activate(host) entry point. The host hands the bundle a single object, the
BundleHost, carrying everything it may touch: contribution registration,
document reads, the one mutation door, selection, viewport, overlays, storage,
and diagnostics. Everything a bundle registers is disposable, and the host
tracks all of it — deactivating a plugin restores the editor exactly as it was.
The packages
| Package | Role |
|---|---|
@paged-media/plugin-api | the contract: manifest types and schema, the bundle lifecycle, the full BundleHost surface, and curated re-exports of the contribution and wire types. Type-only — nothing in it exists at runtime. |
@paged-media/plugin-sdk | the runtime: defineBundle, loadBundle, the in-process host implementation, the gesture kit, version negotiation. |
@paged-media/plugin-cli | tooling: paged-plugin validate <manifest.json> checks a manifest against the schema and the namespace rule. |
Status: incubating. The SDK is at API v0.2 and not yet published to npm — it is being proven by Paged's own first-party plugins (paged.draw, the vector tool set, ships through it today) before the v1 freeze. Expect breaking changes between 0.x minors; this reference tracks the implemented contract, not an aspiration.
Dogfooding first
The platform's design discipline: every first-party plugin uses only this
public surface. paged.draw's pen and anchor tools register through the same
activate(host) door a third-party bundle will use — no private backdoors. The
places where the surface fell short of what a real plugin needed are recorded
in a public punch list, and that list decides what enters API v1. Nothing is
added speculatively.
What a plugin can do today
- Contribute tools to the tool rail — with gesture handlers, cursors, flyout grouping, activation commands, and keyboard shortcuts.
- Contribute panels (React components composed from the host's UI kit, so they are visually indistinguishable from native panels), commands, keybindings, and canvas overlays.
- Read the document broadly — collections (swatches, layers, styles, …), metadata, path geometry, hit-testing, the scene tree.
- Write through one door — every change is a
Mutationon the editor's single undoable Operation channel. Plugin edits and native edits share one history;Cmd+Zdoes not care who authored a change. - Persist settings in namespaced storage, report diagnostics, and detect host capabilities at runtime.
What is deliberately not there yet
Edit contexts (double-click into plugin-owned content), plugin-defined object
types, retained scene layers, and process isolation are declared in the
contract but reserved — calling them throws a visible
PluginApiNotImplemented, never a silent no-op. The platform ships honest
seams, in its UI and in its API.
Start with Your first plugin, then read The bundle model for the architecture and The BundleHost for the full surface.
The docs examples loop
Every example in this reference is a hand-authored, unzipped IDML package that CI assembles into a real .idml and runs through the pinned renderer on each build — a structural parse-and-build gate that breaks the docs if the renderer ever stops accepting it.
Your first plugin
Build a working Paged plugin from scratch — manifest, activate entry point, a command with a keyboard shortcut, and a clean teardown — in about forty lines.