@vgai/engine 0.5.4 → 0.5.6
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/dist/adapter/adapter-surface.d.ts +30 -0
- package/dist/adapter/adapter-surface.d.ts.map +1 -0
- package/dist/adapter/adapter-surface.js +18 -0
- package/dist/adapter/authoring.d.ts +597 -0
- package/dist/adapter/authoring.d.ts.map +1 -0
- package/dist/adapter/authoring.js +22 -0
- package/dist/adapter/colyseus-networking-adapter.d.ts +77 -0
- package/dist/adapter/colyseus-networking-adapter.d.ts.map +1 -0
- package/dist/adapter/colyseus-networking-adapter.js +76 -0
- package/dist/adapter/first-party-systems.d.ts +23 -0
- package/dist/adapter/first-party-systems.d.ts.map +1 -0
- package/dist/adapter/first-party-systems.js +196 -0
- package/dist/adapter/host-context.d.ts +194 -0
- package/dist/adapter/host-context.d.ts.map +1 -0
- package/dist/adapter/host-context.js +80 -0
- package/dist/adapter/index.d.ts +33 -0
- package/dist/adapter/index.d.ts.map +1 -0
- package/dist/adapter/index.js +25 -0
- package/dist/adapter/ingest/game-contract.d.ts +53 -0
- package/dist/adapter/ingest/game-contract.d.ts.map +1 -0
- package/dist/adapter/ingest/game-contract.js +30 -0
- package/dist/adapter/ingest/scene-capture.d.ts +121 -0
- package/dist/adapter/ingest/scene-capture.d.ts.map +1 -0
- package/dist/adapter/ingest/scene-capture.js +270 -0
- package/dist/adapter/ingest/structural-ids.d.ts +64 -0
- package/dist/adapter/ingest/structural-ids.d.ts.map +1 -0
- package/dist/adapter/ingest/structural-ids.js +110 -0
- package/dist/adapter/ingest/upstream-pin.d.ts +44 -0
- package/dist/adapter/ingest/upstream-pin.d.ts.map +1 -0
- package/dist/adapter/ingest/upstream-pin.js +47 -0
- package/dist/adapter/loop-gate-report.d.ts +34 -0
- package/dist/adapter/loop-gate-report.d.ts.map +1 -0
- package/dist/adapter/loop-gate-report.js +37 -0
- package/dist/adapter/rapier-physics-adapter.d.ts +69 -0
- package/dist/adapter/rapier-physics-adapter.d.ts.map +1 -0
- package/dist/adapter/rapier-physics-adapter.js +135 -0
- package/dist/adapter/root-adapter.d.ts +195 -0
- package/dist/adapter/root-adapter.d.ts.map +1 -0
- package/dist/adapter/root-adapter.js +25 -0
- package/dist/adapter/setup-three-root-adapter.d.ts +87 -0
- package/dist/adapter/setup-three-root-adapter.d.ts.map +1 -0
- package/dist/adapter/setup-three-root-adapter.js +791 -0
- package/dist/adapter/system-adapter.d.ts +453 -0
- package/dist/adapter/system-adapter.d.ts.map +1 -0
- package/dist/adapter/system-adapter.js +13 -0
- package/dist/adapter/transform.d.ts +18 -0
- package/dist/adapter/transform.d.ts.map +1 -0
- package/dist/adapter/transform.js +1 -0
- package/dist/ai/navigation.d.ts +78 -0
- package/dist/ai/navigation.d.ts.map +1 -0
- package/dist/ai/navigation.js +152 -0
- package/dist/animation/anim-graph-types.d.ts +25 -0
- package/dist/animation/anim-graph-types.d.ts.map +1 -0
- package/dist/animation/anim-graph-types.js +1 -0
- package/dist/animation/animation-clock.d.ts +213 -0
- package/dist/animation/animation-clock.d.ts.map +1 -0
- package/dist/animation/animation-clock.js +301 -0
- package/dist/animation/blend-node.d.ts +22 -0
- package/dist/animation/blend-node.d.ts.map +1 -0
- package/dist/animation/blend-node.js +97 -0
- package/dist/animation/camera-ownership.d.ts +249 -0
- package/dist/animation/camera-ownership.d.ts.map +1 -0
- package/dist/animation/camera-ownership.js +169 -0
- package/dist/animation/cinematic-cues.d.ts +200 -0
- package/dist/animation/cinematic-cues.d.ts.map +1 -0
- package/dist/animation/cinematic-cues.js +213 -0
- package/dist/animation/clip-map.d.ts +12 -0
- package/dist/animation/clip-map.d.ts.map +1 -0
- package/dist/animation/clip-map.js +31 -0
- package/dist/animation/cubic-spline-interpolant.d.ts +54 -0
- package/dist/animation/cubic-spline-interpolant.d.ts.map +1 -0
- package/dist/animation/cubic-spline-interpolant.js +111 -0
- package/dist/animation/theatre-clock-binding.d.ts +89 -0
- package/dist/animation/theatre-clock-binding.d.ts.map +1 -0
- package/dist/animation/theatre-clock-binding.js +29 -0
- package/dist/animation/theatre-director.d.ts +277 -0
- package/dist/animation/theatre-director.d.ts.map +1 -0
- package/dist/animation/theatre-director.js +248 -0
- package/dist/animation/theatre-object-binding.d.ts +305 -0
- package/dist/animation/theatre-object-binding.d.ts.map +1 -0
- package/dist/animation/theatre-object-binding.js +351 -0
- package/dist/animation/xstate-animation-binding.d.ts +119 -0
- package/dist/animation/xstate-animation-binding.d.ts.map +1 -0
- package/dist/animation/xstate-animation-binding.js +349 -0
- package/dist/animation/xstate-animation-meta.d.ts +266 -0
- package/dist/animation/xstate-animation-meta.d.ts.map +1 -0
- package/dist/animation/xstate-animation-meta.js +252 -0
- package/dist/asset-formats/camera.d.ts +15 -0
- package/dist/asset-formats/camera.d.ts.map +1 -0
- package/dist/asset-formats/camera.js +15 -0
- package/dist/asset-formats/collider.d.ts +21 -0
- package/dist/asset-formats/collider.d.ts.map +1 -0
- package/dist/asset-formats/collider.js +53 -0
- package/dist/asset-formats/index.d.ts +46 -0
- package/dist/asset-formats/index.d.ts.map +1 -0
- package/dist/asset-formats/index.js +36 -0
- package/dist/asset-formats/instances.d.ts +17 -0
- package/dist/asset-formats/instances.d.ts.map +1 -0
- package/dist/asset-formats/instances.js +31 -0
- package/dist/asset-formats/light.d.ts +21 -0
- package/dist/asset-formats/light.d.ts.map +1 -0
- package/dist/asset-formats/light.js +35 -0
- package/dist/asset-formats/material.d.ts +129 -0
- package/dist/asset-formats/material.d.ts.map +1 -0
- package/dist/asset-formats/material.js +88 -0
- package/dist/asset-formats/mesh.d.ts +22 -0
- package/dist/asset-formats/mesh.d.ts.map +1 -0
- package/dist/asset-formats/mesh.js +64 -0
- package/dist/asset-formats/parse.d.ts +20 -0
- package/dist/asset-formats/parse.d.ts.map +1 -0
- package/dist/asset-formats/parse.js +34 -0
- package/dist/asset-formats/particles.d.ts +1390 -0
- package/dist/asset-formats/particles.d.ts.map +1 -0
- package/dist/asset-formats/particles.js +319 -0
- package/dist/asset-formats/render-env.d.ts +387 -0
- package/dist/asset-formats/render-env.d.ts.map +1 -0
- package/dist/asset-formats/render-env.js +300 -0
- package/dist/asset-formats/tuples.d.ts +12 -0
- package/dist/asset-formats/tuples.d.ts.map +1 -0
- package/dist/asset-formats/tuples.js +14 -0
- package/dist/asset-loaders.d.ts +97 -0
- package/dist/asset-loaders.d.ts.map +1 -0
- package/dist/asset-loaders.js +209 -0
- package/dist/asset-parse-error.d.ts +24 -0
- package/dist/asset-parse-error.d.ts.map +1 -0
- package/dist/asset-parse-error.js +29 -0
- package/dist/asset-registry.d.ts +38 -0
- package/dist/asset-registry.d.ts.map +1 -0
- package/dist/asset-registry.js +66 -0
- package/dist/assets.d.ts +26 -0
- package/dist/assets.d.ts.map +1 -0
- package/dist/assets.js +55 -0
- package/dist/audio/wav-encode.d.ts +38 -0
- package/dist/audio/wav-encode.d.ts.map +1 -0
- package/dist/audio/wav-encode.js +97 -0
- package/dist/canvas-react/engine-bridge.d.ts +45 -0
- package/dist/canvas-react/engine-bridge.d.ts.map +1 -0
- package/dist/canvas-react/engine-bridge.js +45 -0
- package/dist/canvas-react/index.d.ts +42 -0
- package/dist/canvas-react/index.d.ts.map +1 -0
- package/dist/canvas-react/index.js +41 -0
- package/dist/canvas-react/pixi-primitive.d.ts +85 -0
- package/dist/canvas-react/pixi-primitive.d.ts.map +1 -0
- package/dist/canvas-react/pixi-primitive.js +181 -0
- package/dist/canvas-react/pixi-react-adapter.d.ts +71 -0
- package/dist/canvas-react/pixi-react-adapter.d.ts.map +1 -0
- package/dist/canvas-react/pixi-react-adapter.js +229 -0
- package/dist/canvas-react/pixi-react-root-factory.d.ts +56 -0
- package/dist/canvas-react/pixi-react-root-factory.d.ts.map +1 -0
- package/dist/canvas-react/pixi-react-root-factory.js +73 -0
- package/dist/canvas-react/world-context.d.ts +88 -0
- package/dist/canvas-react/world-context.d.ts.map +1 -0
- package/dist/canvas-react/world-context.js +212 -0
- package/dist/config.d.ts +9 -0
- package/dist/config.d.ts.map +1 -0
- package/dist/config.js +8 -0
- package/dist/core/frame-pacing.d.ts +90 -0
- package/dist/core/frame-pacing.d.ts.map +1 -0
- package/dist/core/frame-pacing.js +89 -0
- package/dist/core/game-loop.d.ts +62 -0
- package/dist/core/game-loop.d.ts.map +1 -0
- package/dist/core/game-loop.js +189 -0
- package/dist/core/seeded-random.d.ts +69 -0
- package/dist/core/seeded-random.d.ts.map +1 -0
- package/dist/core/seeded-random.js +121 -0
- package/dist/core/sim-clock.d.ts +199 -0
- package/dist/core/sim-clock.d.ts.map +1 -0
- package/dist/core/sim-clock.js +291 -0
- package/dist/core/system-runner.d.ts +96 -0
- package/dist/core/system-runner.d.ts.map +1 -0
- package/dist/core/system-runner.js +253 -0
- package/dist/core/types.d.ts +111 -0
- package/dist/core/types.d.ts.map +1 -0
- package/dist/core/types.js +25 -0
- package/dist/data/data-asset.d.ts +101 -0
- package/dist/data/data-asset.d.ts.map +1 -0
- package/dist/data/data-asset.js +122 -0
- package/dist/data/data-check-core.d.ts +109 -0
- package/dist/data/data-check-core.d.ts.map +1 -0
- package/dist/data/data-check-core.js +177 -0
- package/dist/data/data-ref.d.ts +79 -0
- package/dist/data/data-ref.d.ts.map +1 -0
- package/dist/data/data-ref.js +130 -0
- package/dist/data/vite-plugin-data.d.ts +79 -0
- package/dist/data/vite-plugin-data.d.ts.map +1 -0
- package/dist/data/vite-plugin-data.js +217 -0
- package/dist/defaults.d.ts +233 -0
- package/dist/defaults.d.ts.map +1 -0
- package/dist/defaults.js +137 -0
- package/dist/dev/chrome-trace.d.ts +45 -0
- package/dist/dev/chrome-trace.d.ts.map +1 -0
- package/dist/dev/chrome-trace.js +114 -0
- package/dist/dev/console-bridge.d.ts +22 -0
- package/dist/dev/console-bridge.d.ts.map +1 -0
- package/dist/dev/console-bridge.js +71 -0
- package/dist/dev/debug-draw.d.ts +24 -0
- package/dist/dev/debug-draw.d.ts.map +1 -0
- package/dist/dev/debug-draw.js +73 -0
- package/dist/dev/instruments.d.ts +133 -0
- package/dist/dev/instruments.d.ts.map +1 -0
- package/dist/dev/instruments.js +231 -0
- package/dist/dev/logger.d.ts +30 -0
- package/dist/dev/logger.d.ts.map +1 -0
- package/dist/dev/logger.js +90 -0
- package/dist/dev/performance-profiler.d.ts +111 -0
- package/dist/dev/performance-profiler.d.ts.map +1 -0
- package/dist/dev/performance-profiler.js +215 -0
- package/dist/dev/render-debug-adapter.d.ts +57 -0
- package/dist/dev/render-debug-adapter.d.ts.map +1 -0
- package/dist/dev/render-debug-adapter.js +141 -0
- package/dist/dev/render-memory.d.ts +53 -0
- package/dist/dev/render-memory.d.ts.map +1 -0
- package/dist/dev/render-memory.js +190 -0
- package/dist/dev/webgl-frame-capture.d.ts +134 -0
- package/dist/dev/webgl-frame-capture.d.ts.map +1 -0
- package/dist/dev/webgl-frame-capture.js +270 -0
- package/dist/dev/webgl-gpu-timer.d.ts +8 -0
- package/dist/dev/webgl-gpu-timer.d.ts.map +1 -0
- package/dist/dev/webgl-gpu-timer.js +52 -0
- package/dist/ecs/scene-index.d.ts +179 -0
- package/dist/ecs/scene-index.d.ts.map +1 -0
- package/dist/ecs/scene-index.js +331 -0
- package/dist/ecs/scene-query.d.ts +6 -0
- package/dist/ecs/scene-query.d.ts.map +1 -0
- package/dist/ecs/scene-query.js +40 -0
- package/dist/ecs/user-data.d.ts +193 -0
- package/dist/ecs/user-data.d.ts.map +1 -0
- package/dist/ecs/user-data.js +145 -0
- package/dist/index.d.ts +35 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +29 -0
- package/dist/input/input-manager.d.ts +944 -0
- package/dist/input/input-manager.d.ts.map +1 -0
- package/dist/input/input-manager.js +2209 -0
- package/dist/input/input-types.d.ts +174 -0
- package/dist/input/input-types.d.ts.map +1 -0
- package/dist/input/input-types.js +1 -0
- package/dist/input/prompt-labels.d.ts +21 -0
- package/dist/input/prompt-labels.d.ts.map +1 -0
- package/dist/input/prompt-labels.js +121 -0
- package/dist/input/rebind-controller.d.ts +59 -0
- package/dist/input/rebind-controller.d.ts.map +1 -0
- package/dist/input/rebind-controller.js +85 -0
- package/dist/input/schema.d.ts +16 -0
- package/dist/input/schema.d.ts.map +1 -0
- package/dist/input/schema.js +228 -0
- package/dist/loader.d.ts +76 -0
- package/dist/loader.d.ts.map +1 -0
- package/dist/loader.js +114 -0
- package/dist/manifest/editor-port.d.ts +53 -0
- package/dist/manifest/editor-port.d.ts.map +1 -0
- package/dist/manifest/editor-port.js +67 -0
- package/dist/manifest/filename.d.ts +14 -0
- package/dist/manifest/filename.d.ts.map +1 -0
- package/dist/manifest/filename.js +43 -0
- package/dist/manifest/index.d.ts +6 -0
- package/dist/manifest/index.d.ts.map +1 -0
- package/dist/manifest/index.js +9 -0
- package/dist/manifest/load-file.d.ts +7 -0
- package/dist/manifest/load-file.d.ts.map +1 -0
- package/dist/manifest/load-file.js +23 -0
- package/dist/manifest/load.d.ts +161 -0
- package/dist/manifest/load.d.ts.map +1 -0
- package/dist/manifest/load.js +269 -0
- package/dist/manifest/locate.d.ts +24 -0
- package/dist/manifest/locate.d.ts.map +1 -0
- package/dist/manifest/locate.js +48 -0
- package/dist/manifest/schema.d.ts +293 -0
- package/dist/manifest/schema.d.ts.map +1 -0
- package/dist/manifest/schema.js +633 -0
- package/dist/physics/collider-dimensions.d.ts +63 -0
- package/dist/physics/collider-dimensions.d.ts.map +1 -0
- package/dist/physics/collider-dimensions.js +98 -0
- package/dist/physics/collision-system.d.ts +41 -0
- package/dist/physics/collision-system.d.ts.map +1 -0
- package/dist/physics/collision-system.js +64 -0
- package/dist/physics/physics-registry.d.ts +45 -0
- package/dist/physics/physics-registry.d.ts.map +1 -0
- package/dist/physics/physics-registry.js +65 -0
- package/dist/physics/transform-writer.d.ts +16 -0
- package/dist/physics/transform-writer.d.ts.map +1 -0
- package/dist/physics/transform-writer.js +38 -0
- package/dist/pixi/authoring.d.ts +93 -0
- package/dist/pixi/authoring.d.ts.map +1 -0
- package/dist/pixi/authoring.js +207 -0
- package/dist/pixi/index.d.ts +16 -0
- package/dist/pixi/index.d.ts.map +1 -0
- package/dist/pixi/index.js +15 -0
- package/dist/pixi/ingest-iframe.d.ts +82 -0
- package/dist/pixi/ingest-iframe.d.ts.map +1 -0
- package/dist/pixi/ingest-iframe.js +166 -0
- package/dist/pixi/ingest.d.ts +97 -0
- package/dist/pixi/ingest.d.ts.map +1 -0
- package/dist/pixi/ingest.js +40 -0
- package/dist/pixi/physics-registry.d.ts +24 -0
- package/dist/pixi/physics-registry.d.ts.map +1 -0
- package/dist/pixi/physics-registry.js +38 -0
- package/dist/pixi/scene-capture.d.ts +43 -0
- package/dist/pixi/scene-capture.d.ts.map +1 -0
- package/dist/pixi/scene-capture.js +92 -0
- package/dist/pixi/system-adapters.d.ts +16 -0
- package/dist/pixi/system-adapters.d.ts.map +1 -0
- package/dist/pixi/system-adapters.js +37 -0
- package/dist/react/unmanaged-root-detector.d.ts +18 -0
- package/dist/react/unmanaged-root-detector.d.ts.map +1 -0
- package/dist/react/unmanaged-root-detector.js +70 -0
- package/dist/react/use-data.d.ts +60 -0
- package/dist/react/use-data.d.ts.map +1 -0
- package/dist/react/use-data.js +101 -0
- package/dist/react/use-selection.d.ts +54 -0
- package/dist/react/use-selection.d.ts.map +1 -0
- package/dist/react/use-selection.js +71 -0
- package/dist/react/world-state.d.ts +154 -0
- package/dist/react/world-state.d.ts.map +1 -0
- package/dist/react/world-state.js +220 -0
- package/dist/render/auto-batcher.d.ts +34 -0
- package/dist/render/auto-batcher.d.ts.map +1 -0
- package/dist/render/auto-batcher.js +140 -0
- package/dist/render/instance-mesh.d.ts +5 -0
- package/dist/render/instance-mesh.d.ts.map +1 -0
- package/dist/render/instance-mesh.js +19 -0
- package/dist/render/light-camera-factory.d.ts +24 -0
- package/dist/render/light-camera-factory.d.ts.map +1 -0
- package/dist/render/light-camera-factory.js +71 -0
- package/dist/render/lod.d.ts +13 -0
- package/dist/render/lod.d.ts.map +1 -0
- package/dist/render/lod.js +16 -0
- package/dist/render/material-factory.d.ts +15 -0
- package/dist/render/material-factory.d.ts.map +1 -0
- package/dist/render/material-factory.js +186 -0
- package/dist/render/mesh-shadow.d.ts +11 -0
- package/dist/render/mesh-shadow.d.ts.map +1 -0
- package/dist/render/mesh-shadow.js +19 -0
- package/dist/render/particles-factory.d.ts +99 -0
- package/dist/render/particles-factory.d.ts.map +1 -0
- package/dist/render/particles-factory.js +361 -0
- package/dist/render/render-batch-system.d.ts +33 -0
- package/dist/render/render-batch-system.d.ts.map +1 -0
- package/dist/render/render-batch-system.js +223 -0
- package/dist/render/render-features.d.ts +47 -0
- package/dist/render/render-features.d.ts.map +1 -0
- package/dist/render/render-features.js +105 -0
- package/dist/render/render-settings.d.ts +35 -0
- package/dist/render/render-settings.d.ts.map +1 -0
- package/dist/render/render-settings.js +51 -0
- package/dist/render/spark-renderer-lifecycle.d.ts +18 -0
- package/dist/render/spark-renderer-lifecycle.d.ts.map +1 -0
- package/dist/render/spark-renderer-lifecycle.js +57 -0
- package/dist/render/viewport-shading.d.ts +17 -0
- package/dist/render/viewport-shading.d.ts.map +1 -0
- package/dist/render/viewport-shading.js +87 -0
- package/dist/runtime/create-runtime.d.ts +259 -0
- package/dist/runtime/create-runtime.d.ts.map +1 -0
- package/dist/runtime/create-runtime.js +666 -0
- package/dist/runtime/debug-bridge.d.ts +288 -0
- package/dist/runtime/debug-bridge.d.ts.map +1 -0
- package/dist/runtime/debug-bridge.js +277 -0
- package/dist/runtime/debug-registry.d.ts +287 -0
- package/dist/runtime/debug-registry.d.ts.map +1 -0
- package/dist/runtime/debug-registry.js +528 -0
- package/dist/runtime/dev-layers.d.ts +34 -0
- package/dist/runtime/dev-layers.d.ts.map +1 -0
- package/dist/runtime/dev-layers.js +40 -0
- package/dist/runtime/frame-selector-cache.d.ts +41 -0
- package/dist/runtime/frame-selector-cache.d.ts.map +1 -0
- package/dist/runtime/frame-selector-cache.js +65 -0
- package/dist/runtime/game.d.ts +576 -0
- package/dist/runtime/game.d.ts.map +1 -0
- package/dist/runtime/game.js +1003 -0
- package/dist/runtime/gameplay-rng-trap.d.ts +47 -0
- package/dist/runtime/gameplay-rng-trap.d.ts.map +1 -0
- package/dist/runtime/gameplay-rng-trap.js +95 -0
- package/dist/runtime/input-router.d.ts +78 -0
- package/dist/runtime/input-router.d.ts.map +1 -0
- package/dist/runtime/input-router.js +171 -0
- package/dist/runtime/mount-game.d.ts +126 -0
- package/dist/runtime/mount-game.d.ts.map +1 -0
- package/dist/runtime/mount-game.js +159 -0
- package/dist/runtime/mount-manifest.d.ts +174 -0
- package/dist/runtime/mount-manifest.d.ts.map +1 -0
- package/dist/runtime/mount-manifest.js +304 -0
- package/dist/runtime/presentation.d.ts +85 -0
- package/dist/runtime/presentation.d.ts.map +1 -0
- package/dist/runtime/presentation.js +92 -0
- package/dist/runtime/render-audio-control.d.ts +126 -0
- package/dist/runtime/render-audio-control.d.ts.map +1 -0
- package/dist/runtime/render-audio-control.js +116 -0
- package/dist/runtime/render-control.d.ts +347 -0
- package/dist/runtime/render-control.d.ts.map +1 -0
- package/dist/runtime/render-control.js +317 -0
- package/dist/runtime/render-seed.d.ts +56 -0
- package/dist/runtime/render-seed.d.ts.map +1 -0
- package/dist/runtime/render-seed.js +73 -0
- package/dist/runtime/state-bridge.d.ts +60 -0
- package/dist/runtime/state-bridge.d.ts.map +1 -0
- package/dist/runtime/state-bridge.js +62 -0
- package/dist/runtime/types.d.ts +285 -0
- package/dist/runtime/types.d.ts.map +1 -0
- package/dist/runtime/types.js +1 -0
- package/dist/runtime/unexported-game-trap.d.ts +36 -0
- package/dist/runtime/unexported-game-trap.d.ts.map +1 -0
- package/dist/runtime/unexported-game-trap.js +80 -0
- package/dist/setup/setup-audio.d.ts +20 -0
- package/dist/setup/setup-audio.d.ts.map +1 -0
- package/dist/setup/setup-audio.js +41 -0
- package/dist/setup/setup-particles.d.ts +17 -0
- package/dist/setup/setup-particles.d.ts.map +1 -0
- package/dist/setup/setup-particles.js +16 -0
- package/dist/setup/setup-physics.d.ts +25 -0
- package/dist/setup/setup-physics.d.ts.map +1 -0
- package/dist/setup/setup-physics.js +51 -0
- package/dist/setup/setup-renderer.d.ts +82 -0
- package/dist/setup/setup-renderer.d.ts.map +1 -0
- package/dist/setup/setup-renderer.js +381 -0
- package/dist/world3d-react/engine-bridge.d.ts +47 -0
- package/dist/world3d-react/engine-bridge.d.ts.map +1 -0
- package/dist/world3d-react/engine-bridge.js +48 -0
- package/dist/world3d-react/index.d.ts +47 -0
- package/dist/world3d-react/index.d.ts.map +1 -0
- package/dist/world3d-react/index.js +46 -0
- package/dist/world3d-react/r3f-adapter.d.ts +51 -0
- package/dist/world3d-react/r3f-adapter.d.ts.map +1 -0
- package/dist/world3d-react/r3f-adapter.js +368 -0
- package/dist/world3d-react/r3f-root-factory.d.ts +62 -0
- package/dist/world3d-react/r3f-root-factory.d.ts.map +1 -0
- package/dist/world3d-react/r3f-root-factory.js +79 -0
- package/dist/world3d-react/rapier-physics-bridge.d.ts +76 -0
- package/dist/world3d-react/rapier-physics-bridge.d.ts.map +1 -0
- package/dist/world3d-react/rapier-physics-bridge.js +120 -0
- package/dist/world3d-react/renderer-config.d.ts +58 -0
- package/dist/world3d-react/renderer-config.d.ts.map +1 -0
- package/dist/world3d-react/renderer-config.js +96 -0
- package/dist/world3d-react/world-context.d.ts +123 -0
- package/dist/world3d-react/world-context.d.ts.map +1 -0
- package/dist/world3d-react/world-context.js +204 -0
- package/dist-config/config.js +303 -0
- package/dist-config/config.js.map +7 -0
- package/package.json +14 -3
- package/src/adapter/rapier-physics-adapter.ts +77 -34
- package/src/config.ts +8 -0
- package/src/core/frame-pacing.ts +26 -0
- package/src/core/game-loop.ts +4 -3
- package/src/dev/instruments.ts +302 -0
- package/src/runtime/mount-game.ts +6 -0
- package/src/runtime/unexported-game-trap.ts +82 -0
- package/src/setup/setup-renderer.ts +2 -0
- package/src/world3d-react/index.ts +9 -0
- package/src/world3d-react/rapier-physics-bridge.tsx +137 -0
|
@@ -0,0 +1,85 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* runtime/presentation.ts — how a game with a DECLARED resolution is presented in a host panel.
|
|
3
|
+
*
|
|
4
|
+
* `vgai.project.json`'s `resolution` is the game's own LOGICAL size: the coordinate space its
|
|
5
|
+
* cameras frame, its DOM overlay lays out in, and its 2D worlds author positions against. A host
|
|
6
|
+
* panel is whatever size the user dragged it to, and the two are not the same number.
|
|
7
|
+
*
|
|
8
|
+
* The rule, and it is the whole module:
|
|
9
|
+
*
|
|
10
|
+
* **A declared resolution is rendered AT that resolution, and the RESULT is scaled uniformly to
|
|
11
|
+
* fit the panel, centered, letterboxed.**
|
|
12
|
+
*
|
|
13
|
+
* That is presentation scaling — an OS scaling a game window — and deliberately NOT a stretch mode.
|
|
14
|
+
* Nothing here reflows the game, changes a camera's aspect, or re-anchors a HUD: the game renders
|
|
15
|
+
* one shape and the host draws that shape smaller or larger. Every presented root of one project
|
|
16
|
+
* (a three canvas, a pixi canvas, a dom overlay) therefore shares ONE scaled rect, which is what
|
|
17
|
+
* keeps a HUD registered over the world beneath it.
|
|
18
|
+
*
|
|
19
|
+
* A project that declares no `resolution` is unchanged: the game fills the panel and its cameras
|
|
20
|
+
* follow the panel's aspect ({@link PRESENTATION_FILL}).
|
|
21
|
+
*
|
|
22
|
+
* The math is here, alone and pure, because it had already been written twice inline (the Game
|
|
23
|
+
* panel's device-preview branch and the story preview's artboard) and a third copy would have been
|
|
24
|
+
* the one that drifted.
|
|
25
|
+
*/
|
|
26
|
+
/** A width/height pair in whatever unit the caller is working in. */
|
|
27
|
+
export interface PresentationSize {
|
|
28
|
+
readonly width: number;
|
|
29
|
+
readonly height: number;
|
|
30
|
+
}
|
|
31
|
+
/** Where a logical rect lands inside a container, scaled uniformly and centered. */
|
|
32
|
+
export interface PresentationRect {
|
|
33
|
+
/** Uniform logical→container scale factor. Always finite and > 0. */
|
|
34
|
+
readonly scale: number;
|
|
35
|
+
/** The scaled rect's size in container units. */
|
|
36
|
+
readonly width: number;
|
|
37
|
+
readonly height: number;
|
|
38
|
+
/** The letterbox margins — how far in from the container's top-left the scaled rect starts. */
|
|
39
|
+
readonly offsetX: number;
|
|
40
|
+
readonly offsetY: number;
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Fit `logical` inside `container`, preserving aspect and centering the result.
|
|
44
|
+
*
|
|
45
|
+
* `allowUpscale` is the difference between the two callers this replaces and it is not cosmetic.
|
|
46
|
+
* A DEVICE PREVIEW must never upscale — the point is to see the device's own pixels, so a phone
|
|
47
|
+
* frame in a big panel stays phone-sized. A game's DECLARED resolution must upscale, or a 720x540
|
|
48
|
+
* game sits as a postage stamp in the middle of a maximized panel and the feature reads as broken.
|
|
49
|
+
*
|
|
50
|
+
* A degenerate input (zero, negative, NaN — a panel mid-collapse, a manifest with a 0) yields
|
|
51
|
+
* `scale: 1` and a zero-offset rect rather than an Infinity that would propagate into a CSS
|
|
52
|
+
* transform.
|
|
53
|
+
*/
|
|
54
|
+
export declare function fitPresentation(container: PresentationSize, logical: PresentationSize, options?: {
|
|
55
|
+
readonly allowUpscale?: boolean;
|
|
56
|
+
}): PresentationRect;
|
|
57
|
+
/** The game fills its panel: no declared resolution, no device preset, today's behaviour. */
|
|
58
|
+
export interface PresentationFill {
|
|
59
|
+
readonly kind: 'fill';
|
|
60
|
+
}
|
|
61
|
+
/** The game renders at a fixed logical size and the host scales the result. */
|
|
62
|
+
export interface PresentationLogical {
|
|
63
|
+
readonly kind: 'logical';
|
|
64
|
+
readonly width: number;
|
|
65
|
+
readonly height: number;
|
|
66
|
+
/** `device` — a preview preset the user picked; `manifest` — the project's own `resolution`. */
|
|
67
|
+
readonly source: 'device' | 'manifest';
|
|
68
|
+
/** Device previews never upscale; a declared resolution does. See {@link fitPresentation}. */
|
|
69
|
+
readonly allowUpscale: boolean;
|
|
70
|
+
}
|
|
71
|
+
export type PresentedSize = PresentationFill | PresentationLogical;
|
|
72
|
+
export declare const PRESENTATION_FILL: PresentationFill;
|
|
73
|
+
/**
|
|
74
|
+
* Decide what size a game is presented at, from the two things that can ask for one.
|
|
75
|
+
*
|
|
76
|
+
* PRECEDENCE: an explicitly PICKED device resolution wins over the manifest's declared one. The
|
|
77
|
+
* pick is a live act by whoever is looking at the panel ("show me this on a phone"), and a project
|
|
78
|
+
* setting must not silently override it — otherwise every declared-resolution project would make
|
|
79
|
+
* the device-preview picker do nothing.
|
|
80
|
+
*/
|
|
81
|
+
export declare function resolvePresentedSize(picked: {
|
|
82
|
+
readonly width: number | null;
|
|
83
|
+
readonly height: number | null;
|
|
84
|
+
}, declared?: PresentationSize | undefined): PresentedSize;
|
|
85
|
+
//# sourceMappingURL=presentation.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"presentation.d.ts","sourceRoot":"","sources":["../../src/runtime/presentation.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;GAwBG;AAEH,qEAAqE;AACrE,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;CACzB;AAED,oFAAoF;AACpF,MAAM,WAAW,gBAAgB;IAC/B,qEAAqE;IACrE,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;IACvB,iDAAiD;IACjD,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IACxB,+FAA+F;IAC/F,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;IACzB,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;CAC1B;AAMD;;;;;;;;;;;GAWG;AACH,wBAAgB,eAAe,CAC7B,SAAS,EAAE,gBAAgB,EAC3B,OAAO,EAAE,gBAAgB,EACzB,OAAO,GAAE;IAAE,QAAQ,CAAC,YAAY,CAAC,EAAE,OAAO,CAAA;CAAO,GAChD,gBAAgB,CAmBlB;AAED,6FAA6F;AAC7F,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;CACvB;AAED,+EAA+E;AAC/E,MAAM,WAAW,mBAAmB;IAClC,QAAQ,CAAC,IAAI,EAAE,SAAS,CAAC;IACzB,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IACxB,gGAAgG;IAChG,QAAQ,CAAC,MAAM,EAAE,QAAQ,GAAG,UAAU,CAAC;IACvC,8FAA8F;IAC9F,QAAQ,CAAC,YAAY,EAAE,OAAO,CAAC;CAChC;AAED,MAAM,MAAM,aAAa,GAAG,gBAAgB,GAAG,mBAAmB,CAAC;AAEnE,eAAO,MAAM,iBAAiB,EAAE,gBAAmC,CAAC;AAEpE;;;;;;;GAOG;AACH,wBAAgB,oBAAoB,CAClC,MAAM,EAAE;IAAE,QAAQ,CAAC,KAAK,EAAE,MAAM,GAAG,IAAI,CAAC;IAAC,QAAQ,CAAC,MAAM,EAAE,MAAM,GAAG,IAAI,CAAA;CAAE,EACzE,QAAQ,CAAC,EAAE,gBAAgB,GAAG,SAAS,GACtC,aAAa,CAwBf"}
|
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* runtime/presentation.ts — how a game with a DECLARED resolution is presented in a host panel.
|
|
3
|
+
*
|
|
4
|
+
* `vgai.project.json`'s `resolution` is the game's own LOGICAL size: the coordinate space its
|
|
5
|
+
* cameras frame, its DOM overlay lays out in, and its 2D worlds author positions against. A host
|
|
6
|
+
* panel is whatever size the user dragged it to, and the two are not the same number.
|
|
7
|
+
*
|
|
8
|
+
* The rule, and it is the whole module:
|
|
9
|
+
*
|
|
10
|
+
* **A declared resolution is rendered AT that resolution, and the RESULT is scaled uniformly to
|
|
11
|
+
* fit the panel, centered, letterboxed.**
|
|
12
|
+
*
|
|
13
|
+
* That is presentation scaling — an OS scaling a game window — and deliberately NOT a stretch mode.
|
|
14
|
+
* Nothing here reflows the game, changes a camera's aspect, or re-anchors a HUD: the game renders
|
|
15
|
+
* one shape and the host draws that shape smaller or larger. Every presented root of one project
|
|
16
|
+
* (a three canvas, a pixi canvas, a dom overlay) therefore shares ONE scaled rect, which is what
|
|
17
|
+
* keeps a HUD registered over the world beneath it.
|
|
18
|
+
*
|
|
19
|
+
* A project that declares no `resolution` is unchanged: the game fills the panel and its cameras
|
|
20
|
+
* follow the panel's aspect ({@link PRESENTATION_FILL}).
|
|
21
|
+
*
|
|
22
|
+
* The math is here, alone and pure, because it had already been written twice inline (the Game
|
|
23
|
+
* panel's device-preview branch and the story preview's artboard) and a third copy would have been
|
|
24
|
+
* the one that drifted.
|
|
25
|
+
*/
|
|
26
|
+
function positiveOrZero(value) {
|
|
27
|
+
return Number.isFinite(value) && value > 0 ? value : 0;
|
|
28
|
+
}
|
|
29
|
+
/**
|
|
30
|
+
* Fit `logical` inside `container`, preserving aspect and centering the result.
|
|
31
|
+
*
|
|
32
|
+
* `allowUpscale` is the difference between the two callers this replaces and it is not cosmetic.
|
|
33
|
+
* A DEVICE PREVIEW must never upscale — the point is to see the device's own pixels, so a phone
|
|
34
|
+
* frame in a big panel stays phone-sized. A game's DECLARED resolution must upscale, or a 720x540
|
|
35
|
+
* game sits as a postage stamp in the middle of a maximized panel and the feature reads as broken.
|
|
36
|
+
*
|
|
37
|
+
* A degenerate input (zero, negative, NaN — a panel mid-collapse, a manifest with a 0) yields
|
|
38
|
+
* `scale: 1` and a zero-offset rect rather than an Infinity that would propagate into a CSS
|
|
39
|
+
* transform.
|
|
40
|
+
*/
|
|
41
|
+
export function fitPresentation(container, logical, options = {}) {
|
|
42
|
+
const cw = positiveOrZero(container.width);
|
|
43
|
+
const ch = positiveOrZero(container.height);
|
|
44
|
+
const lw = positiveOrZero(logical.width);
|
|
45
|
+
const lh = positiveOrZero(logical.height);
|
|
46
|
+
if (cw === 0 || ch === 0 || lw === 0 || lh === 0) {
|
|
47
|
+
return { scale: 1, width: lw, height: lh, offsetX: 0, offsetY: 0 };
|
|
48
|
+
}
|
|
49
|
+
const raw = Math.min(cw / lw, ch / lh);
|
|
50
|
+
const scale = options.allowUpscale === true ? raw : Math.min(raw, 1);
|
|
51
|
+
const width = lw * scale;
|
|
52
|
+
const height = lh * scale;
|
|
53
|
+
return {
|
|
54
|
+
scale,
|
|
55
|
+
width,
|
|
56
|
+
height,
|
|
57
|
+
offsetX: (cw - width) / 2,
|
|
58
|
+
offsetY: (ch - height) / 2,
|
|
59
|
+
};
|
|
60
|
+
}
|
|
61
|
+
export const PRESENTATION_FILL = { kind: 'fill' };
|
|
62
|
+
/**
|
|
63
|
+
* Decide what size a game is presented at, from the two things that can ask for one.
|
|
64
|
+
*
|
|
65
|
+
* PRECEDENCE: an explicitly PICKED device resolution wins over the manifest's declared one. The
|
|
66
|
+
* pick is a live act by whoever is looking at the panel ("show me this on a phone"), and a project
|
|
67
|
+
* setting must not silently override it — otherwise every declared-resolution project would make
|
|
68
|
+
* the device-preview picker do nothing.
|
|
69
|
+
*/
|
|
70
|
+
export function resolvePresentedSize(picked, declared) {
|
|
71
|
+
if (picked.width !== null && picked.height !== null) {
|
|
72
|
+
return {
|
|
73
|
+
kind: 'logical',
|
|
74
|
+
width: picked.width,
|
|
75
|
+
height: picked.height,
|
|
76
|
+
source: 'device',
|
|
77
|
+
allowUpscale: false,
|
|
78
|
+
};
|
|
79
|
+
}
|
|
80
|
+
if (declared !== undefined &&
|
|
81
|
+
positiveOrZero(declared.width) > 0 &&
|
|
82
|
+
positiveOrZero(declared.height) > 0) {
|
|
83
|
+
return {
|
|
84
|
+
kind: 'logical',
|
|
85
|
+
width: declared.width,
|
|
86
|
+
height: declared.height,
|
|
87
|
+
source: 'manifest',
|
|
88
|
+
allowUpscale: true,
|
|
89
|
+
};
|
|
90
|
+
}
|
|
91
|
+
return PRESENTATION_FILL;
|
|
92
|
+
}
|
|
@@ -0,0 +1,126 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Render-mode AUDIO control seam (I6, "Encode and Mux" + the audio-capture
|
|
3
|
+
* half of §13 G4). This is `render-control.ts`'s sibling for the audio side:
|
|
4
|
+
* where that module publishes `window.__vgaiRender` (exact-time seeks +
|
|
5
|
+
* composited frame passes), THIS module publishes `window.__vgaiRenderAudio` —
|
|
6
|
+
* an OPT-IN surface a render-mode page installs only when it declares a score,
|
|
7
|
+
* so `vgai render-cinematic` (`packages/vgai-cli/src/render-cinematic.ts`) can
|
|
8
|
+
* detect "this cinematic has a deterministic audio track" with a single
|
|
9
|
+
* property check (`__vgaiRenderAudio?.hasAudio === true`) rather than needing
|
|
10
|
+
* a schema field threaded through every fixture.
|
|
11
|
+
*
|
|
12
|
+
* Deliberately a SEPARATE global from `__vgaiRender`/`VgaiRenderHarness`
|
|
13
|
+
* (`render-control.ts`), not an extra method bolted onto that interface:
|
|
14
|
+
* every existing render-mode page (I0's `render-cinematic` fixture, I8's
|
|
15
|
+
* `reference-cinematic`) has no score at all, and this keeps their
|
|
16
|
+
* bundles/tests completely untouched — `render-control.ts` itself is not
|
|
17
|
+
* modified by this unit.
|
|
18
|
+
*
|
|
19
|
+
* ## What this module is, and what it deliberately is not
|
|
20
|
+
*
|
|
21
|
+
* `window.__vgaiRenderAudio` is a PROTOCOL — the surface the Node-side capture
|
|
22
|
+
* driver reads through `page.evaluate`, the audio counterpart to a debug
|
|
23
|
+
* adapter. That is why it stays in the engine. Producing the samples is not a
|
|
24
|
+
* protocol, so it does not: {@link RenderAudioControlOptions.render} is
|
|
25
|
+
* supplied by the caller and hands back a native `AudioBuffer`. This module
|
|
26
|
+
* owns the render-mode gate, the WAV encoding, and the base64 wire format.
|
|
27
|
+
*
|
|
28
|
+
* It used to call `renderToneOffline` itself, which put `tone` in the engine's
|
|
29
|
+
* dependency list for a page that merely wanted to publish a global. The
|
|
30
|
+
* offline renderer moved to the `music` capability (`src/lib/music/
|
|
31
|
+
* tone-offline-render.ts`); a fixture composes the two in one line, and a page
|
|
32
|
+
* scoring with anything else — a pre-rendered WAV decoded into an
|
|
33
|
+
* `AudioBuffer`, a WebAudio `OfflineAudioContext` graph, another library —
|
|
34
|
+
* satisfies the same contract without touching Tone at all.
|
|
35
|
+
*
|
|
36
|
+
* ## Why `renderAudio` takes `(start, end)` — the offset trap
|
|
37
|
+
*
|
|
38
|
+
* An offline render of `[10, 10.72)` schedules its first event at LOCAL time
|
|
39
|
+
* 0, not absolute time 10. A render-mode page authors its score in
|
|
40
|
+
* ABSOLUTE/canonical time (e.g. "a note at the same t=1.2s the video's
|
|
41
|
+
* Director cut happens"), so whatever the caller's `render` does internally
|
|
42
|
+
* must subtract the requested range's `start` from every scheduled event time.
|
|
43
|
+
* With Tone that means building the `Tone.Offline` callback per call, closed
|
|
44
|
+
* over `start` — see `renderToneOffline`'s own doc. This was the G12 review
|
|
45
|
+
* follow-up named in the unit's build brief ("renderToneOffline gives the
|
|
46
|
+
* composition LOCAL time 0 at `start`, so your composition must close over the
|
|
47
|
+
* range/offset"); it is now the caller's to honour, and the capability's
|
|
48
|
+
* fixture shows it.
|
|
49
|
+
*
|
|
50
|
+
* ## Wire format — why WAV bytes cross as base64, not a raw sample array
|
|
51
|
+
*
|
|
52
|
+
* `page.evaluate`'s return value is JSON-serialized; a `Float32Array`/
|
|
53
|
+
* typed-array result would either fail to serialize or be coerced into a
|
|
54
|
+
* verbose `{ "0": ..., "1": ... }` object, and a plain JS number array of
|
|
55
|
+
* (potentially) hundreds of thousands of floats is slow to serialize and
|
|
56
|
+
* bloats the IPC payload. Encoding the FULL WAV file (header + 16-bit PCM
|
|
57
|
+
* data, `audio/wav-encode.ts`) to a single base64 string in-page keeps the
|
|
58
|
+
* Node-side capture driver (`render-cinematic.ts`) to one
|
|
59
|
+
* `Buffer.from(wavBase64, 'base64')` + one `writeFile` — no PCM assembly
|
|
60
|
+
* logic duplicated on the Node side at all.
|
|
61
|
+
*/
|
|
62
|
+
/** What a caller's renderer hands back: real PCM in a native `AudioBuffer`.
|
|
63
|
+
* `AudioBuffer` — not a vgai type — is the point: any offline audio path in
|
|
64
|
+
* the platform already produces one. */
|
|
65
|
+
export interface RenderedAudio {
|
|
66
|
+
readonly buffer: AudioBuffer;
|
|
67
|
+
readonly durationSeconds: number;
|
|
68
|
+
}
|
|
69
|
+
/** Render `[start, end)` (absolute/canonical seconds) offline and
|
|
70
|
+
* deterministically. The offset trap in the module doc is the renderer's to
|
|
71
|
+
* honour: identical `(start, end)` on an unchanged score must produce
|
|
72
|
+
* identical samples, since the capture driver relies on it. */
|
|
73
|
+
export type OfflineAudioRenderer = (start: number, end: number) => Promise<RenderedAudio>;
|
|
74
|
+
export interface RenderAudioControlOptions {
|
|
75
|
+
/** See {@link OfflineAudioRenderer}. With the `music` capability this is one
|
|
76
|
+
* line over `renderToneOffline`; nothing here knows or cares that it is. */
|
|
77
|
+
readonly render: OfflineAudioRenderer;
|
|
78
|
+
/** Where to publish the harness. Defaults to the real `window` — override in a unit test. */
|
|
79
|
+
readonly target?: Record<string, unknown>;
|
|
80
|
+
/** Where to read `?vgai-render=1` from. Defaults to `window.location`. */
|
|
81
|
+
readonly location?: {
|
|
82
|
+
readonly search: string;
|
|
83
|
+
};
|
|
84
|
+
}
|
|
85
|
+
/** One offline audio render, encoded as a complete WAV file — the exact
|
|
86
|
+
* shape `render-cinematic.ts`'s capture driver reads back via `page.evaluate`. */
|
|
87
|
+
export interface RenderAudioResult {
|
|
88
|
+
/** Base64 of a complete little-endian 16-bit-PCM RIFF/WAVE file (see
|
|
89
|
+
* `audio/wav-encode.ts`) — decode with `Buffer.from(wavBase64, 'base64')`. */
|
|
90
|
+
readonly wavBase64: string;
|
|
91
|
+
readonly sampleRate: number;
|
|
92
|
+
readonly channels: number;
|
|
93
|
+
readonly durationSeconds: number;
|
|
94
|
+
/** RMS/peak over the raw PCM, BEFORE 16-bit quantization — lets a caller
|
|
95
|
+
* assert "genuinely non-silent audio, not a muxed-in silent track"
|
|
96
|
+
* without re-decoding the WAV it just received. */
|
|
97
|
+
readonly rms: number;
|
|
98
|
+
readonly peak: number;
|
|
99
|
+
}
|
|
100
|
+
/** The `window.__vgaiRenderAudio` surface. Presence of this global (guarded
|
|
101
|
+
* by `hasAudio: true`, never a bare `undefined`/`false` value on a present
|
|
102
|
+
* object) IS the "this cinematic declares a score" signal `render-
|
|
103
|
+
* cinematic.ts` checks — see this module's own top doc comment. */
|
|
104
|
+
export interface VgaiRenderAudioHarness {
|
|
105
|
+
readonly hasAudio: true;
|
|
106
|
+
/** Render `[start, end)` (absolute/canonical seconds, exactly the same
|
|
107
|
+
* range `window.__vgaiRender`'s frame walk covers), returning a complete
|
|
108
|
+
* WAV file. Deterministic: identical `(start, end)` on an unchanged score
|
|
109
|
+
* produces byte-identical `wavBase64` every call — this module adds no
|
|
110
|
+
* source of nondeterminism, so the property is exactly whatever the
|
|
111
|
+
* supplied {@link OfflineAudioRenderer} guarantees (with the `music`
|
|
112
|
+
* capability, the `Tone.Offline` determinism G2 already proves). */
|
|
113
|
+
renderAudio(start: number, end: number): Promise<RenderAudioResult>;
|
|
114
|
+
}
|
|
115
|
+
/**
|
|
116
|
+
* Build (and, when render mode is actually requested, publish) the
|
|
117
|
+
* `window.__vgaiRenderAudio` harness — same AC-4-shaped production
|
|
118
|
+
* protection as `installRenderControlHarness`: even called unconditionally
|
|
119
|
+
* on every boot, this only ever constructs/attaches the harness when
|
|
120
|
+
* `isRenderModeRequested(location)` is true, so a normal production gameplay
|
|
121
|
+
* page never gets `window.__vgaiRenderAudio` (and normal play never
|
|
122
|
+
* re-renders its music through an offline context — that would be a
|
|
123
|
+
* separate, much stranger bug).
|
|
124
|
+
*/
|
|
125
|
+
export declare function installRenderAudioHarness(opts: RenderAudioControlOptions): VgaiRenderAudioHarness | undefined;
|
|
126
|
+
//# sourceMappingURL=render-audio-control.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"render-audio-control.d.ts","sourceRoot":"","sources":["../../src/runtime/render-audio-control.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA4DG;AAKH;;yCAEyC;AACzC,MAAM,WAAW,aAAa;IAC5B,QAAQ,CAAC,MAAM,EAAE,WAAW,CAAC;IAC7B,QAAQ,CAAC,eAAe,EAAE,MAAM,CAAC;CAClC;AAED;;;gEAGgE;AAChE,MAAM,MAAM,oBAAoB,GAAG,CAAC,KAAK,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,KAAK,OAAO,CAAC,aAAa,CAAC,CAAC;AAE1F,MAAM,WAAW,yBAAyB;IACxC;iFAC6E;IAC7E,QAAQ,CAAC,MAAM,EAAE,oBAAoB,CAAC;IACtC,6FAA6F;IAC7F,QAAQ,CAAC,MAAM,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAC;IAC1C,0EAA0E;IAC1E,QAAQ,CAAC,QAAQ,CAAC,EAAE;QAAE,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAA;KAAE,CAAC;CACjD;AAED;mFACmF;AACnF,MAAM,WAAW,iBAAiB;IAChC;mFAC+E;IAC/E,QAAQ,CAAC,SAAS,EAAE,MAAM,CAAC;IAC3B,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;IAC1B,QAAQ,CAAC,eAAe,EAAE,MAAM,CAAC;IACjC;;wDAEoD;IACpD,QAAQ,CAAC,GAAG,EAAE,MAAM,CAAC;IACrB,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;CACvB;AAED;;;oEAGoE;AACpE,MAAM,WAAW,sBAAsB;IACrC,QAAQ,CAAC,QAAQ,EAAE,IAAI,CAAC;IACxB;;;;;;yEAMqE;IACrE,WAAW,CAAC,KAAK,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,GAAG,OAAO,CAAC,iBAAiB,CAAC,CAAC;CACrE;AAED;;;;;;;;;GASG;AACH,wBAAgB,yBAAyB,CACvC,IAAI,EAAE,yBAAyB,GAC9B,sBAAsB,GAAG,SAAS,CA8BpC"}
|
|
@@ -0,0 +1,116 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Render-mode AUDIO control seam (I6, "Encode and Mux" + the audio-capture
|
|
3
|
+
* half of §13 G4). This is `render-control.ts`'s sibling for the audio side:
|
|
4
|
+
* where that module publishes `window.__vgaiRender` (exact-time seeks +
|
|
5
|
+
* composited frame passes), THIS module publishes `window.__vgaiRenderAudio` —
|
|
6
|
+
* an OPT-IN surface a render-mode page installs only when it declares a score,
|
|
7
|
+
* so `vgai render-cinematic` (`packages/vgai-cli/src/render-cinematic.ts`) can
|
|
8
|
+
* detect "this cinematic has a deterministic audio track" with a single
|
|
9
|
+
* property check (`__vgaiRenderAudio?.hasAudio === true`) rather than needing
|
|
10
|
+
* a schema field threaded through every fixture.
|
|
11
|
+
*
|
|
12
|
+
* Deliberately a SEPARATE global from `__vgaiRender`/`VgaiRenderHarness`
|
|
13
|
+
* (`render-control.ts`), not an extra method bolted onto that interface:
|
|
14
|
+
* every existing render-mode page (I0's `render-cinematic` fixture, I8's
|
|
15
|
+
* `reference-cinematic`) has no score at all, and this keeps their
|
|
16
|
+
* bundles/tests completely untouched — `render-control.ts` itself is not
|
|
17
|
+
* modified by this unit.
|
|
18
|
+
*
|
|
19
|
+
* ## What this module is, and what it deliberately is not
|
|
20
|
+
*
|
|
21
|
+
* `window.__vgaiRenderAudio` is a PROTOCOL — the surface the Node-side capture
|
|
22
|
+
* driver reads through `page.evaluate`, the audio counterpart to a debug
|
|
23
|
+
* adapter. That is why it stays in the engine. Producing the samples is not a
|
|
24
|
+
* protocol, so it does not: {@link RenderAudioControlOptions.render} is
|
|
25
|
+
* supplied by the caller and hands back a native `AudioBuffer`. This module
|
|
26
|
+
* owns the render-mode gate, the WAV encoding, and the base64 wire format.
|
|
27
|
+
*
|
|
28
|
+
* It used to call `renderToneOffline` itself, which put `tone` in the engine's
|
|
29
|
+
* dependency list for a page that merely wanted to publish a global. The
|
|
30
|
+
* offline renderer moved to the `music` capability (`src/lib/music/
|
|
31
|
+
* tone-offline-render.ts`); a fixture composes the two in one line, and a page
|
|
32
|
+
* scoring with anything else — a pre-rendered WAV decoded into an
|
|
33
|
+
* `AudioBuffer`, a WebAudio `OfflineAudioContext` graph, another library —
|
|
34
|
+
* satisfies the same contract without touching Tone at all.
|
|
35
|
+
*
|
|
36
|
+
* ## Why `renderAudio` takes `(start, end)` — the offset trap
|
|
37
|
+
*
|
|
38
|
+
* An offline render of `[10, 10.72)` schedules its first event at LOCAL time
|
|
39
|
+
* 0, not absolute time 10. A render-mode page authors its score in
|
|
40
|
+
* ABSOLUTE/canonical time (e.g. "a note at the same t=1.2s the video's
|
|
41
|
+
* Director cut happens"), so whatever the caller's `render` does internally
|
|
42
|
+
* must subtract the requested range's `start` from every scheduled event time.
|
|
43
|
+
* With Tone that means building the `Tone.Offline` callback per call, closed
|
|
44
|
+
* over `start` — see `renderToneOffline`'s own doc. This was the G12 review
|
|
45
|
+
* follow-up named in the unit's build brief ("renderToneOffline gives the
|
|
46
|
+
* composition LOCAL time 0 at `start`, so your composition must close over the
|
|
47
|
+
* range/offset"); it is now the caller's to honour, and the capability's
|
|
48
|
+
* fixture shows it.
|
|
49
|
+
*
|
|
50
|
+
* ## Wire format — why WAV bytes cross as base64, not a raw sample array
|
|
51
|
+
*
|
|
52
|
+
* `page.evaluate`'s return value is JSON-serialized; a `Float32Array`/
|
|
53
|
+
* typed-array result would either fail to serialize or be coerced into a
|
|
54
|
+
* verbose `{ "0": ..., "1": ... }` object, and a plain JS number array of
|
|
55
|
+
* (potentially) hundreds of thousands of floats is slow to serialize and
|
|
56
|
+
* bloats the IPC payload. Encoding the FULL WAV file (header + 16-bit PCM
|
|
57
|
+
* data, `audio/wav-encode.ts`) to a single base64 string in-page keeps the
|
|
58
|
+
* Node-side capture driver (`render-cinematic.ts`) to one
|
|
59
|
+
* `Buffer.from(wavBase64, 'base64')` + one `writeFile` — no PCM assembly
|
|
60
|
+
* logic duplicated on the Node side at all.
|
|
61
|
+
*/
|
|
62
|
+
import { encodeWav16, pcmStats } from '../audio/wav-encode';
|
|
63
|
+
import { isRenderModeRequested } from './render-control';
|
|
64
|
+
/**
|
|
65
|
+
* Build (and, when render mode is actually requested, publish) the
|
|
66
|
+
* `window.__vgaiRenderAudio` harness — same AC-4-shaped production
|
|
67
|
+
* protection as `installRenderControlHarness`: even called unconditionally
|
|
68
|
+
* on every boot, this only ever constructs/attaches the harness when
|
|
69
|
+
* `isRenderModeRequested(location)` is true, so a normal production gameplay
|
|
70
|
+
* page never gets `window.__vgaiRenderAudio` (and normal play never
|
|
71
|
+
* re-renders its music through an offline context — that would be a
|
|
72
|
+
* separate, much stranger bug).
|
|
73
|
+
*/
|
|
74
|
+
export function installRenderAudioHarness(opts) {
|
|
75
|
+
const location = opts.location ?? window.location;
|
|
76
|
+
if (!isRenderModeRequested(location))
|
|
77
|
+
return undefined;
|
|
78
|
+
const target = opts.target ?? window;
|
|
79
|
+
const { render } = opts;
|
|
80
|
+
const harness = {
|
|
81
|
+
hasAudio: true,
|
|
82
|
+
async renderAudio(start, end) {
|
|
83
|
+
const rendered = await render(start, end);
|
|
84
|
+
const channelData = [];
|
|
85
|
+
for (let ch = 0; ch < rendered.buffer.numberOfChannels; ch++) {
|
|
86
|
+
channelData.push(rendered.buffer.getChannelData(ch));
|
|
87
|
+
}
|
|
88
|
+
const wavBytes = encodeWav16({ channelData, sampleRate: rendered.buffer.sampleRate });
|
|
89
|
+
const stats = pcmStats(channelData);
|
|
90
|
+
return {
|
|
91
|
+
wavBase64: uint8ArrayToBase64(wavBytes),
|
|
92
|
+
sampleRate: rendered.buffer.sampleRate,
|
|
93
|
+
channels: rendered.buffer.numberOfChannels,
|
|
94
|
+
durationSeconds: rendered.durationSeconds,
|
|
95
|
+
rms: stats.rms,
|
|
96
|
+
peak: stats.peak,
|
|
97
|
+
};
|
|
98
|
+
},
|
|
99
|
+
};
|
|
100
|
+
target['__vgaiRenderAudio'] = harness;
|
|
101
|
+
return harness;
|
|
102
|
+
}
|
|
103
|
+
/** Browser-native base64 encode (`btoa`) over a `Uint8Array`, chunked so a
|
|
104
|
+
* multi-second stereo WAV doesn't blow `String.fromCharCode`'s argument-count
|
|
105
|
+
* limit in one call. Node has no `btoa` for arbitrary bytes reliably across
|
|
106
|
+
* versions, but this module only ever runs in the browser (render-mode
|
|
107
|
+
* pages), matching `tone-offline-render.ts`'s own "browser-only" contract. */
|
|
108
|
+
function uint8ArrayToBase64(bytes) {
|
|
109
|
+
const CHUNK_SIZE = 0x8000;
|
|
110
|
+
let binary = '';
|
|
111
|
+
for (let i = 0; i < bytes.length; i += CHUNK_SIZE) {
|
|
112
|
+
const chunk = bytes.subarray(i, i + CHUNK_SIZE);
|
|
113
|
+
binary += String.fromCharCode(...chunk);
|
|
114
|
+
}
|
|
115
|
+
return btoa(binary);
|
|
116
|
+
}
|