@woosh/meep-engine 3.22.0 → 3.23.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 (267) hide show
  1. package/package.json +1 -1
  2. package/src/core/geom/3d/hash-grid/PointHashGrid3.d.ts +118 -0
  3. package/src/core/geom/3d/hash-grid/PointHashGrid3.d.ts.map +1 -0
  4. package/src/core/geom/3d/hash-grid/PointHashGrid3.js +283 -0
  5. package/src/core/geom/3d/shape/BoxShape3D.d.ts.map +1 -1
  6. package/src/core/geom/3d/shape/BoxShape3D.js +6 -17
  7. package/src/core/geom/3d/shape/CapsuleShape3D.d.ts.map +1 -1
  8. package/src/core/geom/3d/shape/CapsuleShape3D.js +3 -14
  9. package/src/core/geom/3d/shape/CylinderShape3D.d.ts.map +1 -1
  10. package/src/core/geom/3d/shape/CylinderShape3D.js +3 -21
  11. package/src/core/geom/3d/shape/PlaneShape3D.d.ts +105 -0
  12. package/src/core/geom/3d/shape/PlaneShape3D.d.ts.map +1 -0
  13. package/src/core/geom/3d/shape/PlaneShape3D.js +251 -0
  14. package/src/core/geom/3d/shape/SphereShape3D.js +3 -3
  15. package/src/core/geom/3d/shape/json/shape_to_type.d.ts.map +1 -1
  16. package/src/core/geom/3d/shape/json/shape_to_type.js +3 -0
  17. package/src/core/geom/3d/shape/json/type_adapters.d.ts +14 -0
  18. package/src/core/geom/3d/shape/json/type_adapters.d.ts.map +1 -1
  19. package/src/core/geom/3d/shape/json/type_adapters.js +15 -0
  20. package/src/core/geom/3d/shape/sdf/sdf3_box.d.ts +51 -0
  21. package/src/core/geom/3d/shape/sdf/sdf3_box.d.ts.map +1 -0
  22. package/src/core/geom/3d/shape/sdf/sdf3_box.js +113 -0
  23. package/src/core/geom/3d/shape/sdf/sdf3_capsule.d.ts +46 -0
  24. package/src/core/geom/3d/shape/sdf/sdf3_capsule.d.ts.map +1 -0
  25. package/src/core/geom/3d/shape/sdf/sdf3_capsule.js +82 -0
  26. package/src/core/geom/3d/shape/sdf/sdf3_cylinder.d.ts +60 -0
  27. package/src/core/geom/3d/shape/sdf/sdf3_cylinder.d.ts.map +1 -0
  28. package/src/core/geom/3d/shape/sdf/sdf3_cylinder.js +126 -0
  29. package/src/core/geom/3d/shape/sdf/sdf3_degenerate_normal.d.ts +50 -0
  30. package/src/core/geom/3d/shape/sdf/sdf3_degenerate_normal.d.ts.map +1 -0
  31. package/src/core/geom/3d/shape/sdf/sdf3_degenerate_normal.js +53 -0
  32. package/src/core/geom/3d/shape/sdf/sdf3_plane.d.ts +52 -0
  33. package/src/core/geom/3d/shape/sdf/sdf3_plane.d.ts.map +1 -0
  34. package/src/core/geom/3d/shape/sdf/sdf3_plane.js +61 -0
  35. package/src/core/geom/3d/shape/sdf/sdf3_sphere.d.ts +41 -0
  36. package/src/core/geom/3d/shape/sdf/sdf3_sphere.d.ts.map +1 -0
  37. package/src/core/geom/3d/shape/sdf/sdf3_sphere.js +71 -0
  38. package/src/core/process/ConcurrencyGate.d.ts +103 -0
  39. package/src/core/process/ConcurrencyGate.d.ts.map +1 -0
  40. package/src/core/process/ConcurrencyGate.js +207 -0
  41. package/src/engine/asset/AssetManager.d.ts +10 -0
  42. package/src/engine/asset/AssetManager.d.ts.map +1 -1
  43. package/src/engine/asset/AssetManager.js +10 -0
  44. package/src/engine/graphics/CONTEXT_LOSS_RECOVERY_PLAN.md +30 -13
  45. package/src/engine/graphics3/pose/collect_entity_playbacks.d.ts +26 -0
  46. package/src/engine/graphics3/pose/collect_entity_playbacks.d.ts.map +1 -0
  47. package/src/engine/graphics3/pose/collect_entity_playbacks.js +40 -0
  48. package/src/engine/graphics3/pose/query_entity_node_world_pose.d.ts.map +1 -1
  49. package/src/engine/graphics3/pose/query_entity_node_world_pose.js +74 -101
  50. package/src/engine/physics/cloth/MEASUREMENTS.md +1287 -4
  51. package/src/engine/physics/cloth/PLAN.md +1967 -1581
  52. package/src/engine/physics/cloth/build/ClothProxy.d.ts +147 -0
  53. package/src/engine/physics/cloth/build/ClothProxy.d.ts.map +1 -0
  54. package/src/engine/physics/cloth/build/ClothProxy.js +207 -0
  55. package/src/engine/physics/cloth/build/cloth_proxy_from_joints.d.ts +70 -0
  56. package/src/engine/physics/cloth/build/cloth_proxy_from_joints.d.ts.map +1 -0
  57. package/src/engine/physics/cloth/build/cloth_proxy_from_joints.js +256 -0
  58. package/src/engine/physics/cloth/collider/ClothColliderIndex.d.ts +176 -0
  59. package/src/engine/physics/cloth/collider/ClothColliderIndex.d.ts.map +1 -0
  60. package/src/engine/physics/cloth/collider/ClothColliderIndex.js +435 -0
  61. package/src/engine/physics/cloth/collider/ClothColliderKind.d.ts +12 -0
  62. package/src/engine/physics/cloth/collider/ClothColliderKind.d.ts.map +1 -0
  63. package/src/engine/physics/cloth/collider/ClothColliderKind.js +38 -0
  64. package/src/engine/physics/cloth/collider/ClothColliderRecord.d.ts +120 -0
  65. package/src/engine/physics/cloth/collider/ClothColliderRecord.d.ts.map +1 -0
  66. package/src/engine/physics/cloth/collider/ClothColliderRecord.js +137 -0
  67. package/src/engine/physics/cloth/collider/cloth_collider_bounds.d.ts +25 -0
  68. package/src/engine/physics/cloth/collider/cloth_collider_bounds.d.ts.map +1 -0
  69. package/src/engine/physics/cloth/collider/cloth_collider_bounds.js +190 -0
  70. package/src/engine/physics/cloth/collider/cloth_collider_pack.d.ts +44 -0
  71. package/src/engine/physics/cloth/collider/cloth_collider_pack.d.ts.map +1 -0
  72. package/src/engine/physics/cloth/collider/cloth_collider_pack.js +173 -0
  73. package/src/engine/physics/cloth/collider/cloth_collider_sdf.d.ts +94 -0
  74. package/src/engine/physics/cloth/collider/cloth_collider_sdf.d.ts.map +1 -0
  75. package/src/engine/physics/cloth/collider/cloth_collider_sdf.js +275 -0
  76. package/src/engine/physics/cloth/ecs/ClothCollider.d.ts +126 -0
  77. package/src/engine/physics/cloth/ecs/ClothCollider.d.ts.map +1 -0
  78. package/src/engine/physics/cloth/ecs/ClothCollider.js +199 -0
  79. package/src/engine/physics/cloth/ecs/ClothColliderFlags.d.ts +9 -0
  80. package/src/engine/physics/cloth/ecs/ClothColliderFlags.d.ts.map +1 -0
  81. package/src/engine/physics/cloth/ecs/ClothColliderFlags.js +32 -0
  82. package/src/engine/physics/cloth/ecs/ClothColliderSystem.d.ts +114 -0
  83. package/src/engine/physics/cloth/ecs/ClothColliderSystem.d.ts.map +1 -0
  84. package/src/engine/physics/cloth/ecs/ClothColliderSystem.js +243 -0
  85. package/src/engine/physics/cloth/ecs/ClothDynamicsFlags.js +66 -57
  86. package/src/engine/physics/cloth/ecs/ClothInstance.d.ts +109 -1
  87. package/src/engine/physics/cloth/ecs/ClothInstance.d.ts.map +1 -1
  88. package/src/engine/physics/cloth/ecs/ClothInstance.js +479 -363
  89. package/src/engine/physics/cloth/ecs/ClothRig.d.ts +95 -0
  90. package/src/engine/physics/cloth/ecs/ClothRig.d.ts.map +1 -0
  91. package/src/engine/physics/cloth/ecs/ClothRig.js +140 -0
  92. package/src/engine/physics/cloth/ecs/ClothSystem.d.ts +30 -1
  93. package/src/engine/physics/cloth/ecs/ClothSystem.d.ts.map +1 -1
  94. package/src/engine/physics/cloth/ecs/ClothSystem.js +1021 -773
  95. package/src/engine/physics/cloth/ecs/cloth_build_rows.d.ts +90 -0
  96. package/src/engine/physics/cloth/ecs/cloth_build_rows.d.ts.map +1 -0
  97. package/src/engine/physics/cloth/ecs/cloth_build_rows.js +374 -0
  98. package/src/engine/physics/cloth/ecs/cloth_dynamics_library.d.ts +32 -3
  99. package/src/engine/physics/cloth/ecs/cloth_dynamics_library.d.ts.map +1 -1
  100. package/src/engine/physics/cloth/ecs/cloth_dynamics_library.js +283 -254
  101. package/src/engine/physics/cloth/ecs/cloth_gather_colliders.d.ts +59 -0
  102. package/src/engine/physics/cloth/ecs/cloth_gather_colliders.d.ts.map +1 -0
  103. package/src/engine/physics/cloth/ecs/cloth_gather_colliders.js +328 -0
  104. package/src/engine/physics/cloth/ecs/cloth_reconstruct_pose.d.ts +13 -0
  105. package/src/engine/physics/cloth/ecs/cloth_reconstruct_pose.d.ts.map +1 -0
  106. package/src/engine/physics/cloth/ecs/cloth_reconstruct_pose.js +288 -0
  107. package/src/engine/physics/cloth/ecs/cloth_seed_rig.d.ts +58 -0
  108. package/src/engine/physics/cloth/ecs/cloth_seed_rig.d.ts.map +1 -0
  109. package/src/engine/physics/cloth/ecs/cloth_seed_rig.js +199 -0
  110. package/src/engine/physics/cloth/ecs/cloth_seed_subtree.d.ts +8 -63
  111. package/src/engine/physics/cloth/ecs/cloth_seed_subtree.d.ts.map +1 -1
  112. package/src/engine/physics/cloth/ecs/cloth_seed_subtree.js +317 -645
  113. package/src/engine/physics/cloth/ecs/cloth_write_back.d.ts +61 -0
  114. package/src/engine/physics/cloth/ecs/cloth_write_back.d.ts.map +1 -1
  115. package/src/engine/physics/cloth/ecs/cloth_write_back.js +212 -449
  116. package/src/engine/physics/cloth/ecs/cloth_write_back_rig.d.ts +49 -0
  117. package/src/engine/physics/cloth/ecs/cloth_write_back_rig.d.ts.map +1 -0
  118. package/src/engine/physics/cloth/ecs/cloth_write_back_rig.js +115 -0
  119. package/src/engine/physics/cloth/playground/README.md +155 -1
  120. package/src/engine/physics/cloth/playground/collide.html +178 -0
  121. package/src/engine/physics/cloth/playground/collide_build.d.ts +95 -0
  122. package/src/engine/physics/cloth/playground/collide_build.d.ts.map +1 -0
  123. package/src/engine/physics/cloth/playground/collide_build.js +315 -0
  124. package/src/engine/physics/cloth/playground/collide_main.d.ts +2 -0
  125. package/src/engine/physics/cloth/playground/collide_main.d.ts.map +1 -0
  126. package/src/engine/physics/cloth/playground/collide_main.js +720 -0
  127. package/src/engine/physics/cloth/playground/garment.html +182 -0
  128. package/src/engine/physics/cloth/playground/garment_build.d.ts +78 -0
  129. package/src/engine/physics/cloth/playground/garment_build.d.ts.map +1 -0
  130. package/src/engine/physics/cloth/playground/garment_build.js +359 -0
  131. package/src/engine/physics/cloth/playground/garment_main.d.ts +2 -0
  132. package/src/engine/physics/cloth/playground/garment_main.d.ts.map +1 -0
  133. package/src/engine/physics/cloth/playground/garment_main.js +633 -0
  134. package/src/engine/physics/cloth/solver/ClothState.d.ts +208 -5
  135. package/src/engine/physics/cloth/solver/ClothState.d.ts.map +1 -1
  136. package/src/engine/physics/cloth/solver/ClothState.js +302 -8
  137. package/src/engine/physics/cloth/solver/cloth_contact_find.d.ts +87 -0
  138. package/src/engine/physics/cloth/solver/cloth_contact_find.d.ts.map +1 -0
  139. package/src/engine/physics/cloth/solver/cloth_contact_find.js +343 -0
  140. package/src/engine/physics/cloth/solver/cloth_self_find.d.ts +112 -0
  141. package/src/engine/physics/cloth/solver/cloth_self_find.d.ts.map +1 -0
  142. package/src/engine/physics/cloth/solver/cloth_self_find.js +448 -0
  143. package/src/engine/physics/cloth/solver/cloth_solve_vertex.d.ts +4 -1
  144. package/src/engine/physics/cloth/solver/cloth_solve_vertex.d.ts.map +1 -1
  145. package/src/engine/physics/cloth/solver/cloth_solve_vertex.js +16 -1
  146. package/src/engine/physics/cloth/solver/cloth_solver_constants.d.ts +112 -5
  147. package/src/engine/physics/cloth/solver/cloth_solver_constants.d.ts.map +1 -1
  148. package/src/engine/physics/cloth/solver/cloth_solver_constants.js +117 -6
  149. package/src/engine/physics/cloth/solver/cloth_step.d.ts +40 -9
  150. package/src/engine/physics/cloth/solver/cloth_step.d.ts.map +1 -1
  151. package/src/engine/physics/cloth/solver/cloth_step.js +122 -10
  152. package/src/engine/physics/cloth/solver/constraint/cloth_backstop_row.d.ts +95 -0
  153. package/src/engine/physics/cloth/solver/constraint/cloth_backstop_row.d.ts.map +1 -0
  154. package/src/engine/physics/cloth/solver/constraint/cloth_backstop_row.js +285 -0
  155. package/src/engine/physics/cloth/solver/constraint/cloth_contact_row.d.ts +129 -0
  156. package/src/engine/physics/cloth/solver/constraint/cloth_contact_row.d.ts.map +1 -0
  157. package/src/engine/physics/cloth/solver/constraint/cloth_contact_row.js +501 -0
  158. package/src/engine/physics/cloth/solver/constraint/cloth_self_row.d.ts +75 -0
  159. package/src/engine/physics/cloth/solver/constraint/cloth_self_row.d.ts.map +1 -0
  160. package/src/engine/physics/cloth/solver/constraint/cloth_self_row.js +202 -0
  161. package/src/engine/physics/fluid/ecs/FluidObstacleSystem.d.ts +4 -4
  162. package/src/shade/playground/vgeo_viewer/README.md +18 -0
  163. package/src/shade/playground/vgeo_viewer/main.js +87 -50
  164. package/src/shade/renderer/buffer/table/GPUDatabase.d.ts.map +1 -1
  165. package/src/shade/renderer/buffer/table/GPUDatabase.js +191 -62
  166. package/src/shade/renderer/buffer/table/GPUTypedTable.d.ts +94 -2
  167. package/src/shade/renderer/buffer/table/GPUTypedTable.d.ts.map +1 -1
  168. package/src/shade/renderer/buffer/table/GPUTypedTable.js +414 -2
  169. package/src/shade/renderer/buffer/table/GPU_TABLE_PARTIAL_UPLOAD_DESCRIPTOR_WORDS.d.ts +14 -0
  170. package/src/shade/renderer/buffer/table/GPU_TABLE_PARTIAL_UPLOAD_DESCRIPTOR_WORDS.d.ts.map +1 -0
  171. package/src/shade/renderer/buffer/table/GPU_TABLE_PARTIAL_UPLOAD_DESCRIPTOR_WORDS.js +13 -0
  172. package/src/shade/renderer/buffer/table/gpu_table_partial_upload_shader.d.ts +17 -0
  173. package/src/shade/renderer/buffer/table/gpu_table_partial_upload_shader.d.ts.map +1 -0
  174. package/src/shade/renderer/buffer/table/gpu_table_partial_upload_shader.js +116 -0
  175. package/src/shade/renderer/geometry/bvh/GPUGeometryBVHManager.d.ts +9 -4
  176. package/src/shade/renderer/geometry/bvh/GPUGeometryBVHManager.d.ts.map +1 -1
  177. package/src/shade/renderer/geometry/bvh/GPUGeometryBVHManager.js +843 -734
  178. package/src/shade/renderer/geometry/bvh/GPUGeometryMeshletsBVH.d.ts +12 -0
  179. package/src/shade/renderer/geometry/bvh/GPUGeometryMeshletsBVH.d.ts.map +1 -1
  180. package/src/shade/renderer/geometry/bvh/GPUGeometryMeshletsBVH.js +13 -0
  181. package/src/shade/renderer/geometry/meshlet/GPUMeshletManager.d.ts +17 -0
  182. package/src/shade/renderer/geometry/meshlet/GPUMeshletManager.d.ts.map +1 -1
  183. package/src/shade/renderer/geometry/meshlet/GPUMeshletManager.js +185 -30
  184. package/src/shade/renderer/geometry/virtual/MICRON_COMPARISON_2026_08_20.md +17 -0
  185. package/src/shade/renderer/geometry/virtual/VGEO_FORMAT.md +141 -24
  186. package/src/shade/renderer/geometry/virtual/VIRTUAL_GEOMETRY_DESIGN.md +204 -64
  187. package/src/shade/renderer/geometry/virtual/VIRTUAL_GEOMETRY_PLAN.md +110 -10
  188. package/src/shade/renderer/geometry/virtual/VK_LOD_CLUSTERS_COMPARISON_2026_08_20.md +19 -0
  189. package/src/shade/renderer/geometry/virtual/format/read/VGeoByteSource.d.ts +19 -6
  190. package/src/shade/renderer/geometry/virtual/format/read/VGeoByteSource.d.ts.map +1 -1
  191. package/src/shade/renderer/geometry/virtual/format/read/VGeoByteSource.js +26 -7
  192. package/src/shade/renderer/geometry/virtual/format/read/VGeoContainerReader.d.ts +173 -14
  193. package/src/shade/renderer/geometry/virtual/format/read/VGeoContainerReader.d.ts.map +1 -1
  194. package/src/shade/renderer/geometry/virtual/format/read/VGeoContainerReader.js +458 -51
  195. package/src/shade/renderer/geometry/virtual/format/read/VGeoReadOptions.d.ts +49 -13
  196. package/src/shade/renderer/geometry/virtual/format/read/VGeoReadOptions.d.ts.map +1 -1
  197. package/src/shade/renderer/geometry/virtual/format/read/VGeoReadOptions.js +52 -14
  198. package/src/shade/renderer/geometry/virtual/format/read/tool/VGEO_MAX_AUDIT_BYTES.d.ts +20 -0
  199. package/src/shade/renderer/geometry/virtual/format/read/tool/VGEO_MAX_AUDIT_BYTES.d.ts.map +1 -0
  200. package/src/shade/renderer/geometry/virtual/format/read/tool/VGEO_MAX_AUDIT_BYTES.js +19 -0
  201. package/src/shade/renderer/geometry/virtual/format/read/tool/vgeo_audit_container.d.ts +27 -0
  202. package/src/shade/renderer/geometry/virtual/format/read/tool/vgeo_audit_container.d.ts.map +1 -0
  203. package/src/shade/renderer/geometry/virtual/format/read/tool/vgeo_audit_container.js +48 -0
  204. package/src/shade/renderer/geometry/virtual/format/read/tool/vgeo_install_all_pages.d.ts +29 -0
  205. package/src/shade/renderer/geometry/virtual/format/read/tool/vgeo_install_all_pages.d.ts.map +1 -0
  206. package/src/shade/renderer/geometry/virtual/format/read/tool/vgeo_install_all_pages.js +60 -0
  207. package/src/shade/renderer/geometry/virtual/format/read/vgeo_fetch_byte_source.d.ts +8 -1
  208. package/src/shade/renderer/geometry/virtual/format/read/vgeo_fetch_byte_source.d.ts.map +1 -1
  209. package/src/shade/renderer/geometry/virtual/format/read/vgeo_fetch_byte_source.js +32 -2
  210. package/src/shade/renderer/geometry/virtual/residency/VGeoResidencyManager.d.ts +258 -0
  211. package/src/shade/renderer/geometry/virtual/residency/VGeoResidencyManager.d.ts.map +1 -0
  212. package/src/shade/renderer/geometry/virtual/residency/VGeoResidencyManager.js +723 -0
  213. package/src/shade/renderer/geometry/virtual/residency/VGeoResidencyOptions.d.ts +49 -0
  214. package/src/shade/renderer/geometry/virtual/residency/VGeoResidencyOptions.d.ts.map +1 -0
  215. package/src/shade/renderer/geometry/virtual/residency/VGeoResidencyOptions.js +50 -0
  216. package/src/shade/renderer/loader/gltf/tiny-gltf.d.ts +1 -1
  217. package/src/shade/renderer/postprocess/nss/NSS.d.ts +1 -1
  218. package/src/shade/renderer/texture/bindless/GPUBindlessTextureManager.d.ts +3 -0
  219. package/src/shade/renderer/texture/bindless/GPUBindlessTextureManager.d.ts.map +1 -1
  220. package/src/shade/renderer/texture/bindless/GPUBindlessTextureManager.js +121 -21
  221. package/src/shade/renderer/texture/virtual/README.md +6 -4
  222. package/src/shade/renderer/texture/virtual/VirtualTextureManager.d.ts.map +1 -1
  223. package/src/shade/renderer/texture/virtual/VirtualTextureManager.js +7 -0
  224. package/src/shade/renderer/texture/virtual/source/VTSourceTiled.d.ts +3 -3
  225. package/src/shade/renderer/texture/virtual/source/VTSourceTiled.js +3 -3
  226. package/src/engine/ecs/system/SystemExecutionPhase.d.ts +0 -9
  227. package/src/engine/ecs/system/SystemExecutionPhase.d.ts.map +0 -1
  228. package/src/engine/graphics/texture/virtual/NOTES.md +0 -128
  229. package/src/engine/graphics/texture/virtual/VT_DEFAULT_PAGE_RESOLUTION.d.ts +0 -6
  230. package/src/engine/graphics/texture/virtual/VT_DEFAULT_PAGE_RESOLUTION.d.ts.map +0 -1
  231. package/src/engine/graphics/texture/virtual/VT_DEFAULT_PAGE_RESOLUTION.js +0 -5
  232. package/src/engine/graphics/texture/virtual/VirtualTextureTileLoader.d.ts +0 -49
  233. package/src/engine/graphics/texture/virtual/VirtualTextureTileLoader.d.ts.map +0 -1
  234. package/src/engine/graphics/texture/virtual/VirtualTextureTileLoader.js +0 -264
  235. package/src/engine/graphics/texture/virtual/VirtualTextureUsage.d.ts +0 -44
  236. package/src/engine/graphics/texture/virtual/VirtualTextureUsage.d.ts.map +0 -1
  237. package/src/engine/graphics/texture/virtual/VirtualTextureUsage.js +0 -228
  238. package/src/engine/graphics/texture/virtual/VirtualTextureUsageShader.d.ts +0 -3
  239. package/src/engine/graphics/texture/virtual/VirtualTextureUsageShader.d.ts.map +0 -1
  240. package/src/engine/graphics/texture/virtual/VirtualTextureUsageShader.js +0 -73
  241. package/src/engine/graphics/texture/virtual/debug/ResidencyDebugView.d.ts +0 -14
  242. package/src/engine/graphics/texture/virtual/debug/ResidencyDebugView.d.ts.map +0 -1
  243. package/src/engine/graphics/texture/virtual/debug/ResidencyDebugView.js +0 -85
  244. package/src/engine/graphics/texture/virtual/debug/UsageDebugView.d.ts +0 -12
  245. package/src/engine/graphics/texture/virtual/debug/UsageDebugView.d.ts.map +0 -1
  246. package/src/engine/graphics/texture/virtual/debug/UsageDebugView.js +0 -63
  247. package/src/engine/graphics/texture/virtual/debug/UsagePyramidDebugView.d.ts +0 -12
  248. package/src/engine/graphics/texture/virtual/debug/UsagePyramidDebugView.d.ts.map +0 -1
  249. package/src/engine/graphics/texture/virtual/debug/UsagePyramidDebugView.js +0 -243
  250. package/src/engine/graphics/texture/virtual/tile/VirtualTextureTile.d.ts +0 -30
  251. package/src/engine/graphics/texture/virtual/tile/VirtualTextureTile.d.ts.map +0 -1
  252. package/src/engine/graphics/texture/virtual/tile/VirtualTextureTile.js +0 -39
  253. package/src/engine/graphics/texture/virtual/tile/compose_finger_print.d.ts +0 -9
  254. package/src/engine/graphics/texture/virtual/tile/compose_finger_print.d.ts.map +0 -1
  255. package/src/engine/graphics/texture/virtual/tile/compose_finger_print.js +0 -24
  256. package/src/engine/graphics/texture/virtual/tile/compose_tile_address.d.ts +0 -9
  257. package/src/engine/graphics/texture/virtual/tile/compose_tile_address.d.ts.map +0 -1
  258. package/src/engine/graphics/texture/virtual/tile/compose_tile_address.js +0 -26
  259. package/src/engine/graphics/texture/virtual/tile/decompose_finger_print.d.ts +0 -11
  260. package/src/engine/graphics/texture/virtual/tile/decompose_finger_print.d.ts.map +0 -1
  261. package/src/engine/graphics/texture/virtual/tile/decompose_finger_print.js +0 -12
  262. package/src/engine/graphics/texture/virtual/tile/finger_print_to_tile_address.d.ts +0 -7
  263. package/src/engine/graphics/texture/virtual/tile/finger_print_to_tile_address.d.ts.map +0 -1
  264. package/src/engine/graphics/texture/virtual/tile/finger_print_to_tile_address.js +0 -16
  265. package/src/engine/graphics/texture/virtual/tile/tile_address_to_finger_print.d.ts +0 -7
  266. package/src/engine/graphics/texture/virtual/tile/tile_address_to_finger_print.d.ts.map +0 -1
  267. package/src/engine/graphics/texture/virtual/tile/tile_address_to_finger_print.js +0 -35
