@woosh/meep-engine 3.56.0 → 3.57.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (625) hide show
  1. package/build/bundle-worker-terrain.js +1 -1
  2. package/package.json +1 -1
  3. package/src/DUPLICATION_REVIEW_2026_10_24.md +1072 -0
  4. package/src/core/binary/BitSet.js +1 -1
  5. package/src/core/binary/FLOAT16_MAX.d.ts +2 -0
  6. package/src/core/binary/FLOAT16_MAX.d.ts.map +1 -0
  7. package/src/core/binary/FLOAT16_MAX.js +1 -0
  8. package/src/core/binary/base58/base58_encode.js +2 -2
  9. package/src/core/binary/type/TypeBuilder.js +1 -1
  10. package/src/core/bvh2/bvh3/BVH.js +1 -1
  11. package/src/core/bvh2/bvh3/ebvh_optimize_treelet.d.ts.map +1 -1
  12. package/src/core/bvh2/bvh3/ebvh_optimize_treelet.js +7 -3
  13. package/src/core/bvh2/bvh3/ebvh_update_hierarchy_bounds.d.ts.map +1 -1
  14. package/src/core/bvh2/bvh3/ebvh_update_hierarchy_bounds.js +5 -1
  15. package/src/core/bvh2/bvh3/query/compute_tight_near_far_clipping_planes.d.ts.map +1 -1
  16. package/src/core/bvh2/bvh3/query/compute_tight_near_far_clipping_planes.js +195 -246
  17. package/src/core/collection/CuckooFilter.js +1 -1
  18. package/src/core/collection/array/isArrayEqual.d.ts.map +1 -1
  19. package/src/core/collection/array/isArrayEqual.js +33 -58
  20. package/src/core/collection/array/typed/array_buffer_hash.d.ts.map +1 -1
  21. package/src/core/collection/array/typed/array_buffer_hash.js +41 -39
  22. package/src/core/collection/array/typed/float32_array_hash.js +38 -38
  23. package/src/core/collection/array/typed/uint16_array_hash.d.ts +2 -1
  24. package/src/core/collection/array/typed/uint16_array_hash.d.ts.map +1 -1
  25. package/src/core/collection/array/typed/uint16_array_hash.js +30 -29
  26. package/src/core/collection/array/typed/uint32_array_hash.d.ts +2 -1
  27. package/src/core/collection/array/typed/uint32_array_hash.d.ts.map +1 -1
  28. package/src/core/collection/array/typed/uint32_array_hash.js +21 -20
  29. package/src/core/collection/array/typed/uint8_array_hash.d.ts +2 -1
  30. package/src/core/collection/array/typed/uint8_array_hash.d.ts.map +1 -1
  31. package/src/core/collection/array/typed/uint8_array_hash.js +37 -36
  32. package/src/core/collection/array/typed/uint_array_for_count.js +2 -2
  33. package/src/core/collection/list/List.d.ts.map +1 -1
  34. package/src/core/collection/list/List.js +3 -19
  35. package/src/core/collection/table/RowFirstTable.d.ts.map +1 -1
  36. package/src/core/collection/table/RowFirstTable.js +4 -28
  37. package/src/core/debug/matchers/DescribeAs.d.ts.map +1 -1
  38. package/src/core/debug/matchers/DescribeAs.js +62 -64
  39. package/src/core/function/FunctionCompiler.js +4 -4
  40. package/src/core/function/objectsEqual.d.ts.map +1 -1
  41. package/src/core/function/objectsEqual.js +3 -2
  42. package/src/core/geom/2d/bvh/BVH2D.d.ts.map +1 -1
  43. package/src/core/geom/2d/bvh/BVH2D.js +4 -3
  44. package/src/core/geom/2d/convex-hull/convex_hull_fixed_count_2d_relaxation.d.ts +5 -2
  45. package/src/core/geom/2d/convex-hull/convex_hull_fixed_count_2d_relaxation.d.ts.map +1 -1
  46. package/src/core/geom/2d/convex-hull/convex_hull_fixed_count_2d_relaxation.js +49 -11
  47. package/src/core/geom/2d/hash-grid/shg_query_elements_circle.d.ts.map +1 -1
  48. package/src/core/geom/2d/hash-grid/shg_query_elements_circle.js +122 -159
  49. package/src/core/geom/2d/hash-grid/shg_query_elements_line.d.ts.map +1 -1
  50. package/src/core/geom/2d/hash-grid/shg_query_elements_line.js +8 -5
  51. package/src/core/geom/2d/polygon/polygon2_rasterize_coverage.d.ts +18 -0
  52. package/src/core/geom/2d/polygon/polygon2_rasterize_coverage.d.ts.map +1 -0
  53. package/src/core/geom/2d/polygon/polygon2_rasterize_coverage.js +97 -0
  54. package/src/core/geom/2d/r-tree/StaticR2Tree.js +2 -2
  55. package/src/core/geom/2d/triangle/tri2_rasterize_coverage.d.ts +21 -0
  56. package/src/core/geom/2d/triangle/tri2_rasterize_coverage.d.ts.map +1 -0
  57. package/src/core/geom/2d/triangle/tri2_rasterize_coverage.js +54 -0
  58. package/src/core/geom/3d/aabb/aabb3_build_frustum.d.ts.map +1 -1
  59. package/src/core/geom/3d/aabb/aabb3_build_frustum.js +20 -53
  60. package/src/core/geom/3d/aabb/aabb3_score_boxes_SAH.d.ts +1 -1
  61. package/src/core/geom/3d/aabb/aabb3_score_boxes_SAH.d.ts.map +1 -1
  62. package/src/core/geom/3d/aabb/aabb3_score_boxes_SAH.js +11 -42
  63. package/src/core/geom/3d/atlas/pack/atlas_pack_charts.d.ts.map +1 -1
  64. package/src/core/geom/3d/atlas/pack/atlas_pack_charts.js +30 -32
  65. package/src/core/geom/3d/atlas/param/atlas_chart_parameterize_bff.d.ts.map +1 -1
  66. package/src/core/geom/3d/atlas/param/atlas_chart_parameterize_bff.js +1 -5
  67. package/src/core/geom/3d/atlas/param/atlas_chart_parameterize_lscm.d.ts.map +1 -1
  68. package/src/core/geom/3d/atlas/param/atlas_chart_parameterize_lscm.js +1 -15
  69. package/src/core/geom/3d/atlas/segment/atlas_merge_charts.d.ts.map +1 -1
  70. package/src/core/geom/3d/atlas/segment/atlas_merge_charts.js +105 -116
  71. package/src/core/geom/3d/line/line3_compute_segment_point_distance_sqr.d.ts.map +1 -1
  72. package/src/core/geom/3d/line/line3_compute_segment_point_distance_sqr.js +36 -54
  73. package/src/core/geom/3d/plane/plane3_compute_intersection_objects.d.ts +5 -10
  74. package/src/core/geom/3d/plane/plane3_compute_intersection_objects.d.ts.map +1 -1
  75. package/src/core/geom/3d/plane/plane3_compute_intersection_objects.js +20 -82
  76. package/src/core/geom/3d/plane/plane3_slerp.d.ts.map +1 -1
  77. package/src/core/geom/3d/plane/plane3_slerp.js +87 -102
  78. package/src/core/geom/3d/polygon/polygon3_compute_normal.d.ts +12 -0
  79. package/src/core/geom/3d/polygon/polygon3_compute_normal.d.ts.map +1 -1
  80. package/src/core/geom/3d/polygon/polygon3_compute_normal.js +107 -60
  81. package/src/core/geom/3d/ray/ray3_compute_closest_point.d.ts.map +1 -1
  82. package/src/core/geom/3d/ray/ray3_compute_closest_point.js +37 -43
  83. package/src/core/geom/3d/shape/ConvexHullShape3D.d.ts.map +1 -1
  84. package/src/core/geom/3d/shape/ConvexHullShape3D.js +5 -16
  85. package/src/core/geom/3d/shape/MeshShape3D.js +2 -56
  86. package/src/core/geom/3d/shape/TransformedShape3D.d.ts.map +1 -1
  87. package/src/core/geom/3d/shape/TransformedShape3D.js +10 -7
  88. package/src/core/geom/3d/shape/UnionShape3D.d.ts.map +1 -1
  89. package/src/core/geom/3d/shape/UnionShape3D.js +9 -3
  90. package/src/core/geom/3d/shape/json/shape_to_type.js +2 -2
  91. package/src/core/geom/3d/sphere/harmonics/SH3_COEFFICIENTS.js +17 -17
  92. package/src/core/geom/3d/tetrahedra/TetrahedralMesh.d.ts.map +1 -1
  93. package/src/core/geom/3d/tetrahedra/TetrahedralMesh.js +6 -2
  94. package/src/core/geom/3d/tetrahedra/tetrahedral_mesh_carve_outside_surface.d.ts.map +1 -1
  95. package/src/core/geom/3d/tetrahedra/tetrahedral_mesh_carve_outside_surface.js +3 -2
  96. package/src/core/geom/3d/tetrahedra/tetrahedron_contains_point.d.ts +20 -2
  97. package/src/core/geom/3d/tetrahedra/tetrahedron_contains_point.d.ts.map +1 -1
  98. package/src/core/geom/3d/tetrahedra/tetrahedron_contains_point.js +52 -37
  99. package/src/core/geom/3d/topology/struct/binary/io/bt_mesh_compute_face_normals.d.ts.map +1 -1
  100. package/src/core/geom/3d/topology/struct/binary/io/bt_mesh_compute_face_normals.js +40 -56
  101. package/src/core/geom/3d/topology/struct/binary/io/bt_mesh_compute_vertex_quadrics.d.ts.map +1 -1
  102. package/src/core/geom/3d/topology/struct/binary/io/bt_mesh_compute_vertex_quadrics.js +251 -260
  103. package/src/core/geom/3d/topology/struct/binary/io/bt_mesh_compute_wedge_attribute_quadrics.d.ts.map +1 -1
  104. package/src/core/geom/3d/topology/struct/binary/io/bt_mesh_compute_wedge_attribute_quadrics.js +104 -113
  105. package/src/core/geom/3d/topology/struct/binary/io/bt_mesh_resolve_t_junctions.d.ts.map +1 -1
  106. package/src/core/geom/3d/topology/struct/binary/io/bt_mesh_resolve_t_junctions.js +227 -238
  107. package/src/core/geom/3d/topology/struct/binary/io/bt_mesh_simplify.d.ts.map +1 -1
  108. package/src/core/geom/3d/topology/struct/binary/io/bt_mesh_simplify.js +15 -24
  109. package/src/core/geom/3d/topology/struct/binary/io/edge/bt_edge_create.d.ts.map +1 -1
  110. package/src/core/geom/3d/topology/struct/binary/io/edge/bt_edge_create.js +31 -115
  111. package/src/core/geom/3d/topology/struct/binary/io/vertex/bt_vertex_fuse_duplicate_edges.d.ts.map +1 -1
  112. package/src/core/geom/3d/topology/struct/binary/io/vertex/bt_vertex_fuse_duplicate_edges.js +142 -150
  113. package/src/core/geom/3d/topology/struct/binary/io/vertex/bt_vertex_replace.d.ts.map +1 -1
  114. package/src/core/geom/3d/topology/struct/binary/io/vertex/bt_vertex_replace.js +151 -194
  115. package/src/core/geom/3d/topology/struct/binary/query/bt_face_get_incenter.d.ts.map +1 -1
  116. package/src/core/geom/3d/topology/struct/binary/query/bt_face_get_incenter.js +60 -85
  117. package/src/core/geom/3d/topology/struct/binary/query/bt_mesh_build_boundary_distance_field.d.ts.map +1 -1
  118. package/src/core/geom/3d/topology/struct/binary/query/bt_mesh_build_boundary_distance_field.js +156 -171
  119. package/src/core/geom/3d/topology/struct/binary/query/bt_mesh_face_find_path.d.ts.map +1 -1
  120. package/src/core/geom/3d/topology/struct/binary/query/bt_mesh_face_find_path.js +8 -44
  121. package/src/core/geom/3d/topology/struct/binary/query/bt_mesh_face_find_path_polyanya.d.ts.map +1 -1
  122. package/src/core/geom/3d/topology/struct/binary/query/bt_mesh_face_find_path_polyanya.js +2 -7
  123. package/src/core/geom/3d/topology/struct/binary/query/bt_mesh_sample_interior_grid_points.d.ts.map +1 -1
  124. package/src/core/geom/3d/topology/struct/binary/query/bt_mesh_sample_interior_grid_points.js +3 -2
  125. package/src/core/geom/3d/topology/struct/binary/query/bt_mesh_segment_penetrates_surface.d.ts.map +1 -1
  126. package/src/core/geom/3d/topology/struct/binary/query/bt_mesh_segment_penetrates_surface.js +128 -133
  127. package/src/core/geom/3d/topology/struct/binary/query/bt_mesh_surface_ray_parity.d.ts +8 -14
  128. package/src/core/geom/3d/topology/struct/binary/query/bt_mesh_surface_ray_parity.d.ts.map +1 -1
  129. package/src/core/geom/3d/topology/struct/binary/query/bt_mesh_surface_ray_parity.js +36 -82
  130. package/src/core/geom/3d/triangle/tri3_ray_intersection.d.ts.map +1 -1
  131. package/src/core/geom/3d/triangle/tri3_ray_intersection.js +7 -144
  132. package/src/core/geom/ConicRay.d.ts.map +1 -1
  133. package/src/core/geom/ConicRay.js +230 -237
  134. package/src/core/localization/LocaleDataset.d.ts +6 -0
  135. package/src/core/localization/LocaleDataset.d.ts.map +1 -1
  136. package/src/core/localization/LocaleDataset.js +48 -37
  137. package/src/core/localization/LocalizationEngine.d.ts.map +1 -1
  138. package/src/core/localization/LocalizationEngine.js +3 -2
  139. package/src/core/math/lookup/ParameterLookupTable.d.ts.map +1 -1
  140. package/src/core/math/lookup/ParameterLookupTable.js +3 -1
  141. package/src/core/math/spline/spline3_hermite_intersection_spline3_hermite_nd.d.ts.map +1 -1
  142. package/src/core/math/spline/spline3_hermite_intersection_spline3_hermite_nd.js +330 -400
  143. package/src/core/math/spline/spline3_hermite_nearest_point.d.ts +16 -0
  144. package/src/core/math/spline/spline3_hermite_nearest_point.d.ts.map +1 -1
  145. package/src/core/math/spline/spline3_hermite_nearest_point.js +134 -167
  146. package/src/core/model/DebouncedObservedBoolean.d.ts +1 -2
  147. package/src/core/model/DebouncedObservedBoolean.d.ts.map +1 -1
  148. package/src/core/model/DebouncedObservedBoolean.js +1 -1
  149. package/src/core/model/node-graph/node/NodeInstance.d.ts.map +1 -1
  150. package/src/core/model/node-graph/node/NodeInstance.js +2 -7
  151. package/src/core/model/node-graph/node/parameter/NodeParameterDescription.js +1 -1
  152. package/src/core/model/object/optional_equality.d.ts +3 -3
  153. package/src/core/model/object/optional_equality.d.ts.map +1 -1
  154. package/src/core/model/object/optional_equality.js +10 -27
  155. package/src/core/model/object/write_property.js +1 -1
  156. package/src/core/model/reactive/evaluation/MultiPredicateEvaluator.js +2 -2
  157. package/src/core/primitives/strings/string_compute_byte_size.d.ts +3 -3
  158. package/src/core/primitives/strings/string_compute_byte_size.d.ts.map +1 -1
  159. package/src/core/primitives/strings/string_compute_byte_size.js +8 -21
  160. package/src/core/process/executor/ConcurrentExecutor.d.ts.map +1 -1
  161. package/src/core/process/executor/ConcurrentExecutor.js +14 -2
  162. package/src/engine/achievements/gateway/StorageAchievementGateway.d.ts +6 -3
  163. package/src/engine/achievements/gateway/StorageAchievementGateway.d.ts.map +1 -1
  164. package/src/engine/achievements/gateway/StorageAchievementGateway.js +31 -75
  165. package/src/engine/asset/loaders/SVGAssetLoader.d.ts.map +1 -1
  166. package/src/engine/asset/loaders/SVGAssetLoader.js +33 -31
  167. package/src/engine/control/first-person/math/criticallyDampedSpring.d.ts.map +1 -1
  168. package/src/engine/control/first-person/math/criticallyDampedSpring.js +3 -14
  169. package/src/engine/ecs/EntityComponentDataset.d.ts.map +1 -1
  170. package/src/engine/ecs/EntityComponentDataset.js +4 -1
  171. package/src/engine/ecs/storage/binary/object/BinaryObjectSerializationAdapter.d.ts +0 -2
  172. package/src/engine/ecs/storage/binary/object/BinaryObjectSerializationAdapter.d.ts.map +1 -1
  173. package/src/engine/ecs/storage/binary/object/BinaryObjectSerializationAdapter.js +3 -3
  174. package/src/engine/ecs/terrain/ecs/layers/TerrainLayer.js +2 -2
  175. package/src/engine/graphics/sh3/path_tracer/geometry/sort_triangles_by_distance_to_point.js +1 -1
  176. package/src/engine/graphics/texture/sampler/sampler2d_channel_compute_min_indices.js +1 -1
  177. package/src/engine/graphics3/WaterSystem.d.ts.map +1 -1
  178. package/src/engine/graphics3/WaterSystem.js +2 -1
  179. package/src/engine/graphics3/prefab/prefab_skin_frame.d.ts.map +1 -1
  180. package/src/engine/graphics3/prefab/prefab_skin_frame.js +1 -12
  181. package/src/engine/grid/grid2transform/GridPosition2TransformSystem.d.ts +1 -1
  182. package/src/engine/grid/grid2transform/GridPosition2TransformSystem.d.ts.map +1 -1
  183. package/src/engine/grid/grid2transform/GridPosition2TransformSystem.js +141 -137
  184. package/src/engine/input/ecs/systems/InputControllerSystem.d.ts.map +1 -1
  185. package/src/engine/input/ecs/systems/InputControllerSystem.js +13 -3
  186. package/src/engine/input/ecs/systems/InputSystem.d.ts.map +1 -1
  187. package/src/engine/input/ecs/systems/InputSystem.js +2 -1
  188. package/src/engine/intelligence/behavior/composite/ParallelBehavior.d.ts +1 -1
  189. package/src/engine/intelligence/behavior/composite/ParallelBehavior.d.ts.map +1 -1
  190. package/src/engine/intelligence/behavior/composite/ParallelBehavior.js +4 -1
  191. package/src/engine/intelligence/behavior/decorator/InvertStatusBehavior.d.ts.map +1 -1
  192. package/src/engine/intelligence/behavior/decorator/InvertStatusBehavior.js +3 -1
  193. package/src/engine/intelligence/behavior/decorator/RepeatBehavior.d.ts.map +1 -1
  194. package/src/engine/intelligence/behavior/decorator/RepeatBehavior.js +3 -1
  195. package/src/engine/intelligence/behavior/decorator/RepeatBehaviorSerializationAdapter.d.ts.map +1 -1
  196. package/src/engine/intelligence/behavior/decorator/RepeatBehaviorSerializationAdapter.js +39 -33
  197. package/src/engine/intelligence/behavior/util/ConditionalBehavior.d.ts +5 -0
  198. package/src/engine/intelligence/behavior/util/ConditionalBehavior.d.ts.map +1 -1
  199. package/src/engine/intelligence/behavior/util/ConditionalBehavior.js +93 -75
  200. package/src/engine/intelligence/behavior/util/RotationBehavior.d.ts.map +1 -1
  201. package/src/engine/intelligence/behavior/util/RotationBehavior.js +79 -76
  202. package/src/engine/intelligence/blackboard/BlackboardStack.d.ts +1 -0
  203. package/src/engine/intelligence/blackboard/BlackboardStack.d.ts.map +1 -1
  204. package/src/engine/intelligence/blackboard/BlackboardStack.js +159 -123
  205. package/src/engine/intelligence/mcts/StateNode.d.ts.map +1 -1
  206. package/src/engine/intelligence/mcts/StateNode.js +366 -364
  207. package/src/engine/intelligence/resource/ResourceAllocationSolver.js +1 -1
  208. package/src/engine/navigation/ecs/components/Path.d.ts.map +1 -1
  209. package/src/engine/navigation/ecs/components/Path.js +2 -1
  210. package/src/engine/navigation/ecs/path_following/PathFollowingSystem.d.ts.map +1 -1
  211. package/src/engine/navigation/ecs/path_following/PathFollowingSystem.js +5 -2
  212. package/src/engine/physics/body/SolverBodyState.d.ts.map +1 -1
  213. package/src/engine/physics/body/SolverBodyState.js +2 -6
  214. package/src/engine/physics/ccd/linear_sweep.d.ts.map +1 -1
  215. package/src/engine/physics/ccd/linear_sweep.js +3 -16
  216. package/src/engine/physics/cloth/build/cloth_proxy_from_joints.d.ts.map +1 -1
  217. package/src/engine/physics/cloth/build/cloth_proxy_from_joints.js +2 -16
  218. package/src/engine/physics/cloth/ecs/cloth_build_rows.d.ts +13 -1
  219. package/src/engine/physics/cloth/ecs/cloth_build_rows.d.ts.map +1 -1
  220. package/src/engine/physics/cloth/ecs/cloth_build_rows.js +15 -4
  221. package/src/engine/physics/ecs/PhysicsSystem.d.ts.map +1 -1
  222. package/src/engine/physics/ecs/PhysicsSystem.js +2 -5
  223. package/src/engine/physics/inertia/locked_inverse_inertia.d.ts +12 -0
  224. package/src/engine/physics/inertia/locked_inverse_inertia.d.ts.map +1 -0
  225. package/src/engine/physics/inertia/locked_inverse_inertia.js +22 -0
  226. package/src/engine/physics/integration/integrate_velocity.d.ts.map +1 -1
  227. package/src/engine/physics/integration/integrate_velocity.js +3 -18
  228. package/src/engine/physics/mls-mpm/MLS_MPM.d.ts +1 -0
  229. package/src/engine/physics/mls-mpm/MLS_MPM.d.ts.map +1 -1
  230. package/src/engine/physics/mls-mpm/MLS_MPM.js +5 -4
  231. package/src/engine/physics/narrowphase/convex_decomposition.d.ts.map +1 -1
  232. package/src/engine/physics/narrowphase/convex_decomposition.js +7 -16
  233. package/src/engine/physics/vehicle/RaycastVehicle.d.ts.map +1 -1
  234. package/src/engine/physics/vehicle/RaycastVehicle.js +15 -5
  235. package/src/engine/save/StorageBackedList.d.ts +5 -0
  236. package/src/engine/save/StorageBackedList.d.ts.map +1 -1
  237. package/src/engine/save/StorageBackedList.js +161 -144
  238. package/src/engine/simulation/Ticker.d.ts.map +1 -1
  239. package/src/engine/simulation/Ticker.js +394 -391
  240. package/src/engine/sound/simulation/probe/AcousticProbeField.d.ts.map +1 -1
  241. package/src/engine/sound/simulation/probe/AcousticProbeField.js +6 -19
  242. package/src/engine/sound/simulation/probe/probe_edge_visible.d.ts +15 -0
  243. package/src/engine/sound/simulation/probe/probe_edge_visible.d.ts.map +1 -1
  244. package/src/engine/sound/simulation/probe/probe_edge_visible.js +59 -41
  245. package/src/engine/sound/simulation/probe/probe_refine_connectivity.d.ts.map +1 -1
  246. package/src/engine/sound/simulation/probe/probe_refine_connectivity.js +164 -181
  247. package/src/engine/sound/simulation/render/FoaProbeReverbRenderer.d.ts.map +1 -1
  248. package/src/engine/sound/simulation/render/FoaProbeReverbRenderer.js +20 -5
  249. package/src/format/image/avif/av1/decode/Av1FrameContext.d.ts.map +1 -1
  250. package/src/format/image/avif/av1/decode/Av1FrameContext.js +3 -10
  251. package/src/format/image/avif/av1/decode/reconstruct.d.ts +20 -0
  252. package/src/format/image/avif/av1/decode/reconstruct.d.ts.map +1 -1
  253. package/src/format/image/avif/av1/decode/reconstruct.js +22 -9
  254. package/src/format/image/avif/av1/encode/choose_restoration.js +2 -18
  255. package/src/format/image/avif/av1/encode/quantise.d.ts.map +1 -1
  256. package/src/format/image/avif/av1/encode/quantise.js +1 -55
  257. package/src/format/image/avif/av1/filter/loop_restoration.d.ts +9 -0
  258. package/src/format/image/avif/av1/filter/loop_restoration.d.ts.map +1 -1
  259. package/src/format/image/avif/av1/filter/loop_restoration.js +1 -1
  260. package/src/format/texture/basis/transcode/etc1s_to_bc7.js +2 -33
  261. package/src/format/texture/basis/transcode/fit_endpoints.d.ts +11 -0
  262. package/src/format/texture/basis/transcode/fit_endpoints.d.ts.map +1 -1
  263. package/src/format/texture/basis/transcode/fit_endpoints.js +1 -1
  264. package/src/format/texture/basis/uastc/uastc_decode_block.d.ts.map +1 -1
  265. package/src/format/texture/basis/uastc/uastc_decode_block.js +2 -19
  266. package/src/generation/foliage/ANNUAL_SHOOTS_BRIEF_2026_10_25.md +220 -0
  267. package/src/generation/foliage/CROWN_FILLING_BRIEF_2026_10_26.md +172 -0
  268. package/src/generation/foliage/FOLIAGE_DESIGN.md +165 -15
  269. package/src/generation/foliage/LEAF_ARCHITECTURE_BRIEF_2026_10_26.md +158 -0
  270. package/src/generation/foliage/SHOOT_SYSTEMS_ALL_SPECIES_BRIEF_2026_10_26.md +248 -0
  271. package/src/generation/foliage/SPEEDTREE_COMPARISON_2026_10_24.md +694 -0
  272. package/src/generation/foliage/analysis/CrownOpacity.d.ts +118 -0
  273. package/src/generation/foliage/analysis/CrownOpacity.d.ts.map +1 -0
  274. package/src/generation/foliage/analysis/CrownOpacity.js +182 -0
  275. package/src/generation/foliage/analysis/crown_opacity_frames.d.ts +10 -0
  276. package/src/generation/foliage/analysis/crown_opacity_frames.d.ts.map +1 -0
  277. package/src/generation/foliage/analysis/crown_opacity_frames.js +132 -0
  278. package/src/generation/foliage/analysis/crown_opacity_measure.d.ts +51 -0
  279. package/src/generation/foliage/analysis/crown_opacity_measure.d.ts.map +1 -0
  280. package/src/generation/foliage/analysis/crown_opacity_measure.js +649 -0
  281. package/src/generation/foliage/analysis/foliage_measure_leaf_area.d.ts +66 -0
  282. package/src/generation/foliage/analysis/foliage_measure_leaf_area.d.ts.map +1 -0
  283. package/src/generation/foliage/analysis/foliage_measure_leaf_area.js +192 -0
  284. package/src/generation/foliage/analysis/tree_crown_opacity.d.ts +27 -0
  285. package/src/generation/foliage/analysis/tree_crown_opacity.d.ts.map +1 -0
  286. package/src/generation/foliage/analysis/tree_crown_opacity.js +58 -0
  287. package/src/generation/foliage/animation/build_tree_wind_rig.d.ts +3 -2
  288. package/src/generation/foliage/animation/build_tree_wind_rig.d.ts.map +1 -1
  289. package/src/generation/foliage/animation/build_tree_wind_rig.js +12 -30
  290. package/src/generation/foliage/animation/tree_wind_bend_limit.d.ts +12 -0
  291. package/src/generation/foliage/animation/tree_wind_bend_limit.d.ts.map +1 -0
  292. package/src/generation/foliage/animation/tree_wind_bend_limit.js +13 -0
  293. package/src/generation/foliage/asset/TreeAsset.d.ts +5 -0
  294. package/src/generation/foliage/asset/TreeAsset.d.ts.map +1 -1
  295. package/src/generation/foliage/asset/TreeAsset.js +6 -0
  296. package/src/generation/foliage/asset/generate_tree.d.ts.map +1 -1
  297. package/src/generation/foliage/asset/generate_tree.js +23 -6
  298. package/src/generation/foliage/config/{BranchLevelConfig.d.ts → BranchGeneratorConfig.d.ts} +61 -75
  299. package/src/generation/foliage/config/BranchGeneratorConfig.d.ts.map +1 -0
  300. package/src/generation/foliage/config/{BranchLevelConfig.js → BranchGeneratorConfig.js} +83 -126
  301. package/src/generation/foliage/config/BranchSpawnRule.d.ts +118 -0
  302. package/src/generation/foliage/config/BranchSpawnRule.d.ts.map +1 -0
  303. package/src/generation/foliage/config/BranchSpawnRule.js +217 -0
  304. package/src/generation/foliage/config/FoliageCardType.d.ts +1 -1
  305. package/src/generation/foliage/config/FoliageCardType.js +2 -2
  306. package/src/generation/foliage/config/FoliageConfig.d.ts +23 -45
  307. package/src/generation/foliage/config/FoliageConfig.d.ts.map +1 -1
  308. package/src/generation/foliage/config/FoliageConfig.js +47 -93
  309. package/src/generation/foliage/config/FoliageMaterialConfig.d.ts +12 -20
  310. package/src/generation/foliage/config/FoliageMaterialConfig.d.ts.map +1 -1
  311. package/src/generation/foliage/config/FoliageMaterialConfig.js +261 -279
  312. package/src/generation/foliage/config/FoliageSpawnRule.d.ts +77 -0
  313. package/src/generation/foliage/config/FoliageSpawnRule.d.ts.map +1 -0
  314. package/src/generation/foliage/config/FoliageSpawnRule.js +135 -0
  315. package/src/generation/foliage/config/FoliageTileContent.d.ts +9 -0
  316. package/src/generation/foliage/config/FoliageTileContent.d.ts.map +1 -0
  317. package/src/generation/foliage/config/FoliageTileContent.js +12 -0
  318. package/src/generation/foliage/config/LeafApexShape.d.ts +12 -0
  319. package/src/generation/foliage/config/LeafApexShape.d.ts.map +1 -0
  320. package/src/generation/foliage/config/LeafApexShape.js +17 -0
  321. package/src/generation/foliage/config/LeafArchitecture.d.ts +155 -0
  322. package/src/generation/foliage/config/LeafArchitecture.d.ts.map +1 -0
  323. package/src/generation/foliage/config/LeafArchitecture.js +288 -0
  324. package/src/generation/foliage/config/LeafBaseShape.d.ts +14 -0
  325. package/src/generation/foliage/config/LeafBaseShape.d.ts.map +1 -0
  326. package/src/generation/foliage/config/LeafBaseShape.js +21 -0
  327. package/src/generation/foliage/config/LeafLobation.d.ts +10 -0
  328. package/src/generation/foliage/config/LeafLobation.d.ts.map +1 -0
  329. package/src/generation/foliage/config/LeafLobation.js +14 -0
  330. package/src/generation/foliage/config/PhyllotaxisMode.d.ts +11 -0
  331. package/src/generation/foliage/config/PhyllotaxisMode.d.ts.map +1 -1
  332. package/src/generation/foliage/config/PhyllotaxisMode.js +36 -0
  333. package/src/generation/foliage/config/ShootBudZone.d.ts +105 -0
  334. package/src/generation/foliage/config/ShootBudZone.d.ts.map +1 -0
  335. package/src/generation/foliage/config/ShootBudZone.js +219 -0
  336. package/src/generation/foliage/config/ShootGrowthConfig.d.ts +84 -0
  337. package/src/generation/foliage/config/ShootGrowthConfig.d.ts.map +1 -0
  338. package/src/generation/foliage/config/ShootGrowthConfig.js +146 -0
  339. package/src/generation/foliage/config/ShootSystemRule.d.ts +144 -0
  340. package/src/generation/foliage/config/ShootSystemRule.d.ts.map +1 -0
  341. package/src/generation/foliage/config/ShootSystemRule.js +316 -0
  342. package/src/generation/foliage/config/TreeLODConfig.d.ts +1 -1
  343. package/src/generation/foliage/config/TreeLODConfig.js +1 -1
  344. package/src/generation/foliage/config/TreeSpeciesConfig.d.ts +40 -8
  345. package/src/generation/foliage/config/TreeSpeciesConfig.d.ts.map +1 -1
  346. package/src/generation/foliage/config/TreeSpeciesConfig.js +124 -68
  347. package/src/generation/foliage/config/TreeWindConfig.d.ts +23 -10
  348. package/src/generation/foliage/config/TreeWindConfig.d.ts.map +1 -1
  349. package/src/generation/foliage/config/TreeWindConfig.js +34 -25
  350. package/src/generation/foliage/index.d.ts +19 -2
  351. package/src/generation/foliage/index.js +63 -44
  352. package/src/generation/foliage/material/FoliageAtlasCutout.d.ts +59 -0
  353. package/src/generation/foliage/material/FoliageAtlasCutout.d.ts.map +1 -0
  354. package/src/generation/foliage/material/FoliageAtlasCutout.js +93 -0
  355. package/src/generation/foliage/material/compute_foliage_variant_atlas_layout.d.ts +26 -0
  356. package/src/generation/foliage/material/compute_foliage_variant_atlas_layout.d.ts.map +1 -0
  357. package/src/generation/foliage/material/compute_foliage_variant_atlas_layout.js +63 -0
  358. package/src/generation/foliage/material/foliage_atlas_cutout.d.ts +34 -0
  359. package/src/generation/foliage/material/foliage_atlas_cutout.d.ts.map +1 -0
  360. package/src/generation/foliage/material/foliage_atlas_cutout.js +174 -0
  361. package/src/generation/foliage/material/foliage_tile.d.ts +110 -0
  362. package/src/generation/foliage/material/foliage_tile.d.ts.map +1 -0
  363. package/src/generation/foliage/material/foliage_tile.js +286 -0
  364. package/src/generation/foliage/material/leaf_geometry.d.ts +103 -0
  365. package/src/generation/foliage/material/leaf_geometry.d.ts.map +1 -0
  366. package/src/generation/foliage/material/leaf_geometry.js +528 -0
  367. package/src/generation/foliage/material/make_foliage_material.d.ts +13 -33
  368. package/src/generation/foliage/material/make_foliage_material.d.ts.map +1 -1
  369. package/src/generation/foliage/material/make_foliage_material.js +356 -605
  370. package/src/generation/foliage/mesh/foliage_collect_attachments.d.ts +39 -4
  371. package/src/generation/foliage/mesh/foliage_collect_attachments.d.ts.map +1 -1
  372. package/src/generation/foliage/mesh/foliage_collect_attachments.js +637 -569
  373. package/src/generation/foliage/mesh/interpolate_ring_skin_weights4.d.ts +48 -0
  374. package/src/generation/foliage/mesh/interpolate_ring_skin_weights4.d.ts.map +1 -0
  375. package/src/generation/foliage/mesh/interpolate_ring_skin_weights4.js +232 -0
  376. package/src/generation/foliage/mesh/tree_mesh_build_bark.d.ts.map +1 -1
  377. package/src/generation/foliage/mesh/tree_mesh_build_bark.js +1023 -1049
  378. package/src/generation/foliage/mesh/tree_mesh_build_foliage.d.ts +9 -2
  379. package/src/generation/foliage/mesh/tree_mesh_build_foliage.d.ts.map +1 -1
  380. package/src/generation/foliage/mesh/tree_mesh_build_foliage.js +467 -454
  381. package/src/generation/foliage/presets/make_tree_species_preset.d.ts.map +1 -1
  382. package/src/generation/foliage/presets/make_tree_species_preset.js +1648 -870
  383. package/src/generation/foliage/skeleton/ShootFrameworkHash.d.ts +35 -0
  384. package/src/generation/foliage/skeleton/ShootFrameworkHash.d.ts.map +1 -0
  385. package/src/generation/foliage/skeleton/ShootFrameworkHash.js +129 -0
  386. package/src/generation/foliage/skeleton/ShootGirth.d.ts +51 -0
  387. package/src/generation/foliage/skeleton/ShootGirth.d.ts.map +1 -0
  388. package/src/generation/foliage/skeleton/ShootGirth.js +212 -0
  389. package/src/generation/foliage/skeleton/ShootLightField.d.ts +73 -0
  390. package/src/generation/foliage/skeleton/ShootLightField.d.ts.map +1 -0
  391. package/src/generation/foliage/skeleton/ShootLightField.js +197 -0
  392. package/src/generation/foliage/skeleton/TreeSkeleton.d.ts +106 -3
  393. package/src/generation/foliage/skeleton/TreeSkeleton.d.ts.map +1 -1
  394. package/src/generation/foliage/skeleton/TreeSkeleton.js +217 -39
  395. package/src/generation/foliage/skeleton/flare_lobe_phase_offset.d.ts +13 -0
  396. package/src/generation/foliage/skeleton/flare_lobe_phase_offset.d.ts.map +1 -0
  397. package/src/generation/foliage/skeleton/flare_lobe_phase_offset.js +16 -0
  398. package/src/generation/foliage/skeleton/foliage_card_density.d.ts +71 -0
  399. package/src/generation/foliage/skeleton/foliage_card_density.d.ts.map +1 -0
  400. package/src/generation/foliage/skeleton/foliage_card_density.js +101 -0
  401. package/src/generation/foliage/skeleton/foliage_senescence.d.ts +101 -0
  402. package/src/generation/foliage/skeleton/foliage_senescence.d.ts.map +1 -0
  403. package/src/generation/foliage/skeleton/foliage_senescence.js +149 -0
  404. package/src/generation/foliage/skeleton/foliage_unit_cards.d.ts +76 -0
  405. package/src/generation/foliage/skeleton/foliage_unit_cards.d.ts.map +1 -0
  406. package/src/generation/foliage/skeleton/foliage_unit_cards.js +95 -0
  407. package/src/generation/foliage/skeleton/shoot_demography.d.ts +22 -0
  408. package/src/generation/foliage/skeleton/shoot_demography.d.ts.map +1 -0
  409. package/src/generation/foliage/skeleton/shoot_demography.js +96 -0
  410. package/src/generation/foliage/skeleton/shoot_geometry.d.ts +66 -0
  411. package/src/generation/foliage/skeleton/shoot_geometry.d.ts.map +1 -0
  412. package/src/generation/foliage/skeleton/shoot_geometry.js +109 -0
  413. package/src/generation/foliage/skeleton/shoot_systems_simulate.d.ts +166 -0
  414. package/src/generation/foliage/skeleton/shoot_systems_simulate.d.ts.map +1 -0
  415. package/src/generation/foliage/skeleton/shoot_systems_simulate.js +588 -0
  416. package/src/generation/foliage/skeleton/tree_skeleton_assign_skin_joints.d.ts +28 -12
  417. package/src/generation/foliage/skeleton/tree_skeleton_assign_skin_joints.d.ts.map +1 -1
  418. package/src/generation/foliage/skeleton/tree_skeleton_assign_skin_joints.js +137 -102
  419. package/src/generation/foliage/skeleton/tree_skeleton_compute_joint_mechanics.d.ts +112 -0
  420. package/src/generation/foliage/skeleton/tree_skeleton_compute_joint_mechanics.d.ts.map +1 -0
  421. package/src/generation/foliage/skeleton/tree_skeleton_compute_joint_mechanics.js +408 -0
  422. package/src/generation/foliage/skeleton/tree_skeleton_compute_pipe_radii.d.ts.map +1 -1
  423. package/src/generation/foliage/skeleton/tree_skeleton_compute_pipe_radii.js +208 -206
  424. package/src/generation/foliage/skeleton/tree_skeleton_grow.d.ts +5 -2
  425. package/src/generation/foliage/skeleton/tree_skeleton_grow.d.ts.map +1 -1
  426. package/src/generation/foliage/skeleton/tree_skeleton_grow.js +2048 -1871
  427. package/src/generation/foliage/skeleton/tree_skeleton_grow_shoots.d.ts +17 -0
  428. package/src/generation/foliage/skeleton/tree_skeleton_grow_shoots.d.ts.map +1 -0
  429. package/src/generation/foliage/skeleton/tree_skeleton_grow_shoots.js +231 -0
  430. package/src/generation/foliage/skeleton/tree_skeleton_read_joint_motion.d.ts +14 -0
  431. package/src/generation/foliage/skeleton/tree_skeleton_read_joint_motion.d.ts.map +1 -0
  432. package/src/generation/foliage/skeleton/tree_skeleton_read_joint_motion.js +26 -0
  433. package/src/generation/foliage/skeleton/tree_skeleton_read_joint_parents.d.ts +10 -0
  434. package/src/generation/foliage/skeleton/tree_skeleton_read_joint_parents.d.ts.map +1 -0
  435. package/src/generation/foliage/skeleton/tree_skeleton_read_joint_parents.js +20 -0
  436. package/src/generation/grid/generation/road/GridTaskGenerateRoads.d.ts.map +1 -1
  437. package/src/generation/grid/generation/road/GridTaskGenerateRoads.js +4 -1
  438. package/src/generation/markers/GridCellActionPlaceMarkerGroup.d.ts +1 -0
  439. package/src/generation/markers/GridCellActionPlaceMarkerGroup.d.ts.map +1 -1
  440. package/src/generation/markers/GridCellActionPlaceMarkerGroup.js +98 -86
  441. package/src/shade/SHADER_F16_PROPOSAL_2026_10_24.md +263 -0
  442. package/src/shade/descriptor/WebGPUExtensionType.d.ts +17 -0
  443. package/src/shade/descriptor/WebGPUExtensionType.d.ts.map +1 -1
  444. package/src/shade/descriptor/WebGPUExtensionType.js +31 -1
  445. package/src/shade/playground/foliage_wind/FoliageRigOverlay.d.ts +37 -0
  446. package/src/shade/playground/foliage_wind/FoliageRigOverlay.d.ts.map +1 -0
  447. package/src/shade/playground/foliage_wind/FoliageRigOverlay.js +491 -0
  448. package/src/shade/playground/foliage_wind/foliage_world.d.ts.map +1 -1
  449. package/src/shade/playground/foliage_wind/foliage_world.js +600 -602
  450. package/src/shade/playground/foliage_wind/index.html +6 -0
  451. package/src/shade/playground/foliage_wind/main.js +14 -0
  452. package/src/shade/renderer/animation/GPUAnimationManager.d.ts.map +1 -1
  453. package/src/shade/renderer/animation/GPUAnimationManager.js +2 -1
  454. package/src/shade/renderer/animation/foliage/FoliageWindJoint.d.ts +2 -1
  455. package/src/shade/renderer/animation/foliage/FoliageWindJoint.d.ts.map +1 -1
  456. package/src/shade/renderer/animation/foliage/FoliageWindJoint.js +2 -1
  457. package/src/shade/renderer/animation/foliage/chunk_foliage_wind_step.d.ts.map +1 -1
  458. package/src/shade/renderer/animation/foliage/chunk_foliage_wind_step.js +4 -2
  459. package/src/shade/renderer/buffer/table/GPUTypedTable.js +1 -1
  460. package/src/shade/renderer/buffer/table/single/GPUSingleTypeTable.d.ts.map +1 -1
  461. package/src/shade/renderer/buffer/table/single/GPUSingleTypeTable.js +403 -401
  462. package/src/shade/renderer/camera/OrbitalCameraController.d.ts +1 -62
  463. package/src/shade/renderer/camera/OrbitalCameraController.d.ts.map +1 -1
  464. package/src/shade/renderer/camera/OrbitalCameraController.js +1 -374
  465. package/src/shade/renderer/deferred/indirect/chunk_lpv_2d_cache_sample_irradiance.d.ts.map +1 -1
  466. package/src/shade/renderer/deferred/indirect/chunk_lpv_2d_cache_sample_irradiance.js +3 -0
  467. package/src/shade/renderer/deferred/indirect/chunk_lpv_sample_light.d.ts.map +1 -1
  468. package/src/shade/renderer/deferred/indirect/chunk_lpv_sample_light.js +6 -1
  469. package/src/shade/renderer/dynamic/shader_dynamic_mesh_avboit_splat.js +1 -1
  470. package/src/shade/renderer/fluid/GPUFluidCascade.d.ts +2 -2
  471. package/src/shade/renderer/fluid/GPUFluidCascade.d.ts.map +1 -1
  472. package/src/shade/renderer/fluid/GPUFluidCascade.js +6 -3
  473. package/src/shade/renderer/fluid/GPU_FLUID_OCCUPANCY_AND_SOTA_REVIEW_2026_10_26.md +361 -0
  474. package/src/shade/renderer/fluid/coupling/chunk_fluid_cascade_parent.d.ts.map +1 -1
  475. package/src/shade/renderer/fluid/coupling/chunk_fluid_cascade_parent.js +335 -241
  476. package/src/shade/renderer/fluid/coupling/shader_fluid_cascade_ghosts.d.ts.map +1 -1
  477. package/src/shade/renderer/fluid/coupling/shader_fluid_cascade_ghosts.js +108 -101
  478. package/src/shade/renderer/fluid/forcing/chunk_fluid_forcing_query_select.d.ts.map +1 -1
  479. package/src/shade/renderer/fluid/forcing/chunk_fluid_forcing_query_select.js +69 -67
  480. package/src/shade/renderer/fluid/forcing/shader_fluid_forcing_apply.d.ts +7 -6
  481. package/src/shade/renderer/fluid/forcing/shader_fluid_forcing_apply.d.ts.map +1 -1
  482. package/src/shade/renderer/fluid/forcing/shader_fluid_forcing_apply.js +341 -287
  483. package/src/shade/renderer/fluid/mac/FluidMacPasses.d.ts +6 -4
  484. package/src/shade/renderer/fluid/mac/FluidMacPasses.d.ts.map +1 -1
  485. package/src/shade/renderer/fluid/mac/FluidMacPasses.js +427 -400
  486. package/src/shade/renderer/fluid/mac/chunk_fluid_mac_seams.d.ts +10 -5
  487. package/src/shade/renderer/fluid/mac/chunk_fluid_mac_seams.d.ts.map +1 -1
  488. package/src/shade/renderer/fluid/mac/chunk_fluid_mac_seams.js +532 -190
  489. package/src/shade/renderer/fluid/mac/chunk_v3_mac_lattice_corners.d.ts.map +1 -1
  490. package/src/shade/renderer/fluid/mac/chunk_v3_mac_lattice_corners.js +231 -237
  491. package/src/shade/renderer/fluid/mac/shader_fluid_mac_advect_correct.d.ts +2 -2
  492. package/src/shade/renderer/fluid/mac/shader_fluid_mac_advect_correct.d.ts.map +1 -1
  493. package/src/shade/renderer/fluid/mac/shader_fluid_mac_advect_correct.js +282 -245
  494. package/src/shade/renderer/fluid/mac/shader_fluid_mac_advect_predict.d.ts +1 -3
  495. package/src/shade/renderer/fluid/mac/shader_fluid_mac_advect_predict.d.ts.map +1 -1
  496. package/src/shade/renderer/fluid/mac/shader_fluid_mac_advect_predict.js +139 -109
  497. package/src/shade/renderer/fluid/mac/shader_fluid_mac_curl.d.ts +6 -6
  498. package/src/shade/renderer/fluid/mac/shader_fluid_mac_curl.d.ts.map +1 -1
  499. package/src/shade/renderer/fluid/mac/shader_fluid_mac_curl.js +257 -222
  500. package/src/shade/renderer/fluid/mac/shader_fluid_mac_divergence.d.ts +8 -7
  501. package/src/shade/renderer/fluid/mac/shader_fluid_mac_divergence.d.ts.map +1 -1
  502. package/src/shade/renderer/fluid/mac/shader_fluid_mac_divergence.js +119 -92
  503. package/src/shade/renderer/fluid/mac/shader_fluid_mac_gradient.d.ts +6 -9
  504. package/src/shade/renderer/fluid/mac/shader_fluid_mac_gradient.d.ts.map +1 -1
  505. package/src/shade/renderer/fluid/mac/shader_fluid_mac_gradient.js +229 -181
  506. package/src/shade/renderer/fluid/pressure/GPUFluidPressureSolve.d.ts +17 -7
  507. package/src/shade/renderer/fluid/pressure/GPUFluidPressureSolve.d.ts.map +1 -1
  508. package/src/shade/renderer/fluid/pressure/GPUFluidPressureSolve.js +634 -621
  509. package/src/shade/renderer/fluid/pressure/shader_fluid_mg_residual_restrict.d.ts +8 -6
  510. package/src/shade/renderer/fluid/pressure/shader_fluid_mg_residual_restrict.d.ts.map +1 -1
  511. package/src/shade/renderer/fluid/pressure/shader_fluid_mg_residual_restrict.js +166 -149
  512. package/src/shade/renderer/fluid/pressure/shader_fluid_mg_smooth.d.ts +8 -6
  513. package/src/shade/renderer/fluid/pressure/shader_fluid_mg_smooth.d.ts.map +1 -1
  514. package/src/shade/renderer/fluid/pressure/shader_fluid_mg_smooth.js +219 -183
  515. package/src/shade/renderer/fluid/publish/shader_fluid_wind_publish.d.ts.map +1 -1
  516. package/src/shade/renderer/fluid/publish/shader_fluid_wind_publish.js +142 -122
  517. package/src/shade/renderer/geometry/meshlet/COMPACTION_PLAN_2026_09_16.md +674 -663
  518. package/src/shade/renderer/geometry/meshlet/GPUMeshletManager.d.ts +1 -1
  519. package/src/shade/renderer/geometry/meshlet/GPUMeshletManager.d.ts.map +1 -1
  520. package/src/shade/renderer/geometry/meshlet/GPUMeshletManager.js +63 -29
  521. package/src/shade/renderer/geometry/meshlet/build/meshoptimizer/geometry_to_meshlets_meshoptimizer.d.ts.map +1 -1
  522. package/src/shade/renderer/geometry/meshlet/build/meshoptimizer/geometry_to_meshlets_meshoptimizer.js +77 -87
  523. package/src/shade/renderer/geometry/meshlet/build/meshoptimizer/meshopt_clusterizer.d.ts.map +1 -1
  524. package/src/shade/renderer/geometry/meshlet/build/meshoptimizer/meshopt_clusterizer.js +4 -3
  525. package/src/shade/renderer/geometry/meshlet/shader_meshlet_metadata_address_patch.d.ts +11 -11
  526. package/src/shade/renderer/geometry/meshlet/shader_meshlet_metadata_address_patch.d.ts.map +1 -1
  527. package/src/shade/renderer/geometry/meshlet/shader_meshlet_metadata_address_patch.js +17 -19
  528. package/src/shade/renderer/global_illumination/lpv/graph_bake_irradiance_lookup_2d.js +4 -4
  529. package/src/shade/renderer/global_illumination/probe/octahedral/sample/chunk_lpv_mesh_interpolate_radiance_via_atlas.d.ts.map +1 -1
  530. package/src/shade/renderer/global_illumination/probe/octahedral/sample/chunk_lpv_mesh_interpolate_radiance_via_atlas.js +5 -1
  531. package/src/shade/renderer/loader/gltf/load_gltf.d.ts.map +1 -1
  532. package/src/shade/renderer/loader/gltf/load_gltf.js +11 -35
  533. package/src/shade/renderer/loader/usd/load_usd.d.ts.map +1 -1
  534. package/src/shade/renderer/loader/usd/load_usd.js +6 -19
  535. package/src/shade/renderer/particles/shaders/shader_particle_avboit_draw.d.ts.map +1 -1
  536. package/src/shade/renderer/particles/shaders/shader_particle_avboit_draw.js +199 -193
  537. package/src/shade/renderer/particles/shaders/shader_particle_avboit_splat.d.ts.map +1 -1
  538. package/src/shade/renderer/particles/shaders/shader_particle_avboit_splat.js +151 -143
  539. package/src/shade/renderer/postprocess/bloom/chunk_karis_blur4x4_sample.d.ts.map +1 -1
  540. package/src/shade/renderer/postprocess/bloom/chunk_karis_blur4x4_sample.js +11 -5
  541. package/src/shade/renderer/postprocess/denoise/graph_atorus_denoise_luma.d.ts.map +1 -1
  542. package/src/shade/renderer/postprocess/denoise/graph_atorus_denoise_luma.js +6 -18
  543. package/src/shade/renderer/postprocess/gtao/GTAO.js +1 -1
  544. package/src/shade/renderer/postprocess/gtao/ao_reproject_shader.d.ts.map +1 -1
  545. package/src/shade/renderer/postprocess/gtao/ao_reproject_shader.js +3 -5
  546. package/src/shade/renderer/postprocess/gtao/fragment_shader_gtao_with_irradiance.js +1 -1
  547. package/src/shade/renderer/postprocess/nss/chunk_nss_luma_derivative.d.ts.map +1 -1
  548. package/src/shade/renderer/postprocess/nss/chunk_nss_luma_derivative.js +7 -3
  549. package/src/shade/renderer/postprocess/nss/shader_nss_postprocess.d.ts.map +1 -1
  550. package/src/shade/renderer/postprocess/nss/shader_nss_postprocess.js +4 -2
  551. package/src/shade/renderer/postprocess/nss/shader_nss_preprocess.d.ts.map +1 -1
  552. package/src/shade/renderer/postprocess/nss/shader_nss_preprocess.js +4 -1
  553. package/src/shade/renderer/postprocess/ssr/downsample_karis.d.ts.map +1 -1
  554. package/src/shade/renderer/postprocess/ssr/downsample_karis.js +6 -3
  555. package/src/shade/renderer/postprocess/ssr/reproject/chunk_ssr_temporal_accumulate.d.ts.map +1 -1
  556. package/src/shade/renderer/postprocess/ssr/reproject/chunk_ssr_temporal_accumulate.js +4 -3
  557. package/src/shade/renderer/postprocess/ssr/resolve/ssr_resolve_shader.d.ts.map +1 -1
  558. package/src/shade/renderer/postprocess/ssr/resolve/ssr_resolve_shader.js +4 -1
  559. package/src/shade/renderer/postprocess/ssr/ssr_spatial_denoise_shader.d.ts.map +1 -1
  560. package/src/shade/renderer/postprocess/ssr/ssr_spatial_denoise_shader.js +4 -2
  561. package/src/shade/renderer/postprocess/taa/chunk_taa_tonemap.d.ts.map +1 -1
  562. package/src/shade/renderer/postprocess/taa/chunk_taa_tonemap.js +35 -39
  563. package/src/shade/renderer/postprocess/taa/chunk_taa_tonemap_inv.d.ts.map +1 -1
  564. package/src/shade/renderer/postprocess/taa/chunk_taa_tonemap_inv.js +20 -17
  565. package/src/shade/renderer/postprocess/taa/shader_taa.d.ts.map +1 -1
  566. package/src/shade/renderer/postprocess/taa/shader_taa.js +6 -3
  567. package/src/shade/renderer/rasterize/expand/bucket/meshlet/shader_meshlets_extract_bucket.d.ts.map +1 -1
  568. package/src/shade/renderer/rasterize/expand/bucket/meshlet/shader_meshlets_extract_bucket.js +3 -1
  569. package/src/shade/renderer/rasterize/native/avboit/avboit_draw_fragment_body.js +1 -1
  570. package/src/shade/renderer/rasterize/native/avboit/chunk_avboit_splat_slice.js +2 -2
  571. package/src/shade/renderer/rasterize/native/avboit/graph_rasterize_meshes_transparent_avboit.js +1 -1
  572. package/src/shade/renderer/rasterize/native/avboit/shader_avboit_integrate.d.ts.map +1 -1
  573. package/src/shade/renderer/rasterize/native/avboit/shader_avboit_integrate.js +92 -83
  574. package/src/shade/renderer/rasterize/native/avboit/shader_avboit_splat.js +1 -1
  575. package/src/shade/renderer/shader/ShaderDescriptor.d.ts.map +1 -1
  576. package/src/shade/renderer/shader/ShaderDescriptor.js +12 -4
  577. package/src/shade/renderer/shader/chunk/bvh/chunk_bvh_query_aabb_cooperative.d.ts.map +1 -1
  578. package/src/shade/renderer/shader/chunk/bvh/chunk_bvh_query_aabb_cooperative.js +294 -286
  579. package/src/shade/renderer/shader/chunk/light/lpv/chunk_lpv_interpolate_probe_irradiance8.js +5 -5
  580. package/src/shade/renderer/shader/chunk/light/lpv/chunk_lpv_mesh_interpolate_probe.d.ts.map +1 -1
  581. package/src/shade/renderer/shader/chunk/light/lpv/chunk_lpv_mesh_interpolate_probe.js +5 -3
  582. package/src/shade/renderer/shader/chunk/light/lpv/chunk_lpv_mesh_interpolate_probe_irradiance.d.ts.map +1 -1
  583. package/src/shade/renderer/shader/chunk/light/lpv/chunk_lpv_mesh_interpolate_probe_irradiance.js +9 -6
  584. package/src/shade/renderer/shader/chunk/light/lpv/chunk_lpv_sample_sh3_at.d.ts.map +1 -1
  585. package/src/shade/renderer/shader/chunk/light/lpv/chunk_lpv_sample_sh3_at.js +33 -38
  586. package/src/shade/renderer/shader/resource/ShaderResourceSetDescriptor.d.ts.map +1 -1
  587. package/src/shade/renderer/shader/resource/ShaderResourceSetDescriptor.js +690 -675
  588. package/src/shade/renderer/shader/type/WebGPUArray.d.ts +3 -0
  589. package/src/shade/renderer/shader/type/WebGPUArray.d.ts.map +1 -1
  590. package/src/shade/renderer/shader/type/WebGPUArray.js +185 -167
  591. package/src/shade/renderer/shader/type/WebGPUStruct.d.ts.map +1 -1
  592. package/src/shade/renderer/shader/type/WebGPUStruct.js +461 -455
  593. package/src/shade/renderer/shader/type/serde/read_gpu_typed_buffer.d.ts.map +1 -1
  594. package/src/shade/renderer/shader/type/serde/read_gpu_typed_buffer.js +335 -211
  595. package/src/shade/renderer/shader/type/serde/write_gpu_typed_buffer.d.ts.map +1 -1
  596. package/src/shade/renderer/shader/type/serde/write_gpu_typed_buffer.js +329 -221
  597. package/src/shade/renderer/shader/type/type_has_f16.d.ts +12 -0
  598. package/src/shade/renderer/shader/type/type_has_f16.d.ts.map +1 -0
  599. package/src/shade/renderer/shader/type/type_has_f16.js +66 -0
  600. package/src/shade/renderer/volumetrics/shader_volumetrics_build_lighting.d.ts.map +1 -1
  601. package/src/shade/renderer/volumetrics/shader_volumetrics_build_lighting.js +16 -2
  602. package/src/shade/renderer/volumetrics/taa/shader_volumetrics_taa.d.ts.map +1 -1
  603. package/src/shade/renderer/volumetrics/taa/shader_volumetrics_taa.js +5 -2
  604. package/src/shade/renderer/water/shader_water_avboit.js +1 -1
  605. package/src/shade/wgsl/emulator/WGSLJavaScriptCompiler.d.ts.map +1 -1
  606. package/src/shade/wgsl/emulator/WGSLJavaScriptCompiler.js +260 -23
  607. package/src/shade/wgsl/emulator/WGSLLanguageCore.d.ts +6 -7
  608. package/src/shade/wgsl/emulator/WGSLLanguageCore.d.ts.map +1 -1
  609. package/src/shade/wgsl/emulator/WGSLLanguageCore.js +269 -69
  610. package/src/shade/wgsl/validate_wgsl_source.d.ts.map +1 -1
  611. package/src/shade/wgsl/validate_wgsl_source.js +27 -1
  612. package/src/view/controller/controls/ListController.d.ts.map +1 -1
  613. package/src/view/controller/controls/ListController.js +118 -113
  614. package/src/view/controller/controls/Vector1Control.js +97 -97
  615. package/src/view/elements/image/SvgImageView.d.ts +1 -0
  616. package/src/view/elements/image/SvgImageView.d.ts.map +1 -1
  617. package/src/view/elements/image/SvgImageView.js +92 -90
  618. package/src/view/minimap/dom/MinimapTerrainView.d.ts +1 -0
  619. package/src/view/minimap/dom/MinimapTerrainView.d.ts.map +1 -1
  620. package/src/view/minimap/dom/MinimapTerrainView.js +151 -147
  621. package/src/view/tooltip/gml/TooltipParser.js +2 -2
  622. package/src/engine/network/PriorityFetch.d.ts +0 -59
  623. package/src/engine/network/PriorityFetch.d.ts.map +0 -1
  624. package/src/engine/network/PriorityFetch.js +0 -193
  625. package/src/generation/foliage/config/BranchLevelConfig.d.ts.map +0 -1
