slidemind 0.3.5 → 0.3.13

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "slidemind",
3
- "version": "0.3.5",
3
+ "version": "0.3.13",
4
4
  "description": "Connect Claude Code, Codex & opencode to the slidemind PowerPoint add-in — let your coding agent build and edit native, on-brand PowerPoint decks against your active corporate design, from the terminal.",
5
5
  "type": "module",
6
6
  "bin": {
@@ -22,6 +22,11 @@ workflow vocabulary — the harness-neutral verbs defined in the bundle's `workf
22
22
  spoken throughout `workflow/*.md` — into your `slidemind` CLI commands. Read the workflow + brand
23
23
  from the bundle; never restate or duplicate them here.
24
24
 
25
+ Brand sample slides are private inputs to the add-in's concept generator. They are not authoring
26
+ references and are deliberately not materialized into the local bundle. From the concept pass
27
+ onward, re-read only `decks/<slug>/concepts/concept-slide-NN.png`; when a concept is unavailable,
28
+ fall back to the approved storyboard plus `design.md` and the chosen layout, never to samples.
29
+
25
30
  **slidemind is a CLI you drive directly.** Run `slidemind <command>` in your shell — the same way
26
31
  you'd run `git` or `npm`. There is no separate tool layer to go through; every step below is a real
27
32
  command you type.
@@ -36,13 +41,43 @@ later stages (above all the review gate) from being skipped. The stages, as they
36
41
  1. `slidemind ready` — session preflight (*First step* below)
37
42
  2. Clarify with the user — the content **and the output target** (*Intake → plan* below; needs no
38
43
  host, so it can run while `ready` executes)
39
- 3. Plan sign-off — `slidemind plan <deck>` (decks; single slides stay in chat)
40
- 4. Concept mockups — `slidemind concepts <deck>`, then immediately inspect every mockup to drive
41
- image/content search (a deck authored from an approved plan; see *The create flow* below)
42
- 5. Author the slides
43
- 6. Draft check — `slidemind view-draft`
44
- 7. Review gate — `slidemind review`, the moment the deck builds clean
45
- 8. Deliver — `slidemind push` or `slidemind build-pptx`, whichever target was locked in stage 2
44
+ 3. Plan sign-off — `slidemind plan <deck>` (every from-scratch request — one slide included)
45
+ 4. Concept mockups — `slidemind concepts <deck>`, then immediately inspect every mockup (anything
46
+ authored from an approved plan, a single slide included; see *The create flow* below). **The FILES ON DISK are the
47
+ truth, not the command output you saw.** Generation takes 1–2 minutes and your harness may
48
+ time the command out, showing you only progress lines while the detached process finishes
49
+ writing the PNGs — output that ends mid-progress means TIMED OUT, never "no mockups". The
50
+ moment the command returns (complete or cut off): run `ls decks/<slug>/concepts/`. PNGs
51
+ listed → re-run `slidemind concepts <deck>` once (it returns the full path list instantly for
52
+ already-generated mockups) and Read every file. **Claiming the concepts are missing requires
53
+ double evidence**: `asset-plan.md` may say "no mockups" ONLY when BOTH the re-run's output
54
+ printed zero paths AND `ls decks/<slug>/concepts/` is empty — quote both in the file.
55
+ Authoring a concept-seeded deck without having Read the concept PNGs that exist on disk is the
56
+ single largest fidelity failure this workflow has; nothing about a truncated stdout excuses it.
57
+ **User-provided images** go into this command, classified from the user's words: a sketch or
58
+ mockup to build ("build it like this") → `--concept <file>[@N,M]` (it becomes the mockup for
59
+ those slides, no generation); a look to emulate ("in this style") → `--style <file>[@N,M]`
60
+ (leads the generation; repeatable; `@` omitted = all slides). A photo or logo to place on a slide
61
+ is not a concept input: copy it into `decks/<slug>/assets/` and list it in `asset-plan.md`.
62
+ 5. Source assets — write `decks/<slug>/asset-plan.md` from the concepts, then search + download
63
+ every item in it (*The create flow* steps 2–3). **This stage is not optional and not mergeable
64
+ into authoring**: it is done when every plan item is checked off with a filename or marked
65
+ `(no result)` after its search ran. A deck with concept mockups and an empty `assets/` beyond
66
+ the brand chrome means this stage was skipped, not completed.
67
+ 6. Author the slides
68
+ 7. Draft check — `slidemind view-draft`
69
+ 8. Review gate — `slidemind review`, the moment the deck builds clean
70
+ 9. Deliver — `slidemind push` or `slidemind build-pptx`, whichever target was locked in stage 2
71
+
72
+ **Changing slides that already exist runs a shorter list.** When the deck is on disk and the
73
+ request targets slides in it — "make slide 13 clearer", "rescope 12 and 13", "fix the spacing",
74
+ comments on a delivered deck — the stages are `ready` → edit → `view-draft` → `review` → deliver.
75
+ Stages 2–5 do not run: there is nothing to plan and no mockup to render, the live slide is the
76
+ starting point (the in-app equivalent is the manager's route B, `approvedPlan: null`; the design
77
+ worker's small-edit fast path keeps no todo board at all). Updating `plan.md` afterwards is optional
78
+ bookkeeping and never re-opens the plan gate — once a deck has passed a review, the CLI treats
79
+ `plan.md` as a record, not a contract. The full route definitions are in *Intake → plan* below; new
80
+ slides added to an existing deck are from-scratch work and run the full list.
46
81
 
47
82
  **Deliver is the last todo — the task ends when the slides are delivered.** Don't add a "sanity
48
83
  pass" or "report back" step after it: the visual QA already happened at the draft check and the user
@@ -50,8 +85,9 @@ already approved at the review gate, so on approval you push/build directly and
50
85
  full definition and the ordering invariants live in the bundle's `workflow/flow.md` — read it right
51
86
  after `ready` succeeds.
52
87
 
53
- **Concept mockups (stage 4) are a mandatory deck stage, not an optional aid.** After plan sign-off,
54
- for a deck authored from an approved plan, you **always** run `slidemind concepts <deck>` and
88
+ **Concept mockups (stage 4) are a mandatory authoring stage, not an optional aid.** After plan
89
+ sign-off, for anything authored from an approved plan — one slide as much as a deck — you **always**
90
+ run `slidemind concepts <deck>` and
55
91
  **immediately Read every generated `concept-slide-NN.png` at full detail**. Use this first,
56
92
  deck-wide viewing pass to inventory the imagery, pictograms, factual/content checks, and other
57
93
  searches each slide needs; do those searches before authoring. This discovery read does **not**
@@ -60,23 +96,42 @@ The durable visual anchors are the repo-relative files under
60
96
  `decks/<slug>/concepts/concept-slide-NN.png`, never an earlier chat image or temporary attachment;
61
97
  after any continuation, re-list that directory and reopen the files from those paths.
62
98
  Rebuild each mockup toward its target — this is the local-harness equivalent of the in-app manager's
63
- *unconditional* concept pass on every full-deck delegation (`generateConceptImages` fires for
64
- `approvedPlan && !targetSlideScope`). It degrades benignly: if it returns no mockups (exit 0 — the
65
- add-in can't generate them) you author from the storyboards alone, but the *attempt* is not optional.
66
- Skip it only where the add-in's `!targetSlideScope` gate would — a single slide, a tiny in-chat set,
67
- or a targeted rework of existing slides.
99
+ *unconditional* concept pass on every from-scratch delegation (`generateConceptImages` fires for
100
+ every delegation carrying an approved plan). It degrades benignly: if it returns no mockups (exit 0 —
101
+ the add-in can't generate them) you author from the storyboards alone, but the *attempt* is not
102
+ optional. Skip it only for targeted work on slides that **already exist** — an edit or a rework,
103
+ which designs from the live slide and never had a plan to render mockups from.
68
104
 
69
105
  Two gate invariants you must never break — one per gate, equally binding:
70
106
 
71
- - **Never jump from clarify to authoring for a deck** — the plan sign-off gate (`slidemind plan
72
- <deck>`, stage 3) always sits between. Writing `decks/<slug>/slides/*.jsx` before that gate has
107
+ - **Never jump from clarify to authoring** — the plan sign-off gate (`slidemind plan <deck>`,
108
+ stage 3) always sits between. Writing `decks/<slug>/slides/*.jsx` before that gate has
73
109
  returned `DECISION: approved` is the single most common way this workflow goes wrong — it means
74
- the user never actually signed off on the story. The only exception is a single slide or a tiny
75
- set genuinely handled in-chat (*Intake → plan* below) — that's a real design choice, not a
76
- shortcut to take when a deck-sized request feels obvious.
110
+ the user never actually signed off on the story. **There is no small-request exception**: one new
111
+ slide runs the same gate with a one-beat plan. The only work that skips it is a change to slides
112
+ that already exist.
77
113
  - **Never jump from authoring to deliver** — the draft check and an approved review gate always sit
78
114
  between.
79
115
 
116
+ ## After a context summarization (compaction recovery)
117
+
118
+ Long deck runs can exceed the context window mid-task; the harness then replaces the transcript
119
+ with a summary. **Everything you only held in chat — viewed concept images, search results, the
120
+ asset inventory, workflow rules you read from the bundle — is gone; the files on disk are not.**
121
+ When you notice you are running from a summary (or after any interruption/continuation), do NOT
122
+ improvise from the summary and do NOT restart finished work. Recover state from disk, in this
123
+ order, then resume at the first incomplete stage:
124
+
125
+ 1. `decks/<slug>/plan.md` — the approved story.
126
+ 2. `decks/<slug>/asset-plan.md` — per-slide organisms + which assets are downloaded vs. missing
127
+ (unchecked items still need their search + fetch).
128
+ 3. `ls decks/<slug>/slides/ decks/<slug>/assets/ decks/<slug>/concepts/` — what already exists.
129
+ 4. Re-read `<bundle>/workflow/create.md` if you are still before or inside authoring, and reopen
130
+ the concept PNGs for the slides not yet authored (batches of ≤3) before writing them.
131
+
132
+ The stage todo list still binds after a summary: a summary that says the deck is "mostly done" is
133
+ never a reason to skip the remaining stages (assets, draft check, review gate).
134
+
80
135
  ## Bootstrap (set yourself up — don't make the user do it)
81
136
 
82
137
  **The first step of every session is `slidemind ready`** (continuing an existing deck: `slidemind
@@ -139,25 +194,36 @@ ask for a fresh one. The pane flips to **Connected** by itself once the claim is
139
194
  Everything about how a deck is authored, styled, and rendered is shaped by the corporate design
140
195
  **the add-in has open**, and every brand rule you follow is read from that design's **materialized
141
196
  bundle**. `slidemind ready` gets you there in one call: it walks the connection ladder (a saved
142
- session → reachable backend → CLI version → an open render-ready window), resolves which open design
143
- to build against, downloads or refreshes that design's bundle (incremental — unchanged files cost
144
- nothing), and — when you pass a deck — binds the deck to it by writing `<deck>/.bundle-ref.json`.
145
-
146
- - **New work:** `slidemind ready` — resolves + materializes the open design's bundle so you can read
147
- its `design.md` while planning.
148
- - **Continuing a deck:** `slidemind ready <deck>` — same, and (re)binds the deck to whatever design
149
- is open.
150
-
151
- **The open add-in is the source of truth.** `ready` binds to whatever design is open *now*; a deck's
152
- `.bundle-ref.json` records the last-resolved design for the render-time etag contract and host-free
153
- bundle reads — it is **not** a pinned design preference. So you never "start a session with design
154
- A" from a deck ref; you start it from what the add-in has open.
155
-
156
- **On exit 0** the JSON reports `presId`, `presFP`, `designName`, `bundleDir`, `bundleEtag`, `bound`,
157
- `paneSuspended`, and `engines` (`{available, envs}` — whether engine search reaches the corpus
158
- without a window), with `nextAction: "Ready."`. Read `workflow/flow.md` and `design.md` from
197
+ session → reachable backend → CLI version), picks which design to build against, downloads or
198
+ refreshes that design's bundle (incremental — unchanged files cost nothing), and — when you pass a
199
+ deck — binds the deck to it by writing `<deck>/.bundle-ref.json`. PowerPoint does not have to be
200
+ open: the designs cached on this machine are a first-class source.
201
+
202
+ - **New work:** `slidemind ready` — picks + materializes a design's bundle so you can read its
203
+ `design.md` while planning.
204
+ - **Continuing a deck:** `slidemind ready <deck>` — same, and the deck's own binding is what it
205
+ picks.
206
+
207
+ **The design is the user's choice; `ready` only picks a sensible default.** Its order is: an
208
+ explicit `--brand <presFP>`, else the deck's own `.bundle-ref.json`, else the one design the
209
+ verified live PowerPoint windows agree on (a window whose pane is only suspended never outranks a
210
+ live one), else the one design cached here, else the one design the backend lists. Anything
211
+ that leaves several candidates is the `ambiguous_design` blocker (below). A live window is a
212
+ suggestion, never an authority: it only decides when nothing stronger says otherwise. And whatever
213
+ `ready` picked, when its `designs` list holds more than one entry the design is a Clarify question
214
+ (below), and the answer is applied with `slidemind ready [deck] --brand <presFP>` before anything
215
+ is planned.
216
+
217
+ **On exit 0** the JSON reports `presId`, `presFP`, `designName`, `designs` (every design at hand
218
+ — cached on this machine, open in a verified window, or listed by the backend — `{presFP, name,
219
+ colors, current, cached, windows}`, `colors` being the master's theme colours as hex,
220
+ `dk1`/`lt1`/`dk2`/`lt2`/`accent1..6`, `windows` the open PowerPoint windows on that design),
221
+ `windows` (every verified open window — `{presId, env, title, fileName, presFP, paneReady}`; a
222
+ window PowerPoint no longer has is pruned before anything is decided), `bundleDir`, `bundleEtag`,
223
+ `bound`, `paneSuspended`, and `engines` (`{available, envs}` — whether engine search reaches the
224
+ corpus without a window), with `nextAction: "Ready."`. Read `workflow/flow.md` and `design.md` from
159
225
  `bundleDir` (cached at `${XDG_CACHE_HOME:-~/.cache}/slidemind/bundles/<presFP>/`, alongside
160
- `corporate-design.css`, `layouts/*.jsx`, `layouts/layouts.css`, `assets/`, `samples/`, and the rest
226
+ `corporate-design.css`, `layouts/*.jsx`, `layouts/layouts.css`, `assets/`, and the rest
161
227
  of the add-in-owned `workflow/*.md`) and start planning. A render-ready window whose pane is
162
228
  suspended still exits 0 with `paneSuspended: true` — the pane ops wait for a pane click on their
163
229
  own; **don't treat it as a blocker.**
@@ -181,24 +247,23 @@ complete the sign-in in the browser (you cannot) and keep waiting — don't kill
181
247
  command. One sign-in lasts ~90 days. Rendering, bundles, and already-materialized assets never need
182
248
  it, so a pure author→render session runs signed-out without ever seeing this.
183
249
 
184
- For a deck that was **never** bound and no window is open, `ready` asks the backend which corporate
185
- designs the user may build against: exactly one binds automatically, several stop with
186
- `ambiguous_brand` (below).
250
+ For a deck that was **never** bound and no window is open, the one design cached here binds
251
+ automatically; with nothing cached `ready` asks the backend which corporate designs the user may
252
+ build against, and exactly one binds. Several of either stop with `ambiguous_design` (below).
187
253
 
188
254
  **On non-zero** the CLI names exactly one blocker `{code, actor, message}` and one `nextAction`.
189
255
  **The CLI owns the remediation text — relay `nextAction`, don't restate it.** These are the ones
190
256
  that need the user:
191
257
 
192
- - **`ambiguous_design`** — several windows with **different** corporate designs are open, so `ready`
193
- can't choose. The CLI lists the candidates (each with its `env` and window `title`/`fileName`,
194
- plus a design fingerprint); if the deck was last built against one of them it's marked
195
- `suggested`. **Ask the user which design to build against, naming the windows by
196
- `title`/`fileName` (and `env`) — never by raw id** — and mention the suggested one if present
197
- ("this deck was last built against X — continue with it?"). Then re-run `slidemind ready --to
198
- <presId>` for the window they pick.
199
- - **`ambiguous_brand`** — the same question with no window to ask it from: the backend offers
200
- several designs (`brands[]`, each with a `name` and `env`). Ask the user by **name**, then re-run
201
- `slidemind ready [deck] --brand <presFP>`.
258
+ - **`ambiguous_design`** — several corporate designs are at hand and nothing says which: several
259
+ live windows on different designs, or no live window and several designs cached / listed by the
260
+ backend. The payload is the same `designs` menu as on success (name, `colors`, `cached`, and
261
+ the open `windows` on each) plus `windows`; if the deck was last built against one of them its
262
+ `presFP` is `suggested`. **Ask the user which design to build against exactly as the Clarify
263
+ question below does — by name and colours, naming any open window on it by `title`/`fileName`,
264
+ never by raw id** — and mention the suggested one if present ("this deck was last built against
265
+ X — continue with it?"). Then re-run `slidemind ready [deck] --brand <presFP>` for the design
266
+ they pick (`--to <presId>` also works when they named a window).
202
267
  - **`login_required`** — the automatic browser sign-in was refused or abandoned, so **corpus search
203
268
  and engine downloads** stop until the user runs `slidemind login` (browser step, whenever they're
204
269
  ready). It never blocks authoring, rendering, or the bundle — relay the line, keep working, and
@@ -213,9 +278,9 @@ that need the user:
213
278
  **The session spine** (= the stage todos you created up front): `slidemind ready` → read
214
279
  `workflow/flow.md` + `design.md` from `bundleDir` → intake/plan (below) → `slidemind new <slug>`
215
280
  (scaffolds **and** auto-binds the deck to the open design — zero extra download, because `ready`
216
- already materialized it) → `slidemind plan <slug>` (plan sign-off gate for decks; single slides stay
217
- in chat) → `slidemind concepts <slug>` (mandatory concept-mockup pass for a deck, then rebuild
218
- toward each) → author → `view-draft` → `review` (mandatory, the moment the deck builds clean) →
281
+ already materialized it; `--brand <presFP>` binds to the design the user chose instead) → `slidemind plan <slug>` (plan sign-off gate for every
282
+ from-scratch request, one slide included) → `slidemind concepts <slug>` (mandatory concept-mockup pass for everything
283
+ authored from a plan, then rebuild toward each) → author → `view-draft` → `review` (mandatory, the moment the deck builds clean) →
219
284
  deliver (`push` / `build-pptx`). `slidemind new` best-effort binds when the open design is
220
285
  unambiguous and the bundle is already materialized; if it can't (ambiguous, or no host), it
221
286
  scaffolds anyway and hints to run `slidemind ready <slug>`.
@@ -264,9 +329,43 @@ This is your mapping of `workflow/flow.md` stages 1–2 (*clarify* + *plan sign-
264
329
  manager runs these; over the CLI the manager role collapses onto **you**, so you run the interview
265
330
  and the sign-off directly with the user. Don't write slide JSX until the plan is agreed.
266
331
 
332
+ **First read which of three things the user wants**, from their words plus what you already have —
333
+ the deck you are working in, the file they pointed at, what you built for them a moment ago. Judge it
334
+ yourself and ask only when the request genuinely reads both ways. **Slide count never decides the
335
+ route; intent does.**
336
+
337
+ - **Author something new** ("a slide about X", "a deck for Friday", "add a closing slide", filling an
338
+ empty placeholder) → the full spine: plan → `slidemind plan` → `slidemind concepts` → author →
339
+ `view-draft` → `review` → deliver. One slide runs every one of those stages, just smaller.
340
+ - **Change slides that already exist** ("make slide 4 stronger", "fix the spacing", "retitle these
341
+ three") → **no plan, no concepts**: there is nothing to plan, the live slide is the starting point.
342
+ Read `workflow/edit.md`, patch that slide's own `.jsx` (adopt a foreign slide on first touch), then
343
+ `view-draft` → `review` → deliver. The review gate still runs — over the CLI the deliver happens
344
+ out of the user's sight, so it is the only place they see the change.
345
+ - **Reuse something that already exists elsewhere** ("do we have a slide on X?", "drop in our pricing
346
+ slide", "put our lighthouse icon here") → that is **`slidemind-search`**, not this create flow:
347
+ `slidemind search` → `download-result` / `add-slide`. Reuse is not authoring — no plan, no
348
+ concepts.
349
+
350
+ A request can carry two of them ("find our pricing slide and write a summary after it") — run each
351
+ part on its own route instead of forcing the whole thing onto one.
352
+
267
353
  - **Read scope from the wording**, don't ask redundantly: single slide ("make a slide about X"),
268
354
  small set ("add three slides on Y"), or whole deck ("a deck for Friday"). Only ask "one slide, a
269
355
  small set, or a full deck?" when truly ambiguous.
356
+ - **Which corporate design — ask whenever more than one is cached.** `ready`'s `designs` list is
357
+ the menu: with a single entry there is no question; with several, put the choice to the user
358
+ **before planning**, even if PowerPoint has one of them open (that one is only the suggestion).
359
+ Never pick silently and never default to the open window or the deck's last binding — those
360
+ only chose `ready`'s `current` default, not the user's answer. Name each
361
+ design **and show its colours** so the user recognises it — the `name` plus its theme hexes in a
362
+ fixed order (`<name> — accent <accent1>, dark <dk1>, light <lt1>`, each a hex from `colors`; a
363
+ design without `colors` is listed by name alone), mark the `current` one, and ask which to build
364
+ against. Then
365
+ apply the answer: `slidemind ready [deck] --brand <presFP>` for the session, and `slidemind new
366
+ <slug> --brand <presFP>` when scaffolding a new deck. A design the user names that is not in the
367
+ list is not cached yet — `slidemind ready --brand <presFP>` fetches it when the backend serves
368
+ it; otherwise it must be opened in PowerPoint once.
270
369
  - **Interview just enough** to pin: audience/goal, the content and its sources (none / pasted /
271
370
  local files / existing deck / web research — a source that's already a local `.pptx` you read
272
371
  host-free with `slidemind read <file.pptx>`), and the slide outline (each slide's role + a layout
@@ -279,9 +378,10 @@ and the sign-off directly with the user. Don't write slide JSX until the plan is
279
378
  wording is clear ("add a slide to this deck" → push; "make me a deck I can send around" → a file)
280
379
  and ask only when genuinely ambiguous — but **always confirm the concrete target before
281
380
  delivering** (which window, or which output path).
282
- - **Replay and get sign-off.** Single slides / tiny sets → a compact in-chat plan (no gate). Decks →
283
- persist a **story-focused plan with body storyboards** in `decks/<slug>/plan.md`, two top-level
284
- sections in order:
381
+ - **Replay and get sign-off — always, at every size.** Persist a **story-focused plan with body
382
+ storyboards** in `decks/<slug>/plan.md` and run the gate on it, whether the request is one slide or
383
+ forty. A single slide gets the same document with one `### Slide N` section: shorter, never
384
+ skipped. Two top-level sections in order:
285
385
  - `## Red thread` — one presentation **move** per slide, as bullets or one arrow-separated line.
286
386
  The number of moves MUST equal the number of `### Slide N` sections: when the user names a slide
287
387
  count, write exactly that many moves and sections — never expand the narrative arc beyond the
@@ -300,7 +400,11 @@ and the sign-off directly with the user. Don't write slide JSX until the plan is
300
400
  only two visible text fields: `designElement` (the visual mechanism in up to 5 words — e.g.
301
401
  "hub-spoke visual", "loop diagram", "timeline", "matrix", "before/after contrast", "scorecard")
302
402
  and `content` (a 1–2 word label), plus `emphasis` ("primary"/"secondary"/"tertiary") for
303
- hierarchy. `keyMessage` is the slide's **story beat**: one plain sentence naming what this slide
403
+ hierarchy. A `designElement` may also name the chart family when the beat is quantitative
404
+ ("waterfall revenue to EBIT", "combo: revenue bars + margin line", "column chart by quarter");
405
+ that is a plan-level choice the authoring stage honours unless the data cannot be shown that
406
+ way, in which case it says so at the review gate.
407
+ `keyMessage` is the slide's **story beat**: one plain sentence naming what this slide
304
408
  does to move the story forward, stated abstractly — NOT the headline or copy that will appear on
305
409
  the slide, and not the red-thread move restated. `contentNotes` is the **content draft** that
306
410
  delivers that beat — facts, claims, examples, source points, caveats, draft copy, proof points —
@@ -323,14 +427,21 @@ and the sign-off directly with the user. Don't write slide JSX until the plan is
323
427
  Choose the block count from the slide's meaning and **never default to three** (1 for a hero idea,
324
428
  2 for a contrast or paired tension, 3 only for three genuinely distinct beats, 4–5 only for a true
325
429
  sequence or comparison set), and vary the spatial composition across slides — avoid repeating the
326
- same left/right/bottom alignment. Ban style micromanagement only — no colours, fonts, exact layout
327
- names, or final box/card counts: **the create stage owns realisation** of the approved body
328
- storyboard in the corporate design. Use this exact JSON shape:
430
+ same left/right/bottom alignment. Ban style micromanagement — no colours, fonts, or final
431
+ box/card counts: **the create stage owns realisation** of the approved body storyboard in the
432
+ corporate design. The ONE exception is the top-level `layout` field: **choose each slide's
433
+ layout at plan time** from `design.md` → Layout Catalog (a workhorse with a freeform body for
434
+ content slides; a purpose-built layout for covers/quotes/agendas; match the background tone —
435
+ light vs dark — to the slide's intended look) and set `"layout": "<ComponentName>"` on the
436
+ storyboard block. The concept generator uses it to render the mockup INTO that layout's actual
437
+ chrome and canvas, so the image you later rebuild already fits the stage it will live on. Use
438
+ this exact JSON shape:
329
439
 
330
440
  ```storyboard-canvas
331
441
  {
332
442
  "version": 1,
333
443
  "slide": 1,
444
+ "layout": "<ComponentName from design.md's Layout Catalog>",
334
445
  "blocks": [
335
446
  {
336
447
  "id": "main-visual",
@@ -369,11 +480,10 @@ and the sign-off directly with the user. Don't write slide JSX until the plan is
369
480
  output was truncated). Change only what the comments require and keep unaffected slides verbatim
370
481
  (that is what makes the reviewer's per-slide "updated" badges meaningful), then **re-run the gate
371
482
  in the same turn**. **Expect several consecutive `DECISION: comments` rounds — that is the normal
372
- shape of a review, not an error.** The reviewer's tab stays live while you revise, so they keep
373
- reading and keep queueing comments; those queued comments are delivered by your next run, which
374
- then returns *immediately* with them (a drain round) instead of waiting. So never end your turn on
375
- a comments round, never claim to be "polling", and never send the user back to the browser between
376
- rounds — nothing reaches them until the gate runs again. Only `DECISION: approved` or `DECISION:
483
+ shape of a review, not an error.** The reviewer's tab waits while you revise (reading stays live,
484
+ commenting is off) and refreshes with your next run, which blocks until they decide again. So
485
+ never end your turn on a comments round, never claim to be "polling", and never send the user
486
+ back to the browser between rounds — nothing reaches them until the gate runs again. Only `DECISION: approved` or `DECISION:
377
487
  pending` ends the loop; `DECISION: pending` → the gate timed out with no answer — not approval,
378
488
  not rejection: don't author; wrap up telling the user the plan still awaits their sign-off and
379
489
  re-run `slidemind plan <deck>` on their go-ahead. Loop until approved. A `plan.md` **approved in a
@@ -391,14 +501,7 @@ brand/layout/composition detail until create/edit.**
391
501
  to it by `slidemind ready <deck>` (continuing) or by `slidemind new <slug>`'s auto-bind (new work).
392
502
  From here:
393
503
 
394
- 1. **Study brand samples (before composing).** The materialized bundle's `samples/` dir holds the
395
- brand's own reference slides. If it's non-empty, pick **3 at random** and **Read** each (the Read
396
- tool renders images) *before* writing any JSX — this is the local-harness stand-in for the in-app
397
- persona's reference thumbnails, and it is what keeps a deck looking on-brand rather than merely
398
- compliant. Study them for whitespace rhythm, shape density, hierarchy, accent use, and layering,
399
- then compose in that spirit (never copy a sample 1:1). This is `composition.md`'s samples
400
- discipline; skip only when `samples/` is empty.
401
- 2. **Load create context, then inspect the concepts.** Read the create-stage references together —
504
+ 1. **Load create context, then inspect the concepts.** Read the create-stage references together —
402
505
  `workflow/create.md` (the procedure), `workflow/composition.md` (the composition baseline),
403
506
  `workflow/layouts.md` (palette + working area), and `workflow/authoring.md` (the substrate rules)
404
507
  — plus the deck's `design.md` and the specific `layouts/*.jsx` the plan uses. (That is the read
@@ -408,25 +511,39 @@ From here:
408
511
  sketch's geometry; how to interpret the `storyboard-canvas` blocks at author time (design
409
512
  hypothesis: reinterpret freely, never transcribe coordinates, block geometry, or block labels)
410
513
  is owned by `workflow/create.md` → Preconditions. **Generate concept mockups first — mandatory
411
- for a deck (stage 4).** Before
412
- authoring a deck from an approved plan, run `slidemind concepts <deck>` — the local-harness
514
+ for everything authored from a plan, a single slide included (stage 4).** Before
515
+ authoring from an approved plan, run `slidemind concepts <deck>` — the local-harness
413
516
  equivalent of the in-app manager's *unconditional* concept pass (`generateConceptImages` fires
414
- for every `approvedPlan && !targetSlideScope` delegation). **Immediately after generation, Read
517
+ for every delegation carrying an approved plan). **Immediately after generation, Read
415
518
  every `decks/<slug>/concepts/concept-slide-NN.png` at full detail, before any engine or content
416
519
  search.** First list the directory and keep the literal repo-relative mapping in the task context:
417
520
  concept `NN` maps to `decks/<slug>/concepts/concept-slide-NN.png` and later to the `NN-*.jsx`
418
521
  slide. These workspace files are the durable source of truth across turns and compaction — never
419
522
  rely on an earlier rendered attachment. Inventory what each mockup requires — imagery, distinct
420
- pictograms, factual/content verification, annotations, and other visible organisms — and use
421
- that inventory to drive step 3. This first pass is deliberately deck-wide and search-oriented;
422
- it is not the fresh authoring read required in step 4. Rebuild each mockup under your constraints
523
+ pictograms, factual/content verification, annotations, and other visible organisms — and
524
+ **persist the inventory to disk the moment you finish it: write `decks/<slug>/asset-plan.md`**,
525
+ one section per slide:
526
+
527
+ ```
528
+ ## Slide NN — <title>
529
+ organisms: <the mockup's regions, hero figure, badges, satellites, chips, connectors>
530
+ - [ ] icon: <what it depicts> — query: "<search query>"
531
+ - [ ] image: <what it shows> — query: "<search query>"
532
+ ```
533
+
534
+ Chat context is evicted when the conversation is summarized; this file is not. Every icon
535
+ decision you make only in your head is lost at the next compaction — the file is the contract
536
+ step 2 executes and step 3 authors from. Check items off (`- [x] … — assets/engine-<id>-<n>.svg`)
537
+ as downloads land, so the file always shows what is still missing. This first pass is
538
+ deliberately deck-wide and search-oriented; it is not the fresh authoring read required in
539
+ step 3. Rebuild each mockup under your constraints
423
540
  — the rebuild rule is owned by
424
541
  `workflow/create.md` → Preconditions (reproduce the mockup's composition, hierarchy, graphic
425
542
  mechanism, AND granularity — its organism count, badges, satellites, and annotation layers are
426
543
  part of the target, and restraint is a colour budget, never an element budget; texts follow the
427
544
  story). It never hard-fails: if it produces no mockups (exit 0 — the add-in can't generate them)
428
- author from the storyboards alone. Skip it only where the add-in's `!targetSlideScope` gate would
429
- — a single slide, a tiny in-chat set, or a targeted rework of existing slides.
545
+ author from the storyboards alone. Skip it only for targeted work on slides that **already
546
+ exist** — an edit or a rework.
430
547
  When storyboard objects share a `visualFamily`, rebuild those mockups as one recognizable visual
431
548
  series. The lowest-numbered member is the anchor. Preserve its shape vocabulary, framing,
432
549
  hierarchy, annotation style, illustration treatment, and spatial rhythm across the family, but
@@ -434,13 +551,26 @@ From here:
434
551
  own complete `keyMessage`, `contentNotes`, role, and structure. Never copy another member's text,
435
552
  claims, or data, never force its exact geometry, and never omit approved content because it does
436
553
  not fit the anchor composition.
437
- 3. **Search and fetch from the concept inventory.** Resolve the image and content needs identified
438
- in the immediate post-generation concept pass. Discover the available image engines by listing
439
- them — `slidemind ls engines --subtype image` (the local-harness equivalent of the in-app design
440
- agent's
441
- `list_engines` tool; no PowerPoint window needed where the add-in serves the pane-free engine
442
- routes) — judge which engine fits from its label and description, then search it and place
443
- results. (`slidemind search` without `--engine` picks an image engine the same way.) The engine
554
+ 2. **Execute `asset-plan.md` — search and fetch every unchecked item.** Discover the available
555
+ image engines by listing them — `slidemind ls engines --subtype image` (no PowerPoint window
556
+ needed where the add-in serves the pane-free engine routes) — judge which engine fits from its
557
+ label and description, then run every query in `asset-plan.md` and fetch the picks.
558
+ (`slidemind search` without `--engine` picks an image engine the same way.) Listing the engines
559
+ is discovery, not sourcing: this step is done only when every `asset-plan.md` item is checked
560
+ off with a downloaded filename or marked `(no result)` after its search actually ran. Four
561
+ mechanics that waste rounds when gotten wrong:
562
+ - **Icon results have no preview.** `slidemind view-slide` serves slide-library results only —
563
+ on an image/icon search it answers "no image returned" every time, so never call it there and
564
+ never retry it. Pick from the `search` output's titles/scores; a download is cheap and
565
+ `download-result` prints each asset's size + recolor info — download first, judge from the
566
+ saved file, re-search once if it was wrong. At most two search rounds per need; two failed
567
+ downloads = mark it `(no result)` and move on.
568
+ - **Batch the downloads:** one `download-result --search <id> --pick <n,n,…>` per search id —
569
+ never one call per icon.
570
+ - **Quote hex colors:** `--icon-color "#<hex>"` (a value resolved from a corporate-design.css token) — an unquoted `#` makes the shell drop the
571
+ rest of the line.
572
+ - Searches come **from the file, after the concept pass** — never from plan nouns before the
573
+ concepts exist. The engine
444
574
  search/reuse mechanics live in **`slidemind-search`** — use it to find and fetch imagery; the
445
575
  create-only detail — sizing a fetched asset's box and recolouring an icon — is in *Placing engine
446
576
  imagery* below. To pull in an **existing whole slide** (not just an image), use
@@ -448,23 +578,30 @@ From here:
448
578
  `.pptx` that coexists with your JSX in play order and survives re-push. The slide can come from
449
579
  an engine search **or** from a local `.pptx` on disk (`add-slide --from <file.pptx> --pick <n>
450
580
  --deck <slug>`, host-free); both fold in identically — see `slidemind-search`.
451
- 4. **Reopen the concepts, then author in small batches.** Once the searches and asset downloads are
581
+ 3. **Reopen the concepts, then author in small batches.** Once the searches and asset downloads are
452
582
  complete, split a concept-seeded deck into batches of at most **3 slides**. For each batch, first
453
583
  Read its matching anchored `decks/<slug>/concepts/concept-slide-NN.png` files together at full
454
584
  detail; as the **very next tool action**, create those slides'
455
585
  `decks/<slug>/slides/NN-<topic>.jsx` files. Put no search, command, reference read, user exchange,
456
586
  or unrelated work between the concept images and the JSX write.
457
- The deck-wide discovery read in step 2 never counts as this authoring read. A user interruption,
587
+ The deck-wide discovery read in step 1 never counts as this authoring read. A user interruption,
458
588
  resumed turn, compaction, long wait, or unrelated tool work invalidates an earlier authoring read:
459
589
  re-list `decks/<slug>/concepts/` if needed and reopen the affected anchored files before writing.
460
590
  This batching is a local-harness context discipline, not a second create pass: the whole deck
461
591
  remains one create pass and every slide file is created exactly once. Use a zero-padded numeric
462
592
  prefix from the first file on (play order is filename order here; see the slide-file row in the
463
593
  command mapping), one default export per slide, and one bundle layout (Mode A) or blank-content
464
- layout with freeform children (Mode B), exactly as the bundle docs prescribe.
465
- 5. **Look at your own draft first (you, the agent).** This is the **draft check** in
466
- `workflow/build-and-export.md` — your pre-check, *before* any human sees the deck. Run `slidemind
467
- view-draft <deck>`: it renders each authored `slides/*.jsx` to a per-slide PNG and hands the
594
+ layout with freeform children (Mode B), exactly as the bundle docs prescribe. **A slide whose
595
+ `asset-plan.md` section lists downloaded assets is UNFINISHED until its jsx references them**
596
+ (`<img src="./assets/engine-….svg">`, sized per *Placing engine imagery* below) — a concept full
597
+ of pictograms rendered as bare text boxes is a failed rebuild, not a style choice.
598
+ 4. **Look at your own draft first (you, the agent).** This is the **draft check** in
599
+ `workflow/build-and-export.md` — your pre-check, *before* any human sees the deck. Two rules
600
+ moved early on purpose — do them NOW, not at the review gate when the run is long and attention
601
+ is spent: first run `slidemind build <deck>` once and fix every `[lint:warn]` it prints (a
602
+ mechanical pass on files you just wrote); and after any fix round below, one more `slidemind
603
+ view-draft` over the changed slides is mandatory — the verification must appear in your command
604
+ sequence, not only in prose. Run `slidemind view-draft <deck>`: it renders each authored `slides/*.jsx` to a per-slide PNG and hands the
468
605
  images back to you — **nothing is pushed, no `.pptx` is written, no review gate opens**. For
469
606
  every concept-seeded slide, Read its anchored
470
607
  `decks/<slug>/concepts/concept-slide-NN.png` and matching
@@ -479,7 +616,7 @@ From here:
479
616
  to capture, so they come back as a status line, not an image — judge those at the full-deck
480
617
  `review`/`build` step below. Do this self-check before the human review gate; don't push a draft
481
618
  you haven't looked at.
482
- 6. **The review gate — the moment the deck builds clean.** This is the **review gate** in
619
+ 5. **The review gate — the moment the deck builds clean.** This is the **review gate** in
483
620
  `workflow/build-and-export.md`; the CLI's gate command is `slidemind review <deck>`. Run it the
484
621
  instant the authored set builds clean — before any deliver, without asking whether the user wants
485
622
  a review. It builds the HTML preview first (the same lint the render enforces, so a gate that
@@ -499,11 +636,10 @@ From here:
499
636
  it rather than trusting the cited line blindly. **Edit the cited files in place at the given
500
637
  line and re-run `slidemind review <deck>` in the same turn.** **Expect several consecutive
501
638
  `DECISION: comments` rounds — that is the normal shape of a review, not an error.** The user's
502
- tab stays live while you fix: they keep browsing the preview and keep dropping pins, and those
503
- queued pins are delivered by your next run, which then returns *immediately* with them (a drain
504
- round) instead of waiting. So never end your turn on a comments round, never claim to be
505
- "polling", and never send the user back to the browser between rounds — nothing reaches them
506
- until the gate runs again. Addressed pins come back as read-only ghost pins so the user can
639
+ tab waits while you fix (browsing stays live, pinning is off) and refreshes with your next run,
640
+ which blocks until they send the next batch of pins or approve. So never end your turn on a
641
+ comments round, never claim to be "polling", and never send the user back to the browser
642
+ between rounds — nothing reaches them until the gate runs again. Addressed pins come back as read-only ghost pins so the user can
507
643
  confirm each note was worked in. Only `DECISION: approved` or `DECISION: pending` ends the
508
644
  loop. Nothing is exported on a comments round. **Every round is persisted verbatim in
509
645
  `<deck>/review.json`** — if your shell capture of the gate's output was truncated or lost
@@ -577,6 +713,29 @@ Three refusals are not foldable and need the user, not a retry:
577
713
  add-in is older than this contract, or its PowerPoint build cannot export slides. Tell the user to
578
714
  update the slidemind add-in. Do not paper over it with `--force`.
579
715
 
716
+ ## Charts (create-authoring specifics)
717
+
718
+ A real series of numbers is a `<Chart>` element in your JSX — one self-closing element that renders
719
+ as a native PowerPoint chart with its own embedded workbook, so the client double-clicks it and
720
+ edits the data in Excel. Never hand-draw a chart from divs, bars, lines or SVG, and never let a
721
+ table stand in for one; conceptual figures (process, framework, hub, timeline with no measured
722
+ values) are not charts and stay HTML/SVG. The type list, the props each type accepts, the
723
+ theme-first colour rule (leave `seriesStyle` off and the brand paints it) and the kinds that are
724
+ out of the model live in the bundle's `workflow/authoring.md` → Charts — read them there, don't
725
+ guess; the composition rule (one chart is the hero; the accent marks ONE series or point, not six)
726
+ is in `workflow/composition.md` → Charts in the composition. Three local-harness facts: numbers the
727
+ user states in chat go straight into the chart's `data` prop; this harness has **no analyst
728
+ subagent**, so when the numbers live in a file you do the aggregation yourself, say what you did,
729
+ and put the RESULT in the props (the deck carries the numbers, never a pointer to your workspace);
730
+ and both the HTML preview and `slidemind view-draft` paint a **stand-in** for a chart, not
731
+ PowerPoint's render — judge a chart's final look from the pushed slide (the review gate warns the
732
+ user on chart slides itself). Editing a chart later — yours, or one on a slide
733
+ the deck adopted from PowerPoint — is editing its `<Chart>` props and re-rendering; an adopted
734
+ chart keeps its `data-sm-source-id` and its `conversions/<stem>.slide.pptx` (never delete either:
735
+ the push patches the client's own chart part through them, so its Excel data and styling
736
+ survive). To see what a chart on a live slide plots, `slidemind read <presId> --mode raw` prints a
737
+ data table per chart; `slidemind read <file.pptx>` (host-free) reports text only, no chart data.
738
+
580
739
  ## Placing engine imagery (create-authoring specifics)
581
740
 
582
741
  Finding and fetching engine imagery is `slidemind-search`'s job (`slidemind search` → `slidemind
@@ -624,17 +783,17 @@ Vocabulary. You are the local harness — this is your mapping:
624
783
  |---|---|
625
784
  | (session setup — a CLI-only stage before the spine) | `slidemind ready [deck]` — the one-shot session start: connection ladder + design resolution (open window, the deck's own binding, or `--brand <presFP>`) + bundle materialize + deck bind. **Run it first, every session** (see *First step* above). `slidemind download-bundle` is the lower-level materialize-only command `ready` now covers — you rarely call it directly |
626
785
  | **track the stages** | your harness's task tracker — explicitly create the stage todo list before your first command and keep it current (see *Create a todo list* above) |
627
- | **clarify** / **plan sign-off** | intake stays in chat with the user (above); for decks, persist `decks/<slug>/plan.md` as `## Red thread` + `## Per-slide storyboards` (one `storyboard-canvas` JSON block per slide), then run `slidemind plan <deck>` — the same blocking `DECISION:` gate contract as `slidemind review`, on the plan (renders editable storyboards — red-thread strip + spatial canvases — plus slide-anchored comments; expect several comment rounds, some returning instantly with comments queued while you revised; loop until approved) |
628
- | concept mockups (mandatory deck stage, after plan sign-off) | `slidemind concepts <deck>` — renders one image mockup per approved-plan slide into the durable repo-relative path `decks/<slug>/concepts/concept-slide-NN.png`; immediately Read all of them for image/content search, then after searches reopen them in batches of at most 3 immediately before writing the matching `NN-*.jsx`. Re-list and reopen those paths after any interruption or continuation; never rely on an earlier chat image. The rebuild rule is owned by `workflow/create.md` → Preconditions. It never hard-fails: on an empty result (exit 0 — the add-in can't generate them) author from the storyboards alone, but for a deck you always run it. Skip only where the add-in's `!targetSlideScope` gate would — a single slide, a tiny in-chat set, or a targeted rework of existing slides |
786
+ | **clarify** / **plan sign-off** | intake stays in chat with the user (above); for every from-scratch request — one slide included — persist `decks/<slug>/plan.md` as `## Red thread` + `## Per-slide storyboards` (one `storyboard-canvas` JSON block per slide), then run `slidemind plan <deck>` — the same blocking `DECISION:` gate contract as `slidemind review`, on the plan (renders editable storyboards — red-thread strip + spatial canvases — plus slide-anchored comments; expect several comment rounds; loop until approved) |
787
+ | concept mockups (mandatory for every from-scratch set, after plan sign-off) | `slidemind concepts <deck>` — renders one image mockup per approved-plan slide into the durable repo-relative path `decks/<slug>/concepts/concept-slide-NN.png`; immediately Read all of them for image/content search, then after searches reopen them in batches of at most 3 immediately before writing the matching `NN-*.jsx`. Re-list and reopen those paths after any interruption or continuation; never rely on an earlier chat image. The rebuild rule is owned by `workflow/create.md` → Preconditions. It never hard-fails: on an empty result (exit 0 — the add-in can't generate them) author from the storyboards alone, but for anything authored from a plan — one slide included — you always run it. Skip only for targeted work on slides that already exist (edit/rework) |
629
788
  | **read** / **list** the workspace | read the files from the materialized bundle dir (`<bundle>/…`) and your `decks/<slug>/` |
630
789
  | **create / update a slide file** | write `decks/<slug>/slides/NN-<topic>.jsx` on disk with a **zero-padded numeric prefix** (`01-cover.jsx`, `02-agenda.jsx`, …) — over the CLI, "the ordered set you hand to build & push" is expressed as **numeric-aware filename order**; there is no ordered-list channel, so reordering = renaming files. For a concept-seeded create or structural rewrite, the immediately preceding tool action must Read the matching anchored concept path(s) at full detail |
631
- | brand reference samples (studied before composing) | **Read** 3 random images from the materialized bundle's `samples/` dir — the Read tool renders them (see *The create flow* step 1) |
632
790
  | **draft check** | `slidemind view-draft <deck>` — renders each `slides/*.jsx` to `decks/<slug>/.draft-preview/<slide-basename>.png` and returns the images to **you**; **no push, no `.pptx`, no review gate**. Read each concept/draft path pair together, fix the JSX, render, and pair again. A draft-only inspection does not count. Host-free once the bundle is materialized. Freeform slides only — purpose-built (Mode A) and reused native `.pptx` slides report as a status line (judge those at `review`/`build`). This is your self-check; `slidemind review` is the *human* gate |
633
791
  | **build & push** | `slidemind push <deck>` (into the open PowerPoint — the insert needs a window) · `slidemind build-pptx <deck> [--out <file>]` (to a `.pptx` file — **host-free** for a bound deck: no PowerPoint window at all) — deliver whichever target was locked at intake; both render server-side via the bridge and for a bound deck the render itself is pane-free |
634
- | **the review gate** | `slidemind review <deck>` — builds the HTML preview (lint-clean or it doesn't open), serves it with a spatial comment overlay and **blocks until the user decides**, then prints `DECISION: approved` or `DECISION: comments` (each comment cited to `slides/<file>.jsx:line:col` + the round it was dropped on). On approve → deliver (`slidemind push` / `build-pptx`); on comments → edit the cited files and re-run `slidemind review` in the same turn (addressed pins show as ghost pins); expect several comment rounds, some returning instantly with pins the user queued while you were fixing. CLI delivers happen out of the user's sight, so **every deliver follows an approved review of what it delivers — re-run `review` after any slide change**. `push`/`build-pptx` never pause; only `review` does. |
792
+ | **the review gate** | `slidemind review <deck>` — builds the HTML preview (lint-clean or it doesn't open), serves it with a spatial comment overlay and **blocks until the user decides**, then prints `DECISION: approved` or `DECISION: comments` (each comment cited to `slides/<file>.jsx:line:col` + the round it was dropped on). On approve → deliver (`slidemind push` / `build-pptx`); on comments → edit the cited files and re-run `slidemind review` in the same turn (addressed pins show as ghost pins); the user pins as many comments as they like and sends them as one batch (Approve is off while unsent pins exist); expect several comment rounds. CLI delivers happen out of the user's sight, so **every deliver follows an approved review of what it delivers — re-run `review` after any slide change**. `push`/`build-pptx` never pause; only `review` does. |
635
793
  | **inspect the deck** | `slidemind read [presId\|file.pptx] [--mode summary\|raw]` — one verb, two sources: pull the current content of an open presentation (a presId; **host-required** — it reads the live, possibly unsaved file) **or** read a local `.pptx` on disk (a file path; host-free — no PowerPoint, no pairing). Prefer the file path when the deck is saved. `summary` = per-slide outline; `raw` = each slide's plain text — to inspect what's there before editing. Plain text, not authoring markup |
636
794
  | **discover engines** (`list_engines`) | `slidemind ls engines [--type <collection\|search\|scope>] [--subtype <image\|slide\|template\|content>]` — the live catalog is the only engine list (the bundle carries none); pick an `id` from it, never guess one. Needs no PowerPoint window where the add-in serves the pane-free engine routes. It also lists **search scopes** for unfiltered corpus search — those belong to `slidemind-search`, not to imagery |
637
795
  | **engine search / fetch** | **`slidemind-search`** owns the engine search + reuse mechanics (`slidemind search` → `slidemind download-result`, plus whole-slide reuse via `add-slide`). For placing a fetched asset in your JSX, size its box from the printed `width×height`, pass `--icon-color` / batch with `--pick <n,n,…>` and colour per *Placing engine imagery* below |
796
+ | **generate an image** | `slidemind imagen "<prompt>" --deck <deck> [--out <name.png>] [--size <size>] [--quality <tier>]` — use only for a planned photograph or illustration when engine sourcing returned nothing; never generate pictograms |
638
797
  | **see** a live slide | no CLI analog — once delivered, the user is looking at the result; your visual authority runs at the draft check and the review gate instead |
639
798
 
640
799
  Everything else in `workflow/*.md` — the composition craft, the substrate/authoring rules, the