@@ -0,0 +1,90 @@
1
+ /**
2
+ * CSR children per node, from the parent array.
3
+ * @param {ClothInstance} instance
4
+ * @returns {void}
5
+ */
6
+ export function cloth_build_children(instance: ClothInstance): void;
7
+ /**
8
+ * Rows, geodesics and the `ClothState` itself, from a seeded
9
+ * `node_parent` / `animated_position` pair.
10
+ *
11
+ * @param {ClothInstance} instance
12
+ * @param {number} dt
13
+ * @returns {void}
14
+ */
15
+ export function cloth_build_rows(instance: ClothInstance, dt: number): void;
16
+ /**
17
+ * Re-parameterise the rows of an already-seeded cloth from its current
18
+ * {@link ClothDynamics}, without walking the subtree again.
19
+ *
20
+ * This is what makes `cloth.dynamics.slack = 0.2` work live: the topology, the
21
+ * rest lengths and the geodesics are properties of the authored pose and do not
22
+ * move, and everything that does move is a number in a row table.
23
+ *
24
+ * The multipliers are **not** reset. A row whose radius has just changed is
25
+ * carrying a force appropriate to the radius it had, and it is one warm start
26
+ * away from carrying the right one; zeroing them would put a visible jolt into
27
+ * every parameter change instead.
28
+ *
29
+ * @param {ClothInstance} instance
30
+ * @param {number} dt
31
+ * @returns {void}
32
+ */
33
+ export function cloth_reparameterise(instance: ClothInstance, dt: number): void;
34
+ /**
35
+ * Whether a dynamics change needs the subtree walked again rather than merely
36
+ * re-parameterised.
37
+ *
38
+ * Two fields do: turning the strain limit on or off adds or removes rows, and
39
+ * so does moving `slack` across the bound at which its row is provably
40
+ * inactive. Everything else is a number in a table that already exists.
41
+ *
42
+ * @param {ClothDynamics} before
43
+ * @param {ClothDynamics} after
44
+ * @returns {boolean}
45
+ */
46
+ export function cloth_dynamics_change_needs_reseed(before: ClothDynamics, after: ClothDynamics): boolean;
47
+ /**
48
+ * # The rows, and everything that is a number rather than a walk
49
+ *
50
+ * Two seeders reach this module: `cloth_seed_subtree.js` for §11.1's entity
51
+ * hierarchies and `cloth_seed_rig.js` for §11.2's skinned garments. What they
52
+ * do differently is find the particles — a transform-attachment walk against a
53
+ * proxy's baked joint list — and what they do identically is everything after
54
+ * that, because a row does not care what a node was made of.
55
+ *
56
+ * So the split is: a seeder produces `node_parent` and `animated_position`, and
57
+ * {@link cloth_build_rows} turns those into geodesics, link rows, strain-limit
58
+ * rows, skip rows, leashes and the `ClothState` itself. M3 moved this out of
59
+ * `cloth_seed_subtree.js` unchanged rather than writing a second copy for the
60
+ * rig path, which is the whole reason §11 could say "the solver is identical
61
+ * either way; only seeding and write-back differ" and mean it.
62
+ *
63
+ * @author Alex Goldring
64
+ * @copyright Company Named Limited (c) 2026
65
+ */
66
+ /**
67
+ * Mass of one particle, kg. Arbitrary and uniform — see the module docblock for
68
+ * why "arbitrary" is a statement about the solver rather than a shrug.
69
+ * @type {number}
70
+ */
71
+ export const CLOTH_PARTICLE_MASS: number;
72
+ /**
73
+ * Slack radius at `ClothDynamics#slack = 1`, as a multiple of `d_geo`.
74
+ *
75
+ * It is **2**, and that is a derivation rather than a taste. The tether row
76
+ * already holds every particle within `d_geo` of the anchor, and the animated
77
+ * position it is leashed to is itself within `d_geo` of the anchor — a chord is
78
+ * never longer than the arc it subtends. By the triangle inequality the two can
79
+ * therefore never be more than `2·d_geo` apart, so a slack radius of `2·d_geo`
80
+ * is **provably inactive** and `slack = 1` means exactly "no leash" with no
81
+ * sentinel value and no discontinuity to code around.
82
+ *
83
+ * §3.4 writes `r_i = slack · d_geo,i`, which makes `slack = 1` a real and
84
+ * fairly tight constraint instead: a rope hanging straight down cannot swing
85
+ * through 90°, because its tip would move `√2·d_geo` to get there. That is a
86
+ * bound nobody asked for at the setting that is supposed to ask for none.
87
+ * @type {number}
88
+ */
89
+ export const CLOTH_SLACK_REACH: number;
90
+ //# sourceMappingURL=cloth_build_rows.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cloth_build_rows.d.ts","sourceRoot":"","sources":["../../../../../../src/engine/physics/cloth/ecs/cloth_build_rows.js"],"names":[],"mappings":"AAuDA;;;;GAIG;AACH,+DAFa,IAAI,CAyBhB;AAID;;;;;;;GAOG;AACH,8DAHW,MAAM,GACJ,IAAI,CA4LhB;AAWD;;;;;;;;;;;;;;;;GAgBG;AACH,kEAHW,MAAM,GACJ,IAAI,CAoChB;AAED;;;;;;;;;;;GAWG;AACH,iGAFa,OAAO,CAkBnB;AAhXD;;;;;;;;;;;;;;;;;;GAkBG;AAEH;;;;GAIG;AACH,kCAFU,MAAM,CAEwB;AAIxC;;;;;;;;;;;;;;;;GAgBG;AACH,gCAFU,MAAM,CAEmB"}
@@ -0,0 +1,374 @@
1
+ import { ClothState } from "../solver/ClothState.js";
2
+ import { ClothDynamicsFlags } from "./ClothDynamicsFlags.js";
3
+ import { cloth_self_closest_free_pair, cloth_self_exclusions } from "../solver/cloth_self_find.js";
4
+ import { cloth_bend_ratio, cloth_strain_allowance } from "./cloth_dynamics_map.js";
5
+
6
+ /**
7
+ * # The rows, and everything that is a number rather than a walk
8
+ *
9
+ * Two seeders reach this module: `cloth_seed_subtree.js` for §11.1's entity
10
+ * hierarchies and `cloth_seed_rig.js` for §11.2's skinned garments. What they
11
+ * do differently is find the particles — a transform-attachment walk against a
12
+ * proxy's baked joint list — and what they do identically is everything after
13
+ * that, because a row does not care what a node was made of.
14
+ *
15
+ * So the split is: a seeder produces `node_parent` and `animated_position`, and
16
+ * {@link cloth_build_rows} turns those into geodesics, link rows, strain-limit
17
+ * rows, skip rows, leashes and the `ClothState` itself. M3 moved this out of
18
+ * `cloth_seed_subtree.js` unchanged rather than writing a second copy for the
19
+ * rig path, which is the whole reason §11 could say "the solver is identical
20
+ * either way; only seeding and write-back differ" and mean it.
21
+ *
22
+ * @author Alex Goldring
23
+ * @copyright Company Named Limited (c) 2026
24
+ */
25
+
26
+ /**
27
+ * Mass of one particle, kg. Arbitrary and uniform — see the module docblock for
28
+ * why "arbitrary" is a statement about the solver rather than a shrug.
29
+ * @type {number}
30
+ */
31
+ export const CLOTH_PARTICLE_MASS = 0.02;
32
+
33
+
34
+
35
+ /**
36
+ * Slack radius at `ClothDynamics#slack = 1`, as a multiple of `d_geo`.
37
+ *
38
+ * It is **2**, and that is a derivation rather than a taste. The tether row
39
+ * already holds every particle within `d_geo` of the anchor, and the animated
40
+ * position it is leashed to is itself within `d_geo` of the anchor — a chord is
41
+ * never longer than the arc it subtends. By the triangle inequality the two can
42
+ * therefore never be more than `2·d_geo` apart, so a slack radius of `2·d_geo`
43
+ * is **provably inactive** and `slack = 1` means exactly "no leash" with no
44
+ * sentinel value and no discontinuity to code around.
45
+ *
46
+ * §3.4 writes `r_i = slack · d_geo,i`, which makes `slack = 1` a real and
47
+ * fairly tight constraint instead: a rope hanging straight down cannot swing
48
+ * through 90°, because its tip would move `√2·d_geo` to get there. That is a
49
+ * bound nobody asked for at the setting that is supposed to ask for none.
50
+ * @type {number}
51
+ */
52
+ export const CLOTH_SLACK_REACH = 2;
53
+
54
+
55
+
56
+ /**
57
+ * CSR children per node, from the parent array.
58
+ * @param {ClothInstance} instance
59
+ * @returns {void}
60
+ */
61
+ export function cloth_build_children(instance) {
62
+ const node_count = instance.node_count;
63
+ const parent = instance.node_parent;
64
+
65
+ const offset = new Int32Array(node_count + 1);
66
+
67
+ for (let node = 1; node < node_count; node++) {
68
+ offset[parent[node] + 1]++;
69
+ }
70
+
71
+ for (let node = 0; node < node_count; node++) {
72
+ offset[node + 1] += offset[node];
73
+ }
74
+
75
+ const child = new Int32Array(node_count > 0 ? node_count - 1 : 0);
76
+ const cursor = offset.slice(0, node_count);
77
+
78
+ for (let node = 1; node < node_count; node++) {
79
+ child[cursor[parent[node]]++] = node;
80
+ }
81
+
82
+ instance.node_child_offset = offset;
83
+ instance.node_child = child;
84
+ }
85
+
86
+
87
+
88
+ /**
89
+ * Rows, geodesics and the `ClothState` itself, from a seeded
90
+ * `node_parent` / `animated_position` pair.
91
+ *
92
+ * @param {ClothInstance} instance
93
+ * @param {number} dt
94
+ * @returns {void}
95
+ */
96
+ export function cloth_build_rows(instance, dt) {
97
+ const node_count = instance.node_count;
98
+
99
+ const parent = instance.node_parent;
100
+ const rest = instance.animated_position;
101
+
102
+ const dynamics = instance.cloth.dynamics;
103
+
104
+ const strain_limited = (dynamics.flags & ClothDynamicsFlags.StrainLimit) !== 0;
105
+
106
+ const geodesic = new Float32Array(node_count);
107
+
108
+ const mass_inverse = new Float32Array(node_count);
109
+
110
+ // The anchor is the fixed set: zero inverse mass, and a geodesic of zero,
111
+ // which is what makes every derived radius collapse onto it correctly.
112
+ for (let node = 1; node < node_count; node++) {
113
+ mass_inverse[node] = 1 / CLOTH_PARTICLE_MASS;
114
+ }
115
+
116
+ const stretch_particle = [];
117
+ const stretch_rest = [];
118
+ const stretch_stiffness = [];
119
+ const stretch_force_min = [];
120
+ const stretch_force_max = [];
121
+
122
+ const link_row = new Int32Array(node_count).fill(-1);
123
+ const strain_row = new Int32Array(node_count).fill(-1);
124
+ const skip_row = new Int32Array(node_count).fill(-1);
125
+
126
+ const strain = cloth_strain_allowance(dynamics.stretch);
127
+
128
+ // A skip row spans two links and both of its ends are free, so its
129
+ // effective inertia along the constraint is half a particle's.
130
+ const bend_stiffness = cloth_bend_ratio(dynamics.bend)
131
+ * (CLOTH_PARTICLE_MASS * 0.5) / (dt * dt);
132
+
133
+ let reach = 0;
134
+
135
+ for (let node = 1; node < node_count; node++) {
136
+ const p = parent[node];
137
+
138
+ const length = Math.hypot(
139
+ rest[node * 3] - rest[p * 3],
140
+ rest[node * 3 + 1] - rest[p * 3 + 1],
141
+ rest[node * 3 + 2] - rest[p * 3 + 2]
142
+ );
143
+
144
+ geodesic[node] = geodesic[p] + length;
145
+
146
+ if (geodesic[node] > reach) {
147
+ reach = geodesic[node];
148
+ }
149
+
150
+ link_row[node] = stretch_rest.length;
151
+
152
+ // Hard, bilateral: the fabric row. It is hard because a *penalty* stiff
153
+ // enough to be fabric adds energy rather than dissipating it — see
154
+ // `cloth_dynamics_map.js`, and `MEASUREMENTS.md` §6 for the +6.8 J.
155
+ stretch_particle.push(p, node);
156
+ stretch_rest.push(length);
157
+ stretch_stiffness.push(Infinity);
158
+ stretch_force_min.push(-Infinity);
159
+ stretch_force_max.push(Infinity);
160
+
161
+ if (strain_limited) {
162
+ strain_row[node] = stretch_rest.length;
163
+
164
+ // Hard, one-sided: §6's strain limit, and note the clamp. A row
165
+ // that bounds a distance from ABOVE may only apply force that
166
+ // reduces `C`, which for a distance row is the positive half —
167
+ // `[0, +∞)`. §6's table has this row at `(−∞, 0]`, which is the
168
+ // force that pushes the two ends apart; `cloth_leash_row.js`
169
+ // carries the derivation and a spec that shows it directly.
170
+ stretch_particle.push(p, node);
171
+ stretch_rest.push(length * (1 + strain));
172
+ stretch_stiffness.push(Infinity);
173
+ stretch_force_min.push(0);
174
+ stretch_force_max.push(Infinity);
175
+ }
176
+
177
+ const grandparent = parent[p];
178
+
179
+ if (grandparent >= 0 && bend_stiffness > 0) {
180
+ const span = Math.hypot(
181
+ rest[node * 3] - rest[grandparent * 3],
182
+ rest[node * 3 + 1] - rest[grandparent * 3 + 1],
183
+ rest[node * 3 + 2] - rest[grandparent * 3 + 2]
184
+ );
185
+
186
+ skip_row[node] = stretch_rest.length;
187
+
188
+ // Soft, bilateral: the bending model. Its rest length is read from
189
+ // the authored pose, so a chain authored with a curve holds it.
190
+ stretch_particle.push(grandparent, node);
191
+ stretch_rest.push(span);
192
+ stretch_stiffness.push(bend_stiffness);
193
+ stretch_force_min.push(-Infinity);
194
+ stretch_force_max.push(Infinity);
195
+ }
196
+ }
197
+
198
+ const leash_particle = [];
199
+ const leash_radius = [];
200
+
201
+ const slack_row = new Int32Array(node_count).fill(-1);
202
+ const tether_row = new Int32Array(node_count).fill(-1);
203
+
204
+ const slack_scale = CLOTH_SLACK_REACH * clamp01(dynamics.slack);
205
+
206
+ for (let node = 1; node < node_count; node++) {
207
+ // Tether first: §7 P2's long-range attachment, and the row that makes a
208
+ // low iteration budget viable at all, because being hard it is enforced
209
+ // almost exactly in one iteration however deep the chain is.
210
+ tether_row[node] = leash_radius.length;
211
+
212
+ leash_particle.push(node);
213
+ leash_radius.push(geodesic[node]);
214
+
215
+ if (slack_scale < CLOTH_SLACK_REACH) {
216
+ slack_row[node] = leash_radius.length;
217
+
218
+ leash_particle.push(node);
219
+ leash_radius.push(slack_scale * geodesic[node]);
220
+ }
221
+ }
222
+
223
+ let shortest_row = Infinity;
224
+
225
+ for (let row = 0; row < stretch_rest.length; row++) {
226
+ if (stretch_rest[row] > 0 && stretch_rest[row] < shortest_row) {
227
+ shortest_row = stretch_rest[row];
228
+ }
229
+ }
230
+
231
+ // A cloth of one particle has no rows at all, so it has no correction
232
+ // authority to speak of and its reach is the only length it carries.
233
+ instance.shortest_row = shortest_row < Infinity ? shortest_row : reach;
234
+
235
+ instance.geodesic = geodesic;
236
+ instance.reach = reach;
237
+ instance.link_row = link_row;
238
+ instance.strain_row = strain_row;
239
+ instance.skip_row = skip_row;
240
+ instance.slack_row = slack_row;
241
+ instance.tether_row = tether_row;
242
+
243
+ const state = ClothState.from({
244
+ position: rest,
245
+ mass_inverse,
246
+ stretch_particle: Int32Array.from(stretch_particle),
247
+ stretch_rest: Float32Array.from(stretch_rest),
248
+ stretch_stiffness: Float32Array.from(stretch_stiffness),
249
+ stretch_force_min: Float32Array.from(stretch_force_min),
250
+ stretch_force_max: Float32Array.from(stretch_force_max),
251
+ leash_particle: Int32Array.from(leash_particle),
252
+ leash_radius: Float32Array.from(leash_radius)
253
+ });
254
+
255
+ const particle_of_node = new Int32Array(node_count);
256
+
257
+ for (let particle = 0; particle < node_count; particle++) {
258
+ particle_of_node[state.source_of_particle[particle]] = particle;
259
+ }
260
+
261
+ // Everything derived from the rows, derived again — and from the bind pose,
262
+ // which is what `closest_free_pair` has to be measured in: the answer is a
263
+ // property of how the proxy was authored, not of whatever shape the solver
264
+ // happens to have the cloth in when self-collision is first switched on.
265
+ const exclusions = cloth_self_exclusions(state);
266
+
267
+ instance.self_exclusions = exclusions;
268
+
269
+ // Bounded at twice the shortest row, which is where a sheet's answer lies,
270
+ // so the walk is 27 cells rather than the whole cloth. A proxy with nothing
271
+ // that close gets `Infinity`, and then no radius inside the floor can reach
272
+ // anything either.
273
+ instance.closest_free_pair = cloth_self_closest_free_pair(
274
+ state, exclusions, instance.shortest_row * 2
275
+ );
276
+
277
+ instance.particle_of_node = particle_of_node;
278
+ instance.blended_position = new Float64Array(node_count * 3);
279
+ instance.blended_rotation = new Float64Array(node_count * 4);
280
+ instance.state = state;
281
+ instance.seeded = true;
282
+ }
283
+
284
+ /**
285
+ * @param {number} v
286
+ * @returns {number}
287
+ * @private
288
+ */
289
+ function clamp01(v) {
290
+ return v < 0 ? 0 : (v > 1 ? 1 : v);
291
+ }
292
+
293
+ /**
294
+ * Re-parameterise the rows of an already-seeded cloth from its current
295
+ * {@link ClothDynamics}, without walking the subtree again.
296
+ *
297
+ * This is what makes `cloth.dynamics.slack = 0.2` work live: the topology, the
298
+ * rest lengths and the geodesics are properties of the authored pose and do not
299
+ * move, and everything that does move is a number in a row table.
300
+ *
301
+ * The multipliers are **not** reset. A row whose radius has just changed is
302
+ * carrying a force appropriate to the radius it had, and it is one warm start
303
+ * away from carrying the right one; zeroing them would put a visible jolt into
304
+ * every parameter change instead.
305
+ *
306
+ * @param {ClothInstance} instance
307
+ * @param {number} dt
308
+ * @returns {void}
309
+ */
310
+ export function cloth_reparameterise(instance, dt) {
311
+ const dynamics = instance.cloth.dynamics;
312
+
313
+ const state = instance.state;
314
+
315
+ const node_count = instance.node_count;
316
+
317
+ const strain = cloth_strain_allowance(dynamics.stretch);
318
+
319
+ const bend_stiffness = cloth_bend_ratio(dynamics.bend)
320
+ * (CLOTH_PARTICLE_MASS * 0.5) / (dt * dt);
321
+
322
+ const slack_scale = CLOTH_SLACK_REACH * clamp01(dynamics.slack);
323
+
324
+ for (let node = 1; node < node_count; node++) {
325
+ const link = instance.link_row[node];
326
+ const strain_limit = instance.strain_row[node];
327
+ const skip = instance.skip_row[node];
328
+ const slack = instance.slack_row[node];
329
+
330
+ if (strain_limit >= 0) {
331
+ state.stretch_rest[strain_limit] = state.stretch_rest[link] * (1 + strain);
332
+ }
333
+
334
+ if (skip >= 0) {
335
+ state.stretch_stiffness[skip] = bend_stiffness;
336
+ }
337
+
338
+ if (slack >= 0) {
339
+ state.leash_radius[slack] = slack_scale * instance.geodesic[node];
340
+ }
341
+ }
342
+
343
+ instance.dynamics_seen.copy(dynamics);
344
+ }
345
+
346
+ /**
347
+ * Whether a dynamics change needs the subtree walked again rather than merely
348
+ * re-parameterised.
349
+ *
350
+ * Two fields do: turning the strain limit on or off adds or removes rows, and
351
+ * so does moving `slack` across the bound at which its row is provably
352
+ * inactive. Everything else is a number in a table that already exists.
353
+ *
354
+ * @param {ClothDynamics} before
355
+ * @param {ClothDynamics} after
356
+ * @returns {boolean}
357
+ */
358
+ export function cloth_dynamics_change_needs_reseed(before, after) {
359
+ const strain_before = (before.flags & ClothDynamicsFlags.StrainLimit) !== 0;
360
+ const strain_after = (after.flags & ClothDynamicsFlags.StrainLimit) !== 0;
361
+
362
+ if (strain_before !== strain_after) {
363
+ return true;
364
+ }
365
+
366
+ const leashed_before = clamp01(before.slack) < 1;
367
+ const leashed_after = clamp01(after.slack) < 1;
368
+
369
+ if (leashed_before !== leashed_after) {
370
+ return true;
371
+ }
372
+
373
+ return (before.bend > 0) !== (after.bend > 0);
374
+ }
@@ -40,6 +40,21 @@
40
40
  * leather is at the ceiling rather than above it. `cloth_dynamics_map.js`