@@ -1,286 +1,294 @@
1
- import { WebGPUExtensionType } from "../../../../descriptor/WebGPUExtensionType.js";
2
- import { CodeChunk } from "../../compiler/CodeChunk.js";
3
- import { chunk_sort_bitonic_comparator } from "../../../gpu_primitive/sort/chunk_sort_bitonic_comparator.js";
4
- import { BVH2_NODE_STRUCT } from "./BVH2_NODE_STRUCT.js";
5
- import { BVH_NULL_NODE_DEFINITION } from "./BVH_NULL_NODE_DEFINITION.js";
6
- import { chunk_bvh_query_aabb_frontier } from "./chunk_bvh_query_aabb_frontier.js";
7
-
8
- /**
9
- * Every leaf of a BVH whose box overlaps one query box, found by a whole workgroup together and
10
- * returned as payloads in ascending order.
11
- *
12
- * ## Why not a stack per thread
13
- *
14
- * The engine's traversals (`chunk_sdf_query_distance`, `chunk_ray_query_*`) walk a stack per
15
- * thread with no cap on visits, which is right for one ray per thread and wrong for one box per
16
- * workgroup: the box meets a subtree, not a path, and one thread walking it serially is the slowest
17
- * thread of the dispatch. This expands the tree a **level at a time** instead, as the vgeo cut does
18
- * its descent: every node on the current level is tested by its own invocation, the survivors'
19
- * children are appended to the next level, overlapping leaves to the candidate list, and a barrier
20
- * separates the levels. Per-invocation work is bounded by the depth of the tree, not by the size of
21
- * the answer.
22
- *
23
- * ## The contract
24
- *
25
- * Call `bvh_query_aabb_cooperative(root, query, lane)` from every invocation of a workgroup of
26
- * exactly `BVH_QUERY_AABB_WORKGROUP_SIZE` invocations, in uniform control flow, with `lane` the
27
- * `local_invocation_index` and `root` and `query` the same in every invocation. `root` is the
28
- * tree's root word (word 0 of `BVH_BUFFER_LAYOUT`), and `BVH_NULL_NODE` for an empty tree. `query`
29
- * is `[min.xyz, max.xyz]`; touching counts as overlapping, as in `aabb3_intersects_aabb3`.
30
- *
31
- * It returns a `BVHQueryAABBResult` whose fields are workgroup-uniform, so they can bound the
32
- * caller's loops. The payloads are `bvh_query_aabb_candidates[0, candidate_count)`, ascending, and
33
- * visible to every invocation when the call returns. They stay there until the next query.
34
- *
35
- * The node layout is `BVH_BUFFER_LAYOUT`'s: a node is a leaf exactly when `child_1` is
36
- * `BVH_NULL_NODE`, and then `child_2` is its payload.
37
- *
38
- * ## The seam: two functions the enclosing shader defines
39
- *
40
- * The chunk binds nothing. It reads the tree and filters leaves through two functions the shader
41
- * that includes it must define, in the manner of the particle VM's `vm_reg_read` and
42
- * `vm_reg_write`:
43
- *
44
- * - `fn bvh_query_aabb_node(index: u32) -> BVH2Node` returns node `index`, where `BVH2Node` is
45
- * `BVH2_NODE_STRUCT.wgsl_ref`. A tree bound as `BVH_STRUCT` answers with `tree.nodes[index]`; one
46
- * inside a word arena reads its eight words.
47
- * - `fn bvh_query_aabb_accept_leaf(payload: u32, bounds: array<f32, 6>) -> bool` is asked about
48
- * every leaf that overlaps the box, before it takes a place on the list. A caller with nothing to
49
- * filter returns `true`. The fluid's resolution cull lives here: a leaf too small for the cascade
50
- * is refused before it can crowd out one that is not.
51
- *
52
- * ## Deterministic order
53
- *
54
- * Appends from different subgroups land in whatever order the hardware runs them, so the list is
55
- * sorted by payload before it is returned: the bitonic network of `chunk_sort_bitonic_comparator`
56
- * over the smallest power-of-two prefix that holds the candidates (`sort_bitonic_size`), padded
57
- * with `0xffffffff`, one compare-exchange per invocation per stage. A payload that is a stable row index then makes "the lowest K" the same K every frame for
58
- * the same overlaps, however the traversal was scheduled.
59
- *
60
- * ## Bounds, and what is counted
61
- *
62
- * Nothing is dropped silently. A level whose appends pass `BVH_QUERY_AABB_FRONTIER_CAPACITY`, and a
63
- * list still holding nodes when `BVH_QUERY_AABB_LEVEL_BUDGET` levels have been expanded, add those
64
- * nodes to `nodes_dropped`: subtrees never tested. A leaf that passes the filter when the candidate
65
- * list is full adds to `candidates_dropped`. With both zero the candidates are every overlapping
66
- * leaf the filter accepted; with either non-zero they are a subset, and the lowest K of them need
67
- * not be the lowest K overall.
68
- *
69
- * Per invocation, at most `BVH_QUERY_AABB_LEVEL_BUDGET * BVH_QUERY_AABB_FRONTIER_ROUNDS` = 51 * 4 =
70
- * 204 node reads and filter calls, then two padding writes and 28 compare-exchanges. A query that
71
- * meets nothing costs one level: the root is read, misses, and the loop leaves.
72
- *
73
- * Workgroup memory: two lists of 256 node indices, 128 payloads and five words, 2580 bytes.
74
- *
75
- * ## Subgroups
76
- *
77
- * Appends are aggregated per subgroup: an exclusive add numbers the subgroup's appends, one elected
78
- * invocation reserves them all with one workgroup `atomicAdd`, and a broadcast hands each
79
- * invocation its base. Nothing assumes which invocations share a subgroup or that a subgroup's
80
- * invocations are contiguous in `local_invocation_index`: a subgroup reserves a run of its own
81
- * wherever it lands. Every subgroup operation is reached in uniform control flow; the loops' trip
82
- * counts are literals, and the one early exit is on a value read back through
83
- * `workgroupUniformLoad`.
84
- *
85
- * @type {CodeChunk}
86
- */
87
- export const chunk_bvh_query_aabb_cooperative = CodeChunk.from(
88
- //language=WGSL
89
- `
90
- struct BVHQueryAABBResult {
91
- // payloads in bvh_query_aabb_candidates[0, candidate_count), ascending
92
- candidate_count: u32,
93
- // leaves the filter accepted that found the candidate list full
94
- candidates_dropped: u32,
95
- // nodes never tested: frontier overflow, and what was left when the level budget ran out
96
- nodes_dropped: u32,
97
- }
98
-
99
- // two lists of node indices, alternating by level; bvh_query_aabb_list says which one a level reads
100
- var<workgroup> bvh_query_aabb_frontier: array<array<u32, BVH_QUERY_AABB_FRONTIER_CAPACITY>, 2>;
101
- // appends asked of each list; past the capacity they were counted but not stored
102
- var<workgroup> bvh_query_aabb_frontier_reserved: array<atomic<u32>, 2>;
103
- var<workgroup> bvh_query_aabb_candidates: array<u32, BVH_QUERY_AABB_CANDIDATE_CAPACITY>;
104
- var<workgroup> bvh_query_aabb_candidates_reserved: atomic<u32>;
105
- // written by invocation 0 only
106
- var<workgroup> bvh_query_aabb_nodes_dropped: u32;
107
- // what invocation 0 publishes, read back through workgroupUniformLoad
108
- var<workgroup> bvh_query_aabb_broadcast: u32;
109
-
110
- // This invocation's first slot of count appends to a frontier list, reserved for the whole
111
- // subgroup by one atomic.
112
- fn bvh_query_aabb_reserve_frontier(list: u32, count: u32) -> u32 {
113
- let offset = subgroupExclusiveAdd(count);
114
- let total = subgroupAdd(count);
115
-
116
- // elected before the branch, which then holds no subgroup operation and may be non-uniform
117
- let elected = subgroupElect();
118
-
119
- var base = 0u;
120
-
121
- if (elected && total > 0u) {
122
- base = atomicAdd(&bvh_query_aabb_frontier_reserved[list], total);
123
- }
124
-
125
- return subgroupBroadcastFirst(base) + offset;
126
- }
127
-
128
- // The same, for the candidate list.
129
- fn bvh_query_aabb_reserve_candidates(count: u32) -> u32 {
130
- let offset = subgroupExclusiveAdd(count);
131
- let total = subgroupAdd(count);
132
-
133
- let elected = subgroupElect();
134
-
135
- var base = 0u;
136
-
137
- if (elected && total > 0u) {
138
- base = atomicAdd(&bvh_query_aabb_candidates_reserved, total);
139
- }
140
-
141
- return subgroupBroadcastFirst(base) + offset;
142
- }
143
-
144
- // Test this level's list: the children of overlapping internal nodes go on the next list, the
145
- // payloads of overlapping leaves the filter accepts on the candidate list.
146
- fn bvh_query_aabb_expand(list: u32, expand_count: u32, query: array<f32, 6>, lane: u32) {
147
- let next = list ^ 1u;
148
-
149
- for (var iteration = 0u; iteration < BVH_QUERY_AABB_FRONTIER_ROUNDS; iteration++) {
150
- let slot = bvh_query_aabb_slot(iteration, lane);
151
-
152
- var node: ${BVH2_NODE_STRUCT.wgsl_ref};
153
- var kind = BVH_QUERY_AABB_SKIP;
154
-
155
- if (slot < expand_count) {
156
- node = bvh_query_aabb_node(bvh_query_aabb_frontier[list][slot]);
157
-
158
- kind = bvh_query_aabb_classify(node.bounds, node.child_1, query);
159
-
160
- if (kind == BVH_QUERY_AABB_LEAF && !bvh_query_aabb_accept_leaf(node.child_2, node.bounds)) {
161
- kind = BVH_QUERY_AABB_SKIP;
162
- }
163
- }
164
-
165
- // every invocation reserves, holding or not, so the subgroup operations stay uniform
166
- let frontier_slot = bvh_query_aabb_reserve_frontier(next, select(0u, 2u, kind == BVH_QUERY_AABB_DESCEND));
167
- let candidate_slot = bvh_query_aabb_reserve_candidates(select(0u, 1u, kind == BVH_QUERY_AABB_LEAF));
168
-
169
- if (kind == BVH_QUERY_AABB_DESCEND) {
170
- if (frontier_slot < BVH_QUERY_AABB_FRONTIER_CAPACITY) {
171
- bvh_query_aabb_frontier[next][frontier_slot] = node.child_1;
172
- }
173
- if (frontier_slot + 1u < BVH_QUERY_AABB_FRONTIER_CAPACITY) {
174
- bvh_query_aabb_frontier[next][frontier_slot + 1u] = node.child_2;
175
- }
176
- }
177
-
178
- if (kind == BVH_QUERY_AABB_LEAF && candidate_slot < BVH_QUERY_AABB_CANDIDATE_CAPACITY) {
179
- bvh_query_aabb_candidates[candidate_slot] = node.child_2;
180
- }
181
- }
182
- }
183
-
184
- // Order the first count candidates ascending, through the power-of-two prefix that holds them.
185
- fn bvh_query_aabb_sort(count: u32, lane: u32) {
186
- let span = sort_bitonic_size(count);
187
-
188
- // the prefix past the candidates sorts last
189
- for (var iteration = 0u; iteration < BVH_QUERY_AABB_CANDIDATE_ROUNDS; iteration++) {
190
- let slot = iteration * BVH_QUERY_AABB_WORKGROUP_SIZE + lane;
191
-
192
- if (slot >= count && slot < span) {
193
- bvh_query_aabb_candidates[slot] = 0xffffffffu;
194
- }
195
- }
196
-
197
- // span is workgroup-uniform, so is every bound and exit below
198
- for (var k = 2u; k <= BVH_QUERY_AABB_CANDIDATE_CAPACITY; k = k << 1u) {
199
- if (k > span) {
200
- break;
201
- }
202
-
203
- for (var j = k >> 1u; j > 0u; j = j >> 1u) {
204
- workgroupBarrier();
205
-
206
- // the smaller of the two belongs in pair.x
207
- let pair = sort_bitonic_comparator(lane, k, j);
208
-
209
- // a pair is wholly inside the prefix or wholly past it
210
- if (max(pair.x, pair.y) < span) {
211
- let a = bvh_query_aabb_candidates[pair.x];
212
- let b = bvh_query_aabb_candidates[pair.y];
213
-
214
- if (b < a) {
215
- bvh_query_aabb_candidates[pair.x] = b;
216
- bvh_query_aabb_candidates[pair.y] = a;
217
- }
218
- }
219
- }
220
- }
221
- }
222
-
223
- fn bvh_query_aabb_cooperative(root: u32, query: array<f32, 6>, lane: u32) -> BVHQueryAABBResult {
224
- // whatever the workgroup did with a previous query's candidates is done before they are reset
225
- workgroupBarrier();
226
-
227
- if (lane == 0u) {
228
- bvh_query_aabb_frontier[0][0] = root;
229
- atomicStore(&bvh_query_aabb_frontier_reserved[0], select(1u, 0u, root == BVH_NULL_NODE));
230
- atomicStore(&bvh_query_aabb_frontier_reserved[1], 0u);
231
- atomicStore(&bvh_query_aabb_candidates_reserved, 0u);
232
- bvh_query_aabb_nodes_dropped = 0u;
233
- }
234
-
235
- // one pass past the budget, to count what the last expanded level left on its list; that
236
- // pass publishes nothing to expand, so the loop always leaves through the break
237
- for (var level = 0u; level <= BVH_QUERY_AABB_LEVEL_BUDGET; level++) {
238
- let list = bvh_query_aabb_list(level);
239
-
240
- // every append to this level's list has landed
241
- workgroupBarrier();
242
-
243
- if (lane == 0u) {
244
- let published = bvh_query_aabb_publish(atomicLoad(&bvh_query_aabb_frontier_reserved[list]), level);
245
-
246
- bvh_query_aabb_broadcast = published.x;
247
- bvh_query_aabb_nodes_dropped += published.y;
248
-
249
- // the list this level appends to, read two levels ago and empty again
250
- atomicStore(&bvh_query_aabb_frontier_reserved[list ^ 1u], 0u);
251
- }
252
-
253
- let expand_count = workgroupUniformLoad(&bvh_query_aabb_broadcast);
254
-
255
- if (expand_count == 0u) {
256
- break;
257
- }
258
-
259
- bvh_query_aabb_expand(list, expand_count, query, lane);
260
- }
261
-
262
- // every invocation has read the last broadcast before invocation 0 writes the next
263
- workgroupBarrier();
264
-
265
- if (lane == 0u) {
266
- bvh_query_aabb_broadcast = atomicLoad(&bvh_query_aabb_candidates_reserved);
267
- }
268
-
269
- let reserved = workgroupUniformLoad(&bvh_query_aabb_broadcast);
270
- let count = min(reserved, BVH_QUERY_AABB_CANDIDATE_CAPACITY);
271
-
272
- bvh_query_aabb_sort(count, lane);
273
-
274
- // also the barrier that makes the sorted list visible to every invocation
275
- let nodes_dropped = workgroupUniformLoad(&bvh_query_aabb_nodes_dropped);
276
-
277
- return BVHQueryAABBResult(count, reserved - count, nodes_dropped);
278
- }
279
- `, [
280
- BVH2_NODE_STRUCT.declaration_chunk,
281
- BVH_NULL_NODE_DEFINITION,
282
- chunk_bvh_query_aabb_frontier,
283
- chunk_sort_bitonic_comparator,
284
- ]);
285
-
286
- chunk_bvh_query_aabb_cooperative.addExtension(WebGPUExtensionType.Subgroups);
1
+ import { WebGPUExtensionType } from "../../../../descriptor/WebGPUExtensionType.js";
2
+ import { CodeChunk } from "../../compiler/CodeChunk.js";
3
+ import { chunk_sort_bitonic_comparator } from "../../../gpu_primitive/sort/chunk_sort_bitonic_comparator.js";
4
+ import { BVH2_NODE_STRUCT } from "./BVH2_NODE_STRUCT.js";
5
+ import { BVH_NULL_NODE_DEFINITION } from "./BVH_NULL_NODE_DEFINITION.js";
6
+ import { chunk_bvh_query_aabb_frontier } from "./chunk_bvh_query_aabb_frontier.js";
7
+
8
+ /**
9
+ * Every leaf of a BVH whose box overlaps one query box, found by a whole workgroup together and
10
+ * returned as payloads in ascending order.
11
+ *
12
+ * ## Why not a stack per thread
13
+ *
14
+ * The engine's traversals (`chunk_sdf_query_distance`, `chunk_ray_query_*`) walk a stack per
15
+ * thread with no cap on visits, which is right for one ray per thread and wrong for one box per
16
+ * workgroup: the box meets a subtree, not a path, and one thread walking it serially is the slowest
17
+ * thread of the dispatch. This expands the tree a **level at a time** instead, as the vgeo cut does
18
+ * its descent: every node on the current level is tested by its own invocation, the survivors'
19
+ * children are appended to the next level, overlapping leaves to the candidate list, and a barrier
20
+ * separates the levels. Per-invocation work is bounded by the depth of the tree, not by the size of
21
+ * the answer.
22
+ *
23
+ * ## The contract
24
+ *
25
+ * Call `bvh_query_aabb_cooperative(root, query, lane)` from every invocation of a workgroup of
26
+ * exactly `BVH_QUERY_AABB_WORKGROUP_SIZE` invocations, in uniform control flow, with `lane` the
27
+ * `local_invocation_index` and `root` and `query` the same in every invocation. `root` is the
28
+ * tree's root word (word 0 of `BVH_BUFFER_LAYOUT`), and `BVH_NULL_NODE` for an empty tree. `query`
29
+ * is `[min.xyz, max.xyz]`; touching counts as overlapping, as in `aabb3_intersects_aabb3`.
30
+ *
31
+ * It returns a `BVHQueryAABBResult` whose fields are workgroup-uniform, so they can bound the
32
+ * caller's loops. The payloads are `bvh_query_aabb_candidates[0, candidate_count)`, ascending, and
33
+ * visible to every invocation when the call returns. They stay there until the next query.
34
+ *
35
+ * The node layout is `BVH_BUFFER_LAYOUT`'s: a node is a leaf exactly when `child_1` is
36
+ * `BVH_NULL_NODE`, and then `child_2` is its payload.
37
+ *
38
+ * ## The seam: two functions the enclosing shader defines
39
+ *
40
+ * The chunk binds nothing. It reads the tree and filters leaves through two functions the shader
41
+ * that includes it must define, in the manner of the particle VM's `vm_reg_read` and
42
+ * `vm_reg_write`:
43
+ *
44
+ * - `fn bvh_query_aabb_node(index: u32) -> BVH2Node` returns node `index`, where `BVH2Node` is
45
+ * `BVH2_NODE_STRUCT.wgsl_ref`. A tree bound as `BVH_STRUCT` answers with `tree.nodes[index]`; one
46
+ * inside a word arena reads its eight words.
47
+ * - `fn bvh_query_aabb_accept_leaf(payload: u32, bounds: array<f32, 6>) -> bool` is asked about
48
+ * every leaf that overlaps the box, before it takes a place on the list. A caller with nothing to
49
+ * filter returns `true`. The fluid's resolution cull lives here: a leaf too small for the cascade
50
+ * is refused before it can crowd out one that is not.
51
+ *
52
+ * ## Deterministic order
53
+ *
54
+ * Appends from different subgroups land in whatever order the hardware runs them, so the list is
55
+ * sorted by payload before it is returned: the bitonic network of `chunk_sort_bitonic_comparator`
56
+ * over the smallest power-of-two prefix that holds the candidates (`sort_bitonic_size`), padded
57
+ * with `0xffffffff`, one compare-exchange per invocation per stage. A payload that is a stable row index then makes "the lowest K" the same K every frame for
58
+ * the same overlaps, however the traversal was scheduled.
59
+ *
60
+ * ## Bounds, and what is counted
61
+ *
62
+ * Nothing is dropped silently. A level whose appends pass `BVH_QUERY_AABB_FRONTIER_CAPACITY`, and a
63
+ * list still holding nodes when `BVH_QUERY_AABB_LEVEL_BUDGET` levels have been expanded, add those
64
+ * nodes to `nodes_dropped`: subtrees never tested. A leaf that passes the filter when the candidate
65
+ * list is full adds to `candidates_dropped`. With both zero the candidates are every overlapping
66
+ * leaf the filter accepted; with either non-zero they are a subset, and the lowest K of them need
67
+ * not be the lowest K overall.
68
+ *
69
+ * Per invocation, at most `BVH_QUERY_AABB_LEVEL_BUDGET * BVH_QUERY_AABB_FRONTIER_ROUNDS` = 51 * 4 =
70
+ * 204 node reads and filter calls, then two padding writes and 28 compare-exchanges. A query that
71
+ * meets nothing costs one level: the root is read, misses, and the loop leaves.
72
+ *
73
+ * Workgroup memory: two lists of 256 node indices, 128 payloads and five words, 2580 bytes.
74
+ *
75
+ * ## Subgroups
76
+ *
77
+ * Appends are aggregated per subgroup: an exclusive add numbers the subgroup's appends, one elected
78
+ * invocation reserves them all with one workgroup `atomicAdd`, and a broadcast hands each
79
+ * invocation its base. Nothing assumes which invocations share a subgroup or that a subgroup's
80
+ * invocations are contiguous in `local_invocation_index`: a subgroup reserves a run of its own
81
+ * wherever it lands. Every subgroup operation is reached in uniform control flow; the loops' trip
82
+ * counts are literals, and the one early exit is on a value read back through
83
+ * `workgroupUniformLoad`.
84
+ *
85
+ * @type {CodeChunk}
86
+ */
87
+ export const chunk_bvh_query_aabb_cooperative = CodeChunk.from(
88
+ //language=WGSL
89
+ `
90
+ struct BVHQueryAABBResult {
91
+ // payloads in bvh_query_aabb_candidates[0, candidate_count), ascending
92
+ candidate_count: u32,
93
+ // leaves the filter accepted that found the candidate list full
94
+ candidates_dropped: u32,
95
+ // nodes never tested: frontier overflow, and what was left when the level budget ran out
96
+ nodes_dropped: u32,
97
+ }
98
+
99
+ // two lists of node indices, alternating by level; bvh_query_aabb_list says which one a level reads
100
+ var<workgroup> bvh_query_aabb_frontier: array<array<u32, BVH_QUERY_AABB_FRONTIER_CAPACITY>, 2>;
101
+ // appends asked of each list; past the capacity they were counted but not stored
102
+ var<workgroup> bvh_query_aabb_frontier_reserved: array<atomic<u32>, 2>;
103
+ var<workgroup> bvh_query_aabb_candidates: array<u32, BVH_QUERY_AABB_CANDIDATE_CAPACITY>;
104
+ var<workgroup> bvh_query_aabb_candidates_reserved: atomic<u32>;
105
+ // written by invocation 0 only
106
+ var<workgroup> bvh_query_aabb_nodes_dropped: u32;
107
+ // what invocation 0 publishes, read back through workgroupUniformLoad
108
+ var<workgroup> bvh_query_aabb_broadcast: u32;
109
+
110
+ // This invocation's first slot of count appends to a frontier list, reserved for the whole
111
+ // subgroup by one atomic.
112
+ fn bvh_query_aabb_reserve_frontier(list: u32, count: u32) -> u32 {
113
+ let offset = subgroupExclusiveAdd(count);
114
+ let total = subgroupAdd(count);
115
+
116
+ // elected before the branch, which then holds no subgroup operation and may be non-uniform
117
+ let elected = subgroupElect();
118
+
119
+ var base = 0u;
120
+
121
+ if (elected && total > 0u) {
122
+ base = atomicAdd(&bvh_query_aabb_frontier_reserved[list], total);
123
+ }
124
+
125
+ return subgroupBroadcastFirst(base) + offset;
126
+ }
127
+
128
+ // The same, for the candidate list.
129
+ fn bvh_query_aabb_reserve_candidates(count: u32) -> u32 {
130
+ let offset = subgroupExclusiveAdd(count);
131
+ let total = subgroupAdd(count);
132
+
133
+ let elected = subgroupElect();
134
+
135
+ var base = 0u;
136
+
137
+ if (elected && total > 0u) {
138
+ base = atomicAdd(&bvh_query_aabb_candidates_reserved, total);
139
+ }
140
+
141
+ return subgroupBroadcastFirst(base) + offset;
142
+ }
143
+
144
+ // Test this level's list: the children of overlapping internal nodes go on the next list, the
145
+ // payloads of overlapping leaves the filter accepts on the candidate list.
146
+ fn bvh_query_aabb_expand(list: u32, expand_count: u32, query: array<f32, 6>, lane: u32) {
147
+ let next = list ^ 1u;
148
+
149
+ for (var iteration = 0u; iteration < BVH_QUERY_AABB_FRONTIER_ROUNDS; iteration++) {
150
+ if (iteration * BVH_QUERY_AABB_WORKGROUP_SIZE >= expand_count) {
151
+ break;
152
+ }
153
+
154
+ let slot = bvh_query_aabb_slot(iteration, lane);
155
+
156
+ var node: ${BVH2_NODE_STRUCT.wgsl_ref};
157
+ var kind = BVH_QUERY_AABB_SKIP;
158
+
159
+ if (slot < expand_count) {
160
+ node = bvh_query_aabb_node(bvh_query_aabb_frontier[list][slot]);
161
+
162
+ kind = bvh_query_aabb_classify(node.bounds, node.child_1, query);
163
+
164
+ if (kind == BVH_QUERY_AABB_LEAF && !bvh_query_aabb_accept_leaf(node.child_2, node.bounds)) {
165
+ kind = BVH_QUERY_AABB_SKIP;
166
+ }
167
+ }
168
+
169
+ // every invocation reserves, holding or not, so the subgroup operations stay uniform
170
+ let frontier_slot = bvh_query_aabb_reserve_frontier(next, select(0u, 2u, kind == BVH_QUERY_AABB_DESCEND));
171
+ let candidate_slot = bvh_query_aabb_reserve_candidates(select(0u, 1u, kind == BVH_QUERY_AABB_LEAF));
172
+
173
+ if (kind == BVH_QUERY_AABB_DESCEND) {
174
+ if (frontier_slot < BVH_QUERY_AABB_FRONTIER_CAPACITY) {
175
+ bvh_query_aabb_frontier[next][frontier_slot] = node.child_1;
176
+ }
177
+ if (frontier_slot + 1u < BVH_QUERY_AABB_FRONTIER_CAPACITY) {
178
+ bvh_query_aabb_frontier[next][frontier_slot + 1u] = node.child_2;
179
+ }
180
+ }
181
+
182
+ if (kind == BVH_QUERY_AABB_LEAF && candidate_slot < BVH_QUERY_AABB_CANDIDATE_CAPACITY) {
183
+ bvh_query_aabb_candidates[candidate_slot] = node.child_2;
184
+ }
185
+ }
186
+ }
187
+
188
+ // Order the first count candidates ascending, through the power-of-two prefix that holds them.
189
+ fn bvh_query_aabb_sort(count: u32, lane: u32) {
190
+ if (count <= 1u) {
191
+ return;
192
+ }
193
+
194
+ let span = sort_bitonic_size(count);
195
+
196
+ // the prefix past the candidates sorts last
197
+ for (var iteration = 0u; iteration < BVH_QUERY_AABB_CANDIDATE_ROUNDS; iteration++) {
198
+ let slot = iteration * BVH_QUERY_AABB_WORKGROUP_SIZE + lane;
199
+
200
+ if (slot >= count && slot < span) {
201
+ bvh_query_aabb_candidates[slot] = 0xffffffffu;
202
+ }
203
+ }
204
+
205
+ // span is workgroup-uniform, so is every bound and exit below
206
+ for (var k = 2u; k <= BVH_QUERY_AABB_CANDIDATE_CAPACITY; k = k << 1u) {
207
+ if (k > span) {
208
+ break;
209
+ }
210
+
211
+ for (var j = k >> 1u; j > 0u; j = j >> 1u) {
212
+ workgroupBarrier();
213
+
214
+ // the smaller of the two belongs in pair.x
215
+ let pair = sort_bitonic_comparator(lane, k, j);
216
+
217
+ // a pair is wholly inside the prefix or wholly past it
218
+ if (max(pair.x, pair.y) < span) {
219
+ let a = bvh_query_aabb_candidates[pair.x];
220
+ let b = bvh_query_aabb_candidates[pair.y];
221
+
222
+ if (b < a) {
223
+ bvh_query_aabb_candidates[pair.x] = b;
224
+ bvh_query_aabb_candidates[pair.y] = a;
225
+ }
226
+ }
227
+ }
228
+ }
229
+ }
230
+
231
+ fn bvh_query_aabb_cooperative(root: u32, query: array<f32, 6>, lane: u32) -> BVHQueryAABBResult {
232
+ // whatever the workgroup did with a previous query's candidates is done before they are reset
233
+ workgroupBarrier();
234
+
235
+ if (lane == 0u) {
236
+ bvh_query_aabb_frontier[0][0] = root;
237
+ atomicStore(&bvh_query_aabb_frontier_reserved[0], select(1u, 0u, root == BVH_NULL_NODE));
238
+ atomicStore(&bvh_query_aabb_frontier_reserved[1], 0u);
239
+ atomicStore(&bvh_query_aabb_candidates_reserved, 0u);
240
+ bvh_query_aabb_nodes_dropped = 0u;
241
+ }
242
+
243
+ // one pass past the budget, to count what the last expanded level left on its list; that
244
+ // pass publishes nothing to expand, so the loop always leaves through the break
245
+ for (var level = 0u; level <= BVH_QUERY_AABB_LEVEL_BUDGET; level++) {
246
+ let list = bvh_query_aabb_list(level);
247
+
248
+ // every append to this level's list has landed
249
+ workgroupBarrier();
250
+
251
+ if (lane == 0u) {
252
+ let published = bvh_query_aabb_publish(atomicLoad(&bvh_query_aabb_frontier_reserved[list]), level);
253
+
254
+ bvh_query_aabb_broadcast = published.x;
255
+ bvh_query_aabb_nodes_dropped += published.y;
256
+
257
+ // the list this level appends to, read two levels ago and empty again
258
+ atomicStore(&bvh_query_aabb_frontier_reserved[list ^ 1u], 0u);
259
+ }
260
+
261
+ let expand_count = workgroupUniformLoad(&bvh_query_aabb_broadcast);
262
+
263
+ if (expand_count == 0u) {
264
+ break;
265
+ }
266
+
267
+ bvh_query_aabb_expand(list, expand_count, query, lane);
268
+ }
269
+
270
+ // every invocation has read the last broadcast before invocation 0 writes the next
271
+ workgroupBarrier();
272
+
273
+ if (lane == 0u) {
274
+ bvh_query_aabb_broadcast = atomicLoad(&bvh_query_aabb_candidates_reserved);
275
+ }
276
+
277
+ let reserved = workgroupUniformLoad(&bvh_query_aabb_broadcast);
278
+ let count = min(reserved, BVH_QUERY_AABB_CANDIDATE_CAPACITY);
279
+
280
+ bvh_query_aabb_sort(count, lane);
281
+
282
+ // also the barrier that makes the sorted list visible to every invocation
283
+ let nodes_dropped = workgroupUniformLoad(&bvh_query_aabb_nodes_dropped);
284
+
285
+ return BVHQueryAABBResult(count, reserved - count, nodes_dropped);
286
+ }
287
+ `, [
288
+ BVH2_NODE_STRUCT.declaration_chunk,
289
+ BVH_NULL_NODE_DEFINITION,
290
+ chunk_bvh_query_aabb_frontier,
291
+ chunk_sort_bitonic_comparator,
292
+ ]);
293
+
294
+ chunk_bvh_query_aabb_cooperative.addExtension(WebGPUExtensionType.Subgroups);
@@ -1,5 +1,5 @@
1
1
  import { CodeChunk } from "../../../compiler/CodeChunk.js";
