@woosh/meep-engine 3.43.0 → 3.45.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/build/bundle-worker-terrain.js +1 -1
- package/editor/prototypeEditorShell.d.ts.map +1 -1
- package/editor/prototypeEditorShell.js +4 -2
- package/package.json +1 -1
- package/src/core/collection/array/array_sort_insertion_ascending.d.ts +19 -0
- package/src/core/collection/array/array_sort_insertion_ascending.d.ts.map +1 -0
- package/src/core/collection/array/array_sort_insertion_ascending.js +31 -0
- package/src/core/geom/3d/aabb/aabb3_array_round_outward_f32.d.ts +27 -0
- package/src/core/geom/3d/aabb/aabb3_array_round_outward_f32.d.ts.map +1 -0
- package/src/core/geom/3d/aabb/aabb3_array_round_outward_f32.js +39 -0
- package/src/core/geom/3d/aabb/aabb3_from_v3_array.d.ts.map +1 -1
- package/src/core/geom/3d/aabb/aabb3_from_v3_array.js +4 -1
- package/src/core/geom/3d/aabb/aabb3_transform_oriented.d.ts +2 -2
- package/src/core/geom/3d/aabb/aabb3_transform_oriented.d.ts.map +1 -1
- package/src/core/geom/3d/aabb/aabb3_transform_oriented.js +1 -1
- package/src/core/geom/3d/pose/pose3_apply_inverse_point_array.d.ts +21 -0
- package/src/core/geom/3d/pose/pose3_apply_inverse_point_array.d.ts.map +1 -0
- package/src/core/geom/3d/pose/pose3_apply_inverse_point_array.js +36 -0
- package/src/core/geom/3d/pose/pose3_apply_point_array.d.ts +25 -0
- package/src/core/geom/3d/pose/pose3_apply_point_array.d.ts.map +1 -0
- package/src/core/geom/3d/pose/pose3_apply_point_array.js +40 -0
- package/src/core/geom/3d/pose/pose3_compose_array.d.ts +28 -0
- package/src/core/geom/3d/pose/pose3_compose_array.d.ts.map +1 -0
- package/src/core/geom/3d/pose/pose3_compose_array.js +41 -0
- package/src/core/geom/3d/pose/pose3_to_local_array.d.ts +29 -0
- package/src/core/geom/3d/pose/pose3_to_local_array.d.ts.map +1 -0
- package/src/core/geom/3d/pose/pose3_to_local_array.js +42 -0
- package/src/core/geom/3d/quaternion/quat3_clamp_angle_array.d.ts +28 -0
- package/src/core/geom/3d/quaternion/quat3_clamp_angle_array.d.ts.map +1 -0
- package/src/core/geom/3d/quaternion/quat3_clamp_angle_array.js +66 -0
- package/src/core/geom/3d/quaternion/quat3_multiply_conjugate_left_array.d.ts +22 -0
- package/src/core/geom/3d/quaternion/quat3_multiply_conjugate_left_array.d.ts.map +1 -0
- package/src/core/geom/3d/quaternion/quat3_multiply_conjugate_left_array.js +30 -0
- package/src/core/geom/3d/quaternion/quat3_multiply_conjugate_right_array.d.ts +23 -0
- package/src/core/geom/3d/quaternion/quat3_multiply_conjugate_right_array.d.ts.map +1 -0
- package/src/core/geom/3d/quaternion/quat3_multiply_conjugate_right_array.js +31 -0
- package/src/core/geom/3d/triangle/tri3_compute_normal_area_weighted_array.d.ts +26 -0
- package/src/core/geom/3d/triangle/tri3_compute_normal_area_weighted_array.d.ts.map +1 -0
- package/src/core/geom/3d/triangle/tri3_compute_normal_area_weighted_array.js +46 -0
- package/src/core/geom/vec3/v3_distance_array.d.ts +11 -0
- package/src/core/geom/vec3/v3_distance_array.d.ts.map +1 -0
- package/src/core/geom/vec3/v3_distance_array.js +19 -0
- package/src/core/geom/vec3/v3_normalize_array_checked.d.ts +23 -0
- package/src/core/geom/vec3/v3_normalize_array_checked.d.ts.map +1 -0
- package/src/core/geom/vec3/v3_normalize_array_checked.js +49 -0
- package/src/core/geom/vec3/v3_reject_array.d.ts +15 -0
- package/src/core/geom/vec3/v3_reject_array.d.ts.map +1 -0
- package/src/core/geom/vec3/v3_reject_array.js +32 -0
- package/src/core/graph/csr/csr_build_incidence.d.ts +26 -0
- package/src/core/graph/csr/csr_build_incidence.d.ts.map +1 -0
- package/src/core/graph/csr/csr_build_incidence.js +71 -0
- package/src/core/graph/csr/csr_graph_color_greedy.d.ts +25 -0
- package/src/core/graph/csr/csr_graph_color_greedy.d.ts.map +1 -0
- package/src/core/graph/csr/csr_graph_color_greedy.js +83 -0
- package/src/core/graph/csr/csr_graph_validate_coloring.d.ts +15 -0
- package/src/core/graph/csr/csr_graph_validate_coloring.d.ts.map +1 -0
- package/src/core/graph/csr/csr_graph_validate_coloring.js +33 -0
- package/src/core/math/linalg/matrix_symmetric_3x3_solve_ldlt.d.ts +26 -0
- package/src/core/math/linalg/matrix_symmetric_3x3_solve_ldlt.d.ts.map +1 -0
- package/src/core/math/linalg/matrix_symmetric_3x3_solve_ldlt.js +71 -0
- package/src/core/math/max2_exact.d.ts +15 -0
- package/src/core/math/max2_exact.d.ts.map +1 -0
- package/src/core/math/max2_exact.js +30 -0
- package/src/core/math/min2_exact.d.ts +20 -0
- package/src/core/math/min2_exact.d.ts.map +1 -0
- package/src/core/math/min2_exact.js +35 -0
- package/src/engine/Clock.d.ts +15 -0
- package/src/engine/Clock.d.ts.map +1 -1
- package/src/engine/Clock.js +29 -5
- package/src/engine/Engine.d.ts.map +1 -1
- package/src/engine/Engine.js +11 -19
- package/src/engine/ecs/ik/IKGoalSystem.d.ts.map +1 -1
- package/src/engine/ecs/ik/IKGoalSystem.js +3 -19
- package/src/engine/ecs/parent/parent_entity_model_of.d.ts +17 -0
- package/src/engine/ecs/parent/parent_entity_model_of.d.ts.map +1 -0
- package/src/engine/ecs/parent/parent_entity_model_of.js +26 -0
- package/src/engine/ecs/transform/t64_read_pose_array.d.ts +15 -0
- package/src/engine/ecs/transform/t64_read_pose_array.d.ts.map +1 -0
- package/src/engine/ecs/transform/t64_read_pose_array.js +24 -0
- package/src/engine/graphics/ecs/mesh-v2/MeshSkin.d.ts +57 -0
- package/src/engine/graphics/ecs/mesh-v2/MeshSkin.d.ts.map +1 -0
- package/src/engine/graphics/ecs/mesh-v2/MeshSkin.js +84 -0
- package/src/engine/graphics/geometry/geometry_construct_triangle_normal_area_weighted.d.ts +2 -0
- package/src/engine/graphics/geometry/geometry_construct_triangle_normal_area_weighted.d.ts.map +1 -1
- package/src/engine/graphics/geometry/geometry_construct_triangle_normal_area_weighted.js +10 -21
- package/src/engine/graphics3/AnimationGraphSystem.d.ts +28 -13
- package/src/engine/graphics3/AnimationGraphSystem.d.ts.map +1 -1
- package/src/engine/graphics3/AnimationGraphSystem.js +107 -64
- package/src/engine/graphics3/AnimationSystem.d.ts +29 -15
- package/src/engine/graphics3/AnimationSystem.d.ts.map +1 -1
- package/src/engine/graphics3/AnimationSystem.js +112 -61
- package/src/engine/graphics3/MeshSkinSystem.d.ts +56 -0
- package/src/engine/graphics3/MeshSkinSystem.d.ts.map +1 -0
- package/src/engine/graphics3/MeshSkinSystem.js +317 -0
- package/src/engine/graphics3/MeshSystem.d.ts +15 -35
- package/src/engine/graphics3/MeshSystem.d.ts.map +1 -1
- package/src/engine/graphics3/MeshSystem.js +21 -298
- package/src/engine/graphics3/RowChains.d.ts +76 -0
- package/src/engine/graphics3/RowChains.d.ts.map +1 -0
- package/src/engine/graphics3/RowChains.js +347 -0
- package/src/engine/graphics3/ShadedGeometrySystem.d.ts +6 -0
- package/src/engine/graphics3/ShadedGeometrySystem.d.ts.map +1 -1
- package/src/engine/graphics3/ShadedGeometrySystem.js +329 -309
- package/src/engine/graphics3/animation/AnimationClips.d.ts +56 -0
- package/src/engine/graphics3/animation/AnimationClips.d.ts.map +1 -0
- package/src/engine/graphics3/animation/AnimationClips.js +79 -0
- package/src/engine/graphics3/animation/ClipListPlayer.d.ts +13 -14
- package/src/engine/graphics3/animation/ClipListPlayer.d.ts.map +1 -1
- package/src/engine/graphics3/animation/ClipListPlayer.js +262 -263
- package/src/engine/graphics3/animation/write_clip_playback.d.ts +3 -3
- package/src/engine/graphics3/animation/write_clip_playback.js +4 -4
- package/src/engine/graphics3/pose/query_entity_node_world_pose.d.ts +5 -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 +80 -75
- package/src/engine/graphics3/prefab/PrefabInstance.d.ts +4 -24
- package/src/engine/graphics3/prefab/PrefabInstance.d.ts.map +1 -1
- package/src/engine/graphics3/prefab/PrefabInstance.js +60 -80
- package/src/engine/graphics3/prefab/prefab_instantiate.d.ts +16 -3
- package/src/engine/graphics3/prefab/prefab_instantiate.d.ts.map +1 -1
- package/src/engine/graphics3/prefab/prefab_instantiate.js +49 -12
- package/src/engine/graphics3/prefab/prefab_place.d.ts +31 -17
- package/src/engine/graphics3/prefab/prefab_place.d.ts.map +1 -1
- package/src/engine/graphics3/prefab/prefab_place.js +175 -130
- package/src/engine/graphics3/register_clips.d.ts +93 -0
- package/src/engine/graphics3/register_clips.d.ts.map +1 -0
- package/src/engine/graphics3/register_clips.js +166 -0
- package/src/engine/physics/broadphase/compute_fat_world_aabb.d.ts +9 -0
- package/src/engine/physics/broadphase/compute_fat_world_aabb.d.ts.map +1 -1
- package/src/engine/physics/broadphase/compute_fat_world_aabb.js +3 -1
- package/src/engine/physics/cloth/MEASUREMENTS.md +795 -0
- package/src/engine/physics/cloth/PLAN.md +349 -17
- package/src/engine/physics/cloth/build/ClothProxy.d.ts +113 -61
- package/src/engine/physics/cloth/build/ClothProxy.d.ts.map +1 -1
- package/src/engine/physics/cloth/build/ClothProxy.js +142 -77
- package/src/engine/physics/cloth/build/cloth_bind_in_frame.d.ts +44 -0
- package/src/engine/physics/cloth/build/cloth_bind_in_frame.d.ts.map +1 -0
- package/src/engine/physics/cloth/build/cloth_bind_in_frame.js +107 -0
- package/src/engine/physics/cloth/build/cloth_proxy_from_joints.d.ts +43 -30
- package/src/engine/physics/cloth/build/cloth_proxy_from_joints.d.ts.map +1 -1
- package/src/engine/physics/cloth/build/cloth_proxy_from_joints.js +371 -284
- package/src/engine/physics/cloth/build/cloth_proxy_from_mesh.d.ts +62 -0
- package/src/engine/physics/cloth/build/cloth_proxy_from_mesh.d.ts.map +1 -0
- package/src/engine/physics/cloth/build/cloth_proxy_from_mesh.js +275 -0
- package/src/engine/physics/cloth/collider/ClothColliderIndex.d.ts +7 -0
- package/src/engine/physics/cloth/collider/ClothColliderIndex.d.ts.map +1 -1
- package/src/engine/physics/cloth/collider/ClothColliderIndex.js +85 -67
- package/src/engine/physics/cloth/collider/cloth_collider_bounds.d.ts.map +1 -1
- package/src/engine/physics/cloth/collider/cloth_collider_bounds.js +19 -101
- package/src/engine/physics/cloth/collider/cloth_collider_pack.d.ts +2 -5
- package/src/engine/physics/cloth/collider/cloth_collider_pack.d.ts.map +1 -1
- package/src/engine/physics/cloth/collider/cloth_collider_pack.js +7 -15
- package/src/engine/physics/cloth/collider/cloth_collider_sdf.d.ts +1 -1
- package/src/engine/physics/cloth/collider/cloth_collider_sdf.d.ts.map +1 -1
- package/src/engine/physics/cloth/collider/cloth_collider_sdf.js +17 -62
- package/src/engine/physics/cloth/ecs/Cloth.d.ts +17 -9
- package/src/engine/physics/cloth/ecs/Cloth.d.ts.map +1 -1
- package/src/engine/physics/cloth/ecs/Cloth.js +220 -212
- package/src/engine/physics/cloth/ecs/ClothColliderFlags.d.ts +0 -1
- package/src/engine/physics/cloth/ecs/ClothColliderFlags.js +6 -19
- package/src/engine/physics/cloth/ecs/ClothColliderSystem.d.ts +1 -2
- package/src/engine/physics/cloth/ecs/ClothColliderSystem.d.ts.map +1 -1
- package/src/engine/physics/cloth/ecs/ClothColliderSystem.js +3 -12
- package/src/engine/physics/cloth/ecs/ClothDynamicsFlags.js +6 -0
- package/src/engine/physics/cloth/ecs/ClothHold.d.ts +91 -0
- package/src/engine/physics/cloth/ecs/ClothHold.d.ts.map +1 -0
- package/src/engine/physics/cloth/ecs/ClothHold.js +103 -0
- package/src/engine/physics/cloth/ecs/ClothInstance.d.ts +254 -48
- package/src/engine/physics/cloth/ecs/ClothInstance.d.ts.map +1 -1
- package/src/engine/physics/cloth/ecs/ClothInstance.js +277 -47
- package/src/engine/physics/cloth/ecs/ClothPin.d.ts +73 -0
- package/src/engine/physics/cloth/ecs/ClothPin.d.ts.map +1 -0
- package/src/engine/physics/cloth/ecs/ClothPin.js +92 -0
- package/src/engine/physics/cloth/ecs/ClothPinSerializationAdapter.d.ts +36 -0
- package/src/engine/physics/cloth/ecs/ClothPinSerializationAdapter.d.ts.map +1 -0
- package/src/engine/physics/cloth/ecs/ClothPinSerializationAdapter.js +61 -0
- package/src/engine/physics/cloth/ecs/ClothRig.d.ts +23 -17
- package/src/engine/physics/cloth/ecs/ClothRig.d.ts.map +1 -1
- package/src/engine/physics/cloth/ecs/ClothRig.js +29 -27
- package/src/engine/physics/cloth/ecs/ClothSystem.d.ts +12 -14
- package/src/engine/physics/cloth/ecs/ClothSystem.d.ts.map +1 -1
- package/src/engine/physics/cloth/ecs/ClothSystem.js +20 -15
- package/src/engine/physics/cloth/ecs/ClothWorld.d.ts +57 -36
- package/src/engine/physics/cloth/ecs/ClothWorld.d.ts.map +1 -1
- package/src/engine/physics/cloth/ecs/ClothWorld.js +754 -207
- package/src/engine/physics/cloth/ecs/WorkerClothSystem.d.ts +12 -13
- package/src/engine/physics/cloth/ecs/WorkerClothSystem.d.ts.map +1 -1
- package/src/engine/physics/cloth/ecs/WorkerClothSystem.js +20 -14
- package/src/engine/physics/cloth/ecs/cloth_build_rows.d.ts +63 -11
- package/src/engine/physics/cloth/ecs/cloth_build_rows.d.ts.map +1 -1
- package/src/engine/physics/cloth/ecs/cloth_build_rows.js +297 -101
- package/src/engine/physics/cloth/ecs/cloth_dynamics_map.d.ts +9 -7
- package/src/engine/physics/cloth/ecs/cloth_dynamics_map.d.ts.map +1 -1
- package/src/engine/physics/cloth/ecs/cloth_dynamics_map.js +12 -10
- package/src/engine/physics/cloth/ecs/cloth_gather_colliders.d.ts +3 -3
- package/src/engine/physics/cloth/ecs/cloth_gather_colliders.d.ts.map +1 -1
- package/src/engine/physics/cloth/ecs/cloth_gather_colliders.js +60 -120
- package/src/engine/physics/cloth/ecs/cloth_geodesic.d.ts +37 -0
- package/src/engine/physics/cloth/ecs/cloth_geodesic.d.ts.map +1 -0
- package/src/engine/physics/cloth/ecs/cloth_geodesic.js +135 -0
- package/src/engine/physics/cloth/ecs/cloth_holds.d.ts +97 -0
- package/src/engine/physics/cloth/ecs/cloth_holds.d.ts.map +1 -0
- package/src/engine/physics/cloth/ecs/cloth_holds.js +583 -0
- package/src/engine/physics/cloth/ecs/cloth_reconstruct_pose.d.ts +2 -2
- package/src/engine/physics/cloth/ecs/cloth_reconstruct_pose.d.ts.map +1 -1
- package/src/engine/physics/cloth/ecs/cloth_reconstruct_pose.js +168 -51
- package/src/engine/physics/cloth/ecs/cloth_seed_rig.d.ts +17 -22
- package/src/engine/physics/cloth/ecs/cloth_seed_rig.d.ts.map +1 -1
- package/src/engine/physics/cloth/ecs/cloth_seed_rig.js +55 -117
- package/src/engine/physics/cloth/ecs/cloth_seed_subtree.d.ts +21 -6
- package/src/engine/physics/cloth/ecs/cloth_seed_subtree.d.ts.map +1 -1
- package/src/engine/physics/cloth/ecs/cloth_seed_subtree.js +51 -42
- package/src/engine/physics/cloth/ecs/cloth_write_back.d.ts +5 -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 +62 -50
- package/src/engine/physics/cloth/ecs/cloth_write_back_rig.d.ts.map +1 -1
- package/src/engine/physics/cloth/ecs/cloth_write_back_rig.js +65 -58
- package/src/engine/physics/cloth/playground/cloth_playground_build.d.ts.map +1 -1
- package/src/engine/physics/cloth/playground/cloth_playground_build.js +2 -3
- package/src/engine/physics/cloth/playground/collide_main.js +3 -29
- package/src/engine/physics/cloth/playground/garment_build.d.ts.map +1 -1
- package/src/engine/physics/cloth/playground/garment_build.js +17 -5
- package/src/engine/physics/cloth/playground/garment_main.js +5 -20
- package/src/engine/physics/cloth/playground/main.js +6 -48
- package/src/engine/physics/cloth/playground/rig_build.d.ts.map +1 -1
- package/src/engine/physics/cloth/playground/rig_build.js +302 -296
- package/src/engine/physics/cloth/playground/rig_main.js +947 -955
- package/src/engine/physics/cloth/playground/wind_main.js +8 -7
- package/src/engine/physics/cloth/solver/ClothState.d.ts +45 -7
- package/src/engine/physics/cloth/solver/ClothState.d.ts.map +1 -1
- package/src/engine/physics/cloth/solver/ClothState.js +79 -83
- package/src/engine/physics/cloth/solver/cloth_color_particles.d.ts +10 -8
- package/src/engine/physics/cloth/solver/cloth_color_particles.d.ts.map +1 -1
- package/src/engine/physics/cloth/solver/cloth_color_particles.js +30 -102
- package/src/engine/physics/cloth/solver/cloth_contact_find.d.ts +6 -1
- package/src/engine/physics/cloth/solver/cloth_contact_find.d.ts.map +1 -1
- package/src/engine/physics/cloth/solver/cloth_contact_find.js +9 -3
- package/src/engine/physics/cloth/solver/cloth_hold_line.d.ts +114 -0
- package/src/engine/physics/cloth/solver/cloth_hold_line.d.ts.map +1 -0
- package/src/engine/physics/cloth/solver/cloth_hold_line.js +350 -0
- package/src/engine/physics/cloth/solver/cloth_kinetic_energy.d.ts +21 -0
- package/src/engine/physics/cloth/solver/cloth_kinetic_energy.d.ts.map +1 -0
- package/src/engine/physics/cloth/solver/cloth_kinetic_energy.js +45 -0
- package/src/engine/physics/cloth/solver/cloth_particle_coupling.d.ts +32 -0
- package/src/engine/physics/cloth/solver/cloth_particle_coupling.d.ts.map +1 -0
- package/src/engine/physics/cloth/solver/cloth_particle_coupling.js +133 -0
- package/src/engine/physics/cloth/solver/cloth_particle_of_source.d.ts +16 -0
- package/src/engine/physics/cloth/solver/cloth_particle_of_source.d.ts.map +1 -0
- package/src/engine/physics/cloth/solver/cloth_particle_of_source.js +19 -0
- package/src/engine/physics/cloth/solver/cloth_self_find.d.ts +6 -2
- package/src/engine/physics/cloth/solver/cloth_self_find.d.ts.map +1 -1
- package/src/engine/physics/cloth/solver/cloth_self_find.js +19 -68
- package/src/engine/physics/cloth/solver/cloth_solve_vertex.d.ts.map +1 -1
- package/src/engine/physics/cloth/solver/cloth_solve_vertex.js +30 -65
- package/src/engine/physics/cloth/solver/cloth_solver_constants.d.ts +24 -12
- package/src/engine/physics/cloth/solver/cloth_solver_constants.d.ts.map +1 -1
- package/src/engine/physics/cloth/solver/cloth_solver_constants.js +24 -12
- package/src/engine/physics/cloth/solver/cloth_step.d.ts +16 -0
- package/src/engine/physics/cloth/solver/cloth_step.d.ts.map +1 -1
- package/src/engine/physics/cloth/solver/cloth_step.js +189 -48
- package/src/engine/physics/cloth/solver/cloth_step_instance.d.ts +1 -0
- package/src/engine/physics/cloth/solver/cloth_step_instance.d.ts.map +1 -1
- package/src/engine/physics/cloth/solver/cloth_step_instance.js +12 -6
- package/src/engine/physics/cloth/solver/cloth_stretch_residual.d.ts +21 -0
- package/src/engine/physics/cloth/solver/cloth_stretch_residual.d.ts.map +1 -0
- package/src/engine/physics/cloth/solver/cloth_stretch_residual.js +54 -0
- package/src/engine/physics/cloth/solver/cloth_vertex_accumulator.d.ts +15 -0
- package/src/engine/physics/cloth/solver/cloth_vertex_accumulator.d.ts.map +1 -1
- package/src/engine/physics/cloth/solver/cloth_vertex_accumulator.js +28 -0
- package/src/engine/physics/cloth/solver/cloth_worst_tether_ratio.d.ts +30 -0
- package/src/engine/physics/cloth/solver/cloth_worst_tether_ratio.d.ts.map +1 -0
- package/src/engine/physics/cloth/solver/cloth_worst_tether_ratio.js +56 -0
- package/src/engine/physics/cloth/solver/constraint/cloth_contact_row.d.ts.map +1 -1
- package/src/engine/physics/cloth/solver/constraint/cloth_contact_row.js +3 -17
- package/src/engine/physics/cloth/solver/constraint/cloth_leash_row.d.ts +1 -1
- package/src/engine/physics/cloth/solver/constraint/cloth_leash_row.d.ts.map +1 -1
- package/src/engine/physics/cloth/solver/constraint/cloth_leash_row.js +353 -346
- package/src/engine/physics/cloth/solver/constraint/cloth_self_row.d.ts +7 -5
- package/src/engine/physics/cloth/solver/constraint/cloth_self_row.d.ts.map +1 -1
- package/src/engine/physics/cloth/solver/constraint/cloth_self_row.js +7 -5
- package/src/engine/physics/cloth/wind/ClothFluidWind.d.ts +2 -1
- package/src/engine/physics/cloth/wind/ClothFluidWind.d.ts.map +1 -1
- package/src/engine/physics/cloth/wind/ClothFluidWind.js +7 -25
- package/src/engine/physics/cloth/wind/cloth_sample_air.d.ts +12 -10
- package/src/engine/physics/cloth/wind/cloth_sample_air.d.ts.map +1 -1
- package/src/engine/physics/cloth/wind/cloth_sample_air.js +60 -82
- package/src/engine/physics/ecs/ContactProbeSystem.d.ts.map +1 -1
- package/src/engine/physics/ecs/ContactProbeSystem.js +2 -18
- package/src/engine/physics/ecs/PhysicsSystem.d.ts.map +1 -1
- package/src/engine/physics/ecs/PhysicsSystem.js +9 -50
- package/src/engine/physics/fluid/ecs/FluidObstacleSystem.d.ts +4 -4
- package/src/engine/physics/fluid/ecs/fluid_sample_domain_bounds.d.ts +24 -0
- package/src/engine/physics/fluid/ecs/fluid_sample_domain_bounds.d.ts.map +1 -0
- package/src/engine/physics/fluid/ecs/fluid_sample_domain_bounds.js +42 -0
- package/src/engine/physics/fluid/ecs/fluid_sample_velocity_world_mps.d.ts +25 -0
- package/src/engine/physics/fluid/ecs/fluid_sample_velocity_world_mps.d.ts.map +1 -0
- package/src/engine/physics/fluid/ecs/fluid_sample_velocity_world_mps.js +40 -0
- package/src/engine/physics/inverse_kinematics/frame_fabrik/frame_fabrik_solve.d.ts.map +1 -1
- package/src/engine/physics/inverse_kinematics/frame_fabrik/frame_fabrik_solve.js +40 -90
- package/src/engine/physics/narrowphase/capsule_contacts.d.ts.map +1 -1
- package/src/engine/physics/narrowphase/capsule_contacts.js +3 -5
- package/src/engine/physics/narrowphase/decomposition/mesh_enumerate_triangles.d.ts.map +1 -1
- package/src/engine/physics/narrowphase/decomposition/mesh_enumerate_triangles.js +2 -14
- package/src/engine/physics/narrowphase/hull_sphere_contact.d.ts.map +1 -1
- package/src/engine/physics/narrowphase/hull_sphere_contact.js +2 -5
- package/src/engine/physics/narrowphase/narrowphase_step.d.ts.map +1 -1
- package/src/engine/physics/narrowphase/narrowphase_step.js +13 -32
- package/src/engine/physics/narrowphase/sphere_box_contact.d.ts.map +1 -1
- package/src/engine/physics/narrowphase/sphere_box_contact.js +2 -5
- package/src/engine/simulation/Ticker.d.ts +13 -0
- package/src/engine/simulation/Ticker.d.ts.map +1 -1
- package/src/engine/simulation/Ticker.js +43 -8
- package/src/format/texture/basis/transcode/etc1s_to_astc.d.ts.map +1 -1
- package/src/format/texture/basis/transcode/etc1s_to_astc.js +2 -1
- package/src/shade/RENDERER_CONTRACT.md +8 -2
- package/src/shade/playground/image_decode_bench/main.js +2 -1
- package/src/shade/playground/mesh_row_ceiling/main.js +2 -1
- package/src/shade/playground/skinned_blas_refit/diff_traced_against_rasterized.d.ts.map +1 -1
- package/src/shade/playground/skinned_blas_refit/diff_traced_against_rasterized.js +2 -1
- package/src/shade/playground/skinned_blas_refit/main.d.ts.map +1 -1
- package/src/shade/playground/skinned_blas_refit/main.js +11 -19
- package/src/shade/playground/skinned_blas_refit/place_character.d.ts +6 -3
- package/src/shade/playground/skinned_blas_refit/place_character.d.ts.map +1 -1
- package/src/shade/playground/skinned_blas_refit/place_character.js +90 -90
- package/src/shade/playground/skinned_mesh_soup/main.d.ts.map +1 -1
- package/src/shade/playground/skinned_mesh_soup/main.js +502 -509
- package/src/shade/playground/skinned_mesh_soup/verify_clone_vertices.d.ts.map +1 -1
- package/src/shade/playground/skinned_mesh_soup/verify_clone_vertices.js +2 -1
- package/src/shade/playground/ssr_variance/statistics.d.ts.map +1 -1
- package/src/shade/playground/ssr_variance/statistics.js +2 -1
- package/src/shade/playground/texture_encode/README.md +129 -109
- package/src/shade/playground/texture_encode/main.d.ts.map +1 -1
- package/src/shade/playground/texture_encode/main.js +1431 -1430
- package/src/shade/playground/volumetrics_froxel/measure.d.ts.map +1 -1
- package/src/shade/playground/volumetrics_froxel/measure.js +2 -1
- package/src/shade/renderer/animation/GPUAnimationManager.d.ts +45 -14
- package/src/shade/renderer/animation/GPUAnimationManager.d.ts.map +1 -1
- package/src/shade/renderer/animation/GPUAnimationManager.js +316 -64
- package/src/shade/renderer/animation/skinning/GPUMeshSkinningContext.d.ts +5 -0
- package/src/shade/renderer/animation/skinning/GPUMeshSkinningContext.d.ts.map +1 -1
- package/src/shade/renderer/animation/skinning/GPUMeshSkinningContext.js +11 -1
- package/src/shade/renderer/buffer/table/gpu_database_check_links.d.ts.map +1 -1
- package/src/shade/renderer/buffer/table/gpu_database_check_links.js +2 -1
- package/src/shade/renderer/geometry/BoxGeometry.d.ts +1 -11
- package/src/shade/renderer/geometry/BoxGeometry.d.ts.map +1 -1
- package/src/shade/renderer/geometry/BoxGeometry.js +6 -13
- package/src/shade/renderer/geometry/CapsuleGeometry.d.ts +19 -0
- package/src/shade/renderer/geometry/CapsuleGeometry.d.ts.map +1 -0
- package/src/shade/renderer/geometry/CapsuleGeometry.js +24 -0
- package/src/shade/renderer/geometry/ConeGeometry.d.ts +20 -0
- package/src/shade/renderer/geometry/ConeGeometry.d.ts.map +1 -0
- package/src/shade/renderer/geometry/ConeGeometry.js +33 -0
- package/src/shade/renderer/geometry/CylinderGeometry.d.ts +21 -0
- package/src/shade/renderer/geometry/CylinderGeometry.d.ts.map +1 -0
- package/src/shade/renderer/geometry/CylinderGeometry.js +35 -0
- package/src/shade/renderer/geometry/PlaneGeometry.d.ts +17 -0
- package/src/shade/renderer/geometry/PlaneGeometry.d.ts.map +1 -0
- package/src/shade/renderer/geometry/PlaneGeometry.js +22 -0
- package/src/shade/renderer/geometry/TorusGeometry.d.ts +18 -0
- package/src/shade/renderer/geometry/TorusGeometry.d.ts.map +1 -0
- package/src/shade/renderer/geometry/TorusGeometry.js +23 -0
- package/src/shade/renderer/geometry/UVSphereGeometry.d.ts +21 -0
- package/src/shade/renderer/geometry/UVSphereGeometry.d.ts.map +1 -0
- package/src/shade/renderer/geometry/UVSphereGeometry.js +34 -0
- package/src/shade/renderer/geometry/primitives/make_capsule_geometry.d.ts +19 -0
- package/src/shade/renderer/geometry/primitives/make_capsule_geometry.d.ts.map +1 -0
- package/src/shade/renderer/geometry/primitives/make_capsule_geometry.js +205 -0
- package/src/shade/renderer/geometry/primitives/make_cone_geometry.d.ts +21 -0
- package/src/shade/renderer/geometry/primitives/make_cone_geometry.d.ts.map +1 -0
- package/src/shade/renderer/geometry/primitives/make_cone_geometry.js +36 -0
- package/src/shade/renderer/geometry/primitives/make_cylinder_geometry.d.ts +1 -1
- package/src/shade/renderer/geometry/primitives/make_cylinder_geometry.d.ts.map +1 -1
- package/src/shade/renderer/geometry/primitives/make_cylinder_geometry.js +44 -9
- package/src/shade/renderer/geometry/primitives/make_uv_sphere_geometry.d.ts +20 -0
- package/src/shade/renderer/geometry/primitives/make_uv_sphere_geometry.d.ts.map +1 -0
- package/src/shade/renderer/geometry/primitives/make_uv_sphere_geometry.js +190 -0
- package/src/shade/renderer/geometry/virtual/build/level/vgeo_build_group_step.d.ts.map +1 -1
- package/src/shade/renderer/geometry/virtual/build/level/vgeo_build_group_step.js +3 -2
- package/src/shade/renderer/geometry/virtual/build/level/vgeo_build_leaf_frontier.d.ts.map +1 -1
- package/src/shade/renderer/geometry/virtual/build/level/vgeo_build_leaf_frontier.js +2 -1
- package/src/shade/renderer/geometry/virtual/build/level/vgeo_partition_into_groups.d.ts.map +1 -1
- package/src/shade/renderer/geometry/virtual/build/level/vgeo_partition_into_groups.js +2 -1
- package/src/shade/renderer/geometry/virtual/build/level/vgeo_run_round.d.ts.map +1 -1
- package/src/shade/renderer/geometry/virtual/build/level/vgeo_run_round.js +2 -1
- package/src/shade/renderer/geometry/virtual/build/level/vgeo_try_repack.d.ts.map +1 -1
- package/src/shade/renderer/geometry/virtual/build/level/vgeo_try_repack.js +3 -2
- package/src/shade/renderer/geometry/virtual/build/partition/vgeo_graph_components.d.ts.map +1 -1
- package/src/shade/renderer/geometry/virtual/build/partition/vgeo_graph_components.js +2 -1
- package/src/shade/renderer/geometry/virtual/build/partition/vgeo_split_face_set_packed.d.ts.map +1 -1
- package/src/shade/renderer/geometry/virtual/build/partition/vgeo_split_face_set_packed.js +2 -1
- package/src/shade/renderer/geometry/virtual/format/vgeo_write_container.d.ts.map +1 -1
- package/src/shade/renderer/geometry/virtual/format/vgeo_write_container.js +3 -2
- package/src/shade/renderer/geometry/virtual/runtime/graph_vgeo_expand_instances_to_meshlets.d.ts.map +1 -1
- package/src/shade/renderer/geometry/virtual/runtime/graph_vgeo_expand_instances_to_meshlets.js +7 -2
- package/src/shade/renderer/gpu_primitive/prefix_sum/v1/graph_prefix_scan_csdldf.d.ts +26 -8
- package/src/shade/renderer/gpu_primitive/prefix_sum/v1/graph_prefix_scan_csdldf.d.ts.map +1 -1
- package/src/shade/renderer/gpu_primitive/prefix_sum/v1/graph_prefix_scan_csdldf.js +56 -39
- package/src/shade/renderer/gpu_primitive/prefix_sum/v1/shader_prefix_scan_csdldf.d.ts +7 -0
- package/src/shade/renderer/gpu_primitive/prefix_sum/v1/shader_prefix_scan_csdldf.d.ts.map +1 -1
- package/src/shade/renderer/gpu_primitive/prefix_sum/v1/shader_prefix_scan_csdldf.js +46 -4
- package/src/shade/renderer/gpu_primitive/prefix_sum/v1/test_prefix_sum.d.ts.map +1 -1
- package/src/shade/renderer/gpu_primitive/prefix_sum/v1/test_prefix_sum.js +4 -2
- package/src/shade/renderer/gpu_primitive/sort/defs.d.ts +2 -2
- package/src/shade/renderer/gpu_primitive/sort/defs.js +79 -79
- package/src/shade/renderer/gpu_primitive/sort/graph_radix_sort.d.ts +1 -1
- package/src/shade/renderer/gpu_primitive/sort/graph_radix_sort.d.ts.map +1 -1
- package/src/shade/renderer/gpu_primitive/sort/graph_radix_sort.js +7 -3
- package/src/shade/renderer/particles/GPUParticleSystem.js +1 -1
- package/src/shade/renderer/particles/coherence/graph_particle_bucket.d.ts +4 -3
- package/src/shade/renderer/particles/coherence/graph_particle_bucket.d.ts.map +1 -1
- package/src/shade/renderer/particles/coherence/graph_particle_bucket.js +200 -194
- package/src/shade/renderer/particles/graph_particles.d.ts.map +1 -1
- package/src/shade/renderer/particles/graph_particles.js +6 -2
- package/src/shade/renderer/particles/optimizer/dag/particle_vector_extract.d.ts.map +1 -1
- package/src/shade/renderer/particles/optimizer/dag/particle_vector_extract.js +3 -2
- package/src/shade/renderer/particles/warmup/graph_particle_warmup.d.ts.map +1 -1
- package/src/shade/renderer/particles/warmup/graph_particle_warmup.js +334 -329
- package/src/shade/renderer/rasterize/bucket/prepare_meshlet_draw_commands_by_material.d.ts.map +1 -1
- package/src/shade/renderer/rasterize/bucket/prepare_meshlet_draw_commands_by_material.js +7 -2
- package/src/shade/renderer/rasterize/expand/mesh/graph_expand_meshes_to_meshlets.d.ts.map +1 -1
- package/src/shade/renderer/rasterize/expand/mesh/graph_expand_meshes_to_meshlets.js +16 -4
- package/src/shade/renderer/texture/COMPRESSED_TEXTURE_PLAN_2026_09_01.md +2444 -2345
- package/src/shade/renderer/texture/encode/chunk_astc_encode_block_4x4_rgb.d.ts.map +1 -1
- package/src/shade/renderer/texture/encode/chunk_astc_encode_block_4x4_rgb.js +312 -310
- package/src/shade/renderer/texture/encode/chunk_bc1_encode_block.d.ts +3 -3
- package/src/shade/renderer/texture/encode/chunk_bc1_encode_block.d.ts.map +1 -1
- package/src/shade/renderer/texture/encode/chunk_bc1_encode_block.js +383 -375
- package/src/shade/renderer/texture/encode/chunk_bc6h_encode_block_mode11.d.ts.map +1 -1
- package/src/shade/renderer/texture/encode/chunk_bc6h_encode_block_mode11.js +349 -346
- package/src/shade/renderer/texture/encode/chunk_bc7_encode_block.d.ts +58 -0
- package/src/shade/renderer/texture/encode/chunk_bc7_encode_block.d.ts.map +1 -0
- package/src/shade/renderer/texture/encode/chunk_bc7_encode_block.js +536 -0
- package/src/shade/renderer/texture/encode/chunk_bc7_encode_block_mode6.d.ts +21 -7
- package/src/shade/renderer/texture/encode/chunk_bc7_encode_block_mode6.d.ts.map +1 -1
- package/src/shade/renderer/texture/encode/chunk_bc7_encode_block_mode6.js +291 -327
- package/src/shade/renderer/texture/encode/chunk_bc7_pack_mode1.d.ts +25 -0
- package/src/shade/renderer/texture/encode/chunk_bc7_pack_mode1.d.ts.map +1 -0
- package/src/shade/renderer/texture/encode/chunk_bc7_pack_mode1.js +99 -0
- package/src/shade/renderer/texture/encode/chunk_bc7_pack_mode6.d.ts +5 -3
- package/src/shade/renderer/texture/encode/chunk_bc7_pack_mode6.d.ts.map +1 -1
- package/src/shade/renderer/texture/encode/chunk_bc7_pack_mode6.js +47 -71
- package/src/shade/renderer/texture/encode/chunk_bc7_partition_2.d.ts +10 -0
- package/src/shade/renderer/texture/encode/chunk_bc7_partition_2.d.ts.map +1 -0
- package/src/shade/renderer/texture/encode/chunk_bc7_partition_2.js +50 -0
- package/src/shade/renderer/texture/encode/shader_texture_encode_bc7.d.ts +4 -5
- package/src/shade/renderer/texture/encode/shader_texture_encode_bc7.d.ts.map +1 -1
- package/src/shade/renderer/texture/encode/shader_texture_encode_bc7.js +7 -8
- package/src/shade/renderer/water/chunk_water_transport.d.ts.map +1 -1
- package/src/shade/renderer/water/chunk_water_transport.js +7 -5
- package/src/shade/renderer/water/medium/GPUWaterBodies.d.ts.map +1 -1
- package/src/shade/renderer/water/medium/GPUWaterBodies.js +8 -2
- package/src/shade/renderer/water/optics/chunk_water_receiver_downwelling.d.ts +3 -2
- package/src/shade/renderer/water/optics/chunk_water_receiver_downwelling.d.ts.map +1 -1
- package/src/shade/renderer/water/optics/chunk_water_receiver_downwelling.js +3 -2
- package/src/shade/renderer/water/shader_water.d.ts.map +1 -1
- package/src/shade/renderer/water/shader_water.js +3 -1
- package/src/shade/renderer/water/surface/GPUWaterSurface.d.ts.map +1 -1
- package/src/shade/renderer/water/surface/GPUWaterSurface.js +3 -1
- package/src/shade/renderer/water/surface/graph_water_tessellation.d.ts.map +1 -1
- package/src/shade/renderer/water/surface/graph_water_tessellation.js +11 -4
- package/src/shade/renderer/water/surface/particles/GPUWaterParticles.d.ts.map +1 -1
- package/src/shade/renderer/water/surface/particles/GPUWaterParticles.js +37 -20
- package/src/shade/wgsl/validate_wgsl_source.d.ts.map +1 -1
- package/src/shade/wgsl/validate_wgsl_source.js +74 -3
- package/src/engine/graphics3/register_instance_animation.d.ts +0 -114
- package/src/engine/graphics3/register_instance_animation.d.ts.map +0 -1
- package/src/engine/graphics3/register_instance_animation.js +0 -201
|
@@ -1,3 +1,5 @@
|
|
|
1
|
+
import { clamp01 } from "../../../../core/math/clamp01.js";
|
|
2
|
+
|
|
1
3
|
/**
|
|
2
4
|
* # Normalised coordinates → row parameters
|
|
3
5
|
*
|
|
@@ -129,9 +131,10 @@ export const CLOTH_VELOCITY_CORRECTION_MARGIN = 4;
|
|
|
129
131
|
export const CLOTH_DAMPING_RATE = 20;
|
|
130
132
|
|
|
131
133
|
/**
|
|
132
|
-
* How far a cloth's
|
|
134
|
+
* How far a cloth's frame may carry it in one fixed step, as a multiple of the
|
|
133
135
|
* cloth's own reach. Motion above this is felt as though it were exactly this,
|
|
134
|
-
* which is what "anchor speed limit" means in §7 P7
|
|
136
|
+
* which is what "anchor speed limit" means in §7 P7 — the frame being what the
|
|
137
|
+
* cloth rides.
|
|
135
138
|
*
|
|
136
139
|
* Expressing it as a fraction of reach rather than in metres per second is what
|
|
137
140
|
* makes it work for a 3 cm pendant and a 30 m mooring line at the same time: a
|
|
@@ -142,10 +145,10 @@ export const CLOTH_DAMPING_RATE = 20;
|
|
|
142
145
|
* badly-keyed cut does exceed.
|
|
143
146
|
* @type {number}
|
|
144
147
|
*/
|
|
145
|
-
export const
|
|
148
|
+
export const CLOTH_FRAME_TRAVEL_REACH = 0.5;
|
|
146
149
|
|
|
147
150
|
/**
|
|
148
|
-
* How far a cloth's
|
|
151
|
+
* How far a cloth's frame may rotate in one fixed step, radians. Rotation
|
|
149
152
|
* above this is felt as though it were exactly this.
|
|
150
153
|
*
|
|
151
154
|
* Unlike the travel limit this has no length scale to hang off — an angle is
|
|
@@ -153,11 +156,12 @@ export const CLOTH_ANCHOR_TRAVEL_REACH = 0.5;
|
|
|
153
156
|
* about 1,700 degrees a second, which is a spin rather than a turn.
|
|
154
157
|
* @type {number}
|
|
155
158
|
*/
|
|
156
|
-
export const
|
|
159
|
+
export const CLOTH_FRAME_ROTATION_LIMIT = 0.5;
|
|
157
160
|
|
|
158
161
|
/**
|
|
159
|
-
*
|
|
160
|
-
* above which the motion is a **teleport**
|
|
162
|
+
* Displacement of the frame, or of a holder in the frame, in one fixed step, as
|
|
163
|
+
* a multiple of the cloth's reach, above which the motion is a **teleport**
|
|
164
|
+
* rather than locomotion (§7 P6).
|
|
161
165
|
*
|
|
162
166
|
* Four reaches in one step is 240 reaches a second: for a 1 m rope that is
|
|
163
167
|
* 240 m/s, well past anything the world moves at and well short of the values a
|
|
@@ -267,9 +271,7 @@ export const CLOTH_SLEEP_STEPS = 30;
|
|
|
267
271
|
* @returns {number} strain, `L_max = L₀·(1 + ε)`
|
|
268
272
|
*/
|
|
269
273
|
export function cloth_strain_allowance(stretch) {
|
|
270
|
-
|
|
271
|
-
|
|
272
|
-
return CLOTH_STRAIN_MAX * Math.pow(CLOTH_STRAIN_MIN / CLOTH_STRAIN_MAX, t);
|
|
274
|
+
return CLOTH_STRAIN_MAX * Math.pow(CLOTH_STRAIN_MIN / CLOTH_STRAIN_MAX, clamp01(stretch));
|
|
273
275
|
}
|
|
274
276
|
|
|
275
277
|
/**
|
|
@@ -8,17 +8,17 @@
|
|
|
8
8
|
* step, the colliders that could touch it are queried out of the index and
|
|
9
9
|
* rewritten into its frame.
|
|
10
10
|
*
|
|
11
|
-
* ## Both poses go into the *current*
|
|
11
|
+
* ## Both poses go into the cloth's *current* frame
|
|
12
12
|
*
|
|
13
13
|
* A record carries where the collider was and where it is. Both are converted
|
|
14
|
-
* using the
|
|
14
|
+
* using the frame's pose **now**, not each with the frame pose of its own
|
|
15
15
|
* step, so what the sweep interpolates is the collider's motion *relative to
|
|
16
16
|
* the cloth's frame*. That is the motion the particles actually see: the frame
|
|
17
17
|
* change has already been applied to them by `move_local_frame`, scaled by
|
|
18
18
|
* `ClothDynamics#inertia`, before the step begins.
|
|
19
19
|
*
|
|
20
20
|
* The alternative — converting each pose in its own frame — would make a
|
|
21
|
-
* collider appear to move whenever the
|
|
21
|
+
* collider appear to move whenever the frame did, so a character running past
|
|
22
22
|
* a static wall would sweep the wall through their own cape.
|
|
23
23
|
*
|
|
24
24
|
* ## The query box
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"cloth_gather_colliders.d.ts","sourceRoot":"","sources":["../../../../../../src/engine/physics/cloth/ecs/cloth_gather_colliders.js"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"cloth_gather_colliders.d.ts","sourceRoot":"","sources":["../../../../../../src/engine/physics/cloth/ecs/cloth_gather_colliders.js"],"names":[],"mappings":"AAiCA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA8DG;AAEH;;;;;;;;;;;;;;;;;;;;;;;;;;;GA2BG;AACH,qFAHW,MAAM,GACJ,MAAM,CAsBlB;AA2HD;;;;;;GAMG;AACH,kGAHW,MAAM,GACJ,MAAM,CAmBlB;AA2ED;;;;;;;;;;;;;;;;;;;;;;;;;;;GA2BG;AACH,2FAFa,OAAO,CAkBnB;AAED;;;;;;;;GAQG;AACH,yEAHW,MAAM,GACJ,IAAI,CAgBhB"}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
|
-
import {
|
|
2
|
-
import {
|
|
3
|
-
import {
|
|
1
|
+
import { aabb3_from_v3_array } from "../../../../core/geom/3d/aabb/aabb3_from_v3_array.js";
|
|
2
|
+
import { aabb3_transform_oriented_array } from "../../../../core/geom/3d/aabb/aabb3_transform_oriented.js";
|
|
3
|
+
import { pose3_to_local_array } from "../../../../core/geom/3d/pose/pose3_to_local_array.js";
|
|
4
4
|
import {
|
|
5
5
|
CCR_AABB_MAX_X,
|
|
6
6
|
CCR_AABB_MAX_Y,
|
|
@@ -16,17 +16,11 @@ import {
|
|
|
16
16
|
CCR_PARAM_1,
|
|
17
17
|
CCR_PARAM_2,
|
|
18
18
|
CCR_PARAM_3,
|
|
19
|
-
CCR_PREV_QW,
|
|
20
19
|
CCR_PREV_QX,
|
|
21
|
-
CCR_PREV_QY,
|
|
22
|
-
CCR_PREV_QZ,
|
|
23
20
|
CCR_PREV_TX,
|
|
24
21
|
CCR_PREV_TY,
|
|
25
22
|
CCR_PREV_TZ,
|
|
26
|
-
CCR_QW,
|
|
27
23
|
CCR_QX,
|
|
28
|
-
CCR_QY,
|
|
29
|
-
CCR_QZ,
|
|
30
24
|
CCR_STRIDE,
|
|
31
25
|
CCR_TX,
|
|
32
26
|
CCR_TY,
|
|
@@ -47,17 +41,17 @@ import { CLOTH_COLLIDER_SLOTS } from "../solver/cloth_solver_constants.js";
|
|
|
47
41
|
* step, the colliders that could touch it are queried out of the index and
|
|
48
42
|
* rewritten into its frame.
|
|
49
43
|
*
|
|
50
|
-
* ## Both poses go into the *current*
|
|
44
|
+
* ## Both poses go into the cloth's *current* frame
|
|
51
45
|
*
|
|
52
46
|
* A record carries where the collider was and where it is. Both are converted
|
|
53
|
-
* using the
|
|
47
|
+
* using the frame's pose **now**, not each with the frame pose of its own
|
|
54
48
|
* step, so what the sweep interpolates is the collider's motion *relative to
|
|
55
49
|
* the cloth's frame*. That is the motion the particles actually see: the frame
|
|
56
50
|
* change has already been applied to them by `move_local_frame`, scaled by
|
|
57
51
|
* `ClothDynamics#inertia`, before the step begins.
|
|
58
52
|
*
|
|
59
53
|
* The alternative — converting each pose in its own frame — would make a
|
|
60
|
-
* collider appear to move whenever the
|
|
54
|
+
* collider appear to move whenever the frame did, so a character running past
|
|
61
55
|
* a static wall would sweep the wall through their own cape.
|
|
62
56
|
*
|
|
63
57
|
* ## The query box
|
|
@@ -167,46 +161,33 @@ function query_colliders(instance, index, reach) {
|
|
|
167
161
|
const particle_count = state.particle_count;
|
|
168
162
|
const position = state.position;
|
|
169
163
|
|
|
170
|
-
let min_x = Infinity;
|
|
171
|
-
let min_y = Infinity;
|
|
172
|
-
let min_z = Infinity;
|
|
173
|
-
let max_x = -Infinity;
|
|
174
|
-
let max_y = -Infinity;
|
|
175
|
-
let max_z = -Infinity;
|
|
176
|
-
|
|
177
|
-
for (let i = 0; i < particle_count; i++) {
|
|
178
|
-
const p = i * 3;
|
|
179
|
-
|
|
180
|
-
const x = position[p];
|
|
181
|
-
const y = position[p + 1];
|
|
182
|
-
const z = position[p + 2];
|
|
183
|
-
|
|
184
|
-
if (x < min_x) { min_x = x; }
|
|
185
|
-
if (y < min_y) { min_y = y; }
|
|
186
|
-
if (z < min_z) { min_z = z; }
|
|
187
|
-
if (x > max_x) { max_x = x; }
|
|
188
|
-
if (y > max_y) { max_y = y; }
|
|
189
|
-
if (z > max_z) { max_z = z; }
|
|
190
|
-
}
|
|
191
|
-
|
|
192
164
|
if (particle_count === 0) {
|
|
193
165
|
return 0;
|
|
194
166
|
}
|
|
195
167
|
|
|
196
|
-
|
|
168
|
+
aabb3_from_v3_array(LOCAL_BOX, position, particle_count * 3);
|
|
169
|
+
|
|
170
|
+
let min_x = LOCAL_BOX[0];
|
|
171
|
+
let min_y = LOCAL_BOX[1];
|
|
172
|
+
let min_z = LOCAL_BOX[2];
|
|
173
|
+
let max_x = LOCAL_BOX[3];
|
|
174
|
+
let max_y = LOCAL_BOX[4];
|
|
175
|
+
let max_z = LOCAL_BOX[5];
|
|
176
|
+
|
|
177
|
+
// The frame pose the particles were carried into this step, not the live
|
|
197
178
|
// component — those are the same value by the time this runs, and the
|
|
198
179
|
// cached pair is the one `move_local_frame` used.
|
|
199
|
-
const
|
|
200
|
-
const
|
|
201
|
-
const
|
|
180
|
+
const frame_x = instance.frame_translation[0];
|
|
181
|
+
const frame_y = instance.frame_translation[1];
|
|
182
|
+
const frame_z = instance.frame_translation[2];
|
|
202
183
|
|
|
203
|
-
const
|
|
184
|
+
const frame_rotation = instance.frame_rotation;
|
|
204
185
|
|
|
205
186
|
const contact_reach = reach + state.contact_radius * (1 + CLOTH_CONTACT_MARGIN);
|
|
206
187
|
const local_scale = Math.max(Math.abs(min_x), Math.abs(max_x))
|
|
207
188
|
+ Math.max(Math.abs(min_y), Math.abs(max_y))
|
|
208
189
|
+ Math.max(Math.abs(min_z), Math.abs(max_z)) + contact_reach;
|
|
209
|
-
const world_scale = local_scale + Math.abs(
|
|
190
|
+
const world_scale = local_scale + Math.abs(frame_x) + Math.abs(frame_y) + Math.abs(frame_z);
|
|
210
191
|
const margin = contact_reach + cloth_contact_rounding(local_scale, world_scale);
|
|
211
192
|
|
|
212
193
|
min_x -= margin;
|
|
@@ -216,46 +197,29 @@ function query_colliders(instance, index, reach) {
|
|
|
216
197
|
max_y += margin;
|
|
217
198
|
max_z += margin;
|
|
218
199
|
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
|
|
224
|
-
|
|
225
|
-
|
|
226
|
-
|
|
227
|
-
|
|
228
|
-
|
|
229
|
-
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
const y = CORNER[1] + anchor_y;
|
|
240
|
-
const z = CORNER[2] + anchor_z;
|
|
241
|
-
|
|
242
|
-
if (x < world_min_x) { world_min_x = x; }
|
|
243
|
-
if (y < world_min_y) { world_min_y = y; }
|
|
244
|
-
if (z < world_min_z) { world_min_z = z; }
|
|
245
|
-
if (x > world_max_x) { world_max_x = x; }
|
|
246
|
-
if (y > world_max_y) { world_max_y = y; }
|
|
247
|
-
if (z > world_max_z) { world_max_z = z; }
|
|
248
|
-
}
|
|
200
|
+
LOCAL_BOX[0] = min_x;
|
|
201
|
+
LOCAL_BOX[1] = min_y;
|
|
202
|
+
LOCAL_BOX[2] = min_z;
|
|
203
|
+
LOCAL_BOX[3] = max_x;
|
|
204
|
+
LOCAL_BOX[4] = max_y;
|
|
205
|
+
LOCAL_BOX[5] = max_z;
|
|
206
|
+
|
|
207
|
+
// The frame pose as the seven contiguous numbers the transform reads,
|
|
208
|
+
// translation then rotation; the instance keeps the two apart.
|
|
209
|
+
FRAME_POSE[0] = frame_x;
|
|
210
|
+
FRAME_POSE[1] = frame_y;
|
|
211
|
+
FRAME_POSE[2] = frame_z;
|
|
212
|
+
FRAME_POSE[3] = frame_rotation[0];
|
|
213
|
+
FRAME_POSE[4] = frame_rotation[1];
|
|
214
|
+
FRAME_POSE[5] = frame_rotation[2];
|
|
215
|
+
FRAME_POSE[6] = frame_rotation[3];
|
|
216
|
+
|
|
217
|
+
// A rotated box is not a box, so the world query volume is the bounds of
|
|
218
|
+
// the rotated one rather than the rotation of the bounds.
|
|
219
|
+
aabb3_transform_oriented_array(QUERY_BOX, 0, LOCAL_BOX, 0, FRAME_POSE, 0);
|
|
249
220
|
|
|
250
221
|
const cloth = instance.cloth;
|
|
251
222
|
|
|
252
|
-
QUERY_BOX[0] = world_min_x;
|
|
253
|
-
QUERY_BOX[1] = world_min_y;
|
|
254
|
-
QUERY_BOX[2] = world_min_z;
|
|
255
|
-
QUERY_BOX[3] = world_max_x;
|
|
256
|
-
QUERY_BOX[4] = world_max_y;
|
|
257
|
-
QUERY_BOX[5] = world_max_z;
|
|
258
|
-
|
|
259
223
|
const candidates = index.queryArray(HANDLES, QUERY_BOX, 0, cloth.layer, cloth.mask, true);
|
|
260
224
|
|
|
261
225
|
// A half-space has no bounded world-space conversion allowance, so the
|
|
@@ -339,8 +303,8 @@ export function cloth_gather_colliders(instance, index, reach) {
|
|
|
339
303
|
* @private
|
|
340
304
|
*/
|
|
341
305
|
function localise_record(table, record, source, handle, instance) {
|
|
342
|
-
const
|
|
343
|
-
const
|
|
306
|
+
const frame_translation = instance.frame_translation;
|
|
307
|
+
const frame_rotation = instance.frame_rotation;
|
|
344
308
|
const from = handle * CCR_STRIDE;
|
|
345
309
|
const to = record * CCR_STRIDE;
|
|
346
310
|
|
|
@@ -356,13 +320,13 @@ function localise_record(table, record, source, handle, instance) {
|
|
|
356
320
|
localise(
|
|
357
321
|
table, to + CCR_TX, to + CCR_QX,
|
|
358
322
|
source, from + CCR_TX, from + CCR_QX,
|
|
359
|
-
|
|
323
|
+
frame_translation, frame_rotation
|
|
360
324
|
);
|
|
361
325
|
|
|
362
326
|
localise(
|
|
363
327
|
table, to + CCR_PREV_TX, to + CCR_PREV_QX,
|
|
364
328
|
source, from + CCR_PREV_TX, from + CCR_PREV_QX,
|
|
365
|
-
|
|
329
|
+
frame_translation, frame_rotation
|
|
366
330
|
);
|
|
367
331
|
|
|
368
332
|
cloth_collider_refit_bounds(table, record, CCR_STRIDE);
|
|
@@ -382,36 +346,23 @@ function localise_record(table, record, source, handle, instance) {
|
|
|
382
346
|
* @param {Float32Array|Float64Array} source the world pose's record table
|
|
383
347
|
* @param {number} source_translation_slot `[x, y, z]`
|
|
384
348
|
* @param {number} source_rotation_slot `[x, y, z, w]`
|
|
385
|
-
* @param {Float64Array}
|
|
386
|
-
* @param {Float64Array}
|
|
349
|
+
* @param {Float64Array} frame_translation `[x, y, z]`
|
|
350
|
+
* @param {Float64Array} frame_rotation `[x, y, z, w]`
|
|
387
351
|
* @private
|
|
388
352
|
*/
|
|
389
353
|
function localise(
|
|
390
354
|
table, translation_slot, rotation_slot,
|
|
391
355
|
source, source_translation_slot, source_rotation_slot,
|
|
392
|
-
|
|
356
|
+
frame_translation, frame_rotation
|
|
393
357
|
) {
|
|
394
|
-
|
|
395
|
-
|
|
396
|
-
|
|
397
|
-
|
|
398
|
-
|
|
399
|
-
|
|
400
|
-
|
|
401
|
-
|
|
402
|
-
table[translation_slot + 2] = LOCAL_TRANSLATION[2];
|
|
403
|
-
|
|
404
|
-
ANCHOR_CONJUGATE[0] = -anchor_rotation[0];
|
|
405
|
-
ANCHOR_CONJUGATE[1] = -anchor_rotation[1];
|
|
406
|
-
ANCHOR_CONJUGATE[2] = -anchor_rotation[2];
|
|
407
|
-
ANCHOR_CONJUGATE[3] = anchor_rotation[3];
|
|
408
|
-
|
|
409
|
-
quat3_multiply_array(LOCAL_ROTATION, 0, ANCHOR_CONJUGATE, 0, source, source_rotation_slot);
|
|
410
|
-
|
|
411
|
-
table[rotation_slot] = LOCAL_ROTATION[0];
|
|
412
|
-
table[rotation_slot + 1] = LOCAL_ROTATION[1];
|
|
413
|
-
table[rotation_slot + 2] = LOCAL_ROTATION[2];
|
|
414
|
-
table[rotation_slot + 3] = LOCAL_ROTATION[3];
|
|
358
|
+
pose3_to_local_array(
|
|
359
|
+
table, translation_slot,
|
|
360
|
+
table, rotation_slot,
|
|
361
|
+
frame_translation, 0,
|
|
362
|
+
frame_rotation, 0,
|
|
363
|
+
source, source_translation_slot,
|
|
364
|
+
source, source_rotation_slot
|
|
365
|
+
);
|
|
415
366
|
}
|
|
416
367
|
|
|
417
368
|
/**
|
|
@@ -495,29 +446,18 @@ const HANDLES = [];
|
|
|
495
446
|
const PLANE_RECORD = new Float32Array(CCR_STRIDE);
|
|
496
447
|
|
|
497
448
|
/**
|
|
449
|
+
* The cloth's particle bounds, then the same fattened by the query margin, in its local frame.
|
|
498
450
|
* @type {Float64Array}
|
|
499
451
|
* @private
|
|
500
452
|
*/
|
|
501
|
-
const
|
|
502
|
-
|
|
503
|
-
/**
|
|
504
|
-
* @type {Float64Array}
|
|
505
|
-
* @private
|
|
506
|
-
*/
|
|
507
|
-
const LOCAL_TRANSLATION = new Float64Array(3);
|
|
508
|
-
|
|
509
|
-
/**
|
|
510
|
-
* @type {Float64Array}
|
|
511
|
-
* @private
|
|
512
|
-
*/
|
|
513
|
-
const LOCAL_ROTATION = new Float64Array(4);
|
|
453
|
+
const LOCAL_BOX = new Float64Array(6);
|
|
514
454
|
|
|
515
455
|
/**
|
|
516
|
-
* The
|
|
456
|
+
* The cloth's frame pose, `[px, py, pz, qx, qy, qz, qw]`, for {@link aabb3_transform_oriented_array}.
|
|
517
457
|
* @type {Float64Array}
|
|
518
458
|
* @private
|
|
519
459
|
*/
|
|
520
|
-
const
|
|
460
|
+
const FRAME_POSE = new Float64Array(7);
|
|
521
461
|
|
|
522
462
|
/**
|
|
523
463
|
* The world box {@link query_colliders} asks the index about, `[min_x, min_y, min_z, max_x, max_y,
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Edges incident on each node, CSR, from an edge list.
|
|
3
|
+
*
|
|
4
|
+
* @param {number} node_count
|
|
5
|
+
* @param {Int32Array} edge node pairs, 2 per edge
|
|
6
|
+
* @returns {{offset: Int32Array, edge: Int32Array}} `edge[offset[n] .. offset[n + 1]]` are the
|
|
7
|
+
* edges touching `n`
|
|
8
|
+
*/
|
|
9
|
+
export function cloth_edge_incidence(node_count: number, edge: Int32Array): {
|
|
10
|
+
offset: Int32Array;
|
|
11
|
+
edge: Int32Array;
|
|
12
|
+
};
|
|
13
|
+
/**
|
|
14
|
+
* Distance from every node to the nearest of a set of source nodes, along the
|
|
15
|
+
* edges, and which source that is.
|
|
16
|
+
*
|
|
17
|
+
* A node marked in `blocked` can be reached but is never passed through. That is
|
|
18
|
+
* Chaos Cloth's rule for its long-range attachments (`ClothTetherData.cpp`):
|
|
19
|
+
* a path from one island of held particles does not run through another, because
|
|
20
|
+
* the far side of another island is that island's business.
|
|
21
|
+
*
|
|
22
|
+
* @param {Float64Array} out_distance per node; `Infinity` where no source reaches
|
|
23
|
+
* @param {Int32Array} out_nearest per node, the source it is nearest; `−1` where none reaches
|
|
24
|
+
* @param {number} node_count
|
|
25
|
+
* @param {Int32Array} edge node pairs, 2 per edge
|
|
26
|
+
* @param {Float64Array} edge_length rest length per edge
|
|
27
|
+
* @param {{offset: Int32Array, edge: Int32Array}} incidence from {@link cloth_edge_incidence}
|
|
28
|
+
* @param {Int32Array|number[]} source
|
|
29
|
+
* @param {number} source_count
|
|
30
|
+
* @param {Uint8Array|null} blocked per node, non-zero for a node no path may pass through;
|
|
31
|
+
* `null` for none
|
|
32
|
+
*/
|
|
33
|
+
export function cloth_geodesic_field(out_distance: Float64Array, out_nearest: Int32Array, node_count: number, edge: Int32Array, edge_length: Float64Array, incidence: {
|
|
34
|
+
offset: Int32Array;
|
|
35
|
+
edge: Int32Array;
|
|
36
|
+
}, source: Int32Array | number[], source_count: number, blocked: Uint8Array | null): void;
|
|
37
|
+
//# sourceMappingURL=cloth_geodesic.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"cloth_geodesic.d.ts","sourceRoot":"","sources":["../../../../../../src/engine/physics/cloth/ecs/cloth_geodesic.js"],"names":[],"mappings":"AAuCA;;;;;;;GAOG;AACH,iDALW,MAAM,QACN,UAAU,GACR;IAAC,MAAM,EAAE,UAAU,CAAC;IAAC,IAAI,EAAE,UAAU,CAAA;CAAC,CAiBlD;AAED;;;;;;;;;;;;;;;;;;;GAmBG;AACH,mDAXW,YAAY,eACZ,UAAU,cACV,MAAM,QACN,UAAU,eACV,YAAY,aACZ;IAAC,MAAM,EAAE,UAAU,CAAC;IAAC,IAAI,EAAE,UAAU,CAAA;CAAC,UACtC,UAAU,GAAC,MAAM,EAAE,gBACnB,MAAM,WACN,UAAU,GAAC,IAAI,QAsDzB"}
|
|
@@ -0,0 +1,135 @@
|
|
|
1
|
+
import { Uint32Heap } from "../../../../core/collection/heap/Uint32Heap.js";
|
|
2
|
+
import { csr_build_incidence } from "../../../../core/graph/csr/csr_build_incidence.js";
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* # How far each particle is from a set of particles, along the fabric
|
|
6
|
+
*
|
|
7
|
+
* The tether row (§6, §7 P2) bounds a particle's distance from a held one by
|
|
8
|
+
* the length of fabric between them, so it needs that length: the shortest path
|
|
9
|
+
* through the cloth's stretch edges, each weighted by its rest length. A chain
|
|
10
|
+
* has one path and the answer is a sum; a sheet has many and the answer is
|
|
11
|
+
* Dijkstra's.
|
|
12
|
+
*
|
|
13
|
+
* A path along edges is never shorter than the surface geodesic it follows, and
|
|
14
|
+
* that is never shorter than the straight line, so in the rest pose a tether
|
|
15
|
+
* built from it is never taut. That is the property the tether needs; how much
|
|
16
|
+
* longer a grid path is than the true geodesic is how much slack the bound
|
|
17
|
+
* carries, and it is the price of a bound that costs nothing at runtime.
|
|
18
|
+
*
|
|
19
|
+
* ## In double, and label-correcting
|
|
20
|
+
*
|
|
21
|
+
* The distances are accumulated in `Float64` from `Float64` edge lengths. The
|
|
22
|
+
* open set is a {@link Uint32Heap}, whose scores are `Float32`, so two
|
|
23
|
+
* candidates closer together than a single-precision step can pop in the wrong
|
|
24
|
+
* order; a node is therefore never closed, and a shorter path arriving after it
|
|
25
|
+
* popped is relaxed through again. The answer is the exact shortest path
|
|
26
|
+
* whatever the heap's rounding, and on the graphs this sees the extra pops are
|
|
27
|
+
* a handful.
|
|
28
|
+
*
|
|
29
|
+
* @author Alex Goldring
|
|
30
|
+
* @copyright Company Named Limited (c) 2026
|
|
31
|
+
*/
|
|
32
|
+
|
|
33
|
+
/**
|
|
34
|
+
* The open set. Module-level: a search runs start to finish synchronously, and
|
|
35
|
+
* it runs when a cloth is seeded or its held set changes, never per step.
|
|
36
|
+
* @type {Uint32Heap}
|
|
37
|
+
*/
|
|
38
|
+
const OPEN = new Uint32Heap();
|
|
39
|
+
|
|
40
|
+
/**
|
|
41
|
+
* Edges incident on each node, CSR, from an edge list.
|
|
42
|
+
*
|
|
43
|
+
* @param {number} node_count
|
|
44
|
+
* @param {Int32Array} edge node pairs, 2 per edge
|
|
45
|
+
* @returns {{offset: Int32Array, edge: Int32Array}} `edge[offset[n] .. offset[n + 1]]` are the
|
|
46
|
+
* edges touching `n`
|
|
47
|
+
*/
|
|
48
|
+
export function cloth_edge_incidence(node_count, edge) {
|
|
49
|
+
const edge_count = edge.length >> 1;
|
|
50
|
+
|
|
51
|
+
const offset = new Int32Array(node_count + 1);
|
|
52
|
+
const incident = new Int32Array(edge_count * 2);
|
|
53
|
+
|
|
54
|
+
csr_build_incidence(offset, incident, edge, edge_count * 2, node_count);
|
|
55
|
+
|
|
56
|
+
// an endpoint's flat index `e·2 + k` to its edge `e`
|
|
57
|
+
for (let i = 0; i < edge_count * 2; i++) {
|
|
58
|
+
incident[i] >>= 1;
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
return { offset, edge: incident };
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
/**
|
|
65
|
+
* Distance from every node to the nearest of a set of source nodes, along the
|
|
66
|
+
* edges, and which source that is.
|
|
67
|
+
*
|
|
68
|
+
* A node marked in `blocked` can be reached but is never passed through. That is
|
|
69
|
+
* Chaos Cloth's rule for its long-range attachments (`ClothTetherData.cpp`):
|
|
70
|
+
* a path from one island of held particles does not run through another, because
|
|
71
|
+
* the far side of another island is that island's business.
|
|
72
|
+
*
|
|
73
|
+
* @param {Float64Array} out_distance per node; `Infinity` where no source reaches
|
|
74
|
+
* @param {Int32Array} out_nearest per node, the source it is nearest; `−1` where none reaches
|
|
75
|
+
* @param {number} node_count
|
|
76
|
+
* @param {Int32Array} edge node pairs, 2 per edge
|
|
77
|
+
* @param {Float64Array} edge_length rest length per edge
|
|
78
|
+
* @param {{offset: Int32Array, edge: Int32Array}} incidence from {@link cloth_edge_incidence}
|
|
79
|
+
* @param {Int32Array|number[]} source
|
|
80
|
+
* @param {number} source_count
|
|
81
|
+
* @param {Uint8Array|null} blocked per node, non-zero for a node no path may pass through;
|
|
82
|
+
* `null` for none
|
|
83
|
+
*/
|
|
84
|
+
export function cloth_geodesic_field(
|
|
85
|
+
out_distance, out_nearest,
|
|
86
|
+
node_count, edge, edge_length, incidence,
|
|
87
|
+
source, source_count,
|
|
88
|
+
blocked
|
|
89
|
+
) {
|
|
90
|
+
out_distance.fill(Infinity, 0, node_count);
|
|
91
|
+
out_nearest.fill(-1, 0, node_count);
|
|
92
|
+
|
|
93
|
+
OPEN.clear();
|
|
94
|
+
|
|
95
|
+
for (let i = 0; i < source_count; i++) {
|
|
96
|
+
const s = source[i];
|
|
97
|
+
|
|
98
|
+
out_distance[s] = 0;
|
|
99
|
+
out_nearest[s] = s;
|
|
100
|
+
|
|
101
|
+
OPEN.insert(s, 0);
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
const offset = incidence.offset;
|
|
105
|
+
const incident = incidence.edge;
|
|
106
|
+
|
|
107
|
+
while (!OPEN.is_empty()) {
|
|
108
|
+
const u = OPEN.pop_min();
|
|
109
|
+
|
|
110
|
+
const d = out_distance[u];
|
|
111
|
+
|
|
112
|
+
if (d > 0 && blocked !== null && blocked[u] !== 0) {
|
|
113
|
+
// Reached, and that is where the path stops.
|
|
114
|
+
continue;
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
const nearest = out_nearest[u];
|
|
118
|
+
|
|
119
|
+
for (let k = offset[u]; k < offset[u + 1]; k++) {
|
|
120
|
+
const e = incident[k];
|
|
121
|
+
|
|
122
|
+
const a = edge[e * 2];
|
|
123
|
+
const v = a === u ? edge[e * 2 + 1] : a;
|
|
124
|
+
|
|
125
|
+
const candidate = d + edge_length[e];
|
|
126
|
+
|
|
127
|
+
if (candidate < out_distance[v]) {
|
|
128
|
+
out_distance[v] = candidate;
|
|
129
|
+
out_nearest[v] = nearest;
|
|
130
|
+
|
|
131
|
+
OPEN.insert(v, candidate);
|
|
132
|
+
}
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
}
|
|
@@ -0,0 +1,97 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* # What holding a particle does to a cloth
|
|
3
|
+
*
|
|
4
|
+
* A {@link ClothPin} holds particles, and that one fact decides four things the
|
|
5
|
+
* rows depend on. This module is where they are decided, once per change in
|
|
6
|
+
* what is held ({@link cloth_apply_holds}) and once per step
|
|
7
|
+
* ({@link cloth_hold_step}):
|
|
8
|
+
*
|
|
9
|
+
* - **Who is kinematic.** A held particle has inverse mass zero and follows its
|
|
10
|
+
* holder: the solver carries it through the step towards
|
|
11
|
+
* `ClothState#kinematic_target`.
|
|
12
|
+
* - **What each free particle hangs from.** Its nearest held particle, along the
|
|
13
|
+
* fabric — one multi-source Dijkstra over the stretch edges, every held
|
|
14
|
+
* particle a source, so a path never runs through one held particle to reach
|
|
15
|
+
* another. Nothing held in reach means nothing to hang from.
|
|
16
|
+
* - **The tether and the slack**, §6's two leash rows, both measured from that
|
|
17
|
+
* particle (`ClothState#leash_source`), so that they follow it through the step
|
|
18
|
+
* rather than lag a step behind it. One tether per particle, to the nearest
|
|
19
|
+
* hold only: two hard tethers to two holders pulled apart are two bounds no
|
|
20
|
+
* position satisfies, and the fabric between them already says everything a
|
|
21
|
+
* second tether could.
|
|
22
|
+
* - **The animated pose**, which is the rest pose hung from that particle and
|
|
23
|
+
* turned by its holder — see `ClothInstance#animated_position`.
|
|
24
|
+
*
|
|
25
|
+
* A particle nothing held reaches gets a tether and a slack row of radius
|
|
26
|
+
* `Infinity`, which say nothing, and a cloth nothing holds is all such
|
|
27
|
+
* particles: there is no case here for it.
|
|
28
|
+
*
|
|
29
|
+
* ## The tether never pulls
|
|
30
|
+
*
|
|
31
|
+
* A hold that begins mid-run — a hand closing on a falling ribbon — begins
|
|
32
|
+
* wherever the fabric is, and a free configuration is routinely further from
|
|
33
|
+
* the new hold than the geodesic, because the fabric stretches and the tether
|
|
34
|
+
* only binds when something pulls. A tether switched on at its full tightness
|
|
35
|
+
* would snap the cloth onto the hold inside one step. So a tether's radius
|
|
36
|
+
* starts at the larger of `d_geo` and where the particle is, and each step comes
|
|
37
|
+
* down to wherever the particle has since come to, never below `d_geo`: it
|
|
38
|
+
* stops a particle going further than it has been since the hold began, and
|
|
39
|
+
* it never drags one in. A cloth seeded at rest is inside `d_geo` everywhere,
|
|
40
|
+
* so its tethers are `d_geo` from the first step, which is what they always
|
|
41
|
+
* were — and only a tether that began loose is looked at again, so a cloth
|
|
42
|
+
* whose holds have not changed pays nothing for it.
|
|
43
|
+
*
|
|
44
|
+
* @author Alex Goldring
|
|
45
|
+
* @copyright Company Named Limited (c) 2026
|
|
46
|
+
*/
|
|
47
|
+
/**
|
|
48
|
+
* Take a hold's offsets: each of its particles relative to the holder, in the
|
|
49
|
+
* holder's own frame, from where the particle is now.
|
|
50
|
+
*
|
|
51
|
+
* Done in world terms, because the particles are in the frame they were last
|
|
52
|
+
* stepped in and the holder is where it is this step; the two meet in the
|
|
53
|
+
* world. The holder's turn is then measured from its pose in this step's frame,
|
|
54
|
+
* {@link ClothHold#pose}, so a hold begins unturned.
|
|
55
|
+
*
|
|
56
|
+
* @param {ClothInstance} instance
|
|
57
|
+
* @param {ClothHold} hold with {@link ClothHold#world} and {@link ClothHold#pose}
|
|
58
|
+
* this step's
|
|
59
|
+
* @param {Float64Array} frame_translation the frame the particle positions are in
|
|
60
|
+
* @param {Float64Array} frame_rotation
|
|
61
|
+
* @returns {void}
|
|
62
|
+
*/
|
|
63
|
+
export function cloth_capture_hold(instance: ClothInstance, hold: ClothHold, frame_translation: Float64Array, frame_rotation: Float64Array): void;
|
|
64
|
+
/**
|
|
65
|
+
* Re-derive everything that depends on what is held: who is kinematic, what
|
|
66
|
+
* each free particle hangs from, the leash rows, and `reach`.
|
|
67
|
+
*
|
|
68
|
+
* Called once a seed and once per change in the set of holds — never per step.
|
|
69
|
+
* Writes into the instance's existing `ClothState`; nothing is re-built, so a
|
|
70
|
+
* worker that holds the buffer sees it on the next step without a second
|
|
71
|
+
* registration.
|
|
72
|
+
*
|
|
73
|
+
* @param {ClothInstance} instance
|
|
74
|
+
* @returns {void}
|
|
75
|
+
*/
|
|
76
|
+
export function cloth_apply_holds(instance: ClothInstance): void;
|
|
77
|
+
/**
|
|
78
|
+
* Everything a hold changes per step: where each held particle is to be, the
|
|
79
|
+
* animated pose hung from them, the leash centres and the tethers' ratchet.
|
|
80
|
+
*
|
|
81
|
+
* Reads each hold's {@link ClothHold#pose} — the holder in this step's frame —
|
|
82
|
+
* and the particle positions as the frame carry left them.
|
|
83
|
+
*
|
|
84
|
+
* **Nothing is recomputed that cannot have changed.** Every quantity here
|
|
85
|
+
* except the ratchet is a function of the holds' poses in the frame, and a
|
|
86
|
+
* holder riding the frame — a rope's own top, a cape's shoulder in a cape riding
|
|
87
|
+
* that shoulder — has the same pose in it every step however the frame moves.
|
|
88
|
+
* So when no hold has moved in the frame since the last step, and nothing has
|
|
89
|
+
* rewritten the particles since ({@link ClothInstance#holds_dirty}), the
|
|
90
|
+
* targets, the animated pose and the leash offsets are left as they are: the
|
|
91
|
+
* question is a fact the step already has, not a kind of cloth.
|
|
92
|
+
*
|
|
93
|
+
* @param {ClothInstance} instance
|
|
94
|
+
* @returns {void}
|
|
95
|
+
*/
|
|
96
|
+
export function cloth_hold_step(instance: ClothInstance): void;
|
|
97
|
+
//# sourceMappingURL=cloth_holds.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"cloth_holds.d.ts","sourceRoot":"","sources":["../../../../../../src/engine/physics/cloth/ecs/cloth_holds.js"],"names":[],"mappings":"AAWA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA6CG;AAEH;;;;;;;;;;;;;;;GAeG;AACH,gGAJW,YAAY,kBACZ,YAAY,GACV,IAAI,CAyChB;AAED;;;;;;;;;;;GAWG;AACH,4DAFa,IAAI,CA0KhB;AAED;;;;;;;;;;;;;;;;;;GAkBG;AACH,0DAFa,IAAI,CA+JhB"}
|