@forgeax/engine-render 0.1.34 → 0.1.35

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 (243) hide show
  1. package/README.md +52 -3
  2. package/dist/assembly/device-feature-admission.d.ts +2 -2
  3. package/dist/assembly/host-contract.d.ts +3 -2
  4. package/dist/assembly/host-contract.d.ts.map +1 -1
  5. package/dist/assembly/recovery/renderer-recover.d.ts.map +1 -1
  6. package/dist/assembly/render-target-host.d.ts +5 -0
  7. package/dist/assembly/render-target-host.d.ts.map +1 -1
  8. package/dist/assembly/renderer-facade.d.ts.map +1 -1
  9. package/dist/assembly/webgpu-renderer.d.ts +1 -0
  10. package/dist/assembly/webgpu-renderer.d.ts.map +1 -1
  11. package/dist/authoring.mjs +2 -4
  12. package/dist/authoring.mjs.map +1 -1
  13. package/dist/chunk-3XUBWRY2.mjs +1842 -0
  14. package/dist/chunk-3XUBWRY2.mjs.map +1 -0
  15. package/dist/{chunk-UI5SFODX.mjs → chunk-G6HDNGY7.mjs} +2329 -1776
  16. package/dist/chunk-G6HDNGY7.mjs.map +1 -0
  17. package/dist/{chunk-HEB564WF.mjs → chunk-LM5IE7GF.mjs} +4 -4
  18. package/dist/{chunk-HEB564WF.mjs.map → chunk-LM5IE7GF.mjs.map} +1 -1
  19. package/dist/{chunk-MKDIT2EM.mjs → chunk-LNIUIKQ7.mjs} +143 -246
  20. package/dist/chunk-LNIUIKQ7.mjs.map +1 -0
  21. package/dist/chunk-MXTWKZO4.mjs +3268 -0
  22. package/dist/chunk-MXTWKZO4.mjs.map +1 -0
  23. package/dist/{chunk-ODZWR6JQ.mjs → chunk-MZ4C7EHF.mjs} +2042 -27
  24. package/dist/chunk-MZ4C7EHF.mjs.map +1 -0
  25. package/dist/chunk-RIPAEGI6.mjs +48 -0
  26. package/dist/chunk-RIPAEGI6.mjs.map +1 -0
  27. package/dist/{chunk-OCDLEI6I.mjs → chunk-SGPUJW3F.mjs} +117 -5
  28. package/dist/chunk-SGPUJW3F.mjs.map +1 -0
  29. package/dist/{chunk-ELJFJ2BU.mjs → chunk-X2KA6WHM.mjs} +29 -4
  30. package/dist/chunk-X2KA6WHM.mjs.map +1 -0
  31. package/dist/{chunk-BLXGONR2.mjs → chunk-XSFB7XXQ.mjs} +51 -4
  32. package/dist/chunk-XSFB7XXQ.mjs.map +1 -0
  33. package/dist/cloud/frame-context.d.ts +2 -2
  34. package/dist/cloud/frame-context.d.ts.map +1 -1
  35. package/dist/construct-renderer.mjs +810 -2073
  36. package/dist/construct-renderer.mjs.map +1 -1
  37. package/dist/device/gpu-residency.d.ts +19 -19
  38. package/dist/device/gpu-residency.d.ts.map +1 -1
  39. package/dist/errors/render.d.ts +3 -2
  40. package/dist/errors/render.d.ts.map +1 -1
  41. package/dist/extract/material-context.d.ts +7 -0
  42. package/dist/extract/material-context.d.ts.map +1 -0
  43. package/dist/features/host.d.ts +5 -0
  44. package/dist/features/host.d.ts.map +1 -1
  45. package/dist/features/plan.d.ts +2 -0
  46. package/dist/features/plan.d.ts.map +1 -1
  47. package/dist/features/types.d.ts +4 -0
  48. package/dist/features/types.d.ts.map +1 -1
  49. package/dist/glyph-text-layout-system.d.ts +1 -1
  50. package/dist/glyph-text-layout-system.d.ts.map +1 -1
  51. package/dist/gpu-driven/shadow-ownership.d.ts +3 -3
  52. package/dist/gpu-driven/shadow-ownership.d.ts.map +1 -1
  53. package/dist/ibl/frame-resources.d.ts.map +1 -1
  54. package/dist/ibl/skylight-bind-group.d.ts +4 -4
  55. package/dist/ibl/skylight-bind-group.d.ts.map +1 -1
  56. package/dist/index.d.ts +3 -0
  57. package/dist/index.d.ts.map +1 -1
  58. package/dist/index.mjs +530 -9
  59. package/dist/index.mjs.map +1 -1
  60. package/dist/instances.d.ts +3 -4
  61. package/dist/instances.d.ts.map +1 -1
  62. package/dist/internal.mjs +7 -8
  63. package/dist/internal.mjs.map +1 -1
  64. package/dist/pbr-pipeline.d.ts +3 -3
  65. package/dist/pbr-pipeline.d.ts.map +1 -1
  66. package/dist/pipeline/standard-output/lut-gpu.d.ts +2 -2
  67. package/dist/pipeline/standard-output/lut-gpu.d.ts.map +1 -1
  68. package/dist/pipeline/standard-output/resources.d.ts +2 -2
  69. package/dist/pipeline/standard-output/resources.d.ts.map +1 -1
  70. package/dist/publication/contract.d.ts +77 -0
  71. package/dist/publication/contract.d.ts.map +1 -0
  72. package/dist/publication/dependencies.d.ts +7 -0
  73. package/dist/publication/dependencies.d.ts.map +1 -0
  74. package/dist/publication/prepare-geometry.d.ts +9 -0
  75. package/dist/publication/prepare-geometry.d.ts.map +1 -0
  76. package/dist/publication/programs.d.ts +5 -0
  77. package/dist/publication/programs.d.ts.map +1 -0
  78. package/dist/publication/publisher.d.ts +33 -0
  79. package/dist/publication/publisher.d.ts.map +1 -0
  80. package/dist/publication/receiver.d.ts +29 -0
  81. package/dist/publication/receiver.d.ts.map +1 -0
  82. package/dist/publication/resource-scope.d.ts +18 -0
  83. package/dist/publication/resource-scope.d.ts.map +1 -0
  84. package/dist/publication/targets.d.ts +33 -0
  85. package/dist/publication/targets.d.ts.map +1 -0
  86. package/dist/publication/video.d.ts +5 -0
  87. package/dist/publication/video.d.ts.map +1 -0
  88. package/dist/record/fold-buckets.d.ts +3 -3
  89. package/dist/record/fold-buckets.d.ts.map +1 -1
  90. package/dist/record/frame-snapshot.d.ts +6 -6
  91. package/dist/record/frame-snapshot.d.ts.map +1 -1
  92. package/dist/record/frame.d.ts +5 -4
  93. package/dist/record/frame.d.ts.map +1 -1
  94. package/dist/record/helpers.d.ts +2 -2
  95. package/dist/record/helpers.d.ts.map +1 -1
  96. package/dist/record/main-pass-geometry.d.ts +2 -2
  97. package/dist/record/main-pass-geometry.d.ts.map +1 -1
  98. package/dist/record/main-pass-material.d.ts +7 -9
  99. package/dist/record/main-pass-material.d.ts.map +1 -1
  100. package/dist/record/main-pass-sprite-draws.d.ts +3 -16
  101. package/dist/record/main-pass-sprite-draws.d.ts.map +1 -1
  102. package/dist/record/main-pass.d.ts.map +1 -1
  103. package/dist/record/prepared-material-bindings.d.ts +3 -3
  104. package/dist/record/prepared-material-bindings.d.ts.map +1 -1
  105. package/dist/record/render-context.d.ts +2 -2
  106. package/dist/record/render-context.d.ts.map +1 -1
  107. package/dist/record/sprite-instance-buffer.d.ts +31 -0
  108. package/dist/record/sprite-instance-buffer.d.ts.map +1 -0
  109. package/dist/record/target-capture-graph.d.ts +19 -0
  110. package/dist/record/target-capture-graph.d.ts.map +1 -0
  111. package/dist/record/typed-frame-graph.d.ts +2 -13
  112. package/dist/record/typed-frame-graph.d.ts.map +1 -1
  113. package/dist/record/view-ubo.d.ts.map +1 -1
  114. package/dist/record/volume-params.d.ts +2 -2
  115. package/dist/record/volume-params.d.ts.map +1 -1
  116. package/dist/recovery/render-system-candidate.d.ts +5 -5
  117. package/dist/recovery/render-system-candidate.d.ts.map +1 -1
  118. package/dist/render-contract.d.ts +4 -1
  119. package/dist/render-contract.d.ts.map +1 -1
  120. package/dist/render-system-extract-tail.d.ts.map +1 -1
  121. package/dist/render-system-extract.d.ts +2 -0
  122. package/dist/render-system-extract.d.ts.map +1 -1
  123. package/dist/render-system-presentation.d.ts +2 -2
  124. package/dist/render-system-presentation.d.ts.map +1 -1
  125. package/dist/render-system-projections.d.ts +3 -2
  126. package/dist/render-system-projections.d.ts.map +1 -1
  127. package/dist/render-system-residency.d.ts +2 -2
  128. package/dist/render-system-residency.d.ts.map +1 -1
  129. package/dist/render-system.d.ts +3 -7
  130. package/dist/render-system.d.ts.map +1 -1
  131. package/dist/scene/render-scene.d.ts +8 -4
  132. package/dist/scene/render-scene.d.ts.map +1 -1
  133. package/dist/scene/render-source.d.ts +42 -0
  134. package/dist/scene/render-source.d.ts.map +1 -0
  135. package/dist/scene/source-systems.d.ts +6 -0
  136. package/dist/scene/source-systems.d.ts.map +1 -0
  137. package/dist/systems/skin-palette-allocator.d.ts.map +1 -1
  138. package/dist/systems/skin-palette-types.d.ts +10 -0
  139. package/dist/systems/skin-palette-types.d.ts.map +1 -1
  140. package/dist/systems/transparent-dispatch.d.ts +2 -2
  141. package/dist/systems/transparent-dispatch.d.ts.map +1 -1
  142. package/dist/systems/transparent-sort-config.d.ts +2 -1
  143. package/dist/systems/transparent-sort-config.d.ts.map +1 -1
  144. package/dist/temporal/index.mjs +6 -7
  145. package/package.json +21 -21
  146. package/src/__tests__/auto-exposure-transaction.integration.test.ts +4 -9
  147. package/src/__tests__/device-feature-admission.unit.test.ts +3 -2
  148. package/src/__tests__/gpu-driven-pbr.dawn.test.ts +3 -4
  149. package/src/__tests__/ktx2-basis-gpu-consumer.dawn.test.ts +4 -1
  150. package/src/__tests__/main-pass-material-medium-selection.unit.test.ts +0 -1
  151. package/src/__tests__/materials-standard-contract.unit.test.ts +0 -1
  152. package/src/__tests__/physical-clearcoat.integration.test.ts +23 -23
  153. package/src/__tests__/physical-material-budget.unit.test.ts +40 -0
  154. package/src/__tests__/render-error-code-owner.test-d.ts +1 -0
  155. package/src/__tests__/renderer-factory-material-contract.unit.test.ts +1 -1
  156. package/src/assembly/device-feature-admission.ts +2 -2
  157. package/src/assembly/host-contract.ts +5 -2
  158. package/src/assembly/recovery/renderer-recover.ts +9 -0
  159. package/src/assembly/render-target-host.ts +57 -47
  160. package/src/assembly/renderer-facade.ts +3 -1
  161. package/src/assembly/webgpu-ready.ts +1 -1
  162. package/src/assembly/webgpu-renderer.ts +89 -61
  163. package/src/cloud/frame-context.ts +2 -2
  164. package/src/device/gpu-residency.ts +26 -25
  165. package/src/errors/render.ts +3 -1
  166. package/src/extract/material-context.ts +21 -0
  167. package/src/features/host.ts +13 -5
  168. package/src/features/plan.ts +2 -0
  169. package/src/features/types.ts +4 -0
  170. package/src/glyph-text-layout-system.ts +2 -2
  171. package/src/gpu-driven/shadow-ownership.ts +3 -3
  172. package/src/ibl/frame-resources.ts +0 -1
  173. package/src/ibl/skylight-bind-group.ts +13 -25
  174. package/src/index.ts +9 -0
  175. package/src/instances.ts +9 -6
  176. package/src/pbr-pipeline.ts +11 -17
  177. package/src/pipeline/standard-output/lut-gpu.ts +3 -3
  178. package/src/pipeline/standard-output/resources.ts +2 -2
  179. package/src/publication/__tests__/derived-geometry.integration.test.ts +177 -0
  180. package/src/publication/__tests__/features.integration.test.ts +122 -0
  181. package/src/publication/__tests__/programs.unit.test.ts +25 -0
  182. package/src/publication/__tests__/publication.integration.test.ts +370 -0
  183. package/src/publication/__tests__/targets.integration.test.ts +120 -0
  184. package/src/publication/__tests__/video.browser.test.ts +50 -0
  185. package/src/publication/contract.ts +104 -0
  186. package/src/publication/dependencies.ts +54 -0
  187. package/src/publication/prepare-geometry.ts +94 -0
  188. package/src/publication/programs.ts +45 -0
  189. package/src/publication/publisher.ts +618 -0
  190. package/src/publication/receiver.ts +297 -0
  191. package/src/publication/resource-scope.ts +31 -0
  192. package/src/publication/targets.ts +182 -0
  193. package/src/publication/video.ts +33 -0
  194. package/src/record/__tests__/material-bg-cache.unit.test.ts +15 -1
  195. package/src/record/__tests__/sprite-material-abi.unit.test.ts +8 -10
  196. package/src/record/__tests__/video-texture-view.unit.test.ts +9 -9
  197. package/src/record/fold-buckets.ts +8 -5
  198. package/src/record/frame-snapshot.ts +6 -6
  199. package/src/record/frame.ts +42 -22
  200. package/src/record/helpers.ts +2 -2
  201. package/src/record/main-pass-geometry.ts +21 -2
  202. package/src/record/main-pass-material.ts +37 -33
  203. package/src/record/main-pass-sprite-draws.ts +6 -152
  204. package/src/record/main-pass.ts +8 -7
  205. package/src/record/prepared-material-bindings.ts +11 -6
  206. package/src/record/render-context.ts +2 -2
  207. package/src/record/shadow-pass.ts +0 -3
  208. package/src/record/sprite-instance-buffer.ts +155 -0
  209. package/src/record/target-capture-graph.ts +258 -0
  210. package/src/record/typed-frame-graph.ts +6 -206
  211. package/src/record/view-ubo.ts +1 -1
  212. package/src/record/volume-params.ts +6 -6
  213. package/src/recovery/render-system-candidate.ts +10 -10
  214. package/src/render-contract.ts +6 -1
  215. package/src/render-system-extract-tail.ts +33 -17
  216. package/src/render-system-extract.ts +2 -0
  217. package/src/render-system-presentation.ts +2 -2
  218. package/src/render-system-projections.ts +3 -2
  219. package/src/render-system-residency.ts +2 -2
  220. package/src/render-system.ts +82 -53
  221. package/src/scene/render-scene.ts +110 -100
  222. package/src/scene/render-source.ts +90 -0
  223. package/src/scene/source-systems.ts +33 -0
  224. package/src/systems/skin-palette-allocator.ts +1 -0
  225. package/src/systems/skin-palette-types.ts +11 -0
  226. package/src/systems/transparent-dispatch.ts +2 -2
  227. package/src/systems/transparent-sort-config.ts +3 -1
  228. package/dist/chunk-BLXGONR2.mjs.map +0 -1
  229. package/dist/chunk-ELJFJ2BU.mjs.map +0 -1
  230. package/dist/chunk-ILQ5MEZF.mjs +0 -32
  231. package/dist/chunk-ILQ5MEZF.mjs.map +0 -1
  232. package/dist/chunk-MKDIT2EM.mjs.map +0 -1
  233. package/dist/chunk-OCDLEI6I.mjs.map +0 -1
  234. package/dist/chunk-ODZWR6JQ.mjs.map +0 -1
  235. package/dist/chunk-RXZ3RGOU.mjs +0 -53
  236. package/dist/chunk-RXZ3RGOU.mjs.map +0 -1
  237. package/dist/chunk-SHFUFJ5N.mjs +0 -1781
  238. package/dist/chunk-SHFUFJ5N.mjs.map +0 -1
  239. package/dist/chunk-UI5SFODX.mjs.map +0 -1
  240. package/dist/chunk-UINHLCZA.mjs +0 -2389
  241. package/dist/chunk-UINHLCZA.mjs.map +0 -1
  242. package/dist/chunk-WEX45HKH.mjs +0 -1524
  243. package/dist/chunk-WEX45HKH.mjs.map +0 -1