41
41
  * carries both derivations.
42
42
  *
43
+ * ## Which entries collide with themselves, and why the list moved
44
+ *
45
+ * §9 said the flag belongs on "skirts, long coats, hair" — a list of what the
46
+ * garment *is*. **M4 measured that what decides is `bend`.** On a folding sheet
47
+ * at each entry's own bending: silk, hair and cotton pass through themselves 8
48
+ * to 11 times a sample unaided and the row removes 71% to 81% of it; denim
49
+ * tangles a third as much; leather does not tangle at all — 0.18 crossings a
50
+ * sample — and the row makes it marginally worse, because the handful of pairs
51
+ * it finds on a fabric that will not fold are noise it is adding.
52
+ *
53
+ * So `CLOTH_SILK`, `CLOTH_COTTON` and `CLOTH_HAIR` set it and nothing else
54
+ * does. It costs each of them about a fifth of their frame and all three stay
55
+ * inside 2 ms. The chains have no surface to pass through and a coiling rope is
56
+ * a case that measurement does not cover. `MEASUREMENTS.md` §33.
57
+ *
43
58
  * `stretch` is also the weakest field in the set, and the entries say so by
44
59
  * which of them set `ClothDynamicsFlags.StrainLimit`. Measured on a 24-link
45
60
  * rope dropped through ninety degrees, the strain-limit row removes about a
