@forgeax/engine-devkit 0.1.6 → 0.1.19

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 (57) hide show
  1. package/README.md +155 -2
  2. package/dist/.tsbuildinfo +1 -1
  3. package/dist/__tests__/engine-binding.unit.test.d.ts +2 -0
  4. package/dist/__tests__/engine-binding.unit.test.d.ts.map +1 -0
  5. package/dist/__tests__/native-preview-dispatch.test.d.ts +2 -0
  6. package/dist/__tests__/native-preview-dispatch.test.d.ts.map +1 -0
  7. package/dist/__tests__/native-preview-subject-draw.unit.test.d.ts +2 -0
  8. package/dist/__tests__/native-preview-subject-draw.unit.test.d.ts.map +1 -0
  9. package/dist/__tests__/single-html-runtime.e2e.test.d.ts +2 -0
  10. package/dist/__tests__/single-html-runtime.e2e.test.d.ts.map +1 -0
  11. package/dist/__tests__/single-html.test.d.ts +2 -0
  12. package/dist/__tests__/single-html.test.d.ts.map +1 -0
  13. package/dist/__tests__/software-browser-session.unit.test.d.ts +2 -0
  14. package/dist/__tests__/software-browser-session.unit.test.d.ts.map +1 -0
  15. package/dist/__tests__/software-capture-pixels.unit.test.d.ts +2 -0
  16. package/dist/__tests__/software-capture-pixels.unit.test.d.ts.map +1 -0
  17. package/dist/__tests__/software-capture.unit.test.d.ts +2 -0
  18. package/dist/__tests__/software-capture.unit.test.d.ts.map +1 -0
  19. package/dist/bootstrap-commands.d.ts.map +1 -1
  20. package/dist/cli-output.d.ts.map +1 -1
  21. package/dist/cli.mjs +3350 -475
  22. package/dist/cli.mjs.map +1 -1
  23. package/dist/commands.d.ts +2 -0
  24. package/dist/commands.d.ts.map +1 -1
  25. package/dist/dist.d.ts +2 -2
  26. package/dist/dist.d.ts.map +1 -1
  27. package/dist/engine-binding.d.ts +58 -0
  28. package/dist/engine-binding.d.ts.map +1 -0
  29. package/dist/host.d.ts +6 -1
  30. package/dist/host.d.ts.map +1 -1
  31. package/dist/index.d.ts +10 -3
  32. package/dist/index.d.ts.map +1 -1
  33. package/dist/index.mjs +3679 -1368
  34. package/dist/index.mjs.map +1 -1
  35. package/dist/rhi-debug/cli-context.d.ts.map +1 -1
  36. package/dist/rhi-debug/operations.d.ts +3 -3
  37. package/dist/rhi-debug/operations.d.ts.map +1 -1
  38. package/dist/sdk-bootstrap.d.ts +6 -1
  39. package/dist/sdk-bootstrap.d.ts.map +1 -1
  40. package/dist/sdk-cli.mjs +35 -15
  41. package/dist/sdk-cli.mjs.map +1 -1
  42. package/dist/sdk.d.ts +1 -3
  43. package/dist/sdk.d.ts.map +1 -1
  44. package/dist/single-html.d.ts +43 -0
  45. package/dist/single-html.d.ts.map +1 -0
  46. package/dist/software-capture.d.ts +161 -0
  47. package/dist/software-capture.d.ts.map +1 -0
  48. package/dist/tools/browser-host.d.ts.map +1 -1
  49. package/dist/tools/client.d.ts.map +1 -1
  50. package/dist/tools/commands.d.ts +5 -0
  51. package/dist/tools/commands.d.ts.map +1 -1
  52. package/dist/tools/native-preview.d.ts.map +1 -1
  53. package/dist/tools/preview-contributions.d.ts +0 -5
  54. package/dist/tools/preview-contributions.d.ts.map +1 -1
  55. package/dist/types.d.ts +23 -1
  56. package/dist/types.d.ts.map +1 -1
  57. package/package.json +34 -30