@@ -0,0 +1,42 @@
1
+ import type { Component, EntityHandle, Query, World } from '@forgeax/engine-ecs';
2
+ import { GlobalTransform } from '@forgeax/engine-scene';
3
+ export type GlobalTransformChangeQuery = Query<readonly [typeof GlobalTransform]>;
4
+ export declare const RENDERABLE_SOURCE_COMPONENTS: readonly [Component<"ChildOf", {
5
+ parent: "entity";
6
+ }>, Component<"MeshFilter", {
7
+ readonly assetHandle: "shared<MeshAsset>";
8
+ }>, Component<"MeshRenderer", {
9
+ readonly materials: "array<shared<MaterialAsset>>";
10
+ }>, Component<"Instances", {
11
+ readonly transforms: "array<f32>";
12
+ }>, Component<"SpriteInstances", {
13
+ readonly transforms: "array<f32>";
14
+ readonly regions: "array<f32>";
15
+ }>, Component<"SpriteRegionOverride", {
16
+ readonly region: "array<f32, 4>";
17
+ }>, Component<"Skin", {
18
+ readonly skeleton: "shared<SkeletonAsset>";
19
+ readonly joints: "array<entity>";
20
+ }>, Component<"Layer", {
21
+ readonly value: "i32";
22
+ }>, Component<"Visibility", {
23
+ readonly state: "enum";
24
+ }>, Component<"MorphWeights", {
25
+ readonly weights: "array<f32>";
26
+ }>, Component<"Points", {
27
+ readonly sizePx: "f32";
28
+ readonly shape: "enum";
29
+ }>, Component<"Lines", {
30
+ readonly widthPx: "f32";
31
+ }>, Component<"SortKey", {
32
+ readonly value: "f32";
33
+ }>];
34
+ export declare function createGlobalTransformChangeQuery(world: World): GlobalTransformChangeQuery;
35
+ export declare function createRenderSourceState(world: World, additional?: readonly Component[]): {
36
+ projection: import("@forgeax/engine-ecs/projection").StateProjection;
37
+ entities: Map<number, EntityHandle>;
38
+ contentHandles: Map<number, readonly number[]>;
39
+ batch: import("@forgeax/engine-ecs/projection").StateProjectionBatch;
40
+ };
41
+ export declare function isRenderableMember(world: World, entity: number): boolean;
42
+ //# sourceMappingURL=render-source.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"render-source.d.ts","sourceRoot":"","sources":["../../src/scene/render-source.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,SAAS,EAAE,YAAY,EAAE,KAAK,EAAE,KAAK,EAAE,MAAM,qBAAqB,CAAC;AAEjF,OAAO,EAAW,eAAe,EAA2B,MAAM,uBAAuB,CAAC;AAc1F,MAAM,MAAM,0BAA0B,GAAG,KAAK,CAAC,SAAS,CAAC,OAAO,eAAe,CAAC,CAAC,CAAC;AAKlF,eAAO,MAAM,4BAA4B;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAc/B,CAAC;AACX,wBAAgB,gCAAgC,CAAC,KAAK,EAAE,KAAK,GAAG,0BAA0B,CAQzF;AAED,wBAAgB,uBAAuB,CAAC,KAAK,EAAE,KAAK,EAAE,UAAU,GAAE,SAAS,SAAS,EAAO;;;;;EAkC1F;AAED,wBAAgB,kBAAkB,CAAC,KAAK,EAAE,KAAK,EAAE,MAAM,EAAE,MAAM,GAAG,OAAO,CAMxE"}
@@ -0,0 +1,6 @@
1
+ import type { AssetRegistry } from '@forgeax/engine-assets-runtime';
2
+ import { type World } from '@forgeax/engine-ecs';
3
+ import type { GpuResidencyCache } from '../device/gpu-residency';
4
+ /** Derived authoring stays beside World; only completed mesh data reaches the Renderer. */
5
+ export declare function registerRenderSourceSystems(world: World, assets: AssetRegistry, meshes: Pick<GpuResidencyCache, 'updateMesh'>): () => void;
6
+ //# sourceMappingURL=source-systems.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"source-systems.d.ts","sourceRoot":"","sources":["../../src/scene/source-systems.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,gCAAgC,CAAC;AACpE,OAAO,EAAU,KAAK,KAAK,EAAE,MAAM,qBAAqB,CAAC;AAEzD,OAAO,KAAK,EAAE,iBAAiB,EAAE,MAAM,yBAAyB,CAAC;AAKjE,2FAA2F;AAC3F,wBAAgB,2BAA2B,CACzC,KAAK,EAAE,KAAK,EACZ,MAAM,EAAE,aAAa,EACrB,MAAM,EAAE,IAAI,CAAC,iBAAiB,EAAE,YAAY,CAAC,GAC5C,MAAM,IAAI,CAmBZ"}
@@ -1 +1 @@
1
- {"version":3,"file":"skin-palette-allocator.d.ts","sourceRoot":"","sources":["../../src/systems/skin-palette-allocator.ts"],"names":[],"mappings":"AA4CA,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,sBAAsB,CAAC;AAEjD,OAAO,KAAK,EAAU,SAAS,EAAE,MAAM,qBAAqB,CAAC;AAO7D,OAAO,KAAK,EAEV,kBAAkB,EAClB,gBAAgB,EACjB,MAAM,sBAAsB,CAAC;AAuB9B,MAAM,WAAW,oBAAoB;IACnC,mFAAmF;IACnF,QAAQ,CAAC,eAAe,EAAE,MAAM,CAAC;IACjC;;;;;OAKG;IACH,QAAQ,CAAC,kBAAkB,EAAE,MAAM,CAAC;IACpC;;;;;;OAMG;IACH,QAAQ,CAAC,gBAAgB,EAAE,OAAO,CAAC;IACnC,+EAA+E;IAC/E,uBAAuB,CAAC,KAAK,EAAE;QAC7B,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;QAC1B,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;QAC5B,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;QAC5B,QAAQ,CAAC,MAAM,CAAC,EAAE,YAAY,CAAC;KAChC,GAAG,kBAAkB,CAAC;IACvB;;;;OAIG;IACH,uBAAuB,CACrB,QAAQ,EAAE,MAAM,EAChB,IAAI,EAAE,SAAS,YAAY,EAAE,EAC7B,WAAW,EAAE,SAAS,IAAI,EAAE,GAC3B,SAAS,MAAM,EAAE,CAAC;IACrB,+EAA+E;IAC/E,eAAe,CAAC,QAAQ,EAAE,MAAM,EAAE,MAAM,EAAE,SAAS,MAAM,EAAE,GAAG,IAAI,CAAC;IACnE,0EAA0E;IAC1E,UAAU,IAAI,IAAI,CAAC;IACnB,sEAAsE;IACtE,QAAQ,IAAI,IAAI,CAAC;IACjB,uEAAuE;IACvE,sBAAsB,CAAC,QAAQ,EAAE,MAAM,GAAG,IAAI,CAAC;IAC/C;;;;;;;;;;OAUG;IACH,aAAa,CAAC,UAAU,EAAE,MAAM,GAAG,gBAAgB,CAAC;IACpD;;;;;;;;OAQG;IACH,iBAAiB,CACf,KAAK,EAAE,gBAAgB,EACvB,IAAI,EAAE,SAAS,YAAY,EAAE,EAC7B,WAAW,EAAE,SAAS,IAAI,EAAE,GAC3B,IAAI,CAAC;IACR,mEAAmE;IACnE,2BAA2B,CACzB,OAAO,EAAE,kBAAkB,EAC3B,IAAI,EAAE,SAAS,YAAY,EAAE,EAC7B,WAAW,EAAE,SAAS,IAAI,EAAE,GAC3B,IAAI,CAAC;IACR;;;;OAIG;IACH,aAAa,IAAI,IAAI,CAAC;IACtB,wEAAwE;IACxE,OAAO,IAAI,IAAI,CAAC;CACjB;AAED,wBAAgB,0BAA0B,CACxC,MAAM,EAAE,SAAS,EACjB,cAAc,EAAE,MAAM,EACtB,gBAAgB,UAAO,GACtB,oBAAoB,CAyiBtB"}
1
+ {"version":3,"file":"skin-palette-allocator.d.ts","sourceRoot":"","sources":["../../src/systems/skin-palette-allocator.ts"],"names":[],"mappings":"AA4CA,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,sBAAsB,CAAC;AAEjD,OAAO,KAAK,EAAU,SAAS,EAAE,MAAM,qBAAqB,CAAC;AAO7D,OAAO,KAAK,EAEV,kBAAkB,EAClB,gBAAgB,EACjB,MAAM,sBAAsB,CAAC;AAuB9B,MAAM,WAAW,oBAAoB;IACnC,mFAAmF;IACnF,QAAQ,CAAC,eAAe,EAAE,MAAM,CAAC;IACjC;;;;;OAKG;IACH,QAAQ,CAAC,kBAAkB,EAAE,MAAM,CAAC;IACpC;;;;;;OAMG;IACH,QAAQ,CAAC,gBAAgB,EAAE,OAAO,CAAC;IACnC,+EAA+E;IAC/E,uBAAuB,CAAC,KAAK,EAAE;QAC7B,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;QAC1B,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;QAC5B,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;QAC5B,QAAQ,CAAC,MAAM,CAAC,EAAE,YAAY,CAAC;KAChC,GAAG,kBAAkB,CAAC;IACvB;;;;OAIG;IACH,uBAAuB,CACrB,QAAQ,EAAE,MAAM,EAChB,IAAI,EAAE,SAAS,YAAY,EAAE,EAC7B,WAAW,EAAE,SAAS,IAAI,EAAE,GAC3B,SAAS,MAAM,EAAE,CAAC;IACrB,+EAA+E;IAC/E,eAAe,CAAC,QAAQ,EAAE,MAAM,EAAE,MAAM,EAAE,SAAS,MAAM,EAAE,GAAG,IAAI,CAAC;IACnE,0EAA0E;IAC1E,UAAU,IAAI,IAAI,CAAC;IACnB,sEAAsE;IACtE,QAAQ,IAAI,IAAI,CAAC;IACjB,uEAAuE;IACvE,sBAAsB,CAAC,QAAQ,EAAE,MAAM,GAAG,IAAI,CAAC;IAC/C;;;;;;;;;;OAUG;IACH,aAAa,CAAC,UAAU,EAAE,MAAM,GAAG,gBAAgB,CAAC;IACpD;;;;;;;;OAQG;IACH,iBAAiB,CACf,KAAK,EAAE,gBAAgB,EACvB,IAAI,EAAE,SAAS,YAAY,EAAE,EAC7B,WAAW,EAAE,SAAS,IAAI,EAAE,GAC3B,IAAI,CAAC;IACR,mEAAmE;IACnE,2BAA2B,CACzB,OAAO,EAAE,kBAAkB,EAC3B,IAAI,EAAE,SAAS,YAAY,EAAE,EAC7B,WAAW,EAAE,SAAS,IAAI,EAAE,GAC3B,IAAI,CAAC;IACR;;;;OAIG;IACH,aAAa,IAAI,IAAI,CAAC;IACtB,wEAAwE;IACxE,OAAO,IAAI,IAAI,CAAC;CACjB;AAED,wBAAgB,0BAA0B,CACxC,MAAM,EAAE,SAAS,EACjB,cAAc,EAAE,MAAM,EACtB,gBAAgB,UAAO,GACtB,oBAAoB,CA0iBtB"}
@@ -1,3 +1,4 @@
1
+ import type { Mat4 } from '@forgeax/engine-math';
1
2
  import type { Buffer } from '@forgeax/engine-rhi';
