@pygmalionjs/pygmalion 0.8.1 → 0.9.0

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.
Files changed (129) hide show
  1. package/binding-source.d.ts +25 -0
  2. package/dist-lib/{CameraLayer-B2D29VXQ.js → CameraLayer-BdOko8XE.js} +17 -17
  3. package/dist-lib/pygmalion.js +24599 -12746
  4. package/dist-lib/{runtime-BAy8W1mJ.js → runtime-Dxb-IaLN.js} +12414 -11114
  5. package/dist-lib/style.css +1 -1
  6. package/dist-lib/testing.js +10 -10
  7. package/dist-lib/types/binding/catalog.d.ts +10 -0
  8. package/dist-lib/types/binding/contracts.d.ts +202 -0
  9. package/dist-lib/types/binding/documentCommands.d.ts +38 -0
  10. package/dist-lib/types/binding/index.d.ts +6 -0
  11. package/dist-lib/types/binding/preview.d.ts +37 -0
  12. package/dist-lib/types/binding/source.d.ts +109 -0
  13. package/dist-lib/types/binding/useDataProjection.d.ts +9 -0
  14. package/dist-lib/types/binding/validate.d.ts +8 -0
  15. package/dist-lib/types/core/runtime.d.ts +6 -0
  16. package/dist-lib/types/document/appearance.d.ts +112 -0
  17. package/dist-lib/types/document/assets.d.ts +204 -0
  18. package/dist-lib/types/document/components.d.ts +169 -0
  19. package/dist-lib/types/document/contracts.d.ts +171 -0
  20. package/dist-lib/types/document/engine.d.ts +20 -0
  21. package/dist-lib/types/document/exportSettings.d.ts +45 -0
  22. package/dist-lib/types/document/geometry.d.ts +11 -0
  23. package/dist-lib/types/document/layout.d.ts +53 -0
  24. package/dist-lib/types/document/prototype.d.ts +424 -0
  25. package/dist-lib/types/document/prototypeReferences.d.ts +3 -0
  26. package/dist-lib/types/document/richText.d.ts +185 -0
  27. package/dist-lib/types/document/styles.d.ts +216 -0
  28. package/dist-lib/types/document/svgImport.d.ts +17 -0
  29. package/dist-lib/types/document/vector.d.ts +222 -0
  30. package/dist-lib/types/editor/designCompiler.d.ts +7 -0
  31. package/dist-lib/types/editor/designImport.d.ts +7 -0
  32. package/dist-lib/types/editor/inspect.d.ts +8 -0
  33. package/dist-lib/types/editor/revisionCatalogInstall.d.ts +1 -1
  34. package/dist-lib/types/editor/screenInteractions.d.ts +3 -3
  35. package/dist-lib/types/editor/store.d.ts +1 -1
  36. package/dist-lib/types/host/project.d.ts +44 -0
  37. package/dist-lib/types/host/registryConnections.d.ts +11 -0
  38. package/dist-lib/types/host/sourceFilePlan.d.ts +15 -0
  39. package/dist-lib/types/host/sourceWriteback.d.ts +50 -0
  40. package/dist-lib/types/lib.d.ts +101 -3
  41. package/dist-lib/types/token-library/bindings.d.ts +62 -0
  42. package/dist-lib/types/token-library/contracts.d.ts +117 -0
  43. package/dist-lib/types/token-library/engine.d.ts +13 -0
  44. package/dist-lib/types/workspace/WorkspaceShell.d.ts +9 -0
  45. package/dist-lib/types/workspace/application/ApplicationWorkspace.d.ts +3 -0
  46. package/dist-lib/types/workspace/configuration.d.ts +39 -0
  47. package/dist-lib/types/workspace/contracts.d.ts +64 -0
  48. package/dist-lib/types/workspace/controller.d.ts +35 -0
  49. package/dist-lib/types/workspace/documentSessions.d.ts +42 -0
  50. package/dist-lib/types/workspace/edit/AppearancePanel.d.ts +23 -0
  51. package/dist-lib/types/workspace/edit/ArrangeLayers.d.ts +10 -0
  52. package/dist-lib/types/workspace/edit/AssetsPanel.d.ts +16 -0
  53. package/dist-lib/types/workspace/edit/CanvasGuides.d.ts +19 -0
  54. package/dist-lib/types/workspace/edit/ComponentPanel.d.ts +11 -0
  55. package/dist-lib/types/workspace/edit/DataPanel.d.ts +16 -0
  56. package/dist-lib/types/workspace/edit/DesignWorkspace.d.ts +10 -0
  57. package/dist-lib/types/workspace/edit/LayerTree.d.ts +14 -0
  58. package/dist-lib/types/workspace/edit/LayoutPanel.d.ts +13 -0
  59. package/dist-lib/types/workspace/edit/PrototypePanel.d.ts +12 -0
  60. package/dist-lib/types/workspace/edit/ScopeTransferDialog.d.ts +40 -0
  61. package/dist-lib/types/workspace/edit/SelectionHandles.d.ts +52 -0
  62. package/dist-lib/types/workspace/edit/StylesPanel.d.ts +8 -0
  63. package/dist-lib/types/workspace/edit/TextEditor.d.ts +50 -0
  64. package/dist-lib/types/workspace/edit/VectorEditor.d.ts +89 -0
  65. package/dist-lib/types/workspace/edit/VectorToolbar.d.ts +5 -0
  66. package/dist-lib/types/workspace/edit/canvasGuideModel.d.ts +102 -0
  67. package/dist-lib/types/workspace/edit/clipboard.d.ts +35 -0
  68. package/dist-lib/types/workspace/edit/duplicateMetadata.d.ts +2 -0
  69. package/dist-lib/types/workspace/edit/geometryHandles.d.ts +224 -0
  70. package/dist-lib/types/workspace/edit/layerArrangement.d.ts +39 -0
  71. package/dist-lib/types/workspace/edit/layerMoves.d.ts +44 -0
  72. package/dist-lib/types/workspace/edit/projection.d.ts +12 -0
  73. package/dist-lib/types/workspace/edit/scopeTransfer.d.ts +96 -0
  74. package/dist-lib/types/workspace/edit/textStyles.d.ts +75 -0
  75. package/dist-lib/types/workspace/edit/vectorTools.d.ts +136 -0
  76. package/dist-lib/types/workspace/legacyModeAdapter.d.ts +13 -0
  77. package/dist-lib/types/workspace/source/ResponsiveLayoutPanel.d.ts +20 -0
  78. package/dist-lib/types/workspace/source/SourceReview.d.ts +11 -0
  79. package/dist-lib/types/workspace/source/appearanceSource.d.ts +19 -0
  80. package/dist-lib/types/workspace/source/compiler.d.ts +5 -0
  81. package/dist-lib/types/workspace/source/contracts.d.ts +156 -0
  82. package/dist-lib/types/workspace/source/controller.d.ts +50 -0
  83. package/dist-lib/types/workspace/source/documentRevision.d.ts +2 -0
  84. package/dist-lib/types/workspace/source/draftPreviewClient.d.ts +13 -0
  85. package/dist-lib/types/workspace/source/draftRecipe.d.ts +30 -0
  86. package/dist-lib/types/workspace/source/flowContracts.d.ts +72 -0
  87. package/dist-lib/types/workspace/source/prototypeSource.d.ts +4 -0
  88. package/dist-lib/types/workspace/source/responsive.d.ts +13 -0
  89. package/dist-lib/types/workspace/source/responsiveContracts.d.ts +78 -0
  90. package/dist-lib/types/workspace/source/structure.d.ts +21 -0
  91. package/dist-lib/types/workspace/source/textSource.d.ts +28 -0
  92. package/dist-lib/types/workspace/tokens/TokenLibraryContext.d.ts +11 -0
  93. package/dist-lib/types/workspace/tokens/TokenLibraryWorkspace.d.ts +14 -0
  94. package/dist-lib/types/workspace/tokens/contracts.d.ts +74 -0
  95. package/dist-lib/types/workspace/tokens/controller.d.ts +44 -0
  96. package/dist-lib/types/workspace/view/PrototypePlayer.d.ts +17 -0
  97. package/dist-lib/types/workspace/view/StoryboardWorkspace.d.ts +3 -0
  98. package/dist-lib/types/workspace/view/prototypePlayback.d.ts +46 -0
  99. package/draft-preview.d.ts +54 -0
  100. package/inspect.d.ts +2 -0
  101. package/node/design-session.mjs +3 -0
  102. package/node/inspect-plugin.mjs +3 -1
  103. package/node/inspect-writeback.mjs +18 -2
  104. package/node/preview-artifact-store.mjs +10 -7
  105. package/node/source-archive.mjs +88 -0
  106. package/node/source-bindings.mjs +65 -0
  107. package/node/source-file-lock.mjs +15 -0
  108. package/node/source-file-plan.mjs +162 -0
  109. package/node/source-file-proofs.mjs +44 -0
  110. package/node/source-responsive-codec.d.mts +17 -0
  111. package/node/source-responsive-codec.mjs +133 -0
  112. package/node/source-responsive.mjs +189 -0
  113. package/node/source-structure-reconcile.mjs +186 -0
  114. package/node/source-structure-wrapper-codec.d.mts +20 -0
  115. package/node/source-structure-wrapper-codec.mjs +205 -0
  116. package/node/source-structure.mjs +404 -0
  117. package/node/token-source-references.mjs +136 -0
  118. package/node/workspace-draft-preview-plugin.mjs +70 -0
  119. package/node/workspace-draft-preview.mjs +231 -0
  120. package/node/workspace-source-identity.d.mts +1 -0
  121. package/node/workspace-source-identity.mjs +21 -0
  122. package/node/workspace-source-plan.mjs +195 -0
  123. package/package.json +52 -6
  124. package/source-files.d.ts +35 -0
  125. package/source-responsive.d.ts +10 -0
  126. package/source-structure.d.ts +155 -0
  127. package/workspace-source-plan.d.ts +44 -0
  128. package/docs/coverage-contracts.md +0 -444
  129. package/docs/screen-state-contract.md +0 -252