package/README.md CHANGED
@@ -12,6 +12,9 @@ owns rendering, RHI events, replay backends, and preview execution.
12
12
  ## Navigation
13
13
 
14
14
  - [CLI and catalog](#cli-and-catalog)
15
+ - [Browser compositor capture](#browser-compositor-capture)
16
+ - [Engine source binding](#engine-source-binding)
17
+ - [Startup diagnostics](#startup-diagnostics)
15
18
  - [RHI-debug operations](#rhi-debug-operations)
16
19
  - [Authoring preview](#authoring-preview)
17
20
  - [Project authority](#project-authority)
@@ -22,7 +25,7 @@ owns rendering, RHI events, replay backends, and preview execution.
22
25
  The normal project commands remain available through the `forgeax` CLI:
23
26
 
24
27
  ```text
25
- forgeax new [directory] [--template empty|game-default]
28
+ forgeax new [directory] --template empty|game-3d
26
29
  forgeax init
27
30
  forgeax doctor
28
31
  forgeax skill install
@@ -30,8 +33,9 @@ forgeax skill verify
30
33
  forgeax test
31
34
  forgeax dev
32
35
  forgeax build
36
+ forgeax capture --backend auto --require-ui --output artifacts/capture/game-ui.png --json
33
37
  forgeax preview
34
- forgeax package [--output release/game-web.zip]
38
+ forgeax package [--format web-zip|single-html] [--output release/game-web.zip]
35
39
  forgeax list --json
36
40
  forgeax describe project.build --json
37
41
  forgeax run project.build --input request.json --json
@@ -73,21 +77,170 @@ The selected directory is a derived build root and is emptied before writing.
73
77
  root. An SDK-owned target fails before template copying with `project-target-inside-sdk`; use a
74
78
  sibling directory or an absolute path outside the SDK.
75
79
 
80
+ `forgeax new` requires an explicit template: choose `game-3d` for every 3D game, including custom
81
+ 3D genres, and choose `empty` otherwise. Omitting `--template` fails with `sdk-template-required`.
82
+
76
83
  `forgeax package` rebuilds with relative URLs, verifies the complete `forgeax-dist.json` closure,
77
84
  and emits a deterministic Web ZIP plus an adjacent SHA-256 file. The archive contains the bundled
78
85
  Engine JavaScript/WASM runtime and game assets at its root for HTTPS static or HTML-game hosting;
79
86
  it does not contain source, `node_modules`, or a local development server. Use `forgeax preview`
80
87
  for local HTTP acceptance. Opening the archived `index.html` through `file://` is unsupported.
81
88
 
89
+ `forgeax package --format single-html --output release/game-offline.html` emits a self-contained
90
+ single-HTML candidate and adjacent SHA-256. DevKit derives it from the same verified dist manifest,
91
+ embeds the generated module/worker/WASM/resource closure, and reports the candidate path, digest,
92
+ dist-manifest digest, and embedded asset count. The candidate is the acceptance object: open that
93
+ exact file through `file://` in the release browser profile and require zero remote requests, failed
94
+ requests, console/page errors, and resource misses before promotion. This format does not make
95
+ arbitrary dist `index.html` files or network-dependent services offline.
96
+
82
97
  `discoverRhiDebugOperations()` returns the same descriptors used by help and
83
98
  schema output. The operation manifest is the single discovery and recovery
84
99
  surface for RHI-debug.
85
100
 
101
+ ## Browser compositor capture
102
+
103
+ > [!IMPORTANT]
104
+ > forgeax capture is a development visual-evidence path. It uses the host browser adapter when
105
+ > available and can explicitly use a software lane on machines with no physical GPU or display. It
106
+ > is not a player or release-acceptance gate.
107
+
108
+ The command starts the source-development host on an ephemeral loopback port, creates an Xvfb display
109
+ when `$DISPLAY` is absent on Linux, launches a real Chromium browser, waits for an engine frame signal
110
+ and non-flat **canvas** pixels, then takes a Playwright **page screenshot**. A page screenshot
111
+ composites the WebGPU canvas with normal DOM and open ShadowRoot UI;
112
+ `canvas.toDataURL()` cannot provide that proof. `--wait-ms` is an additional settle interval after the
113
+ first non-flat canvas frame, not a guess for CPU startup time.
114
+
115
+ ```bash
116
+ forgeax capture --backend software --require-ui \
117
+ --output artifacts/capture/game-ui.png \
118
+ --width 1280 --height 720 --wait-ms 4000 --json
119
+ ```
120
+
121
+ The adjacent `game-ui.json` is the schema-v2 run manifest. Its run-level fields record the browser,
122
+ viewport, X display, lavapipe ICD discovery, and browser errors; its ordered `captures[]` rows record
123
+ each PNG digest, checkpoint, actual `GPUAdapterInfo`, canvas/UI witnesses, and canvas-only sampled luma
124
+ backend auto (the default) tries the normal browser adapter and falls back to the software lane only
125
+ when WebGPU is unavailable. backend hardware requires a non-software adapter; backend software pins
126
+ SwiftShader/lavapipe-compatible browser flags. The old --software spelling remains a compatibility
127
+ alias for backend software.
128
+
129
+ range. The witness screenshot temporarily hides every non-canvas element, so a visible HUD cannot
130
+ disguise a black 3D frame; the written PNG remains the complete page compositor output.
131
+ `--require-ui` requires at least one mounted child under the generated host's `#game-ui` root; unrelated
132
+ Engine or browser ShadowRoots are only diagnostics and cannot satisfy the gate. A uniform black frame
133
+ also fails even when canvas and adapter structure exist. Use `--browser` only when Chrome Beta is not at
134
+ `/opt/google/chrome-beta/chrome`.
135
+
136
+ The browser context fixes the viewport and screen size, DPR 1, sRGB colour profile, light colour
137
+ scheme, `en-US` locale, UTC timezone, and waits for `document.fonts.ready`. Projects must ship the same
138
+ Web font files on every machine; a system-font fallback is not a colour or layout parity contract.
139
+
140
+ For local/remote pixel or colour comparison, add `--deterministic`. The command navigates with
141
+ `?forgeaxCapture=1`. The Engine App publishes
142
+ `document.documentElement.dataset.forgeaxFrameSubmitted` (the monotonic frame id) after the Renderer
143
+ crosses its real queue-submit boundary and dispatches `forgeax:frame-submitted` on the canvas. DevKit
144
+ waits for that engine signal and a non-flat canvas crop before consuming the game's
145
+ `document.documentElement.dataset.forgeaxCaptureReady` checkpoint; it never guesses startup time. The
146
+ game remains the time authority: in capture mode it must pin its random seed, viewport-independent
147
+ state, local web fonts, and logical time/frame, render that state, then publish the ready marker. A
148
+ wall-clock delay is useful only as extra settle and is not parity evidence.
149
+
150
+ ```bash
151
+ forgeax capture --backend software --require-ui --deterministic \
152
+ --width 1280 --height 720 --output artifacts/capture/parity.png --json
153
+ ```
154
+
155
+ ### Persistent playthrough capture
156
+
157
+ `capture` is the one-shot adapter over the same browser owner. For one game boot followed by input,
158
+ assertions, and multiple compositor captures, compose the persistent session through `forgeax exec`:
159
+
160
+ ```js
161
+ export default async function playthrough({ browser }) {
162
+ const session = await browser.open({
163
+ backend: 'auto',
164
+ deterministic: true,
165
+ requireUi: true,
166
+ outputDir: 'artifacts/playthrough/boss-flow',
167
+ });
168
+ try {
169
+ const { page } = session;
170
+ await page.getByRole('button', { name: 'Start' }).click();
171
+ const spawn = await session.capture('spawn');
172
+ await page.keyboard.press('KeyW');
173
+ const arena = await session.capture('arena');
174
+ await page.getByRole('button', { name: 'Cast' }).click();
175
+ const bossHit = await session.capture('boss-hit');
176
+ return { report: session.reportPath, captures: [spawn, arena, bossHit] };
177
+ } finally {
178
+ await session.close();
179
+ }
180
+ }
181
+ ```
182
+
183
+ ```bash
184
+ forgeax exec tests/boss-playthrough.mjs --json
185
+ ```
186
+
187
+ The Engine App frame signal and the game checkpoint are separate composable authorities:
188
+ `session.capture('boss-hit')` waits for the engine frame signal, then the exact
189
+ `document.documentElement.dataset.forgeaxCaptureReady` value and non-flat pixels. Playwright remains
190
+ the input/assertion owner through the unwrapped `session.page`.
191
+ DevKit owns Xvfb/Chrome/Vite lifecycle, compositor stabilization, PNG validation, numbering, digests,
192
+ and one `run.json`. A live `Page` or session may not be returned from the program; `exec` accepts only
193
+ JSON-safe results and closes leaked sessions on exit.
194
+
195
+ | Browser backend | Owner | What it proves |
196
+ |:--|:--|:--|
197
+ | Mesa lavapipe | Dawn/Node smoke and explicit GPUTexture readback | Offscreen render pixels without a display; no HTML UI |
198
+ | Chrome hardware adapter | forgeax capture --backend hardware | Browser compositor pixels on the selected adapter plus HTML/Shadow DOM |
199
+ | Chrome SwiftShader under Xvfb | forgeax capture --backend software or forgeax exec browser session | Browser WebGPU canvas plus HTML/Shadow DOM in ordered viewport PNGs |
200
+
201
+ > [!CAUTION]
202
+ > Software pixels are iteration evidence. They do not prove physical-GPU performance, vendor-driver
203
+ > behavior, HDR-display output, or release visual acceptance.
204
+
205
+ ## Engine source binding
206
+
207
+ Built-package games normally resolve @forgeax/engine from the registry. A source-development game
208
+ can bind the same dependency name to a checked-out Engine workspace without editing its manifest:
209
+
210
+ ```bash
211
+ forgeax engine status --json
212
+ forgeax engine use-local ../forgeax-engine --json
213
+ forgeax engine doctor --json
214
+ forgeax engine unlink --json
215
+ ```
216
+
217
+ The binding is stored only in .forgeax/engine-binding.json; file absence is the single normal
218
+ registry/SDK state. The project manifest remains the dependency authority. engine doctor fails
219
+ closed for a pnpm workspace dependency that npm cannot consume, for an unbuilt local workspace, or
220
+ for a missing SDK package. Status derives its workspace digest from the actual built entry bytes and
221
+ reports their newest modification time. engine unlink removes the sole override and returns to the
222
+ normal registry/SDK resolution path.
223
+
86
224
  Physical realm consumers use `createRealmDispatch`. Each descriptor is routed to
87
225
  one owner for its declared `build`, `host`, or `engine` realm. A missing owner
88
226
  returns `tool-capability-unavailable` with the realm in `detail`; it never falls
89
227
  through to another realm.
90
228
 
229
+ ## Startup diagnostics
230
+
231
+ The generated game host renders structured startup failures recursively instead
232
+ of coercing thrown objects to `[object Object]`. It preserves `name`, `message`,
233
+ `code`, `expected`, `hint`, `reason`, and bounded nested
234
+ `cause/detail/webgpuError/wgpuError/error` fields. Generic objects use bounded
235
+ JSON serialization and circular objects receive an explicit diagnostic.
236
+
237
+ When the resulting evidence mentions WebGPU, adapter absence, or no usable
238
+ backend, the host also states that ForgeaX supports browser WebGPU and a
239
+ wgpu/WebGL2 fallback. This note is intentionally not a fallback decision: the
240
+ structured cause remains the authority. A publishing Agent must not infer
241
+ unsupported hardware, swallow the entry error, or inject a replacement Canvas
242
+ game merely to remove an uncaught exception.
243
+
91
244
  ## RHI-debug operations
92
245
 
93
246
  The operation manifest describes the complete host contract, but a standalone