2
- import { chunk_sh3_color_get_irradiance_at } from "../../spherical_harmonics/chunk_sh3_color_get_irradiance_at.js";
2
+ import { chunk_sh2_color_get_irradiance_at } from "../../spherical_harmonics/chunk_sh2_color_get_irradiance_at.js";
3
3
  import { chunk_lpv_probe_get_data } from "./chunk_lpv_probe_get_data.js";
4
4
 
5
5
  /**
@@ -15,23 +15,23 @@ fn lpv_interpolate_probe_irradiance8(
15
15
  probe_indices: array<u32, 8>
16
16
  ) -> vec3<f32> {
17
17
 
18
- var combined_sh :array<vec3<f32>, 9>;
18
+ var combined_sh :array<vec3<f32>, 4>;
19
19
 
20
20
  for( var i = 0; i < 8; i++){
21
21
 
22
22
  let sh3 = lpv_probe_get_data(probe_indices[i]);
23
23
 
24
- for( var c = 0; c < 9; c++){
24
+ for( var c = 0; c < 4; c++){
25
25
  combined_sh[c] += sh3[c] * weights[i];
26
26
  }
27
27
  }
28
28
 
29
- let projected = sh3_color_get_irradiance_at(direction, combined_sh);
29
+ let projected = sh2_color_get_irradiance_at(direction, combined_sh);
30
30
 
31
31
  return projected;
32
32
  }
33
33
  `, [
34
- chunk_sh3_color_get_irradiance_at,
34
+ chunk_sh2_color_get_irradiance_at,
35
35
  chunk_lpv_probe_get_data,
36
36
  ]
37
37
  )
@@ -1 +1 @@
1
- {"version":3,"file":"chunk_lpv_mesh_interpolate_probe.d.ts","sourceRoot":"","sources":["../../../../../../../../src/shade/renderer/shader/chunk/light/lpv/chunk_lpv_mesh_interpolate_probe.js"],"names":[],"mappings":"AAKA,+CAcE;AAEF,yDA4BE;0BAjDwB,gCAAgC"}
1
+ {"version":3,"file":"chunk_lpv_mesh_interpolate_probe.d.ts","sourceRoot":"","sources":["../../../../../../../../src/shade/renderer/shader/chunk/light/lpv/chunk_lpv_mesh_interpolate_probe.js"],"names":[],"mappings":"AAKA,+CAcE;AAEF,yDA8BE;0BAnDwB,gCAAgC"}