2
3
  /**
3
4
  * Per-draw palette slice metadata shared by the extract producer and the
@@ -26,4 +27,13 @@ export interface SkinPaletteReceipt extends SkinPaletteSlice {
26
27
  readonly uploadBytes: number;
27
28
  readonly retiredByteOffset?: number;
28
29
  }
30
+ /** Frozen source facts; GPU addresses are assigned only by the consuming Renderer. */
31
+ export interface SkinPose {
32
+ readonly identity: string;
33
+ readonly generation: number;
34
+ readonly jointCount: number;
35
+ readonly bounds?: Float32Array;
36
+ readonly inverseBindMatrices: readonly Float32Array[];
37
+ readonly jointWorlds: readonly Mat4[];
38
+ }
29
39
  //# sourceMappingURL=skin-palette-types.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"skin-palette-types.d.ts","sourceRoot":"","sources":["../../src/systems/skin-palette-types.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,qBAAqB,CAAC;AAElD;;;;GAIG;AACH,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,wEAAwE;IACxE,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,wDAAwD;IACxD,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;CACzB;AAED,MAAM,WAAW,qBAAqB;IACpC,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;CAC7B;AAED,MAAM,WAAW,kBAAmB,SAAQ,gBAAgB;IAC1D,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;IAC1B,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,eAAe,EAAE,MAAM,CAAC;IACjC,QAAQ,CAAC,gBAAgB,EAAE,SAAS,GAAG,SAAS,CAAC;IACjD,QAAQ,CAAC,MAAM,CAAC,EAAE,YAAY,CAAC;IAC/B,QAAQ,CAAC,WAAW,EAAE,SAAS,qBAAqB,EAAE,CAAC;IACvD,QAAQ,CAAC,WAAW,EAAE,MAAM,CAAC;IAC7B,QAAQ,CAAC,iBAAiB,CAAC,EAAE,MAAM,CAAC;CACrC"}
