Honesty and provenance¶
Status: PROPOSED
The DEMO TOOLPATH badge and its runtime state machine are planned in
docs/ui/ui-plan.md:38–41,256–264,277–285. The badge does not exist today.
Current demo labeling is identified separately as HOW IT IS.
The prototype can look like a production slicer while still driving a demo generator. Provenance therefore stays visible wherever a generated path can be mistaken for production output.
DEMO TOOLPATH state machine¶
PROPOSED — the badge describes the source of the currently presented path, not the executable, build, or ProductMode.
flowchart TD
N["No presented toolpath<br/>badge off"] -->|"GenerateGcode succeeds and path is presented"| D["Demo path visible<br/>DEMO TOOLPATH on"]
D -->|"ParseGcode / ParseBgcode succeeds and parsed path is presented"| X["External parsed path visible<br/>badge off"]
X -->|"GenerateGcode succeeds and path is presented"| D
D -->|"Path cleared or future real SliceModel presented"| N
X -->|"Path cleared"| N
| Event | New provenance | Badge |
|---|---|---|
| App launch / no path | None | Off |
GenerateGcode demo route succeeds and its moves become visible |
Demo-generated | On |
ParseGcode succeeds and its moves become visible |
Parsed external | Off |
ParseBgcode succeeds and its moves become visible |
Parsed external | Off |
| Load/parse/generate leaves no presented moves | None | Off |
Future production SliceModel succeeds |
Production-generated | Off |
The planned “clear on ParseGcode / ParseBgcode” rule applies when the parsed
path becomes the presented path. A failed operation must leave provenance
aligned with what remains visible: retain the old demo state if the old path is
kept, or clear to “no path” if the UI clears the viewport. It must never show a
parsed/off state over an unchanged demo path.
Warning
A parsed external file is not NPS demo output. The absence of the badge does not certify that the external G-code is production-safe; it only says NPS did not create it through the demo generator.
Where the badge appears¶
Status bar¶
PROPOSED — when demo provenance is active, the status bar includes a
persistent, high-contrast DEMO TOOLPATH chip. Transient status text cannot
push it out or overwrite it.
HOW IT IS — the shell already has a StatusText property
(src/Nps.Shell/Controls/MainWindowShell.axaml.cs:90–96) and both apps write
status text plus a separate StatusSink mirror
(src/SlicerApp/MainWindow.axaml.cs:918–921;
src/SimulatorApp/MainWindow.axaml.cs:1152–1158). The persistent badge and
summary segments are PROPOSED.
Export dialog¶
PROPOSED — when demo provenance is active, Export repeats the warning inside the dialog, next to the final action:
Contains DEMO TOOLPATH — not a production slice.
The warning remains visible after a filename is selected. It is recorded in the
Activity entry for export success/failure. The dialog writes through the
existing WriteGcodeToFile export; it does not rename or post-process the
content into a “production” result.
Parsed external G-code has the badge off and Export disabled because nothing was generated in-session. Those are independent rules: provenance controls the warning; generated-session ownership controls export availability.
Current honesty surfaces¶
The planned badge extends, rather than replaces, current labeling:
| Surface | Current behavior | Status |
|---|---|---|
| Host facade | Method is named GenerateDemoToolpath and its comment says “NOT a production slice” |
HOW IT IS (src/Nps.EngineHost/EngineSession.cs:330–336) |
| Generated G-code header | Emits demo toolpath and NOT a production slice comments |
HOW IT IS (src/Engine/engine.cpp:1308–1317) |
| Slicer status | Successful presentation includes DEMO TOOLPATH — not a production slice |
HOW IT IS (src/SlicerApp/MainWindow.axaml.cs:439–455) |
| Simulator status | Successful demo load includes DEMO TOOLPATH - not a production slice |
HOW IT IS (src/SimulatorApp/MainWindow.axaml.cs:619) |
| Persistent status badge | Not implemented | PROPOSED |
| Export-dialog warning | Not implemented | PROPOSED |
The public ABI symbol remains GenerateGcode; ABI stability is not a reason to
hide its current demo semantics.
Why this is never a compile-time flag¶
A compile-time flag answers “what was this binary built to do?” Provenance answers “where did the path visible right now come from?” The same running session can:
- generate a demo path;
- open external G-code;
- generate again with different settings;
- eventually present a future production slice.
The badge must therefore change at runtime after each successful presentation. It cannot be derived from:
- Debug versus Release configuration;
- Slicer versus Simulator ProductMode;
- whether non-planar Enable is on;
- file extension;
- the presence of the
GenerateGcodesymbol; - a one-time launch argument.
A compile-time badge would incorrectly mark parsed external G-code as demo, or fail to mark a demo path after the session changed sources.
State ownership¶
PROPOSED — the app/stage host owns a small provenance value alongside the presented toolpath snapshot:
The visible badge derives from DemoGenerated. Export reads the same value;
there is no second boolean for the dialog. Stage changes preserve it. Loading a
profile or editing settings does not change it; only replacing/clearing the
presented path does.
The engine already distinguishes generated text from parsed-source text through
separate accessors (GetLastGeneratedGcode and GetLastParsedGcode at
src/Nps.EngineHost/NpsAbi.cs:335–345), but the planned badge still belongs to
the host presentation state because the UI decides which path is visible.
Failure and transition rules¶
| Situation | Planned response |
|---|---|
| Generate fails before replacing the viewport | Preserve the prior visible path and its provenance |
| Generate succeeds with zero moves | Do not set DemoGenerated; show no-path/error state |
| Parse fails and prior path is preserved | Preserve prior provenance |
| Parse fails after the UI intentionally clears the prior path | Set provenance to None |
| Parse succeeds | Present parsed moves and set ParsedExternal in one transition |
| Stage switch | Preserve provenance |
| App restart | Start at None; do not infer from stale UI settings |
| Export fails | Keep provenance unchanged; report failure |
The state update and path presentation are one logical transaction. This avoids a badge changing before the viewport does.
Documentation tags¶
This guide uses four evidence labels:
| Tag | Meaning | Citation rule |
|---|---|---|
| HOW IT IS | Verified behavior in the current tree | Must carry file:line code citation |
| STATED | Direction recorded in a doc, ADR, bead, or memory | Cite that source; it may not be implemented |
| INFERENCE | A reading of evidence | Mark explicitly; never present it as a promise |
| PROPOSED | Planned UI contract from docs/ui/ui-plan.md |
Treat as unimplemented unless a separate HOW IT IS statement proves otherwise |
Within the UI Prototype section, PROPOSED is the default. A table row or paragraph changes to HOW IT IS only when it names existing behavior and cites current code. Existing exports used by a proposed control remain HOW IT IS exports with a PROPOSED consumer.
Do not use “works,” “available,” or imperative user instructions for a proposed control without its PROPOSED label. Do not convert a proposed ABI name into a HOW IT IS API claim.
See also¶
- Preview for export gating and the dirty banner.
- Prepare for the demo Slice CTA.
- Slicer — interaction map for current demo generation and status text.
- Simulator — interaction map for current parsed/generated playback paths.