@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.
- package/package.json +1 -1
- package/src/core/geom/3d/hash-grid/PointHashGrid3.d.ts +118 -0
- package/src/core/geom/3d/hash-grid/PointHashGrid3.d.ts.map +1 -0
- package/src/core/geom/3d/hash-grid/PointHashGrid3.js +283 -0
- package/src/core/geom/3d/shape/BoxShape3D.d.ts.map +1 -1
- package/src/core/geom/3d/shape/BoxShape3D.js +6 -17
- package/src/core/geom/3d/shape/CapsuleShape3D.d.ts.map +1 -1
- package/src/core/geom/3d/shape/CapsuleShape3D.js +3 -14
- package/src/core/geom/3d/shape/CylinderShape3D.d.ts.map +1 -1
- package/src/core/geom/3d/shape/CylinderShape3D.js +3 -21
- package/src/core/geom/3d/shape/PlaneShape3D.d.ts +105 -0
- package/src/core/geom/3d/shape/PlaneShape3D.d.ts.map +1 -0
- package/src/core/geom/3d/shape/PlaneShape3D.js +251 -0
- package/src/core/geom/3d/shape/SphereShape3D.js +3 -3
- package/src/core/geom/3d/shape/json/shape_to_type.d.ts.map +1 -1
- package/src/core/geom/3d/shape/json/shape_to_type.js +3 -0
- package/src/core/geom/3d/shape/json/type_adapters.d.ts +14 -0
- package/src/core/geom/3d/shape/json/type_adapters.d.ts.map +1 -1
- package/src/core/geom/3d/shape/json/type_adapters.js +15 -0
- package/src/core/geom/3d/shape/sdf/sdf3_box.d.ts +51 -0
- package/src/core/geom/3d/shape/sdf/sdf3_box.d.ts.map +1 -0
- package/src/core/geom/3d/shape/sdf/sdf3_box.js +113 -0
- package/src/core/geom/3d/shape/sdf/sdf3_capsule.d.ts +46 -0
- package/src/core/geom/3d/shape/sdf/sdf3_capsule.d.ts.map +1 -0
- package/src/core/geom/3d/shape/sdf/sdf3_capsule.js +82 -0
- package/src/core/geom/3d/shape/sdf/sdf3_cylinder.d.ts +60 -0
- package/src/core/geom/3d/shape/sdf/sdf3_cylinder.d.ts.map +1 -0
- package/src/core/geom/3d/shape/sdf/sdf3_cylinder.js +126 -0
- package/src/core/geom/3d/shape/sdf/sdf3_degenerate_normal.d.ts +50 -0
- package/src/core/geom/3d/shape/sdf/sdf3_degenerate_normal.d.ts.map +1 -0
- package/src/core/geom/3d/shape/sdf/sdf3_degenerate_normal.js +53 -0
- package/src/core/geom/3d/shape/sdf/sdf3_plane.d.ts +52 -0
- package/src/core/geom/3d/shape/sdf/sdf3_plane.d.ts.map +1 -0
- package/src/core/geom/3d/shape/sdf/sdf3_plane.js +61 -0
- package/src/core/geom/3d/shape/sdf/sdf3_sphere.d.ts +41 -0
- package/src/core/geom/3d/shape/sdf/sdf3_sphere.d.ts.map +1 -0
- package/src/core/geom/3d/shape/sdf/sdf3_sphere.js +71 -0
- package/src/core/process/ConcurrencyGate.d.ts +103 -0
- package/src/core/process/ConcurrencyGate.d.ts.map +1 -0
- package/src/core/process/ConcurrencyGate.js +207 -0
- package/src/engine/asset/AssetManager.d.ts +10 -0
- package/src/engine/asset/AssetManager.d.ts.map +1 -1
- package/src/engine/asset/AssetManager.js +10 -0
- package/src/engine/graphics/CONTEXT_LOSS_RECOVERY_PLAN.md +30 -13
- package/src/engine/graphics3/pose/collect_entity_playbacks.d.ts +26 -0
- package/src/engine/graphics3/pose/collect_entity_playbacks.d.ts.map +1 -0
- package/src/engine/graphics3/pose/collect_entity_playbacks.js +40 -0
- package/src/engine/graphics3/pose/query_entity_node_world_pose.d.ts.map +1 -1
- package/src/engine/graphics3/pose/query_entity_node_world_pose.js +74 -101
- package/src/engine/physics/cloth/MEASUREMENTS.md +1287 -4
- package/src/engine/physics/cloth/PLAN.md +1967 -1581
- package/src/engine/physics/cloth/build/ClothProxy.d.ts +147 -0
- package/src/engine/physics/cloth/build/ClothProxy.d.ts.map +1 -0
- package/src/engine/physics/cloth/build/ClothProxy.js +207 -0
- package/src/engine/physics/cloth/build/cloth_proxy_from_joints.d.ts +70 -0
- package/src/engine/physics/cloth/build/cloth_proxy_from_joints.d.ts.map +1 -0
- package/src/engine/physics/cloth/build/cloth_proxy_from_joints.js +256 -0
- package/src/engine/physics/cloth/collider/ClothColliderIndex.d.ts +176 -0
- package/src/engine/physics/cloth/collider/ClothColliderIndex.d.ts.map +1 -0
- package/src/engine/physics/cloth/collider/ClothColliderIndex.js +435 -0
- package/src/engine/physics/cloth/collider/ClothColliderKind.d.ts +12 -0
- package/src/engine/physics/cloth/collider/ClothColliderKind.d.ts.map +1 -0
- package/src/engine/physics/cloth/collider/ClothColliderKind.js +38 -0
- package/src/engine/physics/cloth/collider/ClothColliderRecord.d.ts +120 -0
- package/src/engine/physics/cloth/collider/ClothColliderRecord.d.ts.map +1 -0
- package/src/engine/physics/cloth/collider/ClothColliderRecord.js +137 -0
- package/src/engine/physics/cloth/collider/cloth_collider_bounds.d.ts +25 -0
- package/src/engine/physics/cloth/collider/cloth_collider_bounds.d.ts.map +1 -0
- package/src/engine/physics/cloth/collider/cloth_collider_bounds.js +190 -0
- package/src/engine/physics/cloth/collider/cloth_collider_pack.d.ts +44 -0
- package/src/engine/physics/cloth/collider/cloth_collider_pack.d.ts.map +1 -0
- package/src/engine/physics/cloth/collider/cloth_collider_pack.js +173 -0
- package/src/engine/physics/cloth/collider/cloth_collider_sdf.d.ts +94 -0
- package/src/engine/physics/cloth/collider/cloth_collider_sdf.d.ts.map +1 -0
- package/src/engine/physics/cloth/collider/cloth_collider_sdf.js +275 -0
- package/src/engine/physics/cloth/ecs/ClothCollider.d.ts +126 -0
- package/src/engine/physics/cloth/ecs/ClothCollider.d.ts.map +1 -0
- package/src/engine/physics/cloth/ecs/ClothCollider.js +199 -0
- package/src/engine/physics/cloth/ecs/ClothColliderFlags.d.ts +9 -0
- package/src/engine/physics/cloth/ecs/ClothColliderFlags.d.ts.map +1 -0
- package/src/engine/physics/cloth/ecs/ClothColliderFlags.js +32 -0
- package/src/engine/physics/cloth/ecs/ClothColliderSystem.d.ts +114 -0
- package/src/engine/physics/cloth/ecs/ClothColliderSystem.d.ts.map +1 -0
- package/src/engine/physics/cloth/ecs/ClothColliderSystem.js +243 -0
- package/src/engine/physics/cloth/ecs/ClothDynamicsFlags.js +66 -57
- package/src/engine/physics/cloth/ecs/ClothInstance.d.ts +109 -1
- package/src/engine/physics/cloth/ecs/ClothInstance.d.ts.map +1 -1
- package/src/engine/physics/cloth/ecs/ClothInstance.js +479 -363
- package/src/engine/physics/cloth/ecs/ClothRig.d.ts +95 -0
- package/src/engine/physics/cloth/ecs/ClothRig.d.ts.map +1 -0
- package/src/engine/physics/cloth/ecs/ClothRig.js +140 -0
- package/src/engine/physics/cloth/ecs/ClothSystem.d.ts +30 -1
- package/src/engine/physics/cloth/ecs/ClothSystem.d.ts.map +1 -1
- package/src/engine/physics/cloth/ecs/ClothSystem.js +1021 -773
- package/src/engine/physics/cloth/ecs/cloth_build_rows.d.ts +90 -0
- package/src/engine/physics/cloth/ecs/cloth_build_rows.d.ts.map +1 -0
- package/src/engine/physics/cloth/ecs/cloth_build_rows.js +374 -0
- package/src/engine/physics/cloth/ecs/cloth_dynamics_library.d.ts +32 -3
- package/src/engine/physics/cloth/ecs/cloth_dynamics_library.d.ts.map +1 -1
- package/src/engine/physics/cloth/ecs/cloth_dynamics_library.js +283 -254
- package/src/engine/physics/cloth/ecs/cloth_gather_colliders.d.ts +59 -0
- package/src/engine/physics/cloth/ecs/cloth_gather_colliders.d.ts.map +1 -0
- package/src/engine/physics/cloth/ecs/cloth_gather_colliders.js +328 -0
- package/src/engine/physics/cloth/ecs/cloth_reconstruct_pose.d.ts +13 -0
- package/src/engine/physics/cloth/ecs/cloth_reconstruct_pose.d.ts.map +1 -0
- package/src/engine/physics/cloth/ecs/cloth_reconstruct_pose.js +288 -0
- package/src/engine/physics/cloth/ecs/cloth_seed_rig.d.ts +58 -0
- package/src/engine/physics/cloth/ecs/cloth_seed_rig.d.ts.map +1 -0
- package/src/engine/physics/cloth/ecs/cloth_seed_rig.js +199 -0
- package/src/engine/physics/cloth/ecs/cloth_seed_subtree.d.ts +8 -63
- package/src/engine/physics/cloth/ecs/cloth_seed_subtree.d.ts.map +1 -1
- package/src/engine/physics/cloth/ecs/cloth_seed_subtree.js +317 -645
- package/src/engine/physics/cloth/ecs/cloth_write_back.d.ts +61 -0
- package/src/engine/physics/cloth/ecs/cloth_write_back.d.ts.map +1 -1
- package/src/engine/physics/cloth/ecs/cloth_write_back.js +212 -449
- package/src/engine/physics/cloth/ecs/cloth_write_back_rig.d.ts +49 -0
- package/src/engine/physics/cloth/ecs/cloth_write_back_rig.d.ts.map +1 -0
- package/src/engine/physics/cloth/ecs/cloth_write_back_rig.js +115 -0
- package/src/engine/physics/cloth/playground/README.md +155 -1
- package/src/engine/physics/cloth/playground/collide.html +178 -0
- package/src/engine/physics/cloth/playground/collide_build.d.ts +95 -0
- package/src/engine/physics/cloth/playground/collide_build.d.ts.map +1 -0
- package/src/engine/physics/cloth/playground/collide_build.js +315 -0
- package/src/engine/physics/cloth/playground/collide_main.d.ts +2 -0
- package/src/engine/physics/cloth/playground/collide_main.d.ts.map +1 -0
- package/src/engine/physics/cloth/playground/collide_main.js +720 -0
- package/src/engine/physics/cloth/playground/garment.html +182 -0
- package/src/engine/physics/cloth/playground/garment_build.d.ts +78 -0
- package/src/engine/physics/cloth/playground/garment_build.d.ts.map +1 -0
- package/src/engine/physics/cloth/playground/garment_build.js +359 -0
- package/src/engine/physics/cloth/playground/garment_main.d.ts +2 -0
- package/src/engine/physics/cloth/playground/garment_main.d.ts.map +1 -0
- package/src/engine/physics/cloth/playground/garment_main.js +633 -0
- package/src/engine/physics/cloth/solver/ClothState.d.ts +208 -5
- package/src/engine/physics/cloth/solver/ClothState.d.ts.map +1 -1
- package/src/engine/physics/cloth/solver/ClothState.js +302 -8
- package/src/engine/physics/cloth/solver/cloth_contact_find.d.ts +87 -0
- package/src/engine/physics/cloth/solver/cloth_contact_find.d.ts.map +1 -0
- package/src/engine/physics/cloth/solver/cloth_contact_find.js +343 -0
- package/src/engine/physics/cloth/solver/cloth_self_find.d.ts +112 -0
- package/src/engine/physics/cloth/solver/cloth_self_find.d.ts.map +1 -0
- package/src/engine/physics/cloth/solver/cloth_self_find.js +448 -0
- package/src/engine/physics/cloth/solver/cloth_solve_vertex.d.ts +4 -1
- package/src/engine/physics/cloth/solver/cloth_solve_vertex.d.ts.map +1 -1
- package/src/engine/physics/cloth/solver/cloth_solve_vertex.js +16 -1
- package/src/engine/physics/cloth/solver/cloth_solver_constants.d.ts +112 -5
- package/src/engine/physics/cloth/solver/cloth_solver_constants.d.ts.map +1 -1
- package/src/engine/physics/cloth/solver/cloth_solver_constants.js +117 -6
- package/src/engine/physics/cloth/solver/cloth_step.d.ts +40 -9
- package/src/engine/physics/cloth/solver/cloth_step.d.ts.map +1 -1
- package/src/engine/physics/cloth/solver/cloth_step.js +122 -10
- package/src/engine/physics/cloth/solver/constraint/cloth_backstop_row.d.ts +95 -0
- package/src/engine/physics/cloth/solver/constraint/cloth_backstop_row.d.ts.map +1 -0
- package/src/engine/physics/cloth/solver/constraint/cloth_backstop_row.js +285 -0
- package/src/engine/physics/cloth/solver/constraint/cloth_contact_row.d.ts +129 -0
- package/src/engine/physics/cloth/solver/constraint/cloth_contact_row.d.ts.map +1 -0
- package/src/engine/physics/cloth/solver/constraint/cloth_contact_row.js +501 -0
- package/src/engine/physics/cloth/solver/constraint/cloth_self_row.d.ts +75 -0
- package/src/engine/physics/cloth/solver/constraint/cloth_self_row.d.ts.map +1 -0
- package/src/engine/physics/cloth/solver/constraint/cloth_self_row.js +202 -0
- package/src/engine/physics/fluid/ecs/FluidObstacleSystem.d.ts +4 -4
- package/src/shade/playground/vgeo_viewer/README.md +18 -0
- package/src/shade/playground/vgeo_viewer/main.js +87 -50
- package/src/shade/renderer/buffer/table/GPUDatabase.d.ts.map +1 -1
- package/src/shade/renderer/buffer/table/GPUDatabase.js +191 -62
- package/src/shade/renderer/buffer/table/GPUTypedTable.d.ts +94 -2
- package/src/shade/renderer/buffer/table/GPUTypedTable.d.ts.map +1 -1
- package/src/shade/renderer/buffer/table/GPUTypedTable.js +414 -2
- package/src/shade/renderer/buffer/table/GPU_TABLE_PARTIAL_UPLOAD_DESCRIPTOR_WORDS.d.ts +14 -0
- package/src/shade/renderer/buffer/table/GPU_TABLE_PARTIAL_UPLOAD_DESCRIPTOR_WORDS.d.ts.map +1 -0
- package/src/shade/renderer/buffer/table/GPU_TABLE_PARTIAL_UPLOAD_DESCRIPTOR_WORDS.js +13 -0
- package/src/shade/renderer/buffer/table/gpu_table_partial_upload_shader.d.ts +17 -0
- package/src/shade/renderer/buffer/table/gpu_table_partial_upload_shader.d.ts.map +1 -0
- package/src/shade/renderer/buffer/table/gpu_table_partial_upload_shader.js +116 -0
- package/src/shade/renderer/geometry/bvh/GPUGeometryBVHManager.d.ts +9 -4
- package/src/shade/renderer/geometry/bvh/GPUGeometryBVHManager.d.ts.map +1 -1
- package/src/shade/renderer/geometry/bvh/GPUGeometryBVHManager.js +843 -734
- package/src/shade/renderer/geometry/bvh/GPUGeometryMeshletsBVH.d.ts +12 -0
- package/src/shade/renderer/geometry/bvh/GPUGeometryMeshletsBVH.d.ts.map +1 -1
- package/src/shade/renderer/geometry/bvh/GPUGeometryMeshletsBVH.js +13 -0
- package/src/shade/renderer/geometry/meshlet/GPUMeshletManager.d.ts +17 -0
- package/src/shade/renderer/geometry/meshlet/GPUMeshletManager.d.ts.map +1 -1
- package/src/shade/renderer/geometry/meshlet/GPUMeshletManager.js +185 -30
- package/src/shade/renderer/geometry/virtual/MICRON_COMPARISON_2026_08_20.md +17 -0
- package/src/shade/renderer/geometry/virtual/VGEO_FORMAT.md +141 -24
- package/src/shade/renderer/geometry/virtual/VIRTUAL_GEOMETRY_DESIGN.md +204 -64
- package/src/shade/renderer/geometry/virtual/VIRTUAL_GEOMETRY_PLAN.md +110 -10
- package/src/shade/renderer/geometry/virtual/VK_LOD_CLUSTERS_COMPARISON_2026_08_20.md +19 -0
- package/src/shade/renderer/geometry/virtual/format/read/VGeoByteSource.d.ts +19 -6
- package/src/shade/renderer/geometry/virtual/format/read/VGeoByteSource.d.ts.map +1 -1
- package/src/shade/renderer/geometry/virtual/format/read/VGeoByteSource.js +26 -7
- package/src/shade/renderer/geometry/virtual/format/read/VGeoContainerReader.d.ts +173 -14
- package/src/shade/renderer/geometry/virtual/format/read/VGeoContainerReader.d.ts.map +1 -1
- package/src/shade/renderer/geometry/virtual/format/read/VGeoContainerReader.js +458 -51
- package/src/shade/renderer/geometry/virtual/format/read/VGeoReadOptions.d.ts +49 -13
- package/src/shade/renderer/geometry/virtual/format/read/VGeoReadOptions.d.ts.map +1 -1
- package/src/shade/renderer/geometry/virtual/format/read/VGeoReadOptions.js +52 -14
- package/src/shade/renderer/geometry/virtual/format/read/tool/VGEO_MAX_AUDIT_BYTES.d.ts +20 -0
- package/src/shade/renderer/geometry/virtual/format/read/tool/VGEO_MAX_AUDIT_BYTES.d.ts.map +1 -0
- package/src/shade/renderer/geometry/virtual/format/read/tool/VGEO_MAX_AUDIT_BYTES.js +19 -0
- package/src/shade/renderer/geometry/virtual/format/read/tool/vgeo_audit_container.d.ts +27 -0
- package/src/shade/renderer/geometry/virtual/format/read/tool/vgeo_audit_container.d.ts.map +1 -0
- package/src/shade/renderer/geometry/virtual/format/read/tool/vgeo_audit_container.js +48 -0
- package/src/shade/renderer/geometry/virtual/format/read/tool/vgeo_install_all_pages.d.ts +29 -0
- package/src/shade/renderer/geometry/virtual/format/read/tool/vgeo_install_all_pages.d.ts.map +1 -0
- package/src/shade/renderer/geometry/virtual/format/read/tool/vgeo_install_all_pages.js +60 -0
- package/src/shade/renderer/geometry/virtual/format/read/vgeo_fetch_byte_source.d.ts +8 -1
- package/src/shade/renderer/geometry/virtual/format/read/vgeo_fetch_byte_source.d.ts.map +1 -1
- package/src/shade/renderer/geometry/virtual/format/read/vgeo_fetch_byte_source.js +32 -2
- package/src/shade/renderer/geometry/virtual/residency/VGeoResidencyManager.d.ts +258 -0
- package/src/shade/renderer/geometry/virtual/residency/VGeoResidencyManager.d.ts.map +1 -0
- package/src/shade/renderer/geometry/virtual/residency/VGeoResidencyManager.js +723 -0
- package/src/shade/renderer/geometry/virtual/residency/VGeoResidencyOptions.d.ts +49 -0
- package/src/shade/renderer/geometry/virtual/residency/VGeoResidencyOptions.d.ts.map +1 -0
- package/src/shade/renderer/geometry/virtual/residency/VGeoResidencyOptions.js +50 -0
- package/src/shade/renderer/loader/gltf/tiny-gltf.d.ts +1 -1
- package/src/shade/renderer/postprocess/nss/NSS.d.ts +1 -1
- package/src/shade/renderer/texture/bindless/GPUBindlessTextureManager.d.ts +3 -0
- package/src/shade/renderer/texture/bindless/GPUBindlessTextureManager.d.ts.map +1 -1
- package/src/shade/renderer/texture/bindless/GPUBindlessTextureManager.js +121 -21
- package/src/shade/renderer/texture/virtual/README.md +6 -4
- package/src/shade/renderer/texture/virtual/VirtualTextureManager.d.ts.map +1 -1
- package/src/shade/renderer/texture/virtual/VirtualTextureManager.js +7 -0
- package/src/shade/renderer/texture/virtual/source/VTSourceTiled.d.ts +3 -3
- package/src/shade/renderer/texture/virtual/source/VTSourceTiled.js +3 -3
- package/src/engine/ecs/system/SystemExecutionPhase.d.ts +0 -9
- package/src/engine/ecs/system/SystemExecutionPhase.d.ts.map +0 -1
- package/src/engine/graphics/texture/virtual/NOTES.md +0 -128
- package/src/engine/graphics/texture/virtual/VT_DEFAULT_PAGE_RESOLUTION.d.ts +0 -6
- package/src/engine/graphics/texture/virtual/VT_DEFAULT_PAGE_RESOLUTION.d.ts.map +0 -1
- package/src/engine/graphics/texture/virtual/VT_DEFAULT_PAGE_RESOLUTION.js +0 -5
- package/src/engine/graphics/texture/virtual/VirtualTextureTileLoader.d.ts +0 -49
- package/src/engine/graphics/texture/virtual/VirtualTextureTileLoader.d.ts.map +0 -1
- package/src/engine/graphics/texture/virtual/VirtualTextureTileLoader.js +0 -264
- package/src/engine/graphics/texture/virtual/VirtualTextureUsage.d.ts +0 -44
- package/src/engine/graphics/texture/virtual/VirtualTextureUsage.d.ts.map +0 -1
- package/src/engine/graphics/texture/virtual/VirtualTextureUsage.js +0 -228
- package/src/engine/graphics/texture/virtual/VirtualTextureUsageShader.d.ts +0 -3
- package/src/engine/graphics/texture/virtual/VirtualTextureUsageShader.d.ts.map +0 -1
- package/src/engine/graphics/texture/virtual/VirtualTextureUsageShader.js +0 -73
- package/src/engine/graphics/texture/virtual/debug/ResidencyDebugView.d.ts +0 -14
- package/src/engine/graphics/texture/virtual/debug/ResidencyDebugView.d.ts.map +0 -1
- package/src/engine/graphics/texture/virtual/debug/ResidencyDebugView.js +0 -85
- package/src/engine/graphics/texture/virtual/debug/UsageDebugView.d.ts +0 -12
- package/src/engine/graphics/texture/virtual/debug/UsageDebugView.d.ts.map +0 -1
- package/src/engine/graphics/texture/virtual/debug/UsageDebugView.js +0 -63
- package/src/engine/graphics/texture/virtual/debug/UsagePyramidDebugView.d.ts +0 -12
- package/src/engine/graphics/texture/virtual/debug/UsagePyramidDebugView.d.ts.map +0 -1
- package/src/engine/graphics/texture/virtual/debug/UsagePyramidDebugView.js +0 -243
- package/src/engine/graphics/texture/virtual/tile/VirtualTextureTile.d.ts +0 -30
- package/src/engine/graphics/texture/virtual/tile/VirtualTextureTile.d.ts.map +0 -1
- package/src/engine/graphics/texture/virtual/tile/VirtualTextureTile.js +0 -39
- package/src/engine/graphics/texture/virtual/tile/compose_finger_print.d.ts +0 -9
- package/src/engine/graphics/texture/virtual/tile/compose_finger_print.d.ts.map +0 -1
- package/src/engine/graphics/texture/virtual/tile/compose_finger_print.js +0 -24
- package/src/engine/graphics/texture/virtual/tile/compose_tile_address.d.ts +0 -9
- package/src/engine/graphics/texture/virtual/tile/compose_tile_address.d.ts.map +0 -1
- package/src/engine/graphics/texture/virtual/tile/compose_tile_address.js +0 -26
- package/src/engine/graphics/texture/virtual/tile/decompose_finger_print.d.ts +0 -11
- package/src/engine/graphics/texture/virtual/tile/decompose_finger_print.d.ts.map +0 -1
- package/src/engine/graphics/texture/virtual/tile/decompose_finger_print.js +0 -12
- package/src/engine/graphics/texture/virtual/tile/finger_print_to_tile_address.d.ts +0 -7
- package/src/engine/graphics/texture/virtual/tile/finger_print_to_tile_address.d.ts.map +0 -1
- package/src/engine/graphics/texture/virtual/tile/finger_print_to_tile_address.js +0 -16
- package/src/engine/graphics/texture/virtual/tile/tile_address_to_finger_print.d.ts +0 -7
- package/src/engine/graphics/texture/virtual/tile/tile_address_to_finger_print.d.ts.map +0 -1
- package/src/engine/graphics/texture/virtual/tile/tile_address_to_finger_print.js +0 -35
|
@@ -0,0 +1,176 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* # The index of live cloth colliders
|
|
3
|
+
*
|
|
4
|
+
* A flat `Float64Array` of packed records in **world** coordinates, plus a
|
|
5
|
+
* parallel `Int32Array` of layer, mask and entity. §8.1's shape, and the same
|
|
6
|
+
* shape `AcousticOccluderIndex` + `OccluderBody` take in the sound simulation —
|
|
7
|
+
* a compact, pose-cached, broadphase-able view of a set of colliders that is
|
|
8
|
+
* deliberately **not** the physics BVH, because `ColliderObserverSystem` skips
|
|
9
|
+
* colliders with no owning body and a character's bone colliders have none.
|
|
10
|
+
*
|
|
11
|
+
* ## Why a linear scan and not a BVH
|
|
12
|
+
*
|
|
13
|
+
* `AcousticOccluderIndex` puts a BVH over its bodies and this does not, for two
|
|
14
|
+
* reasons that are both about what the query is.
|
|
15
|
+
*
|
|
16
|
+
* The query here is one AABB overlap per cloth per step against a set that is a
|
|
17
|
+
* character's bones — twenty or so, and never the whole world, because a
|
|
18
|
+
* `ClothCollider` is an opt-in marker rather than every collider in the scene.
|
|
19
|
+
* A tree over twenty leaves that all move every frame costs more to keep than
|
|
20
|
+
* to skip.
|
|
21
|
+
*
|
|
22
|
+
* And a {@link PlaneShape3D} has an **unbounded** AABB, which a BVH cannot hold
|
|
23
|
+
* — every refit would grow the root to infinity and every query would visit
|
|
24
|
+
* everything. A linear scan holds an infinity without complaint, because
|
|
25
|
+
* `min ≤ other_max` is still an answer when one side is `Infinity`. If a scene
|
|
26
|
+
* ever wants thousands of cloth colliders, the shape of the fix is a BVH over
|
|
27
|
+
* the bounded ones with the planes kept in a short list beside it.
|
|
28
|
+
*
|
|
29
|
+
* ## The previous pose is the index's, not the caller's
|
|
30
|
+
*
|
|
31
|
+
* Swept collision (§8.2) needs where each collider *was* as well as where it
|
|
32
|
+
* is. {@link advance} rolls the current pose into the previous one, and it is
|
|
33
|
+
* called once per fixed step by {@link ClothColliderSystem} before any pose is
|
|
34
|
+
* written. A collider that has just been added has both poses equal, so its
|
|
35
|
+
* first step sweeps nothing — which is right: it did not move, it appeared.
|
|
36
|
+
*
|
|
37
|
+
* @author Alex Goldring
|
|
38
|
+
* @copyright Company Named Limited (c) 2026
|
|
39
|
+
*/
|
|
40
|
+
export class ClothColliderIndex {
|
|
41
|
+
/**
|
|
42
|
+
* Packed records, `CCR_STRIDE` doubles each. `Float64` rather than the
|
|
43
|
+
* `Float32` the per-cloth table uses, because these are world coordinates
|
|
44
|
+
* and a world coordinate can be kilometres from the origin, where `Float32`
|
|
45
|
+
* has given up the millimetre a contact is measured in.
|
|
46
|
+
* @type {Float64Array}
|
|
47
|
+
*/
|
|
48
|
+
table: Float64Array;
|
|
49
|
+
/**
|
|
50
|
+
* Layer, mask and entity per record. Integers, and not folded into
|
|
51
|
+
* {@link table}, because a mask of `0xFFFFFFFF` needs 32 bits of mantissa
|
|
52
|
+
* and rounding it would silently merge the highest layers.
|
|
53
|
+
* @type {Int32Array}
|
|
54
|
+
*/
|
|
55
|
+
meta: Int32Array;
|
|
56
|
+
/**
|
|
57
|
+
* Live records. Slots below this may still be retired — see
|
|
58
|
+
* {@link #free_slots}.
|
|
59
|
+
* @type {number}
|
|
60
|
+
*/
|
|
61
|
+
count: number;
|
|
62
|
+
/**
|
|
63
|
+
* Add a collider. The shape is packed once, here; the pose is written by
|
|
64
|
+
* {@link setPose} and must be before the first query.
|
|
65
|
+
*
|
|
66
|
+
* @param {AbstractShape3D} shape in its canonical local frame
|
|
67
|
+
* @param {number} friction combined Coulomb coefficient
|
|
68
|
+
* @param {number} inflation metres
|
|
69
|
+
* @param {number} layer
|
|
70
|
+
* @param {number} mask
|
|
71
|
+
* @param {number} entity for diagnostics — the index never resolves it
|
|
72
|
+
* @returns {number} a handle, or `-1` if the shape is not one cloth collides against
|
|
73
|
+
*/
|
|
74
|
+
add(shape: AbstractShape3D, friction: number, inflation: number, layer: number, mask: number, entity: number): number;
|
|
75
|
+
/**
|
|
76
|
+
* Retire a handle. Its slot is reused by the next {@link add}, and any
|
|
77
|
+
* cloth holding warm-started contacts against it drops them on its next
|
|
78
|
+
* step because the handle it remembers no longer names the same collider.
|
|
79
|
+
*
|
|
80
|
+
* @param {number} handle
|
|
81
|
+
* @returns {void}
|
|
82
|
+
*/
|
|
83
|
+
remove(handle: number): void;
|
|
84
|
+
/**
|
|
85
|
+
* Whether a handle names a live collider.
|
|
86
|
+
* @param {number} handle
|
|
87
|
+
* @returns {boolean}
|
|
88
|
+
*/
|
|
89
|
+
isLive(handle: number): boolean;
|
|
90
|
+
/**
|
|
91
|
+
* Roll every live record's current pose into its previous one. Called once
|
|
92
|
+
* per fixed step, before any pose for this step is written.
|
|
93
|
+
* @returns {void}
|
|
94
|
+
*/
|
|
95
|
+
advance(): void;
|
|
96
|
+
/**
|
|
97
|
+
* Place a collider and refresh its swept world bounds.
|
|
98
|
+
*
|
|
99
|
+
* PRECONDITION, inherited from `OccluderBody`: the pose is rigid. A
|
|
100
|
+
* `Transform64`'s scale is ignored here exactly as the physics narrowphase
|
|
101
|
+
* ignores it, so a distance in the shape's local frame is a distance in
|
|
102
|
+
* world space.
|
|
103
|
+
*
|
|
104
|
+
* @param {number} handle
|
|
105
|
+
* @param {number} tx
|
|
106
|
+
* @param {number} ty
|
|
107
|
+
* @param {number} tz
|
|
108
|
+
* @param {number} qx
|
|
109
|
+
* @param {number} qy
|
|
110
|
+
* @param {number} qz
|
|
111
|
+
* @param {number} qw
|
|
112
|
+
* @returns {void}
|
|
113
|
+
*/
|
|
114
|
+
setPose(handle: number, tx: number, ty: number, tz: number, qx: number, qy: number, qz: number, qw: number): void;
|
|
115
|
+
/**
|
|
116
|
+
* Also set the previous pose, so the collider reads as having been placed
|
|
117
|
+
* rather than having moved. Used when a collider is first linked and when
|
|
118
|
+
* something has teleported it — a swept collision against a jump is a
|
|
119
|
+
* collider smeared across a kilometre.
|
|
120
|
+
*
|
|
121
|
+
* @param {number} handle
|
|
122
|
+
* @param {number} tx
|
|
123
|
+
* @param {number} ty
|
|
124
|
+
* @param {number} tz
|
|
125
|
+
* @param {number} qx
|
|
126
|
+
* @param {number} qy
|
|
127
|
+
* @param {number} qz
|
|
128
|
+
* @param {number} qw
|
|
129
|
+
* @returns {void}
|
|
130
|
+
*/
|
|
131
|
+
placePose(handle: number, tx: number, ty: number, tz: number, qx: number, qy: number, qz: number, qw: number): void;
|
|
132
|
+
/**
|
|
133
|
+
* Surface friction and inflation, after the fact. Both are read from
|
|
134
|
+
* components that an author can change while the scene runs.
|
|
135
|
+
*
|
|
136
|
+
* @param {number} handle
|
|
137
|
+
* @param {number} friction
|
|
138
|
+
* @param {number} inflation
|
|
139
|
+
* @returns {void}
|
|
140
|
+
*/
|
|
141
|
+
setSurface(handle: number, friction: number, inflation: number): void;
|
|
142
|
+
/**
|
|
143
|
+
* @param {number} handle
|
|
144
|
+
* @param {number} layer
|
|
145
|
+
* @param {number} mask
|
|
146
|
+
* @returns {void}
|
|
147
|
+
*/
|
|
148
|
+
setFilter(handle: number, layer: number, mask: number): void;
|
|
149
|
+
/**
|
|
150
|
+
* @param {number} handle
|
|
151
|
+
* @returns {number} the entity the collider was registered for
|
|
152
|
+
*/
|
|
153
|
+
entityOf(handle: number): number;
|
|
154
|
+
/**
|
|
155
|
+
* Every live collider whose swept bounds overlap the box and whose
|
|
156
|
+
* layer/mask agree with the caller's, written into `out` as handles.
|
|
157
|
+
*
|
|
158
|
+
* The filter is `RigidBody`'s and is symmetric: each side has to be in the
|
|
159
|
+
* other's mask, so a cloth that ignores a collider and a collider that
|
|
160
|
+
* ignores a cloth are the same statement made from two directions.
|
|
161
|
+
*
|
|
162
|
+
* @param {number[]} out grown as needed; only `[0, returned)` is valid
|
|
163
|
+
* @param {number} min_x
|
|
164
|
+
* @param {number} min_y
|
|
165
|
+
* @param {number} min_z
|
|
166
|
+
* @param {number} max_x
|
|
167
|
+
* @param {number} max_y
|
|
168
|
+
* @param {number} max_z
|
|
169
|
+
* @param {number} layer the querier's layer
|
|
170
|
+
* @param {number} mask the querier's mask
|
|
171
|
+
* @returns {number} how many handles were written
|
|
172
|
+
*/
|
|
173
|
+
query(out: number[], min_x: number, min_y: number, min_z: number, max_x: number, max_y: number, max_z: number, layer: number, mask: number): number;
|
|
174
|
+
#private;
|
|
175
|
+
}
|
|
176
|
+
//# sourceMappingURL=ClothColliderIndex.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ClothColliderIndex.d.ts","sourceRoot":"","sources":["../../../../../../src/engine/physics/cloth/collider/ClothColliderIndex.js"],"names":[],"mappings":"AAiCA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAsCG;AACH;IAEI;;;;;;OAMG;IACH,OAFU,YAAY,CAEM;IAE5B;;;;;OAKG;IACH,MAFU,UAAU,CAEK;IAEzB;;;;OAIG;IACH,OAFU,MAAM,CAEN;IAoBV;;;;;;;;;;;OAWG;IACH,sCAPW,MAAM,aACN,MAAM,SACN,MAAM,QACN,MAAM,UACN,MAAM,GACJ,MAAM,CAuClB;IAED;;;;;;;OAOG;IACH,eAHW,MAAM,GACJ,IAAI,CAqBhB;IAED;;;;OAIG;IACH,eAHW,MAAM,GACJ,OAAO,CAInB;IAED;;;;OAIG;IACH,WAFa,IAAI,CAqBhB;IAED;;;;;;;;;;;;;;;;;OAiBG;IACH,gBAVW,MAAM,MACN,MAAM,MACN,MAAM,MACN,MAAM,MACN,MAAM,MACN,MAAM,MACN,MAAM,MACN,MAAM,GACJ,IAAI,CAmBhB;IAED;;;;;;;;;;;;;;;OAeG;IACH,kBAVW,MAAM,MACN,MAAM,MACN,MAAM,MACN,MAAM,MACN,MAAM,MACN,MAAM,MACN,MAAM,MACN,MAAM,GACJ,IAAI,CAiBhB;IAED;;;;;;;;OAQG;IACH,mBALW,MAAM,YACN,MAAM,aACN,MAAM,GACJ,IAAI,CAOhB;IAED;;;;;OAKG;IACH,kBALW,MAAM,SACN,MAAM,QACN,MAAM,GACJ,IAAI,CAOhB;IAED;;;OAGG;IACH,iBAHW,MAAM,GACJ,MAAM,CAIlB;IAED;;;;;;;;;;;;;;;;;;OAkBG;IACH,WAXW,MAAM,EAAE,SACR,MAAM,SACN,MAAM,SACN,MAAM,SACN,MAAM,SACN,MAAM,SACN,MAAM,SACN,MAAM,QACN,MAAM,GACJ,MAAM,CAyClB;;CAsCJ"}
|
|
@@ -0,0 +1,435 @@
|
|
|
1
|
+
import { assert } from "../../../../core/assert.js";
|
|
2
|
+
import {
|
|
3
|
+
CCR_AABB_MAX_X,
|
|
4
|
+
CCR_AABB_MAX_Y,
|
|
5
|
+
CCR_AABB_MAX_Z,
|
|
6
|
+
CCR_AABB_MIN_X,
|
|
7
|
+
CCR_AABB_MIN_Y,
|
|
8
|
+
CCR_AABB_MIN_Z,
|
|
9
|
+
CCR_FRICTION,
|
|
10
|
+
CCR_INFLATION,
|
|
11
|
+
CCR_META_ENTITY,
|
|
12
|
+
CCR_META_LAYER,
|
|
13
|
+
CCR_META_MASK,
|
|
14
|
+
CCR_META_STRIDE,
|
|
15
|
+
CCR_PREV_QW,
|
|
16
|
+
CCR_PREV_QX,
|
|
17
|
+
CCR_PREV_QY,
|
|
18
|
+
CCR_PREV_QZ,
|
|
19
|
+
CCR_PREV_TX,
|
|
20
|
+
CCR_PREV_TY,
|
|
21
|
+
CCR_PREV_TZ,
|
|
22
|
+
CCR_QW,
|
|
23
|
+
CCR_QX,
|
|
24
|
+
CCR_QY,
|
|
25
|
+
CCR_QZ,
|
|
26
|
+
CCR_STRIDE,
|
|
27
|
+
CCR_TX,
|
|
28
|
+
CCR_TY,
|
|
29
|
+
CCR_TZ
|
|
30
|
+
} from "./ClothColliderRecord.js";
|
|
31
|
+
import { cloth_collider_refit_bounds } from "./cloth_collider_bounds.js";
|
|
32
|
+
import { cloth_collider_pack } from "./cloth_collider_pack.js";
|
|
33
|
+
|
|
34
|
+
/**
|
|
35
|
+
* # The index of live cloth colliders
|
|
36
|
+
*
|
|
37
|
+
* A flat `Float64Array` of packed records in **world** coordinates, plus a
|
|
38
|
+
* parallel `Int32Array` of layer, mask and entity. §8.1's shape, and the same
|
|
39
|
+
* shape `AcousticOccluderIndex` + `OccluderBody` take in the sound simulation —
|
|
40
|
+
* a compact, pose-cached, broadphase-able view of a set of colliders that is
|
|
41
|
+
* deliberately **not** the physics BVH, because `ColliderObserverSystem` skips
|
|
42
|
+
* colliders with no owning body and a character's bone colliders have none.
|
|
43
|
+
*
|
|
44
|
+
* ## Why a linear scan and not a BVH
|
|
45
|
+
*
|
|
46
|
+
* `AcousticOccluderIndex` puts a BVH over its bodies and this does not, for two
|
|
47
|
+
* reasons that are both about what the query is.
|
|
48
|
+
*
|
|
49
|
+
* The query here is one AABB overlap per cloth per step against a set that is a
|
|
50
|
+
* character's bones — twenty or so, and never the whole world, because a
|
|
51
|
+
* `ClothCollider` is an opt-in marker rather than every collider in the scene.
|
|
52
|
+
* A tree over twenty leaves that all move every frame costs more to keep than
|
|
53
|
+
* to skip.
|
|
54
|
+
*
|
|
55
|
+
* And a {@link PlaneShape3D} has an **unbounded** AABB, which a BVH cannot hold
|
|
56
|
+
* — every refit would grow the root to infinity and every query would visit
|
|
57
|
+
* everything. A linear scan holds an infinity without complaint, because
|
|
58
|
+
* `min ≤ other_max` is still an answer when one side is `Infinity`. If a scene
|
|
59
|
+
* ever wants thousands of cloth colliders, the shape of the fix is a BVH over
|
|
60
|
+
* the bounded ones with the planes kept in a short list beside it.
|
|
61
|
+
*
|
|
62
|
+
* ## The previous pose is the index's, not the caller's
|
|
63
|
+
*
|
|
64
|
+
* Swept collision (§8.2) needs where each collider *was* as well as where it
|
|
65
|
+
* is. {@link advance} rolls the current pose into the previous one, and it is
|
|
66
|
+
* called once per fixed step by {@link ClothColliderSystem} before any pose is
|
|
67
|
+
* written. A collider that has just been added has both poses equal, so its
|
|
68
|
+
* first step sweeps nothing — which is right: it did not move, it appeared.
|
|
69
|
+
*
|
|
70
|
+
* @author Alex Goldring
|
|
71
|
+
* @copyright Company Named Limited (c) 2026
|
|
72
|
+
*/
|
|
73
|
+
export class ClothColliderIndex {
|
|
74
|
+
|
|
75
|
+
/**
|
|
76
|
+
* Packed records, `CCR_STRIDE` doubles each. `Float64` rather than the
|
|
77
|
+
* `Float32` the per-cloth table uses, because these are world coordinates
|
|
78
|
+
* and a world coordinate can be kilometres from the origin, where `Float32`
|
|
79
|
+
* has given up the millimetre a contact is measured in.
|
|
80
|
+
* @type {Float64Array}
|
|
81
|
+
*/
|
|
82
|
+
table = new Float64Array(0);
|
|
83
|
+
|
|
84
|
+
/**
|
|
85
|
+
* Layer, mask and entity per record. Integers, and not folded into
|
|
86
|
+
* {@link table}, because a mask of `0xFFFFFFFF` needs 32 bits of mantissa
|
|
87
|
+
* and rounding it would silently merge the highest layers.
|
|
88
|
+
* @type {Int32Array}
|
|
89
|
+
*/
|
|
90
|
+
meta = new Int32Array(0);
|
|
91
|
+
|
|
92
|
+
/**
|
|
93
|
+
* Live records. Slots below this may still be retired — see
|
|
94
|
+
* {@link #free_slots}.
|
|
95
|
+
* @type {number}
|
|
96
|
+
*/
|
|
97
|
+
count = 0;
|
|
98
|
+
|
|
99
|
+
/**
|
|
100
|
+
* Retired slots, reused before the table grows. A handle is a slot index,
|
|
101
|
+
* so reuse is what keeps handles dense; it also means a handle can name a
|
|
102
|
+
* *different* collider after a removal, which is why a cloth's warm-started
|
|
103
|
+
* contacts are keyed on the handle and dropped when the collider behind it
|
|
104
|
+
* changes (`cloth_contact_find.js`).
|
|
105
|
+
* @type {number[]}
|
|
106
|
+
* @private
|
|
107
|
+
*/
|
|
108
|
+
#free_slots = [];
|
|
109
|
+
|
|
110
|
+
/**
|
|
111
|
+
* `true` for a live slot.
|
|
112
|
+
* @type {Uint8Array}
|
|
113
|
+
* @private
|
|
114
|
+
*/
|
|
115
|
+
#live = new Uint8Array(0);
|
|
116
|
+
|
|
117
|
+
/**
|
|
118
|
+
* Add a collider. The shape is packed once, here; the pose is written by
|
|
119
|
+
* {@link setPose} and must be before the first query.
|
|
120
|
+
*
|
|
121
|
+
* @param {AbstractShape3D} shape in its canonical local frame
|
|
122
|
+
* @param {number} friction combined Coulomb coefficient
|
|
123
|
+
* @param {number} inflation metres
|
|
124
|
+
* @param {number} layer
|
|
125
|
+
* @param {number} mask
|
|
126
|
+
* @param {number} entity for diagnostics — the index never resolves it
|
|
127
|
+
* @returns {number} a handle, or `-1` if the shape is not one cloth collides against
|
|
128
|
+
*/
|
|
129
|
+
add(shape, friction, inflation, layer, mask, entity) {
|
|
130
|
+
const handle = this.#free_slots.length > 0 ? this.#free_slots.pop() : this.count;
|
|
131
|
+
|
|
132
|
+
if (handle >= this.#capacity()) {
|
|
133
|
+
this.#grow(handle + 1);
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
if (!cloth_collider_pack(this.table, handle, shape, CCR_STRIDE)) {
|
|
137
|
+
this.#free_slots.push(handle);
|
|
138
|
+
|
|
139
|
+
return -1;
|
|
140
|
+
}
|
|
141
|
+
|
|
142
|
+
if (handle >= this.count) {
|
|
143
|
+
this.count = handle + 1;
|
|
144
|
+
}
|
|
145
|
+
|
|
146
|
+
const r = handle * CCR_STRIDE;
|
|
147
|
+
|
|
148
|
+
this.table[r + CCR_FRICTION] = friction;
|
|
149
|
+
this.table[r + CCR_INFLATION] = inflation;
|
|
150
|
+
|
|
151
|
+
const m = handle * CCR_META_STRIDE;
|
|
152
|
+
|
|
153
|
+
this.meta[m + CCR_META_LAYER] = layer;
|
|
154
|
+
this.meta[m + CCR_META_MASK] = mask;
|
|
155
|
+
this.meta[m + CCR_META_ENTITY] = entity;
|
|
156
|
+
|
|
157
|
+
this.#live[handle] = 1;
|
|
158
|
+
|
|
159
|
+
// No pose yet, and a record with an uninitialised rotation is a
|
|
160
|
+
// quaternion of all zeros — which normalises to nothing and poses
|
|
161
|
+
// everything at the origin. Identity until told otherwise.
|
|
162
|
+
this.table[r + CCR_QW] = 1;
|
|
163
|
+
this.table[r + CCR_PREV_QW] = 1;
|
|
164
|
+
|
|
165
|
+
return handle;
|
|
166
|
+
}
|
|
167
|
+
|
|
168
|
+
/**
|
|
169
|
+
* Retire a handle. Its slot is reused by the next {@link add}, and any
|
|
170
|
+
* cloth holding warm-started contacts against it drops them on its next
|
|
171
|
+
* step because the handle it remembers no longer names the same collider.
|
|
172
|
+
*
|
|
173
|
+
* @param {number} handle
|
|
174
|
+
* @returns {void}
|
|
175
|
+
*/
|
|
176
|
+
remove(handle) {
|
|
177
|
+
if (handle < 0 || handle >= this.count || this.#live[handle] === 0) {
|
|
178
|
+
return;
|
|
179
|
+
}
|
|
180
|
+
|
|
181
|
+
this.#live[handle] = 0;
|
|
182
|
+
this.#free_slots.push(handle);
|
|
183
|
+
|
|
184
|
+
// A retired record must not be found by a query. Its bounds are emptied
|
|
185
|
+
// rather than its slot compacted, because compacting would move every
|
|
186
|
+
// handle above it and handles are what contacts are keyed on.
|
|
187
|
+
const r = handle * CCR_STRIDE;
|
|
188
|
+
|
|
189
|
+
this.table[r + CCR_AABB_MIN_X] = Infinity;
|
|
190
|
+
this.table[r + CCR_AABB_MIN_Y] = Infinity;
|
|
191
|
+
this.table[r + CCR_AABB_MIN_Z] = Infinity;
|
|
192
|
+
this.table[r + CCR_AABB_MAX_X] = -Infinity;
|
|
193
|
+
this.table[r + CCR_AABB_MAX_Y] = -Infinity;
|
|
194
|
+
this.table[r + CCR_AABB_MAX_Z] = -Infinity;
|
|
195
|
+
}
|
|
196
|
+
|
|
197
|
+
/**
|
|
198
|
+
* Whether a handle names a live collider.
|
|
199
|
+
* @param {number} handle
|
|
200
|
+
* @returns {boolean}
|
|
201
|
+
*/
|
|
202
|
+
isLive(handle) {
|
|
203
|
+
return handle >= 0 && handle < this.count && this.#live[handle] === 1;
|
|
204
|
+
}
|
|
205
|
+
|
|
206
|
+
/**
|
|
207
|
+
* Roll every live record's current pose into its previous one. Called once
|
|
208
|
+
* per fixed step, before any pose for this step is written.
|
|
209
|
+
* @returns {void}
|
|
210
|
+
*/
|
|
211
|
+
advance() {
|
|
212
|
+
const table = this.table;
|
|
213
|
+
|
|
214
|
+
for (let handle = 0; handle < this.count; handle++) {
|
|
215
|
+
if (this.#live[handle] === 0) {
|
|
216
|
+
continue;
|
|
217
|
+
}
|
|
218
|
+
|
|
219
|
+
const r = handle * CCR_STRIDE;
|
|
220
|
+
|
|
221
|
+
table[r + CCR_PREV_TX] = table[r + CCR_TX];
|
|
222
|
+
table[r + CCR_PREV_TY] = table[r + CCR_TY];
|
|
223
|
+
table[r + CCR_PREV_TZ] = table[r + CCR_TZ];
|
|
224
|
+
|
|
225
|
+
table[r + CCR_PREV_QX] = table[r + CCR_QX];
|
|
226
|
+
table[r + CCR_PREV_QY] = table[r + CCR_QY];
|
|
227
|
+
table[r + CCR_PREV_QZ] = table[r + CCR_QZ];
|
|
228
|
+
table[r + CCR_PREV_QW] = table[r + CCR_QW];
|
|
229
|
+
}
|
|
230
|
+
}
|
|
231
|
+
|
|
232
|
+
/**
|
|
233
|
+
* Place a collider and refresh its swept world bounds.
|
|
234
|
+
*
|
|
235
|
+
* PRECONDITION, inherited from `OccluderBody`: the pose is rigid. A
|
|
236
|
+
* `Transform64`'s scale is ignored here exactly as the physics narrowphase
|
|
237
|
+
* ignores it, so a distance in the shape's local frame is a distance in
|
|
238
|
+
* world space.
|
|
239
|
+
*
|
|
240
|
+
* @param {number} handle
|
|
241
|
+
* @param {number} tx
|
|
242
|
+
* @param {number} ty
|
|
243
|
+
* @param {number} tz
|
|
244
|
+
* @param {number} qx
|
|
245
|
+
* @param {number} qy
|
|
246
|
+
* @param {number} qz
|
|
247
|
+
* @param {number} qw
|
|
248
|
+
* @returns {void}
|
|
249
|
+
*/
|
|
250
|
+
setPose(handle, tx, ty, tz, qx, qy, qz, qw) {
|
|
251
|
+
assert.ok(this.isLive(handle), `cloth collider handle ${handle} is not live`);
|
|
252
|
+
|
|
253
|
+
const table = this.table;
|
|
254
|
+
|
|
255
|
+
const r = handle * CCR_STRIDE;
|
|
256
|
+
|
|
257
|
+
table[r + CCR_TX] = tx;
|
|
258
|
+
table[r + CCR_TY] = ty;
|
|
259
|
+
table[r + CCR_TZ] = tz;
|
|
260
|
+
|
|
261
|
+
table[r + CCR_QX] = qx;
|
|
262
|
+
table[r + CCR_QY] = qy;
|
|
263
|
+
table[r + CCR_QZ] = qz;
|
|
264
|
+
table[r + CCR_QW] = qw;
|
|
265
|
+
|
|
266
|
+
cloth_collider_refit_bounds(this.table, handle, CCR_STRIDE);
|
|
267
|
+
}
|
|
268
|
+
|
|
269
|
+
/**
|
|
270
|
+
* Also set the previous pose, so the collider reads as having been placed
|
|
271
|
+
* rather than having moved. Used when a collider is first linked and when
|
|
272
|
+
* something has teleported it — a swept collision against a jump is a
|
|
273
|
+
* collider smeared across a kilometre.
|
|
274
|
+
*
|
|
275
|
+
* @param {number} handle
|
|
276
|
+
* @param {number} tx
|
|
277
|
+
* @param {number} ty
|
|
278
|
+
* @param {number} tz
|
|
279
|
+
* @param {number} qx
|
|
280
|
+
* @param {number} qy
|
|
281
|
+
* @param {number} qz
|
|
282
|
+
* @param {number} qw
|
|
283
|
+
* @returns {void}
|
|
284
|
+
*/
|
|
285
|
+
placePose(handle, tx, ty, tz, qx, qy, qz, qw) {
|
|
286
|
+
assert.ok(this.isLive(handle), `cloth collider handle ${handle} is not live`);
|
|
287
|
+
|
|
288
|
+
const r = handle * CCR_STRIDE;
|
|
289
|
+
|
|
290
|
+
this.table[r + CCR_PREV_TX] = tx;
|
|
291
|
+
this.table[r + CCR_PREV_TY] = ty;
|
|
292
|
+
this.table[r + CCR_PREV_TZ] = tz;
|
|
293
|
+
|
|
294
|
+
this.table[r + CCR_PREV_QX] = qx;
|
|
295
|
+
this.table[r + CCR_PREV_QY] = qy;
|
|
296
|
+
this.table[r + CCR_PREV_QZ] = qz;
|
|
297
|
+
this.table[r + CCR_PREV_QW] = qw;
|
|
298
|
+
|
|
299
|
+
this.setPose(handle, tx, ty, tz, qx, qy, qz, qw);
|
|
300
|
+
}
|
|
301
|
+
|
|
302
|
+
/**
|
|
303
|
+
* Surface friction and inflation, after the fact. Both are read from
|
|
304
|
+
* components that an author can change while the scene runs.
|
|
305
|
+
*
|
|
306
|
+
* @param {number} handle
|
|
307
|
+
* @param {number} friction
|
|
308
|
+
* @param {number} inflation
|
|
309
|
+
* @returns {void}
|
|
310
|
+
*/
|
|
311
|
+
setSurface(handle, friction, inflation) {
|
|
312
|
+
const r = handle * CCR_STRIDE;
|
|
313
|
+
|
|
314
|
+
this.table[r + CCR_FRICTION] = friction;
|
|
315
|
+
this.table[r + CCR_INFLATION] = inflation;
|
|
316
|
+
}
|
|
317
|
+
|
|
318
|
+
/**
|
|
319
|
+
* @param {number} handle
|
|
320
|
+
* @param {number} layer
|
|
321
|
+
* @param {number} mask
|
|
322
|
+
* @returns {void}
|
|
323
|
+
*/
|
|
324
|
+
setFilter(handle, layer, mask) {
|
|
325
|
+
const m = handle * CCR_META_STRIDE;
|
|
326
|
+
|
|
327
|
+
this.meta[m + CCR_META_LAYER] = layer;
|
|
328
|
+
this.meta[m + CCR_META_MASK] = mask;
|
|
329
|
+
}
|
|
330
|
+
|
|
331
|
+
/**
|
|
332
|
+
* @param {number} handle
|
|
333
|
+
* @returns {number} the entity the collider was registered for
|
|
334
|
+
*/
|
|
335
|
+
entityOf(handle) {
|
|
336
|
+
return this.meta[handle * CCR_META_STRIDE + CCR_META_ENTITY];
|
|
337
|
+
}
|
|
338
|
+
|
|
339
|
+
/**
|
|
340
|
+
* Every live collider whose swept bounds overlap the box and whose
|
|
341
|
+
* layer/mask agree with the caller's, written into `out` as handles.
|
|
342
|
+
*
|
|
343
|
+
* The filter is `RigidBody`'s and is symmetric: each side has to be in the
|
|
344
|
+
* other's mask, so a cloth that ignores a collider and a collider that
|
|
345
|
+
* ignores a cloth are the same statement made from two directions.
|
|
346
|
+
*
|
|
347
|
+
* @param {number[]} out grown as needed; only `[0, returned)` is valid
|
|
348
|
+
* @param {number} min_x
|
|
349
|
+
* @param {number} min_y
|
|
350
|
+
* @param {number} min_z
|
|
351
|
+
* @param {number} max_x
|
|
352
|
+
* @param {number} max_y
|
|
353
|
+
* @param {number} max_z
|
|
354
|
+
* @param {number} layer the querier's layer
|
|
355
|
+
* @param {number} mask the querier's mask
|
|
356
|
+
* @returns {number} how many handles were written
|
|
357
|
+
*/
|
|
358
|
+
query(out, min_x, min_y, min_z, max_x, max_y, max_z, layer, mask) {
|
|
359
|
+
const table = this.table;
|
|
360
|
+
const meta = this.meta;
|
|
361
|
+
|
|
362
|
+
let found = 0;
|
|
363
|
+
|
|
364
|
+
for (let handle = 0; handle < this.count; handle++) {
|
|
365
|
+
if (this.#live[handle] === 0) {
|
|
366
|
+
continue;
|
|
367
|
+
}
|
|
368
|
+
|
|
369
|
+
const m = handle * CCR_META_STRIDE;
|
|
370
|
+
|
|
371
|
+
if ((mask & meta[m + CCR_META_LAYER]) === 0) {
|
|
372
|
+
continue;
|
|
373
|
+
}
|
|
374
|
+
|
|
375
|
+
if ((meta[m + CCR_META_MASK] & layer) === 0) {
|
|
376
|
+
continue;
|
|
377
|
+
}
|
|
378
|
+
|
|
379
|
+
const r = handle * CCR_STRIDE;
|
|
380
|
+
|
|
381
|
+
if (table[r + CCR_AABB_MIN_X] > max_x || table[r + CCR_AABB_MAX_X] < min_x) {
|
|
382
|
+
continue;
|
|
383
|
+
}
|
|
384
|
+
|
|
385
|
+
if (table[r + CCR_AABB_MIN_Y] > max_y || table[r + CCR_AABB_MAX_Y] < min_y) {
|
|
386
|
+
continue;
|
|
387
|
+
}
|
|
388
|
+
|
|
389
|
+
if (table[r + CCR_AABB_MIN_Z] > max_z || table[r + CCR_AABB_MAX_Z] < min_z) {
|
|
390
|
+
continue;
|
|
391
|
+
}
|
|
392
|
+
|
|
393
|
+
out[found++] = handle;
|
|
394
|
+
}
|
|
395
|
+
|
|
396
|
+
return found;
|
|
397
|
+
}
|
|
398
|
+
|
|
399
|
+
/**
|
|
400
|
+
* @returns {number}
|
|
401
|
+
* @private
|
|
402
|
+
*/
|
|
403
|
+
#capacity() {
|
|
404
|
+
return this.#live.length;
|
|
405
|
+
}
|
|
406
|
+
|
|
407
|
+
/**
|
|
408
|
+
* @param {number} required
|
|
409
|
+
* @private
|
|
410
|
+
*/
|
|
411
|
+
#grow(required) {
|
|
412
|
+
let capacity = this.#capacity();
|
|
413
|
+
|
|
414
|
+
if (capacity === 0) {
|
|
415
|
+
capacity = 8;
|
|
416
|
+
}
|
|
417
|
+
|
|
418
|
+
while (capacity < required) {
|
|
419
|
+
capacity *= 2;
|
|
420
|
+
}
|
|
421
|
+
|
|
422
|
+
const table = new Float64Array(capacity * CCR_STRIDE);
|
|
423
|
+
const meta = new Int32Array(capacity * CCR_META_STRIDE);
|
|
424
|
+
const live = new Uint8Array(capacity);
|
|
425
|
+
|
|
426
|
+
table.set(this.table);
|
|
427
|
+
meta.set(this.meta);
|
|
428
|
+
live.set(this.#live);
|
|
429
|
+
|
|
430
|
+
this.table = table;
|
|
431
|
+
this.meta = meta;
|
|
432
|
+
this.#live = live;
|
|
433
|
+
}
|
|
434
|
+
|
|
435
|
+
}
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* *
|
|
3
|
+
*/
|
|
4
|
+
export type ClothColliderKind = number;
|
|
5
|
+
export namespace ClothColliderKind {
|
|
6
|
+
let Sphere: number;
|
|
7
|
+
let Capsule: number;
|
|
8
|
+
let Box: number;
|
|
9
|
+
let Cylinder: number;
|
|
10
|
+
let Plane: number;
|
|
11
|
+
}
|
|
12
|
+
//# sourceMappingURL=ClothColliderKind.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ClothColliderKind.d.ts","sourceRoot":"","sources":["../../../../../../src/engine/physics/cloth/collider/ClothColliderKind.js"],"names":[],"mappings":";;;gCAeU,MAAM"}
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The shapes cloth collides against.
|
|
3
|
+
*
|
|
4
|
+
* §8.2: analytic primitives only, which is universal in shipping cloth systems
|
|
5
|
+
* — MagicaCloth2 offers sphere, capsule and plane; Chaos Cloth adds tapered
|
|
6
|
+
* capsules and convex hulls — and is what makes the inner loop a handful of
|
|
7
|
+
* arithmetic instead of a BVH descent. A `Collider` carrying a mesh or a
|
|
8
|
+
* heightmap is skipped with one warning naming the entity, and the documented
|
|
9
|
+
* answer is to add primitive `ClothCollider` children, which is what an author
|
|
10
|
+
* would do for a character anyway.
|
|
11
|
+
*
|
|
12
|
+
* The values are indices into a dispatch, so they are contiguous from zero and
|
|
13
|
+
* their order is the order `cloth_collider_sdf.js` branches in.
|
|
14
|
+
*
|
|
15
|
+
* @readonly
|
|
16
|
+
* @enum {number}
|
|
17
|
+
*
|
|
18
|
+
* @author Alex Goldring
|
|
19
|
+
* @copyright Company Named Limited (c) 2026
|
|
20
|
+
*/
|
|
21
|
+
export const ClothColliderKind = {
|
|
22
|
+
/** Radius in `CCR_PARAM_0`. */
|
|
23
|
+
Sphere: 0,
|
|
24
|
+
|
|
25
|
+
/** Radius in `CCR_PARAM_0`, segment length in `CCR_PARAM_1`, about local Y. */
|
|
26
|
+
Capsule: 1,
|
|
27
|
+
|
|
28
|
+
/** Half-extents in `CCR_PARAM_0..2`. */
|
|
29
|
+
Box: 2,
|
|
30
|
+
|
|
31
|
+
/** Radius in `CCR_PARAM_0`, height in `CCR_PARAM_1`, about local Y. */
|
|
32
|
+
Cylinder: 3,
|
|
33
|
+
|
|
34
|
+
/** Outward unit normal in `CCR_PARAM_0..2`, offset in `CCR_PARAM_3`. */
|
|
35
|
+
Plane: 4
|
|
36
|
+
};
|
|
37
|
+
|
|
38
|
+
Object.freeze(ClothColliderKind);
|