@@ -64,6 +79,11 @@
64
79
  * and iterations, so it keeps both and pays for them everywhere else; at 2×4
65
80
  * the fabric row is inside 1.4% of strain unaided and the strain-limit row
66
81
  * would buy half a per cent of that for 15% of the frame.
82
+ *
83
+ * *Self-collision:* **on, and it is the third lever's worth.** 1.46 ms to
84
+ * 1.78 ms, +22%, still inside. Silk is the floppiest fabric in the set and a
85
+ * folding sheet of it passes through itself 8 times a sample without the row;
86
+ * with it, 2.4. `MEASUREMENTS.md` §33.
67
87
  * @type {Readonly<ClothDynamics>}
68
88
  */
69
89
  export const CLOTH_SILK: Readonly<ClothDynamics>;
@@ -73,6 +93,11 @@ export const CLOTH_SILK: Readonly<ClothDynamics>;
73
93
  *
74
94
  * *Budget:* **400 particles at 2×4 — 1.49 ms.** Fewer particles, and no
75
95
  * strain-limit row, for the same reason silk drops it.
96
+ *
97
+ * *Self-collision:* **on.** 1.51 ms to 1.82 ms, +21%, still inside. This is
98
+ * the entry every other one is a deviation from, and a default that passes
99
+ * through itself nine times a sample while it moves is a bad default.
100
+ * `MEASUREMENTS.md` §33.
76
101
  * @type {Readonly<ClothDynamics>}
