Added PowerPoint templates to the Slide Assistant (#1055)

Co-authored-by: Thorsten Sommer <SommerEngineering@users.noreply.github.com>
This commit is contained in:
Sabrina-devopsandThorsten Sommer authored and GitHub committed 2026-10-25 18:52:39 +01:00
1 parent 8c5cfa78b6
commit 6eb23ebbcb
136 files changed
+16535 -522

No files matched your search

@@ -0,0 +1,79 @@
# AGENTS.md
These instructions cover the PowerPoint tools in `app/MindWork AI Studio/Tools/PowerPoint/`, with which
the Slide Assistant (`app/MindWork AI Studio/Assistants/SlideBuilder/`) plans slides for the
layouts of a template and writes PowerPoint files. They add to the `AGENTS.md` in the repository root and
to `app/AGENTS.md`, which apply here as well.
## How a presentation comes about
1. `PresentationTemplate.Read` reads a .pptx or .potx with the Open XML SDK (`DocumentFormat.OpenXml`):
its layouts, grouped into families of color variants, and the slides it carries. Without a template,
`PresentationTemplate.CreateDefault` stands in, so that one prompt and one check serve both cases.
2. `ToCatalogPrompt` and `ToTemplateSlidesPrompt` describe the layouts and the chosen template slides to
the model in words: where each slot sits, what a label belongs to, and how much text fits.
3. `SlideDeckSpec.TryParse` reads the JSON answer of the model leniently.
4. `SlideDeckSpecValidator` checks the deck against the template. Its issues are written for the model,
which gets one repair round.
5. `SlideDeckSpec.ToMarkdownOutline` shows the result as an outline, and `PresentationWriter.WriteAsync`
writes the file: a copy of the template, with its slides replaced. `PresentationFile.CreateAsync` makes
that copy in the temporary folder and streams it into the target once it is complete.
## Rules which are easy to break
- **The validator is the only gate.** `PresentationWriter` relies on a deck which passed
`SlideDeckSpecValidator`, checks nothing again, and throws when it meets what the validator should
have caught. A new rule about what fits a template belongs into the validator, worded for the model.
`SlideDeckSpecValidator.CanWrite` decides which issues leave a deck unusable at all.
- **Slot names are a contract.** The model reads and writes slots and elements by names such as
`title`, `text 2`, `label 1`, or `element 3`. The catalog (`PresentationTemplate.Catalog.cs`),
`PlaceholderRoleExtensions.TryParseSlotName`, `TemplateSlide.FindElement`, the validator, the writer,
and the outline all depend on them, so change them together. Slots are numbered per role in reading
order; the copies of a slot on a template slide continue that numbering.
- **No knowledge of a particular template.** Everything comes from the file: roles from the type and
size of a placeholder, variants from the layout names, the design from masters and layouts. Never add
the names, labels, or language of a corporate template to the code.
- **Prompt texts stay in English, the user's texts do not.** Catalog, issues, and rules are written for
the model. Every text the user reads, the outline included, goes through `T()` or `TB()`.
- **Template texts are content of a file.** This holds for the names of the layouts as well as for the
texts of the slides. They reach the model in the request, as `LAYOUTS` and `TEMPLATE_SLIDES`, never
in the system prompt, and they pass `PromptInjectionGuardService` with the reporting scope of the
request. The names of the attached pictures go with the request as well, as `PICTURES`.
- **Pictures for the slides are not source material.** The user attaches them in a zone of their own;
each goes on exactly one slide, which the validator checks. Images among the documents are source
material, which the model reads and never places. A file is never both: the pictures for the slides
win. Pictures go to the model as images only when it reads images; otherwise their names are all it has.
- **A picture library offers names, never pictures.** `PictureLibrary` reads PNG and JPEG files of a
folder, at most `MAX_LIBRARY_PICTURES`, sampled anew for every planning. Their numbers follow those
of the pictures for the slides. The names are content of a folder which others may write to, so
`PICTURE_LIBRARY` passes `PromptInjectionGuardService` like the texts of a template. A picture
counts as an icon when its name or one of its folders, the library folder included, starts with
"icon": icons may repeat, are never cropped, and never go into a backdrop
(`PresentationTemplate.IsBackdrop`), which the catalog marks and the validator checks.
- **Layout choices travel by name.** The user chooses layouts for kinds of slides (`LayoutPurpose`) by
their names, which outlive sessions and new versions of a template. `ChosenLayouts` finds them in the
template, and only their IDs go into the system prompt. The validator checks the two kinds which show
in a deck, the title slide and the start of a chapter; every other choice is a rule for the model.
A choice says which layout a kind uses, not whether the deck has one, except for the kinds with a
`PromptPlacement`: a choice for them adds such a slide, and the validator checks that a new slide uses
their layout and that an imprint comes last. Everything about a kind of slide lives in the file of its
area, `LayoutPurposeExtensions.<Area>.cs`; a new kind goes there and into `LayoutPurpose`, within its area.
- **New slides carry no formatting of their own.** They fill the placeholders of their layout and
leave out every placeholder without content, so that no prompt text such as "Click to add text"
remains. Only empty picture placeholders stay when the user asks for it
(`PresentationWriteOptions.KeepEmptyPicturePlaceholders`), for pictures of their own.
- **No copy of a file in memory.** Templates of organizations carry pictures and videos and easily reach
a hundred megabytes, and AI Studio also runs on small devices. Read templates from their file, and
let the writer edit a copy on disk. The Open XML SDK holds the compressed parts of the file in memory
while it saves, which is all it costs; a `MemoryStream` with the whole file multiplies that.
- **Write only into the file the user chose.** Inside the Flatpak, the save dialog grants access to
exactly that file, so nothing may be created, renamed, or moved next to it. Temporary files go into
the temporary folder, and the finished presentation is written over the chosen file, never moved there.
- **Removing a shape removes what only it used:** its image, chart, or diagram parts, and the animations
of its slide, see `PresentationWriter.RemoveShape`. Otherwise PowerPoint offers to repair the file.
## Tests
The tests in `app/Tests/Tools/PowerPoint/` build their templates in code with `TestTemplate`, so no
binary template is checked in. A test which writes a file also runs the `OpenXmlValidator` over it,
see `ValidationErrorsOf`.