@@ -1,252 +0,0 @@
1
- # Screen state contract
2
-
3
- Pygmalion uses six review placements. A host must choose the placement from
4
- how the variation is reproduced, not from how different its pixels look.
5
-
6
- | Placement | Use when | Pygmalion declaration |
7
- | --- | --- | --- |
8
- | Frame | The variation is an independent task, journey checkpoint, structural composition, overlay context, or supported viewport that reviewers must navigate to directly. | `DesignScreenCase` |
9
- | Interaction state | The same booted screen has a deterministic, reversible visual endpoint, reached either directly or through a local gesture. | `ScreenStateAxisDef` with `kind: 'interaction'` and `desiredState` or `steps` |
10
- | Condition state | The same screen needs external data, network, storage, permission, media, or timing conditions before it boots. | `ScreenStateAxisDef` with `kind: 'condition'` |
11
- | Editable parameter | The variation only samples text length, row count, content, or another freely editable value and has no distinct product endpoint. | Edit mode, component props, list controls, viewport controls, or QA data |
12
- | Motion preview | The same screen continuously changes through CSS or Web Animations without becoming a new product state. | Nothing to declare: a live frame animates on its own; a capture holds the settled baseline |
13
- | Behavior | The action has no stable visual endpoint to preserve. | `DesignBehaviorScenario` or an automated interaction test |
14
-
15
- The practical test is: after reproducing the variation, is there a stable state
16
- that another reviewer should be able to select again? If yes, use a frame or a
17
- screen-state axis. If the answer is only “this value is longer” or “the request
18
- was sent,” keep it in editing or QA instead.
19
-
20
- ## Frame versus same-frame state
21
-
22
- Preserve a separate frame when at least one of these is true:
23
-
24
- - it is a named step in a user journey;
25
- - it changes the screen's primary task or structural composition;
26
- - it provides an independent review anchor that must remain visible beside
27
- another screen;
28
- - it is a supported viewport whose responsive composition must be compared.
29
-
30
- Use a same-frame axis when all of these are true:
31
-
32
- - the route, task, and main structure stay the same;
33
- - the variation is deterministic and can be recreated from the captured base;
34
- - choosing it does not depend on an undocumented sequence;
35
- - the final visual state remains visible long enough to capture.
36
-
37
- Pseudo states such as hover, keyboard focus, and pointer active are always
38
- interaction states. They must not become duplicate frames.
39
-
40
- ## Frame size
41
-
42
- The W and H controls in the frame inspector change the frame viewport, not the
43
- canvas camera. A committed size is part of the frame fingerprint and its exact
44
- capture recipe. The request carries the route, width, height, conditions,
45
- desired state, and interactions that produced that fingerprint. A returned
46
- artifact is seeded under that requested recipe instead of the authored catalog
47
- key.
48
-
49
- This distinction is observable: resizing a frame may change responsive layout,
50
- while changing canvas zoom only changes how large the same frame appears in the
51
- editor. Hosts that implement an on-demand capture adapter must apply the
52
- requested `route`, `width`, and `height` overrides before launching the capture.
53
-
54
- ## Automatic pseudo-state coverage
55
-
56
- Pygmalion discovers pseudo-state surfaces while it serializes a screen. Every
57
- rendered target matched by `:hover`, `:focus`, `:focus-visible`,
58
- `:focus-within`, or `:active` is stamped into the inert DOM preview. React
59
- hover and focus handlers are discovered from the rendered element props; the
60
- inspect transform also marks native JSX event surfaces. The right panel's
61
- variant matrix shows the chosen target as an **Elements** row with Default,
62
- Hover, Focus, and Pressed options as applicable; a filterable picker chooses
63
- the target, and picking an element with Inspect on chooses it from the canvas.
64
-
65
- Discovery does not apply a semantic or size threshold. A plain button whose
66
- only hover effect is a color, border, shadow, or opacity change belongs in the
67
- panel just as much as a title that reveals an edit affordance. Transparent hit
68
- areas are included when they occupy layout space. This makes pseudo-state
69
- coverage a property of the captured UI instead of a list each host must keep
70
- in sync by hand.
71
-
72
- Hosts still declare an interaction axis when the endpoint needs several steps,
73
- a product-specific label, or behavior beyond a pseudo gesture. If a declared
74
- axis targets the same element and pseudo action, Pygmalion suppresses that
75
- automatic duplicate. Click-driven toggles and other application states remain
76
- declared axes unless they already have their own review frame.
77
-
78
- In view-only mode, `requires.testId` is matched against the frozen preview's
79
- lightweight **reachable** test-id index as well as an imported layer tree. A
80
- test id under `display: none`, hidden visibility, zero opacity, or an inert
81
- ancestor does not qualify merely because React kept that branch mounted. This
82
- keeps right-panel state controls available without turning selection into a
83
- layer import or live boot, while hiding axes that the captured frame cannot
84
- actually reach. Legacy snapshots without a capture-time index are measured
85
- after their inert DOM mounts.
86
-
87
- ## Automatic motion coverage
88
-
89
- Pygmalion discovers visible CSS animation owners, animated pseudo elements,
90
- matching animation rules, and Web Animations API targets while it serializes a
91
- screen, and stamps every target into the inert preview. The stamps are what
92
- the capture runtime settles: finite animations at their terminal state,
93
- repeating animations at the start of their cycle. This keeps entrance motion
94
- from hiding the base UI while screenshots and visual comparisons remain
95
- repeatable, and a mounted frozen preview holds the same baseline.
96
-
97
- Motion discovery has no semantic or size threshold. Small progress dots,
98
- ordinary status indicators, shimmer bars, and full-surface animation are
99
- settled the same way. There are no playback controls in the editor: a live
100
- frame runs the real application, so its motion plays as it does in the
101
- product, and a capture is by definition still.
102
-
103
- An animation does not need duplicate frames merely to show several points in
104
- its cycle. Preserve a separate frame only when the motion ends in an independent
105
- task, journey checkpoint, structural composition, or other state that already
106
- meets the frame criteria above.
107
-
108
- ## Required axis classification
109
-
110
- `kind` is mandatory and is enforced when the editor installs the axes.
111
- `validateScreenStateAxes` is also exported for host validation gates.
112
-
113
- ```ts
114
- import type { ScreenStateAxisDef } from '@pygmalionjs/pygmalion';
115
-
116
- export const screenStateAxes: readonly ScreenStateAxisDef[] = [
117
- {
118
- id: 'editable-heading',
119
- label: 'Heading',
120
- kind: 'interaction',
121
- requires: { testId: 'editable-heading' },
122
- options: [
123
- { id: 'rest', label: 'Rest' },
124
- {
125
- id: 'hover',
126
- label: 'Hover',
127
- steps: [
128
- {
129
- action: 'hover',
130
- label: 'Hover heading',
131
- selector: '[data-testid="editable-heading"]',
132
- },
133
- ],
134
- },
135
- {
136
- id: 'editing',
137
- label: 'Editing',
138
- steps: [
139
- {
140
- action: 'click',
141
- label: 'Open heading editor',
142
- selector: '[data-testid="editable-heading"]',
143
- },
144
- {
145
- action: 'wait',
146
- label: 'Heading input is visible',
147
- selector: '[data-testid="heading-input"]',
148
- },
149
- ],
150
- },
151
- {
152
- id: 'collapsed',
153
- label: 'Collapsed',
154
- desiredState: 'collapsed',
155
- },
156
- ],
157
- },
158
- {
159
- id: 'results',
160
- label: 'Results',
161
- kind: 'condition',
162
- options: [
163
- { id: 'loaded', label: 'Loaded' },
164
- {
165
- id: 'failed',
166
- label: 'Failed',
167
- environment: {
168
- network: {
169
- conditions: [
170
- { match: '/api/results', outcome: { kind: 'fail', status: 500 } },
171
- ],
172
- },
173
- },
174
- },
175
- ],
176
- },
177
- ];
178
-
179
- <PygmalionEditor screenStateAxes={screenStateAxes} />;
180
- ```
181
-
182
- An interaction option cannot declare `environment`. Every non-base condition
183
- option must declare one. A direct `desiredState` value cannot be combined with
184
- steps or an environment on the same option. An interaction option ending in
185
- `fill` is rejected unless a later targeted `wait` proves that the input reached
186
- a distinct visual result. This keeps empty strings and maximum-length samples
187
- out of the state panel while still allowing a search input to reproduce a real
188
- empty-result state.
189
-
190
- ## Direct desired state
191
-
192
- Use direct desired state for a locally controlled endpoint whose final visual
193
- state matters more than the gestures used to reach it. Pygmalion builds a
194
- complete map from selected axes, such as `{ sidebar: 'collapsed' }`, and calls
195
- the host's `executeDesiredState` adapter after mount and before any remaining
196
- interaction steps. The map participates in capture and preview identity.
197
-
198
- The adapter must replace its whole preview state, not merge it. Pygmalion calls
199
- it with `{}` as well, so a warm iframe reused for another frame cannot retain a
200
- previous override. A typical React host exposes the map through an external
201
- store and lets each component read only its own axis. The adapter is preview
202
- infrastructure: it must not dispatch the application's production store or
203
- write persistent product state. When a reviewer uses the real control, the
204
- component should release its preview override and continue from the currently
205
- displayed value.
206
-
207
- The right-panel selection starts delivery in the same input task. Once one
208
- option has a live document, sibling direct-state options share that document:
209
- Pygmalion skips boot, route entry, gesture replay, assertions, and geometry
210
- settling, then sends the replacement map to the host adapter. The React commit
211
- is the presentation boundary; snapshot serialization may continue afterward
212
- without blocking the visible state. A live direct-state document is pinned
213
- against normal warm-pool eviction and cannot be claimed through gesture-prefix
214
- matching, because those signatures do not describe host-owned state.
215
- Sibling delivery calls the live adapter directly rather than joining the replay
216
- runner's FIFO. Frames that expose a direct-state axis also reserve their
217
- activation-warmed document from unrelated gesture prefetch and align it
218
- invisibly behind the frozen frame. The first selection can therefore reveal the
219
- already-positioned React document after its adapter commit; speculative work
220
- cannot reintroduce a queue between the panel click and that commit.
221
-
222
- Keep gesture steps when the transition itself is under review, when effects
223
- outside local render state establish the endpoint, or when the host has no safe
224
- preview-only adapter for that state.
225
-
226
- ## Scroll positions
227
-
228
- A stable scroll endpoint is an interaction state. Use a `scroll` recipe step
229
- with absolute `scrollX` and/or `scrollY` coordinates. With no selector the step
230
- restores the document viewport; a selector targets a specific overflow
231
- container. An omitted axis keeps its current position.
232
-
233
- Absolute coordinates make the endpoint repeatable in both the in-editor replay
234
- and the capture worker. A free wheel gesture remains transient until the host
235
- preserves its endpoint as a recipe. The frame inspector enumerates the document
236
- viewport and independently scrollable nested surfaces. Preserving one records
237
- both its stable selector and coordinates; the target picker keeps nested list
238
- or panel scroll distinct from the document viewport.
239
-
240
- ## Held pseudo states
241
-
242
- Recipes support `hover`, `focus-visible`, and `active` in addition to `focus`.
243
- These actions remain held through capture. The browser runner dispatches the
244
- corresponding events, the Playwright worker performs the real pointer or focus
245
- gesture, and frozen DOM previews materialize `:hover`, `:focus`,
246
- `:focus-visible`, `:focus-within`, and `:active` selectors as scoped data
247
- attributes. A DOM preview therefore preserves the same pseudo-state styling as
248
- the captured application rather than relying on the editor's current pointer.
249
-
250
- A held pseudo action must be terminal; only `wait` steps may follow it. This
251
- prevents a declaration from claiming a transient hover that a later click has
252
- already replaced.