77
102
  */
78
103
  export const CLOTH_COTTON: Readonly<ClothDynamics>;
@@ -132,9 +157,13 @@ export const CLOTH_CHAIN: Readonly<ClothDynamics>;
132
157
  * does.
133
158
  *
134
159
  * *Budget:* **400 particles across all strands at 2×4 — 1.49 ms**, the same
135
- * two levers silk takes. `ClothDynamicsFlags.SelfCollision` is a claim about
136
- * the fabric that M4 will have to re-price when it can honour it, and it is
137
- * the reason this entry has the least headroom in the library.
160
+ * two levers silk takes.
161
+ *
162
+ * *Self-collision:* **on, and M4 priced it.** 1.53 ms to 1.81 ms, +19%, still
163
+ * inside. This was the only entry that set the flag before there was anything
164
+ * to honour it, and the measurement agrees with the claim: hair passes through
165
+ * itself 10.6 times a sample unaided, the most of any entry, and the row
166
+ * removes 81% of that. `MEASUREMENTS.md` §33.
138
167
  * @type {Readonly<ClothDynamics>}
139
168
  */
140
169
  export const CLOTH_HAIR: Readonly<ClothDynamics>;
@@ -1 +1 @@
1
- {"version":3,"file":"cloth_dynamics_library.d.ts","sourceRoot":"","sources":["../../../../../../src/engine/physics/cloth/ecs/cloth_dynamics_library.js"],"names":[],"mappings":"AAGA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAwDG;AAEH;;;;;;;;;;GAUG;AACH,yBAFU,SAAS,aAAa,CAAC,CAa7B;AAEJ;;;;;;;GAOG;AACH,2BAFU,SAAS,aAAa,CAAC,CAa7B;AAEJ;;;;;;;;;;;GAWG;AACH,0BAFU,SAAS,aAAa,CAAC,CAY7B;AAEJ;;;;;;;;GAQG;AACH,4BAFU,SAAS,aAAa,CAAC,CAY7B;AAEJ;;;;;;;;;;;;GAYG;AACH,yBAFU,SAAS,aAAa,CAAC,CAY7B;AAEJ;;;;;;;;;;GAUG;AACH,0BAFU,SAAS,aAAa,CAAC,CAY7B;AAEJ;;;;;;;;;;;GAWG;AACH,yBAFU,SAAS,aAAa,CAAC,CAa7B;AAEJ;;;;;GAKG;AACH,qCAFU,cAAc,SAAS,aAAa,CAAC,CAAC,CAU7C;AAEH;;;;GAIG;AACH,qCAFU;QAAgB,MAAM,GAAE,SAAS,aAAa,CAAC;EAAE,CAUxD;8BA7P2B,oBAAoB"}
1
+ {"version":3,"file":"cloth_dynamics_library.d.ts","sourceRoot":"","sources":["../../../../../../src/engine/physics/cloth/ecs/cloth_dynamics_library.js"],"names":[],"mappings":"AAGA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAuEG;AAEH;;;;;;;;;;;;;;;GAeG;AACH,yBAFU,SAAS,aAAa,CAAC,CAa7B;AAEJ;;;;;;;;;;;;GAYG;AACH,2BAFU,SAAS,aAAa,CAAC,CAa7B;AAEJ;;;;;;;;;;;GAWG;AACH,0BAFU,SAAS,aAAa,CAAC,CAY7B;AAEJ;;;;;;;;GAQG;AACH,4BAFU,SAAS,aAAa,CAAC,CAY7B;AAEJ;;;;;;;;;;;;GAYG;AACH,yBAFU,SAAS,aAAa,CAAC,CAY7B;AAEJ;;;;;;;;;;GAUG;AACH,0BAFU,SAAS,aAAa,CAAC,CAY7B;AAEJ;;;;;;;;;;;;;;;GAeG;AACH,yBAFU,SAAS,aAAa,CAAC,CAa7B;AAEJ;;;;;GAKG;AACH,qCAFU,cAAc,SAAS,aAAa,CAAC,CAAC,CAU7C;AAEH;;;;GAIG;AACH,qCAFU;QAAgB,MAAM,GAAE,SAAS,aAAa,CAAC;EAAE,CAUxD;8BA1R2B,oBAAoB"}