1
+ {"version":3,"file":"skin-palette-types.d.ts","sourceRoot":"","sources":["../../src/systems/skin-palette-types.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,IAAI,EAAE,MAAM,sBAAsB,CAAC;AACjD,OAAO,KAAK,EAAE,MAAM,EAAE,MAAM,qBAAqB,CAAC;AAElD;;;;GAIG;AACH,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,wEAAwE;IACxE,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,wDAAwD;IACxD,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;CACzB;AAED,MAAM,WAAW,qBAAqB;IACpC,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;CAC7B;AAED,MAAM,WAAW,kBAAmB,SAAQ,gBAAgB;IAC1D,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;IAC1B,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,eAAe,EAAE,MAAM,CAAC;IACjC,QAAQ,CAAC,gBAAgB,EAAE,SAAS,GAAG,SAAS,CAAC;IACjD,QAAQ,CAAC,MAAM,CAAC,EAAE,YAAY,CAAC;IAC/B,QAAQ,CAAC,WAAW,EAAE,SAAS,qBAAqB,EAAE,CAAC;IACvD,QAAQ,CAAC,WAAW,EAAE,MAAM,CAAC;IAC7B,QAAQ,CAAC,iBAAiB,CAAC,EAAE,MAAM,CAAC;CACrC;AAED,sFAAsF;AACtF,MAAM,WAAW,QAAQ;IACvB,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;IAC1B,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,QAAQ,CAAC,UAAU,EAAE,MAAM,CAAC;IAC5B,QAAQ,CAAC,MAAM,CAAC,EAAE,YAAY,CAAC;IAC/B,QAAQ,CAAC,mBAAmB,EAAE,SAAS,YAAY,EAAE,CAAC;IACtD,QAAQ,CAAC,WAAW,EAAE,SAAS,IAAI,EAAE,CAAC;CACvC"}
@@ -1,9 +1,9 @@
1
- import type { World } from '@forgeax/engine-ecs';
1
+ import type { RenderResourceScope } from '../publication/resource-scope';
2
2
  import type { CameraSnapshot } from '../render-contract';
3
3
  import type { DispatchEntry, RenderableSnapshot } from '../render-system-extract';
4
4
  /**
5
5
  * Reorder only the transparent queue while preserving every opaque slot.
6
6
  * Equal depth/layer values use material identity as a fold-friendly tie break.
7
7
  */
8
- export declare function sortTransparentDispatch(dispatch: DispatchEntry[], world: World, cameras: readonly CameraSnapshot[], renderables: readonly RenderableSnapshot[]): DispatchEntry[];
8
+ export declare function sortTransparentDispatch(dispatch: DispatchEntry[], world: RenderResourceScope, cameras: readonly CameraSnapshot[], renderables: readonly RenderableSnapshot[]): DispatchEntry[];
9
9
  //# sourceMappingURL=transparent-dispatch.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"transparent-dispatch.d.ts","sourceRoot":"","sources":["../../src/systems/transparent-dispatch.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,qBAAqB,CAAC;AAEjD,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,oBAAoB,CAAC;AACzD,OAAO,KAAK,EAAE,aAAa,EAAE,kBAAkB,EAAE,MAAM,0BAA0B,CAAC;AASlF;;;GAGG;AACH,wBAAgB,uBAAuB,CACrC,QAAQ,EAAE,aAAa,EAAE,EACzB,KAAK,EAAE,KAAK,EACZ,OAAO,EAAE,SAAS,cAAc,EAAE,EAClC,WAAW,EAAE,SAAS,kBAAkB,EAAE,GACzC,aAAa,EAAE,CAoEjB"}
1
+ {"version":3,"file":"transparent-dispatch.d.ts","sourceRoot":"","sources":["../../src/systems/transparent-dispatch.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,+BAA+B,CAAC;AACzE,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,oBAAoB,CAAC;AACzD,OAAO,KAAK,EAAE,aAAa,EAAE,kBAAkB,EAAE,MAAM,0BAA0B,CAAC;AASlF;;;GAGG;AACH,wBAAgB,uBAAuB,CACrC,QAAQ,EAAE,aAAa,EAAE,EACzB,KAAK,EAAE,mBAAmB,EAC1B,OAAO,EAAE,SAAS,cAAc,EAAE,EAClC,WAAW,EAAE,SAAS,kBAAkB,EAAE,GACzC,aAAa,EAAE,CAoEjB"}
@@ -1,3 +1,4 @@
1
+ import type { RenderResourceScope } from '../publication/resource-scope';
1
2
  import type { World } from '@forgeax/engine-ecs';
2
3
  import { ResourceInvalidValueError } from '@forgeax/engine-ecs/projection';
3
4
  import { type Result } from '@forgeax/engine-types';
@@ -69,7 +70,7 @@ export declare const TransparentSort: Readonly<{
69
70
  * const cfg = getTransparentSortConfig(world);
70
71
  * // cfg.mode === 1, cfg.yzAlpha === 1.0 (yzAlpha ignored by mode=1).
71
72
  */
72
- export declare function getTransparentSortConfig(world: World): TransparentSortConfig;
73
+ export declare function getTransparentSortConfig(world: RenderResourceScope): TransparentSortConfig;
73
74
  /**
74
75
  * Write the world's `TransparentSortConfig` resource, validating `mode`.
75
76
  *
@@ -1 +1 @@
1
- {"version":3,"file":"transparent-sort-config.d.ts","sourceRoot":"","sources":["../../src/systems/transparent-sort-config.ts"],"names":[],"mappings":"AA0DA,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,qBAAqB,CAAC;AACjD,OAAO,EAAE,yBAAyB,EAAE,MAAM,gCAAgC,CAAC;AAC3E,OAAO,EAAW,KAAK,MAAM,EAAE,MAAM,uBAAuB,CAAC;AAM7D;;;;;;;;;;;GAWG;AACH,MAAM,WAAW,qBAAqB;IACpC,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;CAC1B;AAED,gEAAgE;AAChE,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,CAAC,WAAW,EAAE,MAAM,CAAC;IAC7B,QAAQ,CAAC,cAAc,EAAE,MAAM,CAAC;IAChC,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,OAAO,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IACtC,QAAQ,CAAC,eAAe,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;CAC/C;AAED,+DAA+D;AAC/D,eAAO,MAAM,2BAA2B,EAAG,uBAAgC,CAAC;AAE5E,oDAAoD;AACpD,eAAO,MAAM,6BAA6B,IAAI,CAAC;AAE/C,mFAAmF;AACnF,eAAO,MAAM,6BAA6B,IAAI,CAAC;AAE/C,wFAAwF;AACxF,eAAO,MAAM,8BAA8B,IAAI,CAAC;AAEhD,kFAAkF;AAClF,eAAO,MAAM,8BAA8B,IAAI,CAAC;AAEhD,uEAAuE;AACvE,eAAO,MAAM,eAAe;;;;;;EAMjB,CAAC;AA8BZ;;;;;;;;;;;;;;;;;;;;GAoBG;AACH,wBAAgB,wBAAwB,CAAC,KAAK,EAAE,KAAK,GAAG,qBAAqB,CAK5E;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAqCG;AACH,wBAAgB,wBAAwB,CACtC,KAAK,EAAE,KAAK,EACZ,GAAG,EAAE,qBAAqB,GACzB,MAAM,CAAC,IAAI,EAAE,yBAAyB,CAAC,CAczC"}
1
+ {"version":3,"file":"transparent-sort-config.d.ts","sourceRoot":"","sources":["../../src/systems/transparent-sort-config.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,+BAA+B,CAAC;AA2DzE,OAAO,KAAK,EAAE,KAAK,EAAE,MAAM,qBAAqB,CAAC;AACjD,OAAO,EAAE,yBAAyB,EAAE,MAAM,gCAAgC,CAAC;AAC3E,OAAO,EAAW,KAAK,MAAM,EAAE,MAAM,uBAAuB,CAAC;AAM7D;;;;;;;;;;;GAWG;AACH,MAAM,WAAW,qBAAqB;IACpC,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,OAAO,EAAE,MAAM,CAAC;CAC1B;AAED,gEAAgE;AAChE,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,CAAC,WAAW,EAAE,MAAM,CAAC;IAC7B,QAAQ,CAAC,cAAc,EAAE,MAAM,CAAC;IAChC,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,IAAI,EAAE,MAAM,CAAC;IACtB,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,KAAK,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,OAAO,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;IACtC,QAAQ,CAAC,eAAe,CAAC,EAAE,MAAM,GAAG,SAAS,CAAC;CAC/C;AAED,+DAA+D;AAC/D,eAAO,MAAM,2BAA2B,EAAG,uBAAgC,CAAC;AAE5E,oDAAoD;AACpD,eAAO,MAAM,6BAA6B,IAAI,CAAC;AAE/C,mFAAmF;AACnF,eAAO,MAAM,6BAA6B,IAAI,CAAC;AAE/C,wFAAwF;AACxF,eAAO,MAAM,8BAA8B,IAAI,CAAC;AAEhD,kFAAkF;AAClF,eAAO,MAAM,8BAA8B,IAAI,CAAC;AAEhD,uEAAuE;AACvE,eAAO,MAAM,eAAe;;;;;;EAMjB,CAAC;AA8BZ;;;;;;;;;;;;;;;;;;;;GAoBG;AACH,wBAAgB,wBAAwB,CAAC,KAAK,EAAE,mBAAmB,GAAG,qBAAqB,CAM1F;AAED;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAqCG;AACH,wBAAgB,wBAAwB,CACtC,KAAK,EAAE,KAAK,EACZ,GAAG,EAAE,qBAAqB,GACzB,MAAM,CAAC,IAAI,EAAE,yBAAyB,CAAC,CAczC"}
@@ -1,9 +1,8 @@
1
- export { addStandardSceneDataPass, addTaaResolvePass, aggregateTemporalDemand, createStandardSceneDataTarget, describeTemporalDemand, standardTemporalLaneAdmission, standardTemporalPostOrder } from '../chunk-MKDIT2EM.mjs';
2
- import '../chunk-RXZ3RGOU.mjs';
3
- export { SCENE_DATA_TEMPORAL_V1_DESCRIPTOR, SCENE_DATA_TEMPORAL_V1_SCHEMA, createSceneDataCatalog, isSceneDataTarget, registerSceneDataTarget, sceneDataError, sceneDataTargetAsAttachment, sceneDataTargetOwner, sceneDataTokenMismatch } from '../chunk-OCDLEI6I.mjs';
4
- import '../chunk-BLXGONR2.mjs';
5
- export { TEMPORAL_JITTER_SAMPLE_COUNT, TEMPORAL_TAAU_DEPENDENCY_STATUS, TemporalFrameCoordinator, projectTemporalView, snapshotSubmittedTemporalView, temporalJitterSample, temporalViewId } from '../chunk-HEB564WF.mjs';
6
- export { classifySceneDataCoverage, createTemporalCoverage, scanSceneDataCoverage } from '../chunk-SHFUFJ5N.mjs';
7
- import '../chunk-WEX45HKH.mjs';
1
+ export { addStandardSceneDataPass, addTaaResolvePass, aggregateTemporalDemand, createStandardSceneDataTarget, describeTemporalDemand, standardTemporalLaneAdmission, standardTemporalPostOrder } from '../chunk-LNIUIKQ7.mjs';
2
+ export { SCENE_DATA_TEMPORAL_V1_DESCRIPTOR, SCENE_DATA_TEMPORAL_V1_SCHEMA, createSceneDataCatalog, isSceneDataTarget, registerSceneDataTarget, sceneDataError, sceneDataTargetAsAttachment, sceneDataTargetOwner, sceneDataTokenMismatch } from '../chunk-SGPUJW3F.mjs';
3
+ import '../chunk-XSFB7XXQ.mjs';
4
+ export { TEMPORAL_JITTER_SAMPLE_COUNT, TEMPORAL_TAAU_DEPENDENCY_STATUS, TemporalFrameCoordinator, projectTemporalView, snapshotSubmittedTemporalView, temporalJitterSample, temporalViewId } from '../chunk-LM5IE7GF.mjs';
5
+ export { classifySceneDataCoverage, createTemporalCoverage, scanSceneDataCoverage } from '../chunk-RIPAEGI6.mjs';
6
+ import '../chunk-MXTWKZO4.mjs';
8
7
  //# sourceMappingURL=index.mjs.map
9
8
  //# sourceMappingURL=index.mjs.map
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@forgeax/engine-render",
3
- "version": "0.1.34",
3
+ "version": "0.1.35",
4
4
  "description": "Canonical ECS render schemas and renderer boundary.",
5
5
  "private": false,
6
6
  "type": "module",
@@ -37,28 +37,28 @@
37
37
  "LICENSE"
38
38
  ],
39
39
  "dependencies": {
40
- "@forgeax/engine-assets-runtime": "0.1.34",
41
- "@forgeax/engine-audio-webaudio": "0.1.34",
42
- "@forgeax/engine-codec": "0.1.34",
43
- "@forgeax/engine-ecs": "0.1.34",
44
- "@forgeax/engine-geometry": "0.1.34",
45
- "@forgeax/engine-graphics-extras": "0.1.34",
46
- "@forgeax/engine-math": "0.1.34",
47
- "@forgeax/engine-pack": "0.1.34",
48
- "@forgeax/engine-plugin": "0.1.34",
49
- "@forgeax/engine-profiler": "0.1.34",
50
- "@forgeax/engine-render-graph": "0.1.34",
51
- "@forgeax/engine-rhi": "0.1.34",
52
- "@forgeax/engine-scene": "0.1.34",
53
- "@forgeax/engine-shader": "0.1.34",
54
- "@forgeax/engine-skinning": "0.1.34",
55
- "@forgeax/engine-types": "0.1.34"
40
+ "@forgeax/engine-assets-runtime": "0.1.35",
41
+ "@forgeax/engine-audio-webaudio": "0.1.35",
42
+ "@forgeax/engine-codec": "0.1.35",
43
+ "@forgeax/engine-ecs": "0.1.35",
44
+ "@forgeax/engine-geometry": "0.1.35",
45
+ "@forgeax/engine-graphics-extras": "0.1.35",
46
+ "@forgeax/engine-math": "0.1.35",
47
+ "@forgeax/engine-pack": "0.1.35",
48
+ "@forgeax/engine-plugin": "0.1.35",
49
+ "@forgeax/engine-profiler": "0.1.35",
50
+ "@forgeax/engine-render-graph": "0.1.35",
51
+ "@forgeax/engine-rhi": "0.1.35",
52
+ "@forgeax/engine-scene": "0.1.35",
53
+ "@forgeax/engine-shader": "0.1.35",
54
+ "@forgeax/engine-skinning": "0.1.35",
55
+ "@forgeax/engine-types": "0.1.35"
56
56
  },
57
57
  "devDependencies": {
58
- "@forgeax/engine-rhi-debug": "0.1.34",
59
- "@forgeax/engine-rhi-null": "0.1.34",
60
- "@forgeax/engine-rhi-webgpu": "0.1.34",
61
- "@forgeax/engine-vite-plugin-shader": "0.1.34",
58
+ "@forgeax/engine-rhi-debug": "0.1.35",
59
+ "@forgeax/engine-rhi-null": "0.1.35",
60
+ "@forgeax/engine-rhi-webgpu": "0.1.35",
61
+ "@forgeax/engine-vite-plugin-shader": "0.1.35",
62
62
  "@webgpu/types": "^0.1.71"
63
63
  },
64
64
  "forgeax": {
@@ -1,5 +1,4 @@
1
- import { readFileSync } from 'node:fs';
2
- import { Time, World } from '@forgeax/engine-ecs';
1
+ import { World } from '@forgeax/engine-ecs';
3
2
  import { describe, expect, it } from 'vitest';
4
3
  import {
5
4
  executeAutoExposureFrameTransaction,
@@ -10,10 +9,9 @@ import {
10
9
  commitAutoExposureSubmission,
11
10
  createAutoExposureState,
12
11
  } from '../pipeline/standard-output/auto-exposure/state';
12
+ import { renderTime } from '../publication/resource-scope';
13
13
  import { canonicalizeWorldComposition } from '../render-system-projections';
14
14
 
15
- const renderSystemSource = readFileSync(new URL('../render-system.ts', import.meta.url), 'utf8');
16
-
17
15
  function candidate(): AutoExposureCandidate {
18
16
  return { ev: 1.25, generation: 4, deviceEpoch: 2, frameId: 9 };
19
17
  }
@@ -90,10 +88,7 @@ describe('auto exposure frame transaction', () => {
90
88
  const resolvedCameraWorld = composition.worlds[composition.owners.cameraOwner];
91
89
 
92
90
  expect(resolvedCameraWorld).toBe(cameraWorld);
93
- expect(resolvedCameraWorld?.getResource(Time).delta).toBeCloseTo(1 / 30);
94
- expect(renderSystemSource).toContain(
95
- 'const cameraWorld = compositionWorlds[cameraOwner] as World;',
96
- );
97
- expect(renderSystemSource).not.toContain('const cameraWorld = worlds[cameraOwner] as World;');
91
+ if (resolvedCameraWorld === undefined) throw new Error('Camera owner is missing');
92
+ expect(renderTime(resolvedCameraWorld).delta).toBeCloseTo(1 / 30);
98
93
  });
99
94
  });
@@ -43,8 +43,9 @@ describe('shared device feature admission', () => {
43
43
  });
44
44
 
45
45
  it.each([
46
- [48, 22],
47
- [22, 22],
46
+ [48, 23],
47
+ [23, 23],
48
+ [22, 21],
48
49
  [21, 21],
49
50
  [20, 18],
50
51
  [18, 18],
@@ -641,10 +641,9 @@ describe('GPU-driven production PBR Dawn regression', () => {
641
641
  { binding: 47, resource: { kind: 'textureView' as const, value: materialCubeView } },
642
642
  { binding: 18, resource: { kind: 'sampler' as const, value: baseColorSampler } },
643
643
  { binding: 19, resource: { kind: 'textureView' as const, value: baseColorView } },
644
- { binding: 20, resource: { kind: 'sampler' as const, value: baseColorSampler } },
645
- { binding: 21, resource: { kind: 'buffer' as const, value: { buffer: viewUniform } } },
646
- { binding: 22, resource: { kind: 'sampler' as const, value: baseColorSampler } },
647
- { binding: 23, resource: { kind: 'textureView' as const, value: baseColorView } },
644
+ { binding: 20, resource: { kind: 'buffer' as const, value: { buffer: viewUniform } } },
645
+ { binding: 21, resource: { kind: 'sampler' as const, value: baseColorSampler } },
646
+ { binding: 22, resource: { kind: 'textureView' as const, value: baseColorView } },
648
647
  {
649
648
  binding: 46,
650
649
  resource: {
@@ -560,7 +560,10 @@ describe.skipIf(!pkgBuilt)('KTX2/Basis real GPU texture consumer matrix', () =>
560
560
  store.configureGpuDevice(
561
561
  device as never,
562
562
  undefined,
563
- (world, pod) => ok(world.allocSharedRef('EquirectAsset', pod)),
563
+ (source, pod) => {
564
+ if ('resolveAsset' in source) throw new Error('This fixture only allocates World assets');
565
+ return ok(source.allocSharedRef('EquirectAsset', pod));
566
+ },
564
567
  device.caps,
565
568
  );
566
569
  const rows: GpuCell[] = [];
@@ -63,7 +63,6 @@ function dependencies(
63
63
  skylightPrefilterView: resource(),
64
64
  prefilterSampler: resource(),
65
65
  brdfLutView: resource(),
66
- brdfLutSampler: resource(),
67
66
  intensityBuffer: resource(),
68
67
  },
69
68
  materialBgShared: new Map(),
@@ -139,7 +139,6 @@ describe('Materials.standard clearcoat public contract', () => {
139
139
  prefilterView: view,
140
140
  prefilterSampler: sampler,
141
141
  brdfLutView: view,
142
- brdfLutSampler: sampler,
143
142
  intensityBuffer: {} as Buffer,
144
143
  },
145
144
  undefined,
@@ -76,26 +76,26 @@ describe('Standard clearcoat root contract', () => {
76
76
  );
77
77
 
78
78
  // The canonical seven texture pairs occupy bindings 1..14. IBL remains
79
- // at 15..21 and transmission at 22..23; authored physical maps append at
79
+ // at 15..20 and transmission at 21..22; authored physical maps append at
80
80
  // their canonical fixed slots (26, 27, 30, 31), followed by the
81
81
  // scene-index row at binding 46. Compacting the authored root here shifts WGSL IBL bindings and
82
82
  // causes Dawn to reject the pipeline before any pixels are submitted.
83
- expect(descriptor.entries).toHaveLength(30);
83
+ expect(descriptor.entries).toHaveLength(29);
84
84
  expect(descriptor.entries.slice(0, 15).map((entry) => entry.binding)).toEqual(
85
85
  Array.from({ length: 15 }, (_, binding) => binding),
86
86
  );
87
87
  expect(descriptor.entries[15]?.texture).toMatchObject({ viewDimension: 'cube' });
88
88
  expect(descriptor.entries[17]?.texture).toMatchObject({ viewDimension: 'cube' });
89
- expect(descriptor.entries[22]?.sampler).toMatchObject({ type: 'filtering' });
90
- expect(descriptor.entries[23]?.texture).toMatchObject({ viewDimension: '2d' });
91
- expect(descriptor.entries.slice(24, 28).map((entry) => entry.binding)).toEqual([
89
+ expect(descriptor.entries[21]?.sampler).toMatchObject({ type: 'filtering' });
90
+ expect(descriptor.entries[22]?.texture).toMatchObject({ viewDimension: '2d' });
91
+ expect(descriptor.entries.slice(23, 27).map((entry) => entry.binding)).toEqual([
92
92
  26, 27, 30, 31,
93
93
  ]);
94
- expect(descriptor.entries[29]).toMatchObject({
94
+ expect(descriptor.entries[28]).toMatchObject({
95
95
  binding: 47,
96
96
  texture: { sampleType: 'float', viewDimension: 'cube' },
97
97
  });
98
- expect(descriptor.entries[28]).toMatchObject({
98
+ expect(descriptor.entries[27]).toMatchObject({
99
99
  binding: 46,
100
100
  visibility: GPU_SHADER_STAGE_VERTEX | GPU_SHADER_STAGE_FRAGMENT,
101
101
  buffer: { type: 'read-only-storage', hasDynamicOffset: false },
@@ -122,7 +122,7 @@ describe('Standard clearcoat root contract', () => {
122
122
  // PBR layouts keep the producer-owned scene-material row at binding 46,
123
123
  // even when an authored schema has no numeric parameters.
124
124
  expect(descriptor.entries.map((entry) => entry.binding)).toEqual([
125
- ...Array.from({ length: 10 }, (_, binding) => binding),
125
+ ...Array.from({ length: 9 }, (_, binding) => binding),
126
126
  46,
127
127
  47,
128
128
  ]);
@@ -144,43 +144,43 @@ describe('Standard clearcoat root contract', () => {
144
144
  );
145
145
 
146
146
  expect(descriptor.entries.map((entry) => entry.binding)).toEqual([
147
- ...Array.from({ length: 16 }, (_, binding) => binding),
147
+ ...Array.from({ length: 15 }, (_, binding) => binding),
148
148
  46,
149
149
  ]);
150
- expect(descriptor.entries[10]).toMatchObject({
150
+ expect(descriptor.entries[9]).toMatchObject({
151
151
  sampler: { type: 'non-filtering' },
152
152
  });
153
- expect(descriptor.entries[11]).toMatchObject({
153
+ expect(descriptor.entries[10]).toMatchObject({
154
154
  texture: { sampleType: 'unfilterable-float', viewDimension: '2d' },
155
155
  });
156
- expect(descriptor.entries[12]).toMatchObject({
156
+ expect(descriptor.entries[11]).toMatchObject({
157
157
  sampler: { type: 'filtering' },
158
158
  });
159
- expect(descriptor.entries[13]).toMatchObject({
159
+ expect(descriptor.entries[12]).toMatchObject({
160
160
  texture: { sampleType: 'float', viewDimension: '2d' },
161
161
  });
162
- expect(descriptor.entries[14]).toMatchObject({
162
+ expect(descriptor.entries[13]).toMatchObject({
163
163
  sampler: { type: 'non-filtering' },
164
164
  });
165
- expect(descriptor.entries[15]).toMatchObject({
165
+ expect(descriptor.entries[14]).toMatchObject({
166
166
  texture: { sampleType: 'unfilterable-float', viewDimension: '2d' },
167
167
  });
168
168
 
169
169
  // The medium is a project material artifact with an explicit empty
170
170
  // paramSchema. Its per-shader user region is therefore the reserved UBO
171
- // at binding 0, followed by IBL 1..7, transmission 8..9, and Surface
172
- // resources 10..15. Keep this source assertion next to the descriptor
171
+ // at binding 0, followed by IBL 1..6, transmission 7..8, and Surface
172
+ // resources 9..14. Keep this source assertion next to the descriptor
173
173
  // assertion so a future injection-order change cannot leave a compiled
174
174
  // WGSL binding map out of sync with the runtime BGL.
175
175
  const source = readFileSync(
176
176
  resolve(import.meta.dirname, '../../../shader/src/single-layer-medium.wgsl'),
177
177
  'utf8',
178
178
  );
179
- expect(source).toContain('@group(1) @binding(10) var surfaceRawDepthSampler');
180
- expect(source).toContain('@group(1) @binding(11) var surfaceRawDepthTexture');
181
- expect(source).toContain('@group(1) @binding(12) var surfaceNearestLayerSampler');
182
- expect(source).toContain('@group(1) @binding(13) var surfaceNearestLayerTexture');
183
- expect(source).toContain('@group(1) @binding(14) var surfaceNearestDepthSampler');
184
- expect(source).toContain('@group(1) @binding(15) var surfaceNearestDepthTexture');
179
+ expect(source).toContain('@group(1) @binding(9) var surfaceRawDepthSampler');
180
+ expect(source).toContain('@group(1) @binding(10) var surfaceRawDepthTexture');
181
+ expect(source).toContain('@group(1) @binding(11) var surfaceNearestLayerSampler');
182
+ expect(source).toContain('@group(1) @binding(12) var surfaceNearestLayerTexture');
183
+ expect(source).toContain('@group(1) @binding(13) var surfaceNearestDepthSampler');
184
+ expect(source).toContain('@group(1) @binding(14) var surfaceNearestDepthTexture');
185
185
  });
186
186
  });
@@ -0,0 +1,40 @@
1
+ import { STANDARD_MATERIAL_PARAM_SCHEMA } from '@forgeax/engine-types';
2
+ import { expect, it } from 'vitest';
3
+ import { STANDARD_PHYSICAL_REQUIRED_SAMPLED_TEXTURES } from '../assembly/device-feature-admission';
4
+ import { buildBindGroupLayoutDescriptor, buildPbrViewBglEntries } from '../pbr-pipeline';
5
+ import type { PipelineSpec } from '../pipeline-spec';
6
+
7
+ it('fits the physical carrier and extended-lighting view within the admitted device budget', () => {
8
+ const textureFields = new Set([
9
+ 'baseColorTexture',
10
+ 'metallicRoughnessTexture',
11
+ 'normalTexture',
12
+ 'emissiveTexture',
13
+ 'occlusionTexture',
14
+ 'clearcoatTexture',
15
+ 'clearcoatRoughnessTexture',
16
+ 'clearcoatNormalTexture',
17
+ 'transmissionTexture',
18
+ 'thicknessTexture',
19
+ ]);
20
+ const spec: PipelineSpec = {
21
+ shader: { id: 'budget::physical', passKind: 'forward', variantSet: undefined },
22
+ attachments: { colorFormats: [], depthFormat: undefined, sampleCount: 1 },
23
+ geometry: { topology: 'triangle-list', vertexLayout: {} },
24
+ renderState: undefined,
25
+ };
26
+ const entries = [
27
+ ...buildPbrViewBglEntries({ storageBuffer: true, extendedLighting: true }),
28
+ ...buildBindGroupLayoutDescriptor(spec, {
29
+ kind: 'pbr-material-merged',
30
+ materialParamSchema: STANDARD_MATERIAL_PARAM_SCHEMA.filter(
31
+ (field) => field.type !== 'texture2d' || textureFields.has(field.name),
32
+ ),
33
+ caps: { storageBuffer: true, transmissionBackdrop: true },
34
+ }).entries,
35
+ ].filter((entry) => (entry.visibility & 2) !== 0);
36
+ expect(entries.filter((entry) => entry.sampler !== undefined).length).toBeLessThanOrEqual(16);
37
+ expect(entries.filter((entry) => entry.texture !== undefined).length).toBeLessThanOrEqual(
38
+ STANDARD_PHYSICAL_REQUIRED_SAMPLED_TEXTURES,
39
+ );
40
+ });
@@ -15,6 +15,7 @@ import type {
15
15
  } from '../index';
16
16
 
17
17
  const expectedCodes = [
18
+ 'render-publication-invalid',
18
19
  'auto-exposure-invalid-parameter',
19
20
  'auto-exposure-capability-unavailable',
20
21
  'auto-exposure-stale-generation',
@@ -137,7 +137,7 @@ fn cloud_direct_solar_factorX() -> f32 {
137
137
  } as never),
138
138
  ).toEqual({
139
139
  requiredFeatures: [],
140
- requiredLimits: { maxSampledTexturesPerShaderStage: 22 },
140
+ requiredLimits: { maxSampledTexturesPerShaderStage: 23 },
141
141
  });
142
142
  expect(
143
143
  deviceOptionsForAdapter({
@@ -21,12 +21,12 @@ export function transmissionBackdropAvailable(limit: number | undefined): boolea
21
21
  }
22
22
  /**
23
23
  * The complete Standard physical root can declare all optional texture slots.
24
- * Its material group therefore needs one more sampled-texture entry than the
24
+ * Its material group therefore needs two more sampled-texture entries than the
25
25
  * extended-lighting topology alone. Request this ceiling when the adapter can
26
26
  * provide it; lower-capability devices remain fail-closed at material
27
27
  * pipeline admission instead of receiving an invalid WebGPU layout.
28
28
  */
29
- export const STANDARD_PHYSICAL_REQUIRED_SAMPLED_TEXTURES = 22;
29
+ export const STANDARD_PHYSICAL_REQUIRED_SAMPLED_TEXTURES = 23;
30
30
 
31
31
  export interface DeviceFeatureAdmissionOptions {
32
32
  readonly gpuPassTiming?: object | undefined;
@@ -14,6 +14,7 @@ import type { ObservationUnavailableError, RenderError } from '../errors/render'
14
14
  import type { RenderFeature, RenderFeatureDiagnostics } from '../features/types';
15
15
  import type { GpuDrivenProductionInspection, LodOcclusionInspection } from '../inspection-types';
16
16
  import type { MeshMaterialBindingObservation } from '../mesh-material-bindings';
17
+ import type { PublishedRenderFrameInput } from '../publication/contract';
17
18
  import type { FrameObservation, FrameObservationOptions } from '../record/frame';
18
19
  import type { CurrentGraphTarget, GraphTargetCaptureRequest } from '../record/frame-snapshot';
19
20
  import type {
@@ -120,7 +121,9 @@ export interface RendererHostImplementation {
120
121
  readonly lodOcclusion: LodOcclusionInspection | undefined;
121
122
  readonly gpuDriven: GpuDrivenProductionInspection;
122
123
  };
123
- drawFrame(request: RenderFrameInput): RenderResult<FrameReceipt, RhiError | RenderError>;
124
+ drawFrame(
125
+ request: RenderFrameInput | PublishedRenderFrameInput,
126
+ ): RenderResult<FrameReceipt, RhiError | RenderError>;
124
127
  /** Arm one upcoming frame for receipt-bound color observations. */
125
128
  requestObservation?: (
126
129
  domains: readonly import('../render-contract').FrameObservationDomain[],
@@ -154,7 +157,7 @@ export interface RendererLegacyHostAdapter {
154
157
  attachScene(world: World): RenderResult<void, RhiError>;
155
158
  detachScene(world: World): void;
156
159
  draw(
157
- worldsOrRequest: readonly World[] | RenderFrameInput,
160
+ worldsOrRequest: readonly World[] | RenderFrameInput | PublishedRenderFrameInput,
158
161
  options?: DrawOwnerOptions,
159
162
  ): RenderResult<void | FrameReceipt, RhiError | RenderError>;
160
163
  observeCurrentFrame(
@@ -10,6 +10,7 @@ import type {
10
10
  import { err, ok, type Result, RhiError } from '@forgeax/engine-rhi';
11
11
  import type { MaterialShaderManifestEntry, ShaderCatalog } from '@forgeax/engine-shader';
12
12
  import type { Handle, ParamSchemaEntry } from '@forgeax/engine-types';
13
+ import { AssetError } from '@forgeax/engine-types';
13
14
  import { DeviceScope } from '../../device/device-scope';
14
15
  import { GpuResidencyCache } from '../../device/gpu-residency';
15
16
  import { RecoverError, type RecoverFailure } from '../../errors/recover';
@@ -399,6 +400,14 @@ export function createRendererRecovery(deps: RendererRecoveryDependencies): Rend
399
400
  device,
400
401
  adaptMipmapShaderModuleFactory(internals.pack.createShaderModule),
401
402
  (world, pod) => {
403
+ if ('resolveAsset' in world)
404
+ return err(
405
+ new AssetError({
406
+ code: 'asset-not-found',
407
+ expected: 'source-owned environment asset allocation',
408
+ hint: 'publish the environment asset from its source owner before GPU preparation',
409
+ }),
410
+ );
402
411
  const handle: Handle<'EquirectAsset', 'shared'> = world.allocSharedRef(
403
412
  'EquirectAsset',
404
413
  pod,