Implement multibody joints and the new solver

This commit is contained in:
Sébastien Crozet
2022-01-02 14:47:40 +01:00
parent b45d4b5ac2
commit f74b8401ad
182 changed files with 9871 additions and 12645 deletions

View File

@@ -28,13 +28,13 @@ jobs:
- name: Build rapier3d
run: cargo build --verbose -p rapier3d;
- name: Build rapier2d SIMD
run: cd build/rapier2d; cargo build --verbose --features simd-stable;
run: cd crates/rapier2d; cargo build --verbose --features simd-stable;
- name: Build rapier3d SIMD
run: cd build/rapier3d; cargo build --verbose --features simd-stable;
run: cd crates/rapier3d; cargo build --verbose --features simd-stable;
- name: Build rapier2d SIMD Parallel
run: cd build/rapier2d; cargo build --verbose --features simd-stable --features parallel;
run: cd crates/rapier2d; cargo build --verbose --features simd-stable --features parallel;
- name: Build rapier3d SIMD Parallel
run: cd build/rapier3d; cargo build --verbose --features simd-stable --features parallel;
run: cd crates/rapier3d; cargo build --verbose --features simd-stable --features parallel;
- name: Run tests
run: cargo test
- name: Check rapier_testbed2d
@@ -42,9 +42,9 @@ jobs:
- name: Check rapier_testbed3d
run: cargo check --verbose -p rapier_testbed3d;
- name: Check rapier_testbed2d --features parallel
run: cd build/rapier_testbed2d; cargo check --verbose --features parallel;
run: cd crates/rapier_testbed2d; cargo check --verbose --features parallel;
- name: Check rapier_testbed3d --features parallel
run: cd build/rapier_testbed3d; cargo check --verbose --features parallel;
run: cd crates/rapier_testbed3d; cargo check --verbose --features parallel;
- name: Check rapier-examples-2d
run: cargo check -j 1 --verbose -p rapier-examples-2d;
- name: Check rapier-examples-3d
@@ -57,9 +57,9 @@ jobs:
- uses: actions/checkout@v2
- run: rustup target add wasm32-unknown-unknown
- name: build rapier2d
run: cd build/rapier2d && cargo build --verbose --features wasm-bindgen --target wasm32-unknown-unknown;
run: cd crates/rapier2d && cargo build --verbose --features wasm-bindgen --target wasm32-unknown-unknown;
- name: build rapier3d
run: cd build/rapier3d && cargo build --verbose --features wasm-bindgen --target wasm32-unknown-unknown;
run: cd crates/rapier3d && cargo build --verbose --features wasm-bindgen --target wasm32-unknown-unknown;
build-wasm-emscripten:
runs-on: ubuntu-latest
env:
@@ -68,10 +68,10 @@ jobs:
- uses: actions/checkout@v2
- run: rustup target add wasm32-unknown-emscripten
- name: build rapier2d
run: cd build/rapier2d && cargo build --verbose --target wasm32-unknown-emscripten;
run: cd crates/rapier2d && cargo build --verbose --target wasm32-unknown-emscripten;
- name: build rapier3d
run: cd build/rapier3d && cargo build --verbose --target wasm32-unknown-emscripten;
run: cd crates/rapier3d && cargo build --verbose --target wasm32-unknown-emscripten;
- name: build rapier2d --features simd-stable
run: cd build/rapier2d && cargo build --verbose --target wasm32-unknown-emscripten --features simd-stable;
run: cd crates/rapier2d && cargo build --verbose --target wasm32-unknown-emscripten --features simd-stable;
- name: build rapier3d --features simd-stable
run: cd build/rapier3d && cargo build --verbose --target wasm32-unknown-emscripten --features simd-stable;
run: cd crates/rapier3d && cargo build --verbose --target wasm32-unknown-emscripten --features simd-stable;

View File

@@ -1,21 +1,17 @@
[workspace]
members = [ "build/rapier2d", "build/rapier2d-f64", "build/rapier_testbed2d", "examples2d", "benchmarks2d",
"build/rapier3d", "build/rapier3d-f64", "build/rapier_testbed3d", "examples3d", "benchmarks3d" ]
members = [ "crates/rapier2d", "crates/rapier2d-f64", "crates/rapier_testbed2d", "examples2d", "benchmarks2d",
"crates/rapier3d", "crates/rapier3d-f64", "crates/rapier_testbed3d", "examples3d", "benchmarks3d" ]
resolver = "2"
[patch.crates-io]
#wrapped2d = { git = "https://github.com/Bastacyclop/rust_box2d.git" }
#simba = { path = "../simba" }
#ncollide2d = { path = "../ncollide/build/ncollide2d" }
#ncollide3d = { path = "../ncollide/build/ncollide3d" }
#nphysics2d = { path = "../nphysics/build/nphysics2d" }
#nphysics3d = { path = "../nphysics/build/nphysics3d" }
#kiss3d = { path = "../kiss3d" }
#parry2d = { path = "../parry/build/parry2d" }
#parry3d = { path = "../parry/build/parry3d" }
#parry2d-f64 = { path = "../parry/build/parry2d-f64" }
#parry3d-f64 = { path = "../parry/build/parry3d-f64" }
#parry2d = { path = "../parry/crates/parry2d" }
#parry3d = { path = "../parry/crates/parry3d" }
#parry2d-f64 = { path = "../parry/crates/parry2d-f64" }
#parry3d-f64 = { path = "../parry/crates/parry3d-f64" }
#nalgebra = { path = "../nalgebra" }
#kiss3d = { git = "https://github.com/sebcrozet/kiss3d" }
@@ -24,14 +20,10 @@ resolver = "2"
#parry3d = { git = "https://github.com/dimforge/parry", branch = "special_cases" }
#parry2d-f64 = { git = "https://github.com/dimforge/parry", branch = "special_cases" }
#parry3d-f64 = { git = "https://github.com/dimforge/parry", branch = "special_cases" }
#ncollide2d = { git = "https://github.com/dimforge/ncollide" }
#ncollide3d = { git = "https://github.com/dimforge/ncollide" }
#nphysics2d = { git = "https://github.com/dimforge/nphysics" }
#nphysics3d = { git = "https://github.com/dimforge/nphysics" }
[profile.release]
#debug = true
codegen-units = 1
#codegen-units = 1
#opt-level = 1
#lto = true

View File

@@ -2,7 +2,7 @@
name = "rapier-benchmarks-2d"
version = "0.1.0"
authors = [ "Sébastien Crozet <developer@crozet.re>" ]
edition = "2018"
edition = "2021"
[features]
parallel = [ "rapier2d/parallel", "rapier_testbed2d/parallel" ]
@@ -16,10 +16,10 @@ rand = "0.8"
Inflector = "0.11"
[dependencies.rapier_testbed2d]
path = "../build/rapier_testbed2d"
path = "../crates/rapier_testbed2d"
[dependencies.rapier2d]
path = "../build/rapier2d"
path = "../crates/rapier2d"
[[bin]]
name = "all_benchmarks2"

View File

@@ -7,7 +7,9 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
*/
@@ -58,6 +60,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![0.0, 2.5], 5.0);
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -63,6 +64,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![0.0, 50.0], 10.0);
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -65,6 +66,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![0.0, 50.0], 10.0);
}

View File

@@ -9,7 +9,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -76,6 +77,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![0.0, 50.0], 10.0);
}

View File

@@ -8,7 +8,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -63,6 +64,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![0.0, 50.0], 10.0);
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let mut joints = JointSet::new();
let mut impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Create the balls
@@ -41,16 +42,16 @@ pub fn init_world(testbed: &mut Testbed) {
// Vertical joint.
if i > 0 {
let parent_handle = *body_handles.last().unwrap();
let joint = BallJoint::new(Point::origin(), point![0.0, shift]);
joints.insert(parent_handle, child_handle, joint);
let joint = RevoluteJoint::new().local_anchor2(point![0.0, shift]);
impulse_joints.insert(parent_handle, child_handle, joint);
}
// Horizontal joint.
if k > 0 {
let parent_index = body_handles.len() - numi;
let parent_handle = body_handles[parent_index];
let joint = BallJoint::new(Point::origin(), point![-shift, 0.0]);
joints.insert(parent_handle, child_handle, joint);
let joint = RevoluteJoint::new().local_anchor2(point![-shift, 0.0]);
impulse_joints.insert(parent_handle, child_handle, joint);
}
body_handles.push(child_handle);
@@ -60,6 +61,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![numk as f32 * rad, numi as f32 * -rad], 5.0);
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let mut joints = JointSet::new();
let mut impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Create the balls
@@ -46,22 +47,18 @@ pub fn init_world(testbed: &mut Testbed) {
// Vertical joint.
if i > 0 {
let parent_handle = *body_handles.last().unwrap();
let joint = FixedJoint::new(
Isometry::identity(),
Isometry::translation(0.0, shift),
);
joints.insert(parent_handle, child_handle, joint);
let joint =
FixedJoint::new().local_frame2(Isometry::translation(0.0, shift));
impulse_joints.insert(parent_handle, child_handle, joint);
}
// Horizontal joint.
if k > 0 {
let parent_index = body_handles.len() - num;
let parent_handle = body_handles[parent_index];
let joint = FixedJoint::new(
Isometry::identity(),
Isometry::translation(-shift, 0.0),
);
joints.insert(parent_handle, child_handle, joint);
let joint =
FixedJoint::new().local_frame2(Isometry::translation(-shift, 0.0));
impulse_joints.insert(parent_handle, child_handle, joint);
}
body_handles.push(child_handle);
@@ -73,6 +70,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![50.0, 50.0], 5.0);
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let mut joints = JointSet::new();
let mut impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Create the balls
@@ -46,12 +47,10 @@ pub fn init_world(testbed: &mut Testbed) {
UnitVector::new_normalize(vector![-1.0, 1.0])
};
let mut prism =
PrismaticJoint::new(Point::origin(), axis, point![0.0, shift], axis);
prism.limits_enabled = true;
prism.limits[0] = -1.5;
prism.limits[1] = 1.5;
joints.insert(curr_parent, curr_child, prism);
let mut prism = PrismaticJoint::new(axis)
.local_anchor2(point![0.0, shift])
.limit_axis([-1.5, 1.5]);
impulse_joints.insert(curr_parent, curr_child, prism);
curr_parent = curr_child;
}
@@ -61,6 +60,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![80.0, 80.0], 15.0);
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -50,6 +51,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![0.0, 2.5], 5.0);
}

View File

@@ -2,7 +2,7 @@
name = "rapier-benchmarks-3d"
version = "0.1.0"
authors = [ "Sébastien Crozet <developer@crozet.re>" ]
edition = "2018"
edition = "2021"
[features]
parallel = [ "rapier3d/parallel", "rapier_testbed3d/parallel" ]
@@ -16,10 +16,10 @@ rand = "0.8"
Inflector = "0.11"
[dependencies.rapier_testbed3d]
path = "../build/rapier_testbed3d"
path = "../crates/rapier_testbed3d"
[dependencies.rapier3d]
path = "../build/rapier3d"
path = "../crates/rapier3d"
[[bin]]
name = "all_benchmarks3"

View File

@@ -58,10 +58,10 @@ pub fn main() {
("Stacks", stacks3::init_world),
("Pyramid", pyramid3::init_world),
("Trimesh", trimesh3::init_world),
("Joint ball", joint_ball3::init_world),
("Joint fixed", joint_fixed3::init_world),
("Joint revolute", joint_revolute3::init_world),
("Joint prismatic", joint_prismatic3::init_world),
("ImpulseJoint ball", joint_ball3::init_world),
("ImpulseJoint fixed", joint_fixed3::init_world),
("ImpulseJoint revolute", joint_revolute3::init_world),
("ImpulseJoint prismatic", joint_prismatic3::init_world),
("Keva tower", keva3::init_world),
];

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Create the balls
@@ -48,6 +49,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -58,6 +59,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -59,6 +60,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -73,6 +74,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -66,6 +67,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

View File

@@ -9,7 +9,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -73,6 +74,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

View File

@@ -8,7 +8,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -73,6 +74,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let mut joints = JointSet::new();
let mut impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
let rad = 0.4;
let num = 100;
@@ -36,16 +37,16 @@ pub fn init_world(testbed: &mut Testbed) {
// Vertical joint.
if i > 0 {
let parent_handle = *body_handles.last().unwrap();
let joint = BallJoint::new(Point::origin(), point![0.0, 0.0, -shift]);
joints.insert(parent_handle, child_handle, joint);
let joint = SphericalJoint::new().local_anchor2(point![0.0, 0.0, -shift]);
impulse_joints.insert(parent_handle, child_handle, joint);
}
// Horizontal joint.
if k > 0 {
let parent_index = body_handles.len() - num;
let parent_handle = body_handles[parent_index];
let joint = BallJoint::new(Point::origin(), point![-shift, 0.0, 0.0]);
joints.insert(parent_handle, child_handle, joint);
let joint = SphericalJoint::new().local_anchor2(point![-shift, 0.0, 0.0]);
impulse_joints.insert(parent_handle, child_handle, joint);
}
body_handles.push(child_handle);
@@ -55,6 +56,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![-110.0, -46.0, 170.0], point![54.0, -38.0, 29.0]);
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let mut joints = JointSet::new();
let mut impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
let rad = 0.4;
let num = 5;
@@ -49,22 +50,16 @@ pub fn init_world(testbed: &mut Testbed) {
// Vertical joint.
if i > 0 {
let parent_handle = *body_handles.last().unwrap();
let joint = FixedJoint::new(
Isometry::identity(),
Isometry::translation(0.0, 0.0, -shift),
);
joints.insert(parent_handle, child_handle, joint);
let joint = FixedJoint::new().local_anchor2(point![0.0, 0.0, -shift]);
impulse_joints.insert(parent_handle, child_handle, joint);
}
// Horizontal joint.
if k > 0 {
let parent_index = body_handles.len() - num;
let parent_handle = body_handles[parent_index];
let joint = FixedJoint::new(
Isometry::identity(),
Isometry::translation(-shift, 0.0, 0.0),
);
joints.insert(parent_handle, child_handle, joint);
let joint = FixedJoint::new().local_anchor2(point![-shift, 0.0, 0.0]);
impulse_joints.insert(parent_handle, child_handle, joint);
}
body_handles.push(child_handle);
@@ -77,6 +72,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![-38.0, 14.0, 108.0], point![46.0, 12.0, 23.0]);
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let mut joints = JointSet::new();
let mut impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
let rad = 0.4;
let num = 5;
@@ -47,19 +48,10 @@ pub fn init_world(testbed: &mut Testbed) {
UnitVector::new_normalize(vector![-1.0, 1.0, 0.0])
};
let z = Vector::z();
let mut prism = PrismaticJoint::new(
Point::origin(),
axis,
z,
point![0.0, 0.0, -shift],
axis,
z,
);
prism.limits_enabled = true;
prism.limits[0] = -2.0;
prism.limits[1] = 2.0;
joints.insert(curr_parent, curr_child, prism);
let prism = PrismaticJoint::new(axis)
.local_anchor2(point![0.0, 0.0, -shift])
.limit_axis([-2.0, 0.0]);
impulse_joints.insert(curr_parent, curr_child, prism);
curr_parent = curr_child;
}
@@ -70,6 +62,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![262.0, 63.0, 124.0], point![101.0, 4.0, -3.0]);
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let mut joints = JointSet::new();
let mut impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
let rad = 0.4;
let num = 10;
@@ -49,22 +50,21 @@ pub fn init_world(testbed: &mut Testbed) {
colliders.insert_with_parent(collider, handles[k], &mut bodies);
}
// Setup four joints.
let o = Point::origin();
// Setup four impulse_joints.
let x = Vector::x_axis();
let z = Vector::z_axis();
let revs = [
RevoluteJoint::new(o, z, point![0.0, 0.0, -shift], z),
RevoluteJoint::new(o, x, point![-shift, 0.0, 0.0], x),
RevoluteJoint::new(o, z, point![0.0, 0.0, -shift], z),
RevoluteJoint::new(o, x, point![shift, 0.0, 0.0], x),
RevoluteJoint::new(z).local_anchor2(point![0.0, 0.0, -shift]),
RevoluteJoint::new(x).local_anchor2(point![-shift, 0.0, 0.0]),
RevoluteJoint::new(z).local_anchor2(point![0.0, 0.0, -shift]),
RevoluteJoint::new(x).local_anchor2(point![shift, 0.0, 0.0]),
];
joints.insert(curr_parent, handles[0], revs[0]);
joints.insert(handles[0], handles[1], revs[1]);
joints.insert(handles[1], handles[2], revs[2]);
joints.insert(handles[2], handles[3], revs[3]);
impulse_joints.insert(curr_parent, handles[0], revs[0]);
impulse_joints.insert(handles[0], handles[1], revs[1]);
impulse_joints.insert(handles[1], handles[2], revs[2]);
impulse_joints.insert(handles[2], handles[3], revs[3]);
curr_parent = handles[3];
}
@@ -74,6 +74,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![478.0, 83.0, 228.0], point![134.0, 83.0, -116.0]);
}

View File

@@ -83,7 +83,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -132,6 +133,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

View File

@@ -41,7 +41,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -73,6 +74,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

View File

@@ -101,7 +101,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -183,6 +184,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

View File

@@ -8,7 +8,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -78,6 +79,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

View File

@@ -8,9 +8,9 @@ homepage = "http://rapier.rs"
repository = "https://github.com/dimforge/rapier"
readme = "README.md"
categories = [ "science", "game-development", "mathematics", "simulation", "wasm"]
keywords = [ "physics", "dynamics", "rigid", "real-time", "joints" ]
keywords = [ "physics", "dynamics", "rigid", "real-time", "impulse_joints" ]
license = "Apache-2.0"
edition = "2018"
edition = "2021"
[badges]
maintenance = { status = "actively-developed" }
@@ -47,9 +47,9 @@ required-features = [ "dim2", "f64" ]
vec_map = { version = "0.8", optional = true }
instant = { version = "0.1", features = [ "now" ]}
num-traits = "0.2"
nalgebra = "0.29"
parry2d-f64 = "^0.7.1"
simba = "0.6"
nalgebra = "0.30"
parry2d-f64 = "0.8"
simba = "0.7"
approx = "0.5"
rayon = { version = "1", optional = true }
crossbeam = "0.8"

View File

@@ -8,9 +8,9 @@ homepage = "http://rapier.rs"
repository = "https://github.com/dimforge/rapier"
readme = "README.md"
categories = [ "science", "game-development", "mathematics", "simulation", "wasm"]
keywords = [ "physics", "dynamics", "rigid", "real-time", "joints" ]
keywords = [ "physics", "dynamics", "rigid", "real-time", "impulse_joints" ]
license = "Apache-2.0"
edition = "2018"
edition = "2021"
[badges]
maintenance = { status = "actively-developed" }
@@ -47,9 +47,9 @@ required-features = [ "dim2", "f32" ]
vec_map = { version = "0.8", optional = true }
instant = { version = "0.1", features = [ "now" ]}
num-traits = "0.2"
nalgebra = "0.29"
parry2d = "^0.7.1"
simba = "0.6"
nalgebra = "0.30"
parry2d = "0.8"
simba = "0.7"
approx = "0.5"
rayon = { version = "1", optional = true }
crossbeam = "0.8"

View File

@@ -8,9 +8,9 @@ homepage = "http://rapier.rs"
repository = "https://github.com/dimforge/rapier"
readme = "README.md"
categories = [ "science", "game-development", "mathematics", "simulation", "wasm"]
keywords = [ "physics", "dynamics", "rigid", "real-time", "joints" ]
keywords = [ "physics", "dynamics", "rigid", "real-time", "impulse_joints" ]
license = "Apache-2.0"
edition = "2018"
edition = "2021"
[badges]
maintenance = { status = "actively-developed" }
@@ -47,9 +47,9 @@ required-features = [ "dim3", "f64" ]
vec_map = { version = "0.8", optional = true }
instant = { version = "0.1", features = [ "now" ]}
num-traits = "0.2"
nalgebra = "0.29"
parry3d-f64 = "^0.7.1"
simba = "0.6"
nalgebra = "0.30"
parry3d-f64 = "0.8"
simba = "0.7"
approx = "0.5"
rayon = { version = "1", optional = true }
crossbeam = "0.8"

View File

@@ -8,9 +8,9 @@ homepage = "http://rapier.rs"
repository = "https://github.com/dimforge/rapier"
readme = "README.md"
categories = [ "science", "game-development", "mathematics", "simulation", "wasm"]
keywords = [ "physics", "dynamics", "rigid", "real-time", "joints" ]
keywords = [ "physics", "dynamics", "rigid", "real-time", "impulse_joints" ]
license = "Apache-2.0"
edition = "2018"
edition = "2021"
[badges]
maintenance = { status = "actively-developed" }
@@ -47,9 +47,9 @@ required-features = [ "dim3", "f32" ]
vec_map = { version = "0.8", optional = true }
instant = { version = "0.1", features = [ "now" ]}
num-traits = "0.2"
nalgebra = "0.29"
parry3d = "^0.7.1"
simba = "0.6"
nalgebra = "0.30"
parry3d = "0.8"
simba = "0.7"
approx = "0.5"
rayon = { version = "1", optional = true }
crossbeam = "0.8"

View File

@@ -6,9 +6,9 @@ description = "Testbed for the Rapier 2-dimensional physics engine in Rust."
homepage = "http://rapier.org"
repository = "https://github.com/dimforge/rapier"
categories = [ "science", "game-development", "mathematics", "simulation", "wasm"]
keywords = [ "physics", "dynamics", "rigid", "real-time", "joints" ]
keywords = [ "physics", "dynamics", "rigid", "real-time", "impulse_joints" ]
license = "Apache-2.0"
edition = "2018"
edition = "2021"
[badges]
maintenance = { status = "actively-developed" }
@@ -22,20 +22,18 @@ required-features = [ "dim2" ]
default = [ "dim2" ]
dim2 = [ ]
parallel = [ "rapier2d/parallel", "num_cpus" ]
other-backends = [ "wrapped2d", "nphysics2d", "ncollide2d" ]
other-backends = [ "wrapped2d" ]
[dependencies]
nalgebra = { version = "0.29", features = [ "rand" ] }
nalgebra = { version = "0.30", features = [ "rand" ] }
rand = "0.8"
rand_pcg = "0.3"
instant = { version = "0.1", features = [ "web-sys", "now" ]}
bitflags = "1"
num_cpus = { version = "1", optional = true }
wrapped2d = { version = "0.4", optional = true }
parry2d = "0.7"
ncollide2d = { version = "0.32", optional = true }
nphysics2d = { version = "0.24", optional = true }
parry2d = "0.8"
crossbeam = "0.8"
bincode = "1"
Inflector = "0.11"

View File

@@ -6,9 +6,9 @@ description = "Testbed for the Rapier 3-dimensional physics engine in Rust."
homepage = "http://rapier.org"
repository = "https://github.com/dimforge/rapier"
categories = [ "science", "game-development", "mathematics", "simulation", "wasm"]
keywords = [ "physics", "dynamics", "rigid", "real-time", "joints" ]
keywords = [ "physics", "dynamics", "rigid", "real-time", "impulse_joints" ]
license = "Apache-2.0"
edition = "2018"
edition = "2021"
[badges]
maintenance = { status = "actively-developed" }
@@ -22,19 +22,17 @@ required-features = [ "dim3" ]
default = [ "dim3" ]
dim3 = [ ]
parallel = [ "rapier3d/parallel", "num_cpus" ]
other-backends = [ "physx", "physx-sys", "glam", "nphysics3d", "ncollide3d" ]
other-backends = [ "physx", "physx-sys", "glam" ]
[dependencies]
nalgebra = { version = "0.29", features = [ "rand" ] }
nalgebra = { version = "0.30", features = [ "rand" ] }
rand = "0.8"
rand_pcg = "0.3"
instant = { version = "0.1", features = [ "web-sys", "now" ]}
bitflags = "1"
glam = { version = "0.12", optional = true }
num_cpus = { version = "1", optional = true }
parry3d = "0.7"
ncollide3d = { version = "0.32", optional = true }
nphysics3d = { version = "0.24", optional = true }
parry3d = "0.8"
physx = { version = "0.11", optional = true }
physx-sys = { version = "0.4", optional = true }
crossbeam = "0.8"

View File

@@ -2,7 +2,7 @@
name = "rapier-examples-2d"
version = "0.1.0"
authors = [ "Sébastien Crozet <developer@crozet.re>" ]
edition = "2018"
edition = "2021"
default-run = "all_examples2"
[features]
@@ -19,10 +19,10 @@ lyon = "0.17"
usvg = "0.14"
[dependencies.rapier_testbed2d]
path = "../build/rapier_testbed2d"
path = "../crates/rapier_testbed2d"
[dependencies.rapier2d]
path = "../build/rapier2d"
path = "../crates/rapier2d"
[[bin]]
name = "all_examples2"

View File

@@ -4,12 +4,15 @@ use rapier_testbed2d::Testbed;
pub fn init_world(testbed: &mut Testbed) {
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
let rad = 0.5;
let positions = [vector![5.0, -1.0], vector![-5.0, -1.0]];
let platform_handles = std::array::IntoIter::new(positions)
let platform_handles = positions
.into_iter()
.map(|pos| {
let rigid_body = RigidBodyBuilder::new_kinematic_position_based()
.translation(pos)
@@ -57,7 +60,8 @@ pub fn init_world(testbed: &mut Testbed) {
handle,
&mut physics.islands,
&mut physics.colliders,
&mut physics.joints,
&mut physics.impulse_joints,
&mut physics.multibody_joints,
);
if let Some(graphics) = &mut graphics {
@@ -69,6 +73,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![0.0, 0.0], 20.0);
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -123,6 +124,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![0.0, 2.5], 20.0);
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -89,6 +90,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![0.0, 1.0], 100.0);
}

View File

@@ -9,7 +9,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -76,6 +77,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![0.0, 50.0], 10.0);
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Create the balls
@@ -38,6 +39,13 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world_with_params(bodies, colliders, joints, Vector::zeros(), ());
testbed.set_world_with_params(
bodies,
colliders,
impulse_joints,
multibody_joints,
Vector::zeros(),
(),
);
testbed.look_at(point![3.0, 2.0], 50.0);
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -33,6 +34,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![0.0, 0.0], 50.0);
}

View File

@@ -8,7 +8,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -63,6 +64,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![0.0, 0.0], 10.0);
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let mut joints = JointSet::new();
let mut impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Create the balls
@@ -44,16 +45,16 @@ pub fn init_world(testbed: &mut Testbed) {
// Vertical joint.
if i > 0 {
let parent_handle = *body_handles.last().unwrap();
let joint = BallJoint::new(Point::origin(), point![0.0, shift]);
joints.insert(parent_handle, child_handle, joint);
let joint = RevoluteJoint::new().local_anchor2(point![0.0, shift]);
impulse_joints.insert(parent_handle, child_handle, joint);
}
// Horizontal joint.
if k > 0 {
let parent_index = body_handles.len() - numi;
let parent_handle = body_handles[parent_index];
let joint = BallJoint::new(Point::origin(), point![-shift, 0.0]);
joints.insert(parent_handle, child_handle, joint);
let joint = RevoluteJoint::new().local_anchor2(point![-shift, 0.0]);
impulse_joints.insert(parent_handle, child_handle, joint);
}
body_handles.push(child_handle);
@@ -63,6 +64,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![numk as f32 * rad, numi as f32 * -rad], 20.0);
}

View File

@@ -10,7 +10,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* The ground
@@ -51,6 +52,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![0.0, 0.0], 40.0);
}

View File

@@ -62,7 +62,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -126,7 +127,8 @@ pub fn init_world(testbed: &mut Testbed) {
testbed.set_world_with_params(
bodies,
colliders,
joints,
impulse_joints,
multibody_joints,
vector![0.0, -9.81],
physics_hooks,
);

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground.
@@ -89,6 +90,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Run the simulation.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![0.0, 1.0], 40.0);
}

View File

@@ -8,7 +8,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -65,6 +66,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![0.0, 0.0], 10.0);
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -50,6 +51,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![0.0, 2.5], 20.0);
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -44,6 +45,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![0.0, 1.0], 25.0);
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground.
@@ -98,6 +99,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![0.0, 1.0], 100.0);
}

View File

@@ -13,7 +13,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -103,7 +104,7 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![0.0, 20.0], 17.0);
}

View File

@@ -2,7 +2,7 @@
name = "rapier-examples-3d"
version = "0.1.0"
authors = [ "Sébastien Crozet <developer@crozet.re>" ]
edition = "2018"
edition = "2021"
default-run = "all_examples3"
[features]
@@ -20,10 +20,10 @@ wasm-bindgen = "0.2"
obj-rs = { version = "0.6", default-features = false }
[dependencies.rapier_testbed3d]
path = "../build/rapier_testbed3d"
path = "../crates/rapier_testbed3d"
[dependencies.rapier3d]
path = "../build/rapier3d"
path = "../crates/rapier3d"
[[bin]]
name = "all_examples3"

View File

@@ -8,6 +8,7 @@ use inflector::Inflector;
use rapier_testbed3d::{Testbed, TestbedApp};
use std::cmp::Ordering;
mod articulations3;
mod ccd3;
mod collision_groups3;
mod compound3;
@@ -15,6 +16,7 @@ mod convex_decomposition3;
mod convex_polyhedron3;
mod damping3;
mod debug_add_remove_collider3;
mod debug_articulations3;
mod debug_big_colliders3;
mod debug_boxes3;
mod debug_cylinder3;
@@ -29,7 +31,7 @@ mod debug_trimesh3;
mod domino3;
mod fountain3;
mod heightfield3;
mod joints3;
// mod joints3;
mod keva3;
mod locked_rotations3;
mod one_way_platforms3;
@@ -78,6 +80,10 @@ pub fn main() {
let mut builders: Vec<(_, fn(&mut Testbed))> = vec![
("Fountain", fountain3::init_world),
("Primitives", primitives3::init_world),
(
"Multibody joints",
articulations3::init_world_with_articulations,
),
("CCD", ccd3::init_world),
("Collision groups", collision_groups3::init_world),
("Compound", compound3::init_world),
@@ -86,7 +92,7 @@ pub fn main() {
("Damping", damping3::init_world),
("Domino", domino3::init_world),
("Heightfield", heightfield3::init_world),
("Joints", joints3::init_world),
("Impulse Joints", articulations3::init_world_with_joints),
("Locked rotations", locked_rotations3::init_world),
("One-way platforms", one_way_platforms3::init_world),
("Platform", platform3::init_world),
@@ -94,6 +100,7 @@ pub fn main() {
("Sensor", sensor3::init_world),
("TriMesh", trimesh3::init_world),
("Keva tower", keva3::init_world),
("(Debug) multibody_joints", debug_articulations3::init_world),
(
"(Debug) add/rm collider",
debug_add_remove_collider3::init_world,

View File

@@ -0,0 +1,678 @@
use rapier3d::prelude::*;
use rapier_testbed3d::Testbed;
fn create_prismatic_joints(
bodies: &mut RigidBodySet,
colliders: &mut ColliderSet,
impulse_joints: &mut ImpulseJointSet,
multibody_joints: &mut MultibodyJointSet,
origin: Point<f32>,
num: usize,
use_articulations: bool,
) {
let rad = 0.4;
let shift = 2.0;
let ground = RigidBodyBuilder::new_static()
.translation(vector![origin.x, origin.y, origin.z])
.build();
let mut curr_parent = bodies.insert(ground);
let collider = ColliderBuilder::cuboid(rad, rad, rad).build();
colliders.insert_with_parent(collider, curr_parent, bodies);
for i in 0..num {
let z = origin.z + (i + 1) as f32 * shift;
let rigid_body = RigidBodyBuilder::new_dynamic()
.translation(vector![origin.x, origin.y, z])
.build();
let curr_child = bodies.insert(rigid_body);
let collider = ColliderBuilder::cuboid(rad, rad, rad).build();
colliders.insert_with_parent(collider, curr_child, bodies);
let axis = if i % 2 == 0 {
UnitVector::new_normalize(vector![1.0f32, 1.0, 0.0])
} else {
UnitVector::new_normalize(vector![-1.0f32, 1.0, 0.0])
};
let prism = PrismaticJoint::new(axis)
.local_anchor1(point![0.0, 0.0, 0.0])
.local_anchor2(point![0.0, 0.0, -shift])
.limit_axis([-2.0, 2.0]);
if use_articulations {
multibody_joints.insert(curr_parent, curr_child, prism);
} else {
impulse_joints.insert(curr_parent, curr_child, prism);
}
curr_parent = curr_child;
}
}
fn create_actuated_prismatic_joints(
bodies: &mut RigidBodySet,
colliders: &mut ColliderSet,
impulse_joints: &mut ImpulseJointSet,
multibody_joints: &mut MultibodyJointSet,
origin: Point<f32>,
num: usize,
use_articulations: bool,
) {
let rad = 0.4;
let shift = 2.0;
let ground = RigidBodyBuilder::new_static()
.translation(vector![origin.x, origin.y, origin.z])
.build();
let mut curr_parent = bodies.insert(ground);
let collider = ColliderBuilder::cuboid(rad, rad, rad).build();
colliders.insert_with_parent(collider, curr_parent, bodies);
for i in 0..num {
let z = origin.z + (i + 1) as f32 * shift;
let rigid_body = RigidBodyBuilder::new_dynamic()
.translation(vector![origin.x, origin.y, z])
.build();
let curr_child = bodies.insert(rigid_body);
let collider = ColliderBuilder::cuboid(rad, rad, rad).build();
colliders.insert_with_parent(collider, curr_child, bodies);
let axis = if i % 2 == 0 {
UnitVector::new_normalize(vector![1.0, 1.0, 0.0])
} else {
UnitVector::new_normalize(vector![-1.0, 1.0, 0.0])
};
let mut prism = PrismaticJoint::new(axis)
.local_anchor1(point![0.0, 0.0, 0.0])
.local_anchor2(point![0.0, 0.0, -shift]);
if i == 1 {
prism = prism
.limit_axis([-Real::MAX, 5.0])
.motor_velocity(1.0, 1.0)
// We set a max impulse so that the motor doesn't fight
// the limits with large forces.
.motor_max_impulse(1.0);
} else if i > 1 {
prism = prism.motor_position(2.0, 0.01, 1.0);
} else {
prism = prism
.motor_velocity(1.0, 1.0)
// We set a max impulse so that the motor doesn't fight
// the limits with large forces.
.motor_max_impulse(0.7)
.limit_axis([-2.0, 5.0]);
}
if use_articulations {
multibody_joints.insert(curr_parent, curr_child, prism);
} else {
impulse_joints.insert(curr_parent, curr_child, prism);
}
curr_parent = curr_child;
}
}
fn create_revolute_joints(
bodies: &mut RigidBodySet,
colliders: &mut ColliderSet,
impulse_joints: &mut ImpulseJointSet,
multibody_joints: &mut MultibodyJointSet,
origin: Point<f32>,
num: usize,
use_articulations: bool,
) {
let rad = 0.4;
let shift = 2.0;
let ground = RigidBodyBuilder::new_static()
.translation(vector![origin.x, origin.y, 0.0])
.build();
let mut curr_parent = bodies.insert(ground);
let collider = ColliderBuilder::cuboid(rad, rad, rad).build();
colliders.insert_with_parent(collider, curr_parent, bodies);
for i in 0..num {
// Create four bodies.
let z = origin.z + i as f32 * shift * 2.0 + shift;
let positions = [
Isometry::translation(origin.x, origin.y, z),
Isometry::translation(origin.x + shift, origin.y, z),
Isometry::translation(origin.x + shift, origin.y, z + shift),
Isometry::translation(origin.x, origin.y, z + shift),
];
let mut handles = [curr_parent; 4];
for k in 0..4 {
let rigid_body = RigidBodyBuilder::new_dynamic()
.position(positions[k])
.build();
handles[k] = bodies.insert(rigid_body);
let collider = ColliderBuilder::cuboid(rad, rad, rad).build();
colliders.insert_with_parent(collider, handles[k], bodies);
}
// Setup four impulse_joints.
let x = Vector::x_axis();
let z = Vector::z_axis();
let revs = [
RevoluteJoint::new(z).local_anchor2(point![0.0, 0.0, -shift]),
RevoluteJoint::new(x).local_anchor2(point![-shift, 0.0, 0.0]),
RevoluteJoint::new(z).local_anchor2(point![0.0, 0.0, -shift]),
RevoluteJoint::new(x).local_anchor2(point![shift, 0.0, 0.0]),
];
if use_articulations {
multibody_joints.insert(curr_parent, handles[0], revs[0]);
multibody_joints.insert(handles[0], handles[1], revs[1]);
multibody_joints.insert(handles[1], handles[2], revs[2]);
multibody_joints.insert(handles[2], handles[3], revs[3]);
} else {
impulse_joints.insert(curr_parent, handles[0], revs[0]);
impulse_joints.insert(handles[0], handles[1], revs[1]);
impulse_joints.insert(handles[1], handles[2], revs[2]);
impulse_joints.insert(handles[2], handles[3], revs[3]);
}
curr_parent = handles[3];
}
}
fn create_revolute_joints_with_limits(
bodies: &mut RigidBodySet,
colliders: &mut ColliderSet,
impulse_joints: &mut ImpulseJointSet,
multibody_joints: &mut MultibodyJointSet,
origin: Point<f32>,
use_articulations: bool,
) {
let ground = bodies.insert(
RigidBodyBuilder::new_static()
.translation(origin.coords)
.build(),
);
let platform1 = bodies.insert(
RigidBodyBuilder::new_dynamic()
.translation(origin.coords)
.build(),
);
colliders.insert_with_parent(
ColliderBuilder::cuboid(4.0, 0.2, 2.0).build(),
platform1,
bodies,
);
let shift = vector![0.0, 0.0, 6.0];
let platform2 = bodies.insert(
RigidBodyBuilder::new_dynamic()
.translation(origin.coords + shift)
.build(),
);
colliders.insert_with_parent(
ColliderBuilder::cuboid(4.0, 0.2, 2.0).build(),
platform2,
bodies,
);
let z = Vector::z_axis();
let joint1 = RevoluteJoint::new(z).limit_axis([-0.2, 0.2]);
if use_articulations {
multibody_joints.insert(ground, platform1, joint1);
} else {
impulse_joints.insert(ground, platform1, joint1);
}
let joint2 = RevoluteJoint::new(z)
.local_anchor2(-Point::from(shift))
.limit_axis([-0.2, 0.2]);
if use_articulations {
multibody_joints.insert(platform1, platform2, joint2);
} else {
impulse_joints.insert(platform1, platform2, joint2);
}
// Lets add a couple of cuboids that will fall on the platforms, triggering the joint limits.
let cuboid_body1 = bodies.insert(
RigidBodyBuilder::new_dynamic()
.translation(origin.coords + vector![-2.0, 4.0, 0.0])
.build(),
);
colliders.insert_with_parent(
ColliderBuilder::cuboid(0.6, 0.6, 0.6).friction(1.0).build(),
cuboid_body1,
bodies,
);
let cuboid_body2 = bodies.insert(
RigidBodyBuilder::new_dynamic()
.translation(origin.coords + shift + vector![2.0, 16.0, 0.0])
.build(),
);
colliders.insert_with_parent(
ColliderBuilder::cuboid(0.6, 0.6, 0.6).friction(1.0).build(),
cuboid_body2,
bodies,
);
}
fn create_fixed_joints(
bodies: &mut RigidBodySet,
colliders: &mut ColliderSet,
impulse_joints: &mut ImpulseJointSet,
multibody_joints: &mut MultibodyJointSet,
origin: Point<f32>,
num: usize,
use_articulations: bool,
) {
let rad = 0.4;
let shift = 1.0;
let mut body_handles = Vec::new();
for i in 0..num {
for k in 0..num {
let fk = k as f32;
let fi = i as f32;
// NOTE: the num - 2 test is to avoid two consecutive
// fixed bodies. Because physx will crash if we add
// a joint between these.
let status = if i == 0 && (k % 4 == 0 && k != num - 2 || k == num - 1) {
RigidBodyType::Static
} else {
RigidBodyType::Dynamic
};
let rigid_body = RigidBodyBuilder::new(status)
.translation(vector![
origin.x + fk * shift,
origin.y,
origin.z + fi * shift
])
.build();
let child_handle = bodies.insert(rigid_body);
let collider = ColliderBuilder::ball(rad).build();
colliders.insert_with_parent(collider, child_handle, bodies);
// Vertical joint.
if i > 0 {
let parent_index = body_handles.len() - num;
let parent_handle = body_handles[parent_index];
let joint = FixedJoint::new().local_anchor2(point![0.0, 0.0, -shift]);
if use_articulations {
multibody_joints.insert(parent_handle, child_handle, joint);
} else {
impulse_joints.insert(parent_handle, child_handle, joint);
}
}
// Horizontal joint.
if k > 0 {
let parent_index = body_handles.len() - 1;
let parent_handle = body_handles[parent_index];
let joint = FixedJoint::new().local_anchor2(point![-shift, 0.0, 0.0]);
impulse_joints.insert(parent_handle, child_handle, joint);
}
body_handles.push(child_handle);
}
}
}
fn create_spherical_joints(
bodies: &mut RigidBodySet,
colliders: &mut ColliderSet,
impulse_joints: &mut ImpulseJointSet,
multibody_joints: &mut MultibodyJointSet,
num: usize,
use_articulations: bool,
) {
let rad = 0.4;
let shift = 1.0;
let mut body_handles = Vec::new();
for k in 0..num {
for i in 0..num {
let fk = k as f32;
let fi = i as f32;
let status = if i == 0 && (k % 4 == 0 || k == num - 1) {
RigidBodyType::Static
} else {
RigidBodyType::Dynamic
};
let rigid_body = RigidBodyBuilder::new(status)
.translation(vector![fk * shift, 0.0, fi * shift * 2.0])
.build();
let child_handle = bodies.insert(rigid_body);
let collider = ColliderBuilder::capsule_z(rad * 1.25, rad).build();
colliders.insert_with_parent(collider, child_handle, bodies);
// Vertical joint.
if i > 0 {
let parent_handle = *body_handles.last().unwrap();
let joint = SphericalJoint::new().local_anchor2(point![0.0, 0.0, -shift * 2.0]);
if use_articulations {
multibody_joints.insert(parent_handle, child_handle, joint);
} else {
impulse_joints.insert(parent_handle, child_handle, joint);
}
}
// Horizontal joint.
if k > 0 {
let parent_index = body_handles.len() - num;
let parent_handle = body_handles[parent_index];
let joint = SphericalJoint::new().local_anchor2(point![-shift, 0.0, 0.0]);
impulse_joints.insert(parent_handle, child_handle, joint);
}
body_handles.push(child_handle);
}
}
}
fn create_spherical_joints_with_limits(
bodies: &mut RigidBodySet,
colliders: &mut ColliderSet,
impulse_joints: &mut ImpulseJointSet,
multibody_joints: &mut MultibodyJointSet,
origin: Point<f32>,
use_articulations: bool,
) {
let shift = vector![0.0, 0.0, 3.0];
let ground = bodies.insert(
RigidBodyBuilder::new_static()
.translation(origin.coords)
.build(),
);
let ball1 = bodies.insert(
RigidBodyBuilder::new_dynamic()
.translation(origin.coords + shift)
.linvel(vector![20.0, 20.0, 0.0])
.build(),
);
colliders.insert_with_parent(
ColliderBuilder::cuboid(1.0, 1.0, 1.0).build(),
ball1,
bodies,
);
let ball2 = bodies.insert(
RigidBodyBuilder::new_dynamic()
.translation(origin.coords + shift * 2.0)
.build(),
);
colliders.insert_with_parent(
ColliderBuilder::cuboid(1.0, 1.0, 1.0).build(),
ball2,
bodies,
);
let joint1 = SphericalJoint::new()
.local_anchor2(Point::from(-shift))
.limit_axis(JointAxis::X, [-0.2, 0.2])
.limit_axis(JointAxis::Y, [-0.2, 0.2]);
let joint2 = SphericalJoint::new()
.local_anchor2(Point::from(-shift))
.limit_axis(JointAxis::X, [-0.3, 0.3])
.limit_axis(JointAxis::Y, [-0.3, 0.3]);
if use_articulations {
multibody_joints.insert(ground, ball1, joint1);
multibody_joints.insert(ball1, ball2, joint2);
} else {
impulse_joints.insert(ground, ball1, joint1);
impulse_joints.insert(ball1, ball2, joint2);
}
}
fn create_actuated_revolute_joints(
bodies: &mut RigidBodySet,
colliders: &mut ColliderSet,
impulse_joints: &mut ImpulseJointSet,
multibody_joints: &mut MultibodyJointSet,
origin: Point<f32>,
num: usize,
use_articulations: bool,
) {
let rad = 0.4;
let shift = 2.0;
// We will reuse this base configuration for all the impulse_joints here.
let z = Vector::z_axis();
let joint_template = RevoluteJoint::new(z).local_anchor2(point![0.0, 0.0, -shift]);
let mut parent_handle = RigidBodyHandle::invalid();
for i in 0..num {
let fi = i as f32;
// NOTE: the num - 2 test is to avoid two consecutive
// fixed bodies. Because physx will crash if we add
// a joint between these.
let status = if i == 0 {
RigidBodyType::Static
} else {
RigidBodyType::Dynamic
};
let shifty = (i >= 1) as u32 as f32 * -2.0;
let rigid_body = RigidBodyBuilder::new(status)
.translation(vector![origin.x, origin.y + shifty, origin.z + fi * shift])
// .rotation(Vector3::new(0.0, fi * 1.1, 0.0))
.build();
let child_handle = bodies.insert(rigid_body);
let collider = ColliderBuilder::cuboid(rad * 2.0, rad * 6.0 / (fi + 1.0), rad).build();
colliders.insert_with_parent(collider, child_handle, bodies);
if i > 0 {
let mut joint = joint_template.clone();
if i % 3 == 1 {
joint = joint.motor_velocity(-20.0, 0.1);
} else if i == num - 1 {
let stiffness = 0.2;
let damping = 1.0;
joint = joint.motor_position(3.14 / 2.0, stiffness, damping);
}
if i == 1 {
joint = joint
.local_anchor2(point![0.0, 2.0, -shift])
.motor_velocity(-2.0, 0.1);
}
if use_articulations {
multibody_joints.insert(parent_handle, child_handle, joint);
} else {
impulse_joints.insert(parent_handle, child_handle, joint);
}
}
parent_handle = child_handle;
}
}
fn create_actuated_spherical_joints(
bodies: &mut RigidBodySet,
colliders: &mut ColliderSet,
impulse_joints: &mut ImpulseJointSet,
multibody_joints: &mut MultibodyJointSet,
origin: Point<f32>,
num: usize,
use_articulations: bool,
) {
let rad = 0.4;
let shift = 2.0;
// We will reuse this base configuration for all the impulse_joints here.
let joint_template = SphericalJoint::new().local_anchor1(point![0.0, 0.0, shift]);
let mut parent_handle = RigidBodyHandle::invalid();
for i in 0..num {
let fi = i as f32;
// NOTE: the num - 2 test is to avoid two consecutive
// fixed bodies. Because physx will crash if we add
// a joint between these.
let status = if i == 0 {
RigidBodyType::Static
} else {
RigidBodyType::Dynamic
};
let rigid_body = RigidBodyBuilder::new(status)
.translation(vector![origin.x, origin.y, origin.z + fi * shift])
// .rotation(Vector3::new(0.0, fi * 1.1, 0.0))
.build();
let child_handle = bodies.insert(rigid_body);
let collider = ColliderBuilder::capsule_y(rad * 2.0 / (fi + 1.0), rad).build();
colliders.insert_with_parent(collider, child_handle, bodies);
if i > 0 {
let mut joint = joint_template.clone();
if i == 1 {
joint = joint
.motor_velocity(JointAxis::AngX, 0.0, 0.1)
.motor_velocity(JointAxis::AngY, 0.5, 0.1)
.motor_velocity(JointAxis::AngZ, -2.0, 0.1);
} else if i == num - 1 {
let stiffness = 0.2;
let damping = 1.0;
joint = joint
.motor_position(JointAxis::AngX, 0.0, stiffness, damping)
.motor_position(JointAxis::AngY, 1.0, stiffness, damping)
.motor_position(JointAxis::AngZ, 3.14 / 2.0, stiffness, damping);
}
if use_articulations {
multibody_joints.insert(parent_handle, child_handle, joint);
} else {
impulse_joints.insert(parent_handle, child_handle, joint);
}
}
parent_handle = child_handle;
}
}
fn do_init_world(testbed: &mut Testbed, use_articulations: bool) {
/*
* World
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let mut impulse_joints = ImpulseJointSet::new();
let mut multibody_joints = MultibodyJointSet::new();
create_prismatic_joints(
&mut bodies,
&mut colliders,
&mut impulse_joints,
&mut multibody_joints,
point![20.0, 5.0, 0.0],
4,
use_articulations,
);
create_actuated_prismatic_joints(
&mut bodies,
&mut colliders,
&mut impulse_joints,
&mut multibody_joints,
point![25.0, 5.0, 0.0],
4,
use_articulations,
);
create_revolute_joints(
&mut bodies,
&mut colliders,
&mut impulse_joints,
&mut multibody_joints,
point![20.0, 0.0, 0.0],
3,
use_articulations,
);
create_revolute_joints_with_limits(
&mut bodies,
&mut colliders,
&mut impulse_joints,
&mut multibody_joints,
point![34.0, 0.0, 0.0],
use_articulations,
);
create_fixed_joints(
&mut bodies,
&mut colliders,
&mut impulse_joints,
&mut multibody_joints,
point![0.0, 10.0, 0.0],
10,
use_articulations,
);
create_actuated_revolute_joints(
&mut bodies,
&mut colliders,
&mut impulse_joints,
&mut multibody_joints,
point![20.0, 10.0, 0.0],
6,
use_articulations,
);
create_actuated_spherical_joints(
&mut bodies,
&mut colliders,
&mut impulse_joints,
&mut multibody_joints,
point![13.0, 10.0, 0.0],
3,
use_articulations,
);
create_spherical_joints(
&mut bodies,
&mut colliders,
&mut impulse_joints,
&mut multibody_joints,
15,
use_articulations,
);
create_spherical_joints_with_limits(
&mut bodies,
&mut colliders,
&mut impulse_joints,
&mut multibody_joints,
point![-5.0, 0.0, 0.0],
use_articulations,
);
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![15.0, 5.0, 42.0], point![13.0, 1.0, 1.0]);
}
pub fn init_world_with_joints(testbed: &mut Testbed) {
do_init_world(testbed, false)
}
pub fn init_world_with_articulations(testbed: &mut Testbed) {
do_init_world(testbed, true)
}

View File

@@ -44,7 +44,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -153,6 +154,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -93,6 +94,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point!(10.0, 10.0, 10.0), Point::origin());
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -90,6 +91,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

View File

@@ -15,7 +15,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -52,7 +53,6 @@ pub fn init_world(testbed: &mut Testbed) {
.iter()
.map(|v| point![v.0, v.1, v.2])
.collect();
use std::iter::FromIterator;
let indices: Vec<_> = model
.polygons
.into_iter()
@@ -104,7 +104,7 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

View File

@@ -9,7 +9,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -68,6 +69,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![30.0, 30.0, 30.0], Point::origin());
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Create the cubes
@@ -38,6 +39,13 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world_with_params(bodies, colliders, joints, Vector::zeros(), ());
testbed.set_world_with_params(
bodies,
colliders,
impulse_joints,
multibody_joints,
Vector::zeros(),
(),
);
testbed.look_at(point![2.0, 2.5, 20.0], point![2.0, 2.5, 0.0]);
}

View File

@@ -7,7 +7,9 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground.
*/
@@ -54,6 +56,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![10.0, 10.0, 10.0], Point::origin());
}

View File

@@ -0,0 +1,98 @@
use rapier3d::prelude::*;
use rapier_testbed3d::Testbed;
fn create_ball_articulations(
bodies: &mut RigidBodySet,
colliders: &mut ColliderSet,
impulse_joints: &mut ImpulseJointSet,
multibody_joints: &mut MultibodyJointSet,
num: usize,
) {
let rad = 0.4;
let shift = 1.0;
let mut body_handles = Vec::new();
for k in 0..num {
for i in 0..num {
let fk = k as f32;
let fi = i as f32;
let status = if i == 0 {
// && (k % 4 == 0 || k == num - 1) {
RigidBodyType::Static
} else {
RigidBodyType::Dynamic
};
let rigid_body = RigidBodyBuilder::new(status)
.translation(vector![fk * shift, 0.0, fi * shift * 2.0])
.build();
let child_handle = bodies.insert(rigid_body);
let collider = ColliderBuilder::capsule_z(rad * 1.25, rad).build();
colliders.insert_with_parent(collider, child_handle, bodies);
// Vertical multibody_joint.
if i > 0 {
let parent_handle = *body_handles.last().unwrap();
let joint = SphericalJoint::new().local_anchor2(point![0.0, 0.0, -shift * 2.0]);
multibody_joints.insert(parent_handle, child_handle, joint);
}
// Horizontal multibody_joint.
if k > 0 && i > 0 {
let parent_index = body_handles.len() - num;
let parent_handle = body_handles[parent_index];
let joint = SphericalJoint::new().local_anchor2(point![-shift, 0.0, 0.0]);
// let joint =
// PrismaticJoint::new(Vector::y_axis()).local_anchor2(point![-shift, 0.0, 0.0]);
// let joint = FixedJoint::new().local_anchor2(point![-shift, 0.0, 0.0]);
// let joint =
// RevoluteJoint::new(Vector::x_axis()).local_anchor2(point![-shift, 0.0, 0.0]);
impulse_joints.insert(parent_handle, child_handle, joint);
}
body_handles.push(child_handle);
}
}
}
pub fn init_world(testbed: &mut Testbed) {
/*
* World
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let mut impulse_joints = ImpulseJointSet::new();
let mut multibody_joints = MultibodyJointSet::new();
let rigid_body = RigidBodyBuilder::new_dynamic().build();
let collider = ColliderBuilder::cuboid(30.0, 0.01, 30.0) // Vector::y_axis())
.translation(vector![0.0, -3.0, 0.0])
.rotation(vector![0.1, 0.0, 0.1])
.build();
let handle = bodies.insert(rigid_body);
colliders.insert_with_parent(collider, handle, &mut bodies);
let rigid_body = RigidBodyBuilder::new_static().build();
let collider = ColliderBuilder::cuboid(30.0, 0.01, 30.0) // Vector::y_axis())
.translation(vector![0.0, -3.02, 0.0])
.rotation(vector![0.1, 0.0, 0.1])
.build();
let handle = bodies.insert(rigid_body);
colliders.insert_with_parent(collider, handle, &mut bodies);
create_ball_articulations(
&mut bodies,
&mut colliders,
&mut impulse_joints,
&mut multibody_joints,
15,
);
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![15.0, 5.0, 42.0], point![13.0, 1.0, 1.0]);
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -38,6 +39,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![10.0, 10.0, 10.0], Point::origin());
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -25,10 +26,10 @@ pub fn init_world(testbed: &mut Testbed) {
}
// Build the dynamic box rigid body.
for _ in 0..6 {
for _ in 0..2 {
let rigid_body = RigidBodyBuilder::new_dynamic()
.translation(vector![1.1, 0.0, 0.0])
.rotation(vector![0.8, 0.2, 0.1])
// .rotation(vector![0.8, 0.2, 0.1])
.can_sleep(false)
.build();
let handle = bodies.insert(rigid_body);
@@ -39,6 +40,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![10.0, 10.0, 10.0], Point::origin());
}

View File

@@ -10,7 +10,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -55,6 +56,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

View File

@@ -7,7 +7,9 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground.
*/
@@ -114,6 +116,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![10.0, 10.0, 10.0], Point::origin());
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -38,6 +39,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -44,5 +45,5 @@ pub fn init_world(testbed: &mut Testbed) {
* Set up the testbed.
*/
testbed.look_at(point![100.0, -10.0, 100.0], Point::origin());
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
}

View File

@@ -4,7 +4,7 @@ use rapier_testbed3d::Testbed;
fn prismatic_repro(
bodies: &mut RigidBodySet,
colliders: &mut ColliderSet,
joints: &mut JointSet,
impulse_joints: &mut ImpulseJointSet,
box_center: Point<f32>,
) {
let box_rb = bodies.insert(
@@ -39,19 +39,12 @@ fn prismatic_repro(
);
colliders.insert_with_parent(ColliderBuilder::ball(0.5).build(), wheel_rb, bodies);
let mut prismatic = rapier3d::dynamics::PrismaticJoint::new(
point![pos.x, pos.y, pos.z],
Vector::y_axis(),
Vector::zeros(),
Point::origin(),
Vector::y_axis(),
Vector::default(),
);
prismatic.configure_motor_model(rapier3d::dynamics::SpringModel::VelocityBased);
let (stiffness, damping) = (0.05, 0.2);
prismatic.configure_motor_position(0.0, stiffness, damping);
joints.insert(box_rb, wheel_rb, prismatic);
let prismatic = PrismaticJoint::new(Vector::y_axis())
.local_anchor1(point![pos.x, pos.y, pos.z])
.motor_position(0.0, stiffness, damping);
impulse_joints.insert(box_rb, wheel_rb, prismatic);
}
// put a small box under one of the wheels
@@ -73,7 +66,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let mut joints = JointSet::new();
let mut impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -91,13 +85,13 @@ pub fn init_world(testbed: &mut Testbed) {
prismatic_repro(
&mut bodies,
&mut colliders,
&mut joints,
&mut impulse_joints,
point![0.0, 5.0, 0.0],
);
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![10.0, 10.0, 10.0], Point::origin());
}

View File

@@ -7,7 +7,9 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground.
*/
@@ -65,6 +67,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![10.0, 10.0, 10.0], Point::origin());
}

View File

@@ -7,7 +7,9 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground.
*/
@@ -113,6 +115,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![10.0, 10.0, 10.0], Point::origin());
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
// Triangle ground.
let vtx = [
@@ -36,6 +37,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![10.0, 10.0, 10.0], Point::origin());
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
// Triangle ground.
let width = 0.5;
@@ -57,6 +58,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![10.0, 10.0, 10.0], Point::origin());
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -73,6 +74,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

View File

@@ -6,7 +6,9 @@ const MAX_NUMBER_OF_BODIES: usize = 400;
pub fn init_world(testbed: &mut Testbed) {
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
let rad = 0.5;
/*
@@ -63,7 +65,8 @@ pub fn init_world(testbed: &mut Testbed) {
*handle,
&mut physics.islands,
&mut physics.colliders,
&mut physics.joints,
&mut physics.impulse_joints,
&mut physics.multibody_joints,
);
if let Some(graphics) = &mut graphics {
@@ -76,10 +79,10 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
// testbed
// .physics_state_mut()
// .integration_parameters
// .velocity_based_erp = 0.2;
// .erp = 0.2;
testbed.look_at(point![-30.0, 4.0, -30.0], point![0.0, 1.0, 0.0]);
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(harness: &mut Harness) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -59,7 +60,7 @@ pub fn init_world(harness: &mut Harness) {
/*
* Set up the harness.
*/
harness.set_world(bodies, colliders, joints);
harness.set_world(bodies, colliders, impulse_joints, multibody_joints);
}
fn main() {

View File

@@ -8,7 +8,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -95,6 +96,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

View File

@@ -4,7 +4,7 @@ use rapier_testbed3d::Testbed;
fn create_prismatic_joints(
bodies: &mut RigidBodySet,
colliders: &mut ColliderSet,
joints: &mut JointSet,
impulse_joints: &mut ImpulseJointSet,
origin: Point<f32>,
num: usize,
) {
@@ -28,25 +28,17 @@ fn create_prismatic_joints(
colliders.insert_with_parent(collider, curr_child, bodies);
let axis = if i % 2 == 0 {
UnitVector::new_normalize(vector![1.0, 1.0, 0.0])
UnitVector::new_normalize(vector![1.0f32, 1.0, 0.0])
} else {
UnitVector::new_normalize(vector![-1.0, 1.0, 0.0])
UnitVector::new_normalize(vector![-1.0f32, 1.0, 0.0])
};
let z = Vector::z();
let mut prism = PrismaticJoint::new(
point![0.0, 0.0, 0.0],
axis,
z,
point![0.0, 0.0, -shift],
axis,
z,
);
prism.limits_enabled = true;
prism.limits[0] = -2.0;
prism.limits[1] = 2.0;
let mut prism = JointData::prismatic(axis)
.local_anchor1(point![0.0, 0.0, shift])
.local_anchor2(point![0.0, 0.0, 0.0])
.limit_axis(JointAxis::X, [-2.0, 2.0]);
joints.insert(curr_parent, curr_child, prism);
impulse_joints.insert(curr_parent, curr_child, prism);
curr_parent = curr_child;
}
@@ -55,7 +47,7 @@ fn create_prismatic_joints(
fn create_actuated_prismatic_joints(
bodies: &mut RigidBodySet,
colliders: &mut ColliderSet,
joints: &mut JointSet,
impulse_joints: &mut ImpulseJointSet,
origin: Point<f32>,
num: usize,
) {
@@ -84,36 +76,29 @@ fn create_actuated_prismatic_joints(
UnitVector::new_normalize(vector![-1.0, 1.0, 0.0])
};
let z = Vector::z();
let mut prism = PrismaticJoint::new(
point![0.0, 0.0, 0.0],
axis,
z,
point![0.0, 0.0, -shift],
axis,
z,
);
let mut prism = JointData::prismatic(axis)
.local_anchor1(point![0.0, 0.0, 0.0])
.local_anchor2(point![0.0, 0.0, -shift]);
if i == 1 {
prism.configure_motor_velocity(1.0, 1.0);
prism.limits_enabled = true;
prism.limits[1] = 5.0;
// We set a max impulse so that the motor doesn't fight
// the limits with large forces.
prism.motor_max_impulse = 1.0;
prism = prism
.limit_axis(JointAxis::X, [-Real::MAX, 5.0])
.motor_velocity(JointAxis::X, 1.0, 1.0)
// We set a max impulse so that the motor doesn't fight
// the limits with large forces.
.motor_max_impulse(JointAxis::X, 1.0);
} else if i > 1 {
prism.configure_motor_position(2.0, 0.01, 1.0);
prism = prism.motor_position(JointAxis::X, 2.0, 0.01, 1.0);
} else {
prism.configure_motor_velocity(1.0, 1.0);
// We set a max impulse so that the motor doesn't fight
// the limits with large forces.
prism.motor_max_impulse = 0.7;
prism.limits_enabled = true;
prism.limits[0] = -2.0;
prism.limits[1] = 5.0;
prism = prism
.motor_velocity(JointAxis::X, 1.0, 1.0)
// We set a max impulse so that the motor doesn't fight
// the limits with large forces.
.motor_max_impulse(JointAxis::X, 0.7)
.limit_axis(JointAxis::X, [-2.0, 5.0]);
}
joints.insert(curr_parent, curr_child, prism);
impulse_joints.insert(curr_parent, curr_child, prism);
curr_parent = curr_child;
}
@@ -122,7 +107,7 @@ fn create_actuated_prismatic_joints(
fn create_revolute_joints(
bodies: &mut RigidBodySet,
colliders: &mut ColliderSet,
joints: &mut JointSet,
impulse_joints: &mut ImpulseJointSet,
origin: Point<f32>,
num: usize,
) {
@@ -156,22 +141,20 @@ fn create_revolute_joints(
colliders.insert_with_parent(collider, handles[k], bodies);
}
// Setup four joints.
let o = Point::origin();
// Setup four impulse_joints.
let x = Vector::x_axis();
let z = Vector::z_axis();
let revs = [
RevoluteJoint::new(o, z, point![0.0, 0.0, -shift], z),
RevoluteJoint::new(o, x, point![-shift, 0.0, 0.0], x),
RevoluteJoint::new(o, z, point![0.0, 0.0, -shift], z),
RevoluteJoint::new(o, x, point![shift, 0.0, 0.0], x),
RevoluteJoint::new(x).local_anchor2(point![0.0, 0.0, -shift]),
RevoluteJoint::new(z).local_anchor2(point![-shift, 0.0, 0.0]),
RevoluteJoint::new(x).local_anchor2(point![0.0, 0.0, -shift]),
RevoluteJoint::new(z).local_anchor2(point![shift, 0.0, 0.0]),
];
joints.insert(curr_parent, handles[0], revs[0]);
joints.insert(handles[0], handles[1], revs[1]);
joints.insert(handles[1], handles[2], revs[2]);
joints.insert(handles[2], handles[3], revs[3]);
impulse_joints.insert(curr_parent, handles[0], revs[0]);
impulse_joints.insert(handles[0], handles[1], revs[1]);
impulse_joints.insert(handles[1], handles[2], revs[2]);
impulse_joints.insert(handles[2], handles[3], revs[3]);
curr_parent = handles[3];
}
@@ -180,7 +163,7 @@ fn create_revolute_joints(
fn create_revolute_joints_with_limits(
bodies: &mut RigidBodySet,
colliders: &mut ColliderSet,
joints: &mut JointSet,
impulse_joints: &mut ImpulseJointSet,
origin: Point<f32>,
) {
let ground = bodies.insert(
@@ -212,25 +195,14 @@ fn create_revolute_joints_with_limits(
bodies,
);
let mut joint1 = RevoluteJoint::new(
Point::origin(),
Vector::z_axis(),
Point::origin(),
Vector::z_axis(),
);
joint1.limits_enabled = true;
joint1.limits = [-0.2, 0.2];
joints.insert(ground, platform1, joint1);
let z = Vector::z_axis();
let mut joint1 = RevoluteJoint::new(z).limit_axis(JointAxis::X, [-0.2, 0.2]);
impulse_joints.insert(ground, platform1, joint1);
let mut joint2 = RevoluteJoint::new(
Point::origin(),
Vector::z_axis(),
Point::from(-shift),
Vector::z_axis(),
);
joint2.limits_enabled = true;
joint2.limits = [-0.3, 0.3];
joints.insert(platform1, platform2, joint2);
let mut joint2 = RevoluteJoint::new(z)
.local_anchor2(shift.into())
.limit_axis(JointAxis::Z, [-0.2, 0.2]);
impulse_joints.insert(platform1, platform2, joint2);
// Lets add a couple of cuboids that will fall on the platforms, triggering the joint limits.
let cuboid_body1 = bodies.insert(
@@ -259,7 +231,7 @@ fn create_revolute_joints_with_limits(
fn create_fixed_joints(
bodies: &mut RigidBodySet,
colliders: &mut ColliderSet,
joints: &mut JointSet,
impulse_joints: &mut ImpulseJointSet,
origin: Point<f32>,
num: usize,
) {
@@ -268,8 +240,8 @@ fn create_fixed_joints(
let mut body_handles = Vec::new();
for k in 0..num {
for i in 0..num {
for i in 0..num {
for k in 0..num {
let fk = k as f32;
let fi = i as f32;
@@ -295,23 +267,18 @@ fn create_fixed_joints(
// Vertical joint.
if i > 0 {
let parent_handle = *body_handles.last().unwrap();
let joint = FixedJoint::new(
Isometry::identity(),
Isometry::translation(0.0, 0.0, -shift),
);
joints.insert(parent_handle, child_handle, joint);
let parent_index = body_handles.len() - num;
let parent_handle = body_handles[parent_index];
let joint = JointData::fixed().local_anchor2(point![0.0, 0.0, -shift]);
impulse_joints.insert(parent_handle, child_handle, joint);
}
// Horizontal joint.
if k > 0 {
let parent_index = body_handles.len() - num;
let parent_index = body_handles.len() - 1;
let parent_handle = body_handles[parent_index];
let joint = FixedJoint::new(
Isometry::identity(),
Isometry::translation(-shift, 0.0, 0.0),
);
joints.insert(parent_handle, child_handle, joint);
let joint = JointData::fixed().local_anchor2(point![-shift, 0.0, 0.0]);
impulse_joints.insert(parent_handle, child_handle, joint);
}
body_handles.push(child_handle);
@@ -322,7 +289,7 @@ fn create_fixed_joints(
fn create_ball_joints(
bodies: &mut RigidBodySet,
colliders: &mut ColliderSet,
joints: &mut JointSet,
impulse_joints: &mut ImpulseJointSet,
num: usize,
) {
let rad = 0.4;
@@ -351,16 +318,16 @@ fn create_ball_joints(
// Vertical joint.
if i > 0 {
let parent_handle = *body_handles.last().unwrap();
let joint = BallJoint::new(Point::origin(), point![0.0, 0.0, -shift * 2.0]);
joints.insert(parent_handle, child_handle, joint);
let joint = JointData::ball().local_anchor2(point![0.0, 0.0, -shift * 2.0]);
impulse_joints.insert(parent_handle, child_handle, joint);
}
// Horizontal joint.
if k > 0 {
let parent_index = body_handles.len() - num;
let parent_handle = body_handles[parent_index];
let joint = BallJoint::new(Point::origin(), point![-shift, 0.0, 0.0]);
joints.insert(parent_handle, child_handle, joint);
let joint = JointData::ball().local_anchor2(point![-shift, 0.0, 0.0]);
impulse_joints.insert(parent_handle, child_handle, joint);
}
body_handles.push(child_handle);
@@ -371,7 +338,7 @@ fn create_ball_joints(
fn create_ball_joints_with_limits(
bodies: &mut RigidBodySet,
colliders: &mut ColliderSet,
joints: &mut JointSet,
impulse_joints: &mut ImpulseJointSet,
origin: Point<f32>,
) {
let shift = vector![0.0, 0.0, 3.0];
@@ -405,38 +372,32 @@ fn create_ball_joints_with_limits(
bodies,
);
let mut joint1 = BallJoint::new(Point::origin(), Point::from(-shift));
joint1.limits_enabled = true;
joint1.limits_local_axis1 = Vector::z_axis();
joint1.limits_local_axis2 = Vector::z_axis();
joint1.limits_angle = 0.2;
joints.insert(ground, ball1, joint1);
let mut joint1 = JointData::ball()
.local_anchor2(Point::from(-shift))
.limit_axis(JointAxis::X, [-0.2, 0.2])
.limit_axis(JointAxis::Y, [-0.2, 0.2]);
impulse_joints.insert(ground, ball1, joint1);
let mut joint2 = BallJoint::new(Point::origin(), Point::from(-shift));
joint2.limits_enabled = true;
joint2.limits_local_axis1 = Vector::z_axis();
joint2.limits_local_axis2 = Vector::z_axis();
joint2.limits_angle = 0.3;
joints.insert(ball1, ball2, joint2);
let mut joint2 = JointData::ball()
.local_anchor2(Point::from(-shift))
.limit_axis(JointAxis::X, [-0.3, 0.3])
.limit_axis(JointAxis::Y, [-0.3, 0.3]);
impulse_joints.insert(ball1, ball2, joint2);
}
fn create_actuated_revolute_joints(
bodies: &mut RigidBodySet,
colliders: &mut ColliderSet,
joints: &mut JointSet,
impulse_joints: &mut ImpulseJointSet,
origin: Point<f32>,
num: usize,
) {
let rad = 0.4;
let shift = 2.0;
// We will reuse this base configuration for all the joints here.
let joint_template = RevoluteJoint::new(
Point::origin(),
Vector::z_axis(),
point![0.0, 0.0, -shift],
Vector::z_axis(),
);
// We will reuse this base configuration for all the impulse_joints here.
let z = Vector::z_axis();
let joint_template = RevoluteJoint::new(z).local_anchor2(point![0.0, 0.0, -shift]);
let mut parent_handle = RigidBodyHandle::invalid();
@@ -467,19 +428,19 @@ fn create_actuated_revolute_joints(
let mut joint = joint_template.clone();
if i % 3 == 1 {
joint.configure_motor_velocity(-20.0, 0.1);
joint = joint.motor_velocity(JointAxis::AngX, -20.0, 0.1);
} else if i == num - 1 {
let stiffness = 0.2;
let damping = 1.0;
joint.configure_motor_position(3.14 / 2.0, stiffness, damping);
joint = joint.motor_position(JointAxis::AngX, 3.14 / 2.0, stiffness, damping);
}
if i == 1 {
joint.local_anchor2.y = 2.0;
joint.configure_motor_velocity(-2.0, 0.1);
joint.local_frame2.translation.vector.y = 2.0;
joint = joint.motor_velocity(JointAxis::AngX, -2.0, 0.1);
}
joints.insert(parent_handle, child_handle, joint);
impulse_joints.insert(parent_handle, child_handle, joint);
}
parent_handle = child_handle;
@@ -489,15 +450,15 @@ fn create_actuated_revolute_joints(
fn create_actuated_ball_joints(
bodies: &mut RigidBodySet,
colliders: &mut ColliderSet,
joints: &mut JointSet,
impulse_joints: &mut ImpulseJointSet,
origin: Point<f32>,
num: usize,
) {
let rad = 0.4;
let shift = 2.0;
// We will reuse this base configuration for all the joints here.
let joint_template = BallJoint::new(point![0.0, 0.0, shift], Point::origin());
// We will reuse this base configuration for all the impulse_joints here.
let joint_template = JointData::ball().local_anchor1(point![0.0, 0.0, shift]);
let mut parent_handle = RigidBodyHandle::invalid();
@@ -526,18 +487,20 @@ fn create_actuated_ball_joints(
let mut joint = joint_template.clone();
if i == 1 {
joint.configure_motor_velocity(vector![0.0, 0.5, -2.0], 0.1);
joint = joint
.motor_velocity(JointAxis::AngX, 0.0, 0.1)
.motor_velocity(JointAxis::AngY, 0.5, 0.1)
.motor_velocity(JointAxis::AngZ, -2.0, 0.1);
} else if i == num - 1 {
let stiffness = 0.2;
let damping = 1.0;
joint.configure_motor_position(
Rotation::new(vector![0.0, 1.0, 3.14 / 2.0]),
stiffness,
damping,
);
joint = joint
.motor_position(JointAxis::AngX, 0.0, stiffness, damping)
.motor_position(JointAxis::AngY, 1.0, stiffness, damping)
.motor_position(JointAxis::AngZ, 3.14 / 2.0, stiffness, damping);
}
joints.insert(parent_handle, child_handle, joint);
impulse_joints.insert(parent_handle, child_handle, joint);
}
parent_handle = child_handle;
@@ -550,67 +513,68 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let mut joints = JointSet::new();
let mut impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
create_prismatic_joints(
&mut bodies,
&mut colliders,
&mut joints,
&mut impulse_joints,
point![20.0, 5.0, 0.0],
4,
);
create_actuated_prismatic_joints(
&mut bodies,
&mut colliders,
&mut joints,
&mut impulse_joints,
point![25.0, 5.0, 0.0],
4,
);
create_revolute_joints(
&mut bodies,
&mut colliders,
&mut joints,
&mut impulse_joints,
point![20.0, 0.0, 0.0],
3,
);
create_revolute_joints_with_limits(
&mut bodies,
&mut colliders,
&mut joints,
&mut impulse_joints,
point![34.0, 0.0, 0.0],
);
create_fixed_joints(
&mut bodies,
&mut colliders,
&mut joints,
&mut impulse_joints,
point![0.0, 10.0, 0.0],
10,
);
create_actuated_revolute_joints(
&mut bodies,
&mut colliders,
&mut joints,
&mut impulse_joints,
point![20.0, 10.0, 0.0],
6,
);
create_actuated_ball_joints(
&mut bodies,
&mut colliders,
&mut joints,
&mut impulse_joints,
point![13.0, 10.0, 0.0],
3,
);
create_ball_joints(&mut bodies, &mut colliders, &mut joints, 15);
create_ball_joints(&mut bodies, &mut colliders, &mut impulse_joints, 15);
create_ball_joints_with_limits(
&mut bodies,
&mut colliders,
&mut joints,
&mut impulse_joints,
point![-5.0, 0.0, 0.0],
);
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![15.0, 5.0, 42.0], point![13.0, 1.0, 1.0]);
}

View File

@@ -83,7 +83,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -132,6 +133,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

View File

@@ -10,7 +10,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* The ground
@@ -54,6 +55,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![10.0, 3.0, 0.0], point![0.0, 3.0, 0.0]);
}

View File

@@ -62,7 +62,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -126,7 +127,8 @@ pub fn init_world(testbed: &mut Testbed) {
testbed.set_world_with_params(
bodies,
colliders,
joints,
impulse_joints,
multibody_joints,
vector![0.0, -9.81, 0.0],
physics_hooks,
);

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground.
@@ -103,6 +104,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Run the simulation.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![-10.0, 5.0, -10.0], Point::origin());
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -51,13 +52,13 @@ pub fn init_world(testbed: &mut Testbed) {
let handle = bodies.insert(rigid_body);
let collider = match j % 5 {
0 => ColliderBuilder::cuboid(rad, rad, rad).build(),
1 => ColliderBuilder::ball(rad).build(),
// Rounded cylinders are much more efficient that cylinder, even if the
// rounding margin is small.
2 => ColliderBuilder::round_cylinder(rad, rad, rad / 10.0).build(),
3 => ColliderBuilder::cone(rad, rad).build(),
_ => ColliderBuilder::capsule_y(rad, rad).build(),
_ => ColliderBuilder::cuboid(rad, rad, rad).build(),
// 1 => ColliderBuilder::ball(rad).build(),
// // Rounded cylinders are much more efficient that cylinder, even if the
// // rounding margin is small.
// 2 => ColliderBuilder::round_cylinder(rad, rad, rad / 10.0).build(),
// 3 => ColliderBuilder::cone(rad, rad).build(),
// _ => ColliderBuilder::capsule_y(rad, rad).build(),
};
colliders.insert_with_parent(collider, handle, &mut bodies);
@@ -70,6 +71,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

BIN
examples3d/rapier.data Normal file

Binary file not shown.

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -44,6 +45,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![0.0, 3.0, 30.0], point![0.0, 3.0, 0.0]);
}

View File

@@ -7,7 +7,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground.
@@ -102,6 +103,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![-6.0, 4.0, -6.0], point![0.0, 1.0, 0.0]);
}

View File

@@ -8,7 +8,8 @@ pub fn init_world(testbed: &mut Testbed) {
*/
let mut bodies = RigidBodySet::new();
let mut colliders = ColliderSet::new();
let joints = JointSet::new();
let impulse_joints = ImpulseJointSet::new();
let multibody_joints = MultibodyJointSet::new();
/*
* Ground
@@ -100,6 +101,6 @@ pub fn init_world(testbed: &mut Testbed) {
/*
* Set up the testbed.
*/
testbed.set_world(bodies, colliders, joints);
testbed.set_world(bodies, colliders, impulse_joints, multibody_joints);
testbed.look_at(point![100.0, 100.0, 100.0], Point::origin());
}

View File

@@ -6,20 +6,20 @@ echo "$tmp"
cp -r src "$tmp"/.
cp -r src_testbed "$tmp"/.
cp -r build "$tmp"/.
cp -r crates "$tmp"/.
cp -r LICENSE README.md "$tmp"/.
### Publish the 2D version.
sed 's#\.\./\.\./src#src#g' build/rapier_testbed2d/Cargo.toml > "$tmp"/Cargo.toml
sed -i 's#\.\./rapier#./build/rapier#g' "$tmp"/Cargo.toml
sed 's#\.\./\.\./src#src#g' crates/rapier_testbed2d/Cargo.toml > "$tmp"/Cargo.toml
sed -i 's#\.\./rapier#./crates/rapier#g' "$tmp"/Cargo.toml
currdir=$(pwd)
cd "$tmp" && cargo publish
cd "$currdir" || exit
### Publish the 3D version.
sed 's#\.\./\.\./src#src#g' build/rapier_testbed3d/Cargo.toml > "$tmp"/Cargo.toml
sed -i 's#\.\./rapier#./build/rapier#g' "$tmp"/Cargo.toml
sed 's#\.\./\.\./src#src#g' crates/rapier_testbed3d/Cargo.toml > "$tmp"/Cargo.toml
sed -i 's#\.\./rapier#./crates/rapier#g' "$tmp"/Cargo.toml
cp -r LICENSE README.md "$tmp"/.
cd "$tmp" && cargo publish

View File

@@ -14,7 +14,7 @@ mod solver_counters;
mod stages_counters;
mod timer;
/// Aggregation of all the performances counters tracked by nphysics.
/// Aggregation of all the performances counters tracked by rapier.
#[derive(Clone, Copy)]
pub struct Counters {
/// Whether thi counter is enabled or not.
@@ -34,7 +34,7 @@ pub struct Counters {
}
impl Counters {
/// Create a new set of counters initialized to wero.
/// Create a new set of counters initialized to zero.
pub fn new(enabled: bool) -> Self {
Counters {
enabled,

View File

@@ -13,6 +13,14 @@ impl<T> Coarena<T> {
Self { data: Vec::new() }
}
pub fn iter(&self) -> impl Iterator<Item = (Index, &T)> {
self.data
.iter()
.enumerate()
.filter(|(_, elt)| elt.0 != u32::MAX)
.map(|(i, elt)| (Index::from_raw_parts(i as u32, elt.0), &elt.1))
}
/// Gets a specific element from the coarena without specifying its generation number.
///
/// It is strongly encouraged to use `Coarena::get` instead of this method because this method
@@ -23,12 +31,12 @@ impl<T> Coarena<T> {
/// Deletes an element for the coarena and returns its value.
///
/// We can't really remove an element from the coarena. So instead of actually removing
/// it, this method will reset the value to the given `removed_value`.
/// This method will reset the value to the given `removed_value`.
pub fn remove(&mut self, index: Index, removed_value: T) -> Option<T> {
let (i, g) = index.into_raw_parts();
let data = self.data.get_mut(i as usize)?;
if g == data.0 {
data.0 = u32::MAX; // invalidate the generation number.
Some(std::mem::replace(&mut data.1, removed_value))
} else {
None

View File

@@ -644,19 +644,24 @@ impl<'a, E> Iterator for Edges<'a, E> {
// For iterate_over, "both" is represented as None.
// For reverse, "no" is represented as None.
let (iterate_over, reverse) = (None, Some(self.direction.opposite()));
let (iterate_over, _reverse) = (None, Some(self.direction.opposite()));
if iterate_over.unwrap_or(Direction::Outgoing) == Direction::Outgoing {
let i = self.next[0].index();
if let Some(Edge { node, weight, next }) = self.edges.get(i) {
if let Some(Edge {
node: _node,
weight,
next,
}) = self.edges.get(i)
{
self.next[0] = next[0];
return Some(EdgeReference {
index: EdgeIndex(i as u32),
node: if reverse == Some(Direction::Outgoing) {
swap_pair(*node)
} else {
*node
},
// node: if reverse == Some(Direction::Outgoing) {
// swap_pair(*node)
// } else {
// *node
// },
weight,
});
}
@@ -674,11 +679,11 @@ impl<'a, E> Iterator for Edges<'a, E> {
return Some(EdgeReference {
index: edge_index,
node: if reverse == Some(Direction::Incoming) {
swap_pair(*node)
} else {
*node
},
// node: if reverse == Some(Direction::Incoming) {
// swap_pair(*node)
// } else {
// *node
// },
weight,
});
}
@@ -688,10 +693,10 @@ impl<'a, E> Iterator for Edges<'a, E> {
}
}
fn swap_pair<T>(mut x: [T; 2]) -> [T; 2] {
x.swap(0, 1);
x
}
// fn swap_pair<T>(mut x: [T; 2]) -> [T; 2] {
// x.swap(0, 1);
// x
// }
impl<'a, E> Clone for Edges<'a, E> {
fn clone(&self) -> Self {
@@ -742,24 +747,11 @@ impl<N, E> IndexMut<EdgeIndex> for Graph<N, E> {
}
}
/// A “walker” object that can be used to step through the edge list of a node.
///
/// Created with [`.detach()`](struct.Neighbors.html#method.detach).
///
/// The walker does not borrow from the graph, so it lets you step through
/// neighbors or incident edges while also mutating graph weights, as
/// in the following example:
#[derive(Clone)]
pub struct WalkNeighbors {
skip_start: NodeIndex,
next: [EdgeIndex; 2],
}
/// Reference to a `Graph` edge.
#[derive(Debug)]
pub struct EdgeReference<'a, E: 'a> {
index: EdgeIndex,
node: [NodeIndex; 2],
// node: [NodeIndex; 2],
weight: &'a E,
}

View File

@@ -18,18 +18,6 @@ pub struct IntegrationParameters {
/// to numerical instabilities.
pub min_ccd_dt: Real,
/// The Error Reduction Parameter in `[0, 1]` is the proportion of
/// the positional error to be corrected at each time step (default: `0.2`).
pub erp: Real,
/// The Error Reduction Parameter for joints in `[0, 1]` is the proportion of
/// the positional error to be corrected at each time step (default: `0.2`).
pub joint_erp: Real,
/// Each cached impulse are multiplied by this coefficient in `[0, 1]`
/// when they are re-used to initialize the solver (default `1.0`).
pub warmstart_coeff: Real,
/// Correction factor to avoid large warmstart impulse after a strong impact (default `10.0`).
pub warmstart_correction_slope: Real,
/// 0-1: how much of the velocity to dampen out in the constraint solver?
/// (default `1.0`).
pub velocity_solve_fraction: Real,
@@ -40,23 +28,21 @@ pub struct IntegrationParameters {
/// If non-zero, you do not need the positional solver.
/// A good non-zero value is around `0.2`.
/// (default `0.0`).
pub velocity_based_erp: Real,
pub erp: Real,
/// Amount of penetration the engine wont attempt to correct (default: `0.005m`).
/// Amount of penetration the engine wont attempt to correct (default: `0.001m`).
pub allowed_linear_error: Real,
/// The maximal distance separating two objects that will generate predictive contacts (default: `0.002`).
pub prediction_distance: Real,
/// Amount of angular drift of joint limits the engine wont
/// attempt to correct (default: `0.001rad`).
pub allowed_angular_error: Real,
/// Maximum linear correction during one step of the non-linear position solver (default: `0.2`).
pub max_linear_correction: Real,
/// Maximum angular correction during one step of the non-linear position solver (default: `0.2`).
pub max_angular_correction: Real,
/// Maximum number of iterations performed by the velocity constraints solver (default: `4`).
/// Maximum number of iterations performed to solve non-penetration and joint constraints (default: `4`).
pub max_velocity_iterations: usize,
/// Maximum number of iterations performed by the position-based constraints solver (default: `1`).
pub max_position_iterations: usize,
/// Maximum number of iterations performed to solve friction constraints (default: `8`).
pub max_velocity_friction_iterations: usize,
/// Maximum number of iterations performed to remove the energy introduced by penetration corrections (default: `1`).
pub max_stabilization_iterations: usize,
/// If `false`, friction and non-penetration constraints will be solved in the same loop. Otherwise,
/// non-penetration constraints are solved first, and friction constraints are solved after (default: `true`).
pub interleave_restitution_and_friction_resolution: bool,
/// Minimum number of dynamic bodies in each active island (default: `128`).
pub min_island_size: usize,
/// Maximum number of substeps performed by the solver (default: `1`).
@@ -64,46 +50,6 @@ pub struct IntegrationParameters {
}
impl IntegrationParameters {
/// Creates a set of integration parameters with the given values.
#[deprecated = "Use `IntegrationParameters { dt: 60.0, ..Default::default() }` instead"]
pub fn new(
dt: Real,
erp: Real,
joint_erp: Real,
warmstart_coeff: Real,
allowed_linear_error: Real,
allowed_angular_error: Real,
max_linear_correction: Real,
max_angular_correction: Real,
prediction_distance: Real,
max_velocity_iterations: usize,
max_position_iterations: usize,
max_ccd_substeps: usize,
) -> Self {
IntegrationParameters {
dt,
erp,
joint_erp,
warmstart_coeff,
allowed_linear_error,
allowed_angular_error,
max_linear_correction,
max_angular_correction,
prediction_distance,
max_velocity_iterations,
max_position_iterations,
max_ccd_substeps,
..Default::default()
}
}
/// The current time-stepping length.
#[inline(always)]
#[deprecated = "You can just read the `IntegrationParams::dt` value directly"]
pub fn dt(&self) -> Real {
self.dt
}
/// The inverse of the time-stepping length, i.e. the steps per seconds (Hz).
///
/// This is zero if `self.dt` is zero.
@@ -136,10 +82,10 @@ impl IntegrationParameters {
}
}
/// Convenience: `velocity_based_erp / dt`
/// Convenience: `erp / dt`
#[inline]
pub(crate) fn velocity_based_erp_inv_dt(&self) -> Real {
self.velocity_based_erp * self.inv_dt()
pub(crate) fn erp_inv_dt(&self) -> Real {
self.erp * self.inv_dt()
}
}
@@ -148,20 +94,14 @@ impl Default for IntegrationParameters {
Self {
dt: 1.0 / 60.0,
min_ccd_dt: 1.0 / 60.0 / 100.0,
// multithreading_enabled: true,
erp: 0.2,
joint_erp: 0.2,
velocity_solve_fraction: 1.0,
velocity_based_erp: 0.0,
warmstart_coeff: 1.0,
warmstart_correction_slope: 10.0,
allowed_linear_error: 0.005,
erp: 0.8,
allowed_linear_error: 0.001, // 0.005
prediction_distance: 0.002,
allowed_angular_error: 0.001,
max_linear_correction: 0.2,
max_angular_correction: 0.2,
max_velocity_iterations: 4,
max_position_iterations: 1,
max_velocity_friction_iterations: 8,
max_stabilization_iterations: 1,
interleave_restitution_and_friction_resolution: true, // Enabling this makes a big difference for 2D stability.
// FIXME: what is the optimal value for min_island_size?
// It should not be too big so that we don't end up with
// huge islands that don't fit in cache.

View File

@@ -1,7 +1,7 @@
use crate::data::{BundleSet, ComponentSet, ComponentSetMut, ComponentSetOption};
use crate::dynamics::{
JointSet, RigidBodyActivation, RigidBodyColliders, RigidBodyHandle, RigidBodyIds,
RigidBodyType, RigidBodyVelocity,
ImpulseJointSet, MultibodyJointSet, RigidBodyActivation, RigidBodyColliders, RigidBodyHandle,
RigidBodyIds, RigidBodyType, RigidBodyVelocity,
};
use crate::geometry::{ColliderParent, NarrowPhase};
use crate::math::Real;
@@ -175,7 +175,8 @@ impl IslandManager {
bodies: &mut Bodies,
colliders: &Colliders,
narrow_phase: &NarrowPhase,
joints: &JointSet,
impulse_joints: &ImpulseJointSet,
multibody_joints: &MultibodyJointSet,
min_island_size: usize,
) where
Bodies: ComponentSetMut<RigidBodyIds>
@@ -302,11 +303,15 @@ impl IslandManager {
// in contact or joined with this collider.
push_contacting_bodies(rb_colliders, colliders, narrow_phase, &mut self.stack);
for inter in joints.joints_with(handle) {
for inter in impulse_joints.joints_with(handle) {
let other = crate::utils::select_other((inter.0, inter.1), handle);
self.stack.push(other);
}
for other in multibody_joints.attached_bodies(handle) {
self.stack.push(other);
}
bodies.map_mut_internal(handle.0, |activation: &mut RigidBodyActivation| {
activation.wake_up(false);
});

View File

@@ -1,148 +0,0 @@
use crate::dynamics::SpringModel;
use crate::math::{Point, Real, Rotation, UnitVector, Vector};
#[derive(Copy, Clone, PartialEq)]
#[cfg_attr(feature = "serde-serialize", derive(Serialize, Deserialize))]
/// A joint that removes all relative linear motion between a pair of points on two bodies.
pub struct BallJoint {
/// Where the ball joint is attached on the first body, expressed in the first body local frame.
pub local_anchor1: Point<Real>,
/// Where the ball joint is attached on the second body, expressed in the second body local frame.
pub local_anchor2: Point<Real>,
/// The impulse applied by this joint on the first body.
///
/// The impulse applied to the second body is given by `-impulse`.
pub impulse: Vector<Real>,
/// The target relative angular velocity the motor will attempt to reach.
#[cfg(feature = "dim2")]
pub motor_target_vel: Real,
/// The target relative angular velocity the motor will attempt to reach.
#[cfg(feature = "dim3")]
pub motor_target_vel: Vector<Real>,
/// The target angular position of this joint, expressed as an axis-angle.
pub motor_target_pos: Rotation<Real>,
/// The motor's stiffness.
/// See the documentation of `SpringModel` for more information on this parameter.
pub motor_stiffness: Real,
/// The motor's damping.
/// See the documentation of `SpringModel` for more information on this parameter.
pub motor_damping: Real,
/// The maximal impulse the motor is able to deliver.
pub motor_max_impulse: Real,
/// The angular impulse applied by the motor.
#[cfg(feature = "dim2")]
pub motor_impulse: Real,
/// The angular impulse applied by the motor.
#[cfg(feature = "dim3")]
pub motor_impulse: Vector<Real>,
/// The spring-like model used by the motor to reach the target velocity and .
pub motor_model: SpringModel,
/// Are the limits enabled for this joint?
pub limits_enabled: bool,
/// The axis of the limit cone for this joint, if the local-space of the first body.
pub limits_local_axis1: UnitVector<Real>,
/// The axis of the limit cone for this joint, if the local-space of the first body.
pub limits_local_axis2: UnitVector<Real>,
/// The maximum angle allowed between the two limit axes in world-space.
pub limits_angle: Real,
/// The impulse applied to enforce joint limits.
pub limits_impulse: Real,
}
impl BallJoint {
/// Creates a new Ball joint from two anchors given on the local spaces of the respective bodies.
pub fn new(local_anchor1: Point<Real>, local_anchor2: Point<Real>) -> Self {
Self::with_impulse(local_anchor1, local_anchor2, Vector::zeros())
}
pub(crate) fn with_impulse(
local_anchor1: Point<Real>,
local_anchor2: Point<Real>,
impulse: Vector<Real>,
) -> Self {
Self {
local_anchor1,
local_anchor2,
impulse,
motor_target_vel: na::zero(),
motor_target_pos: Rotation::identity(),
motor_stiffness: 0.0,
motor_damping: 0.0,
motor_impulse: na::zero(),
motor_max_impulse: Real::MAX,
motor_model: SpringModel::default(),
limits_enabled: false,
limits_local_axis1: Vector::x_axis(),
limits_local_axis2: Vector::x_axis(),
limits_angle: Real::MAX,
limits_impulse: 0.0,
}
}
/// Can a SIMD constraint be used for resolving this joint?
pub fn supports_simd_constraints(&self) -> bool {
// SIMD ball constraints don't support motors and limits right now.
!self.limits_enabled
&& (self.motor_max_impulse == 0.0
|| (self.motor_stiffness == 0.0 && self.motor_damping == 0.0))
}
/// Set the spring-like model used by the motor to reach the desired target velocity and position.
pub fn configure_motor_model(&mut self, model: SpringModel) {
self.motor_model = model;
}
/// Sets the target velocity and velocity correction factor this motor.
#[cfg(feature = "dim2")]
pub fn configure_motor_velocity(&mut self, target_vel: Real, factor: Real) {
self.configure_motor(self.motor_target_pos, target_vel, 0.0, factor)
}
/// Sets the target velocity and velocity correction factor this motor.
#[cfg(feature = "dim3")]
pub fn configure_motor_velocity(&mut self, target_vel: Vector<Real>, factor: Real) {
self.configure_motor(self.motor_target_pos, target_vel, 0.0, factor)
}
/// Sets the target orientation this motor needs to reach.
pub fn configure_motor_position(
&mut self,
target_pos: Rotation<Real>,
stiffness: Real,
damping: Real,
) {
self.configure_motor(target_pos, na::zero(), stiffness, damping)
}
/// Sets the target orientation this motor needs to reach.
#[cfg(feature = "dim2")]
pub fn configure_motor(
&mut self,
target_pos: Rotation<Real>,
target_vel: Real,
stiffness: Real,
damping: Real,
) {
self.motor_target_vel = target_vel;
self.motor_target_pos = target_pos;
self.motor_stiffness = stiffness;
self.motor_damping = damping;
}
/// Configure both the target orientation and target velocity of the motor.
#[cfg(feature = "dim3")]
pub fn configure_motor(
&mut self,
target_pos: Rotation<Real>,
target_vel: Vector<Real>,
stiffness: Real,
damping: Real,
) {
self.motor_target_vel = target_vel;
self.motor_target_pos = target_pos;
self.motor_stiffness = stiffness;
self.motor_damping = damping;
}
}

View File

@@ -1,38 +1,55 @@
use crate::math::{Isometry, Real, SpacialVector};
use crate::dynamics::{JointAxesMask, JointData};
use crate::math::{Isometry, Point, Real};
#[derive(Copy, Clone, PartialEq)]
#[cfg_attr(feature = "serde-serialize", derive(Serialize, Deserialize))]
/// A joint that prevents all relative movement between two bodies.
///
/// Given two frames of references, this joint aims to ensure these frame always coincide in world-space.
#[derive(Copy, Clone, Debug, PartialEq)]
pub struct FixedJoint {
/// The frame of reference for the first body affected by this joint, expressed in the local frame
/// of the first body.
pub local_frame1: Isometry<Real>,
/// The frame of reference for the second body affected by this joint, expressed in the local frame
/// of the first body.
pub local_frame2: Isometry<Real>,
/// The impulse applied to the first body affected by this joint.
///
/// The impulse applied to the second body affected by this joint is given by `-impulse`.
/// This combines both linear and angular impulses:
/// - In 2D, `impulse.xy()` gives the linear impulse, and `impulse.z` the angular impulse.
/// - In 3D, `impulse.xyz()` gives the linear impulse, and `(impulse[3], impulse[4], impulse[5])` the angular impulse.
pub impulse: SpacialVector<Real>,
data: JointData,
}
impl FixedJoint {
/// Creates a new fixed joint from the frames of reference of both bodies.
pub fn new(local_frame1: Isometry<Real>, local_frame2: Isometry<Real>) -> Self {
Self {
local_frame1,
local_frame2,
impulse: SpacialVector::zeros(),
}
pub fn new() -> Self {
#[cfg(feature = "dim2")]
let mask = JointAxesMask::X | JointAxesMask::Y | JointAxesMask::ANG_X;
#[cfg(feature = "dim3")]
let mask = JointAxesMask::X
| JointAxesMask::Y
| JointAxesMask::Z
| JointAxesMask::ANG_X
| JointAxesMask::ANG_Y
| JointAxesMask::ANG_Z;
let data = JointData::default().lock_axes(mask);
Self { data }
}
/// Can a SIMD constraint be used for resolving this joint?
pub fn supports_simd_constraints(&self) -> bool {
true
#[must_use]
pub fn local_frame1(mut self, local_frame: Isometry<Real>) -> Self {
self.data = self.data.local_frame1(local_frame);
self
}
#[must_use]
pub fn local_frame2(mut self, local_frame: Isometry<Real>) -> Self {
self.data = self.data.local_frame2(local_frame);
self
}
#[must_use]
pub fn local_anchor1(mut self, anchor1: Point<Real>) -> Self {
self.data = self.data.local_anchor1(anchor1);
self
}
#[must_use]
pub fn local_anchor2(mut self, anchor2: Point<Real>) -> Self {
self.data = self.data.local_anchor2(anchor2);
self
}
}
impl Into<JointData> for FixedJoint {
fn into(self) -> JointData {
self.data
}
}

View File

@@ -1,144 +0,0 @@
use crate::dynamics::{BallJoint, FixedJoint, PrismaticJoint, RevoluteJoint};
use crate::math::{Isometry, Real, SpacialVector};
use crate::na::{Rotation3, UnitQuaternion};
#[derive(Copy, Clone, Debug, PartialEq)]
#[cfg_attr(feature = "serde-serialize", derive(Serialize, Deserialize))]
/// A joint that prevents all relative movement between two bodies.
///
/// Given two frames of references, this joint aims to ensure these frame always coincide in world-space.
pub struct GenericJoint {
/// The frame of reference for the first body affected by this joint, expressed in the local frame
/// of the first body.
pub local_anchor1: Isometry<Real>,
/// The frame of reference for the second body affected by this joint, expressed in the local frame
/// of the first body.
pub local_anchor2: Isometry<Real>,
/// The impulse applied to the first body affected by this joint.
///
/// The impulse applied to the second body affected by this joint is given by `-impulse`.
/// This combines both linear and angular impulses:
/// - In 2D, `impulse.xy()` gives the linear impulse, and `impulse.z` the angular impulse.
/// - In 3D, `impulse.xyz()` gives the linear impulse, and `(impulse[3], impulse[4], impulse[5])` the angular impulse.
pub impulse: SpacialVector<Real>,
pub min_position: SpacialVector<Real>,
pub max_position: SpacialVector<Real>,
pub min_velocity: SpacialVector<Real>,
pub max_velocity: SpacialVector<Real>,
/// The minimum negative impulse the joint can apply on each DoF. Must be <= 0.0
pub min_impulse: SpacialVector<Real>,
/// The maximum positive impulse the joint can apply on each DoF. Must be >= 0.0
pub max_impulse: SpacialVector<Real>,
/// The minimum negative position impulse the joint can apply on each DoF. Must be <= 0.0
pub min_pos_impulse: SpacialVector<Real>,
/// The maximum positive position impulse the joint can apply on each DoF. Must be >= 0.0
pub max_pos_impulse: SpacialVector<Real>,
}
impl GenericJoint {
/// Creates a new fixed joint from the frames of reference of both bodies.
pub fn new(local_anchor1: Isometry<Real>, local_anchor2: Isometry<Real>) -> Self {
Self {
local_anchor1,
local_anchor2,
impulse: SpacialVector::zeros(),
min_position: SpacialVector::zeros(),
max_position: SpacialVector::zeros(),
min_velocity: SpacialVector::zeros(),
max_velocity: SpacialVector::zeros(),
min_impulse: SpacialVector::repeat(-Real::MAX),
max_impulse: SpacialVector::repeat(Real::MAX),
min_pos_impulse: SpacialVector::repeat(-Real::MAX),
max_pos_impulse: SpacialVector::repeat(Real::MAX),
}
}
pub fn set_dof_vel(&mut self, dof: u8, target_vel: Real, max_force: Real) {
self.min_velocity[dof as usize] = target_vel;
self.max_velocity[dof as usize] = target_vel;
self.min_impulse[dof as usize] = -max_force;
self.max_impulse[dof as usize] = max_force;
}
pub fn free_dof(&mut self, dof: u8) {
self.min_position[dof as usize] = -Real::MAX;
self.max_position[dof as usize] = Real::MAX;
self.min_velocity[dof as usize] = -Real::MAX;
self.max_velocity[dof as usize] = Real::MAX;
self.min_impulse[dof as usize] = 0.0;
self.max_impulse[dof as usize] = 0.0;
self.min_pos_impulse[dof as usize] = 0.0;
self.max_pos_impulse[dof as usize] = 0.0;
}
pub fn set_dof_limits(&mut self, dof: u8, min: Real, max: Real) {
self.min_position[dof as usize] = min;
self.max_position[dof as usize] = max;
}
}
impl From<RevoluteJoint> for GenericJoint {
fn from(joint: RevoluteJoint) -> Self {
let basis1 = [*joint.local_axis1, joint.basis1[0], joint.basis1[1]];
let basis2 = [*joint.local_axis2, joint.basis2[0], joint.basis2[1]];
let quat1 = UnitQuaternion::from_basis_unchecked(&basis1);
let quat2 = UnitQuaternion::from_basis_unchecked(&basis2);
let local_anchor1 = Isometry::from_parts(joint.local_anchor1.coords.into(), quat1);
let local_anchor2 = Isometry::from_parts(joint.local_anchor2.coords.into(), quat2);
let mut result = Self::new(local_anchor1, local_anchor2);
result.free_dof(3);
if joint.motor_damping != 0.0 {
result.set_dof_vel(3, joint.motor_target_vel, joint.motor_max_impulse);
}
result.impulse[0] = joint.impulse[0];
result.impulse[1] = joint.impulse[1];
result.impulse[2] = joint.impulse[2];
result.impulse[3] = joint.motor_impulse;
result.impulse[4] = joint.impulse[3];
result.impulse[5] = joint.impulse[4];
result
}
}
impl From<BallJoint> for GenericJoint {
fn from(joint: BallJoint) -> Self {
let local_anchor1 = Isometry::new(joint.local_anchor1.coords, na::zero());
let local_anchor2 = Isometry::new(joint.local_anchor2.coords, na::zero());
let mut result = Self::new(local_anchor1, local_anchor2);
result.impulse[0] = joint.impulse[0];
result.impulse[1] = joint.impulse[1];
result.impulse[2] = joint.impulse[2];
result.free_dof(3);
result.free_dof(4);
result.free_dof(5);
result
}
}
impl From<PrismaticJoint> for GenericJoint {
fn from(joint: PrismaticJoint) -> Self {
let basis1 = [*joint.local_axis1, joint.basis1[0], joint.basis1[1]];
let basis2 = [*joint.local_axis2, joint.basis2[0], joint.basis2[1]];
let quat1 = UnitQuaternion::from_basis_unchecked(&basis1);
let quat2 = UnitQuaternion::from_basis_unchecked(&basis2);
let local_anchor1 = Isometry::from_parts(joint.local_anchor1.coords.into(), quat1);
let local_anchor2 = Isometry::from_parts(joint.local_anchor2.coords.into(), quat2);
let mut result = Self::new(local_anchor1, local_anchor2);
result.free_dof(0);
result.set_dof_limits(0, joint.limits[0], joint.limits[1]);
result
}
}
impl From<FixedJoint> for GenericJoint {
fn from(joint: FixedJoint) -> Self {
Self::new(joint.local_anchor1, joint.local_anchor2)
}
}

View File

@@ -0,0 +1,20 @@
use crate::dynamics::{JointData, JointHandle, RigidBodyHandle};
use crate::math::{Real, SpacialVector};
#[cfg_attr(feature = "serde-serialize", derive(Serialize, Deserialize))]
#[derive(Clone, Debug, PartialEq)]
/// A joint attached to two bodies.
pub struct ImpulseJoint {
/// Handle to the first body attached to this joint.
pub body1: RigidBodyHandle,
/// Handle to the second body attached to this joint.
pub body2: RigidBodyHandle,
pub data: JointData,
pub impulses: SpacialVector<Real>,
// A joint needs to know its handle to simplify its removal.
pub(crate) handle: JointHandle,
#[cfg(feature = "parallel")]
pub(crate) constraint_index: usize,
}

View File

@@ -1,10 +1,10 @@
use super::Joint;
use super::ImpulseJoint;
use crate::geometry::{InteractionGraph, RigidBodyGraphIndex, TemporaryInteractionIndex};
use crate::data::arena::Arena;
use crate::data::{BundleSet, Coarena, ComponentSet, ComponentSetMut};
use crate::dynamics::{IslandManager, RigidBodyActivation, RigidBodyIds, RigidBodyType};
use crate::dynamics::{JointParams, RigidBodyHandle};
use crate::dynamics::{JointData, RigidBodyHandle};
/// The unique identifier of a joint added to the joint set.
/// The unique identifier of a collider added to a collider set.
@@ -34,19 +34,19 @@ impl JointHandle {
}
pub(crate) type JointIndex = usize;
pub(crate) type JointGraphEdge = crate::data::graph::Edge<Joint>;
pub(crate) type JointGraphEdge = crate::data::graph::Edge<ImpulseJoint>;
#[cfg_attr(feature = "serde-serialize", derive(Serialize, Deserialize))]
#[derive(Clone, Default)]
/// A set of joints that can be handled by a physics `World`.
pub struct JointSet {
/// A set of impulse_joints that can be handled by a physics `World`.
pub struct ImpulseJointSet {
rb_graph_ids: Coarena<RigidBodyGraphIndex>,
joint_ids: Arena<TemporaryInteractionIndex>, // Map joint handles to edge ids on the graph.
joint_graph: InteractionGraph<RigidBodyHandle, Joint>,
joint_graph: InteractionGraph<RigidBodyHandle, ImpulseJoint>,
}
impl JointSet {
/// Creates a new empty set of joints.
impl ImpulseJointSet {
/// Creates a new empty set of impulse_joints.
pub fn new() -> Self {
Self {
rb_graph_ids: Coarena::new(),
@@ -55,26 +55,26 @@ impl JointSet {
}
}
/// The number of joints on this set.
/// The number of impulse_joints on this set.
pub fn len(&self) -> usize {
self.joint_graph.graph.edges.len()
}
/// `true` if there are no joints in this set.
/// `true` if there are no impulse_joints in this set.
pub fn is_empty(&self) -> bool {
self.joint_graph.graph.edges.is_empty()
}
/// Retrieve the joint graph where edges are joints and nodes are rigid body handles.
pub fn joint_graph(&self) -> &InteractionGraph<RigidBodyHandle, Joint> {
/// Retrieve the joint graph where edges are impulse_joints and nodes are rigid body handles.
pub fn joint_graph(&self) -> &InteractionGraph<RigidBodyHandle, ImpulseJoint> {
&self.joint_graph
}
/// Iterates through all the joitns attached to the given rigid-body.
/// Iterates through all the impulse_joints attached to the given rigid-body.
pub fn joints_with<'a>(
&'a self,
body: RigidBodyHandle,
) -> impl Iterator<Item = (RigidBodyHandle, RigidBodyHandle, &'a Joint)> {
) -> impl Iterator<Item = (RigidBodyHandle, RigidBodyHandle, &'a ImpulseJoint)> {
self.rb_graph_ids
.get(body.0)
.into_iter()
@@ -87,13 +87,13 @@ impl JointSet {
}
/// Gets the joint with the given handle.
pub fn get(&self, handle: JointHandle) -> Option<&Joint> {
pub fn get(&self, handle: JointHandle) -> Option<&ImpulseJoint> {
let id = self.joint_ids.get(handle.0)?;
self.joint_graph.graph.edge_weight(*id)
}
/// Gets a mutable reference to the joint with the given handle.
pub fn get_mut(&mut self, handle: JointHandle) -> Option<&mut Joint> {
pub fn get_mut(&mut self, handle: JointHandle) -> Option<&mut ImpulseJoint> {
let id = self.joint_ids.get(handle.0)?;
self.joint_graph.graph.edge_weight_mut(*id)
}
@@ -107,7 +107,7 @@ impl JointSet {
///
/// Using this is discouraged in favor of `self.get(handle)` which does not
/// suffer form the ABA problem.
pub fn get_unknown_gen(&self, i: u32) -> Option<(&Joint, JointHandle)> {
pub fn get_unknown_gen(&self, i: u32) -> Option<(&ImpulseJoint, JointHandle)> {
let (id, handle) = self.joint_ids.get_unknown_gen(i)?;
Some((
self.joint_graph.graph.edge_weight(*id)?,
@@ -124,7 +124,7 @@ impl JointSet {
///
/// Using this is discouraged in favor of `self.get_mut(handle)` which does not
/// suffer form the ABA problem.
pub fn get_unknown_gen_mut(&mut self, i: u32) -> Option<(&mut Joint, JointHandle)> {
pub fn get_unknown_gen_mut(&mut self, i: u32) -> Option<(&mut ImpulseJoint, JointHandle)> {
let (id, handle) = self.joint_ids.get_unknown_gen(i)?;
Some((
self.joint_graph.graph.edge_weight_mut(*id)?,
@@ -133,7 +133,7 @@ impl JointSet {
}
/// Iterates through all the joint on this set.
pub fn iter(&self) -> impl Iterator<Item = (JointHandle, &Joint)> {
pub fn iter(&self) -> impl Iterator<Item = (JointHandle, &ImpulseJoint)> {
self.joint_graph
.graph
.edges
@@ -142,7 +142,7 @@ impl JointSet {
}
/// Iterates mutably through all the joint on this set.
pub fn iter_mut(&mut self) -> impl Iterator<Item = (JointHandle, &mut Joint)> {
pub fn iter_mut(&mut self) -> impl Iterator<Item = (JointHandle, &mut ImpulseJoint)> {
self.joint_graph
.graph
.edges
@@ -150,8 +150,8 @@ impl JointSet {
.map(|e| (e.weight.handle, &mut e.weight))
}
// /// The set of joints as an array.
// pub(crate) fn joints(&self) -> &[JointGraphEdge] {
// /// The set of impulse_joints as an array.
// pub(crate) fn impulse_joints(&self) -> &[JointGraphEdge] {
// // self.joint_graph
// // .graph
// // .edges
@@ -170,25 +170,22 @@ impl JointSet {
}
/// Inserts a new joint into this set and retrieve its handle.
pub fn insert<J>(
pub fn insert(
&mut self,
body1: RigidBodyHandle,
body2: RigidBodyHandle,
joint_params: J,
) -> JointHandle
where
J: Into<JointParams>,
{
data: impl Into<JointData>,
) -> JointHandle {
let data = data.into();
let handle = self.joint_ids.insert(0.into());
let joint = Joint {
let joint = ImpulseJoint {
body1,
body2,
data,
impulses: na::zero(),
handle: JointHandle(handle),
#[cfg(feature = "parallel")]
constraint_index: 0,
#[cfg(feature = "parallel")]
position_constraint_index: 0,
params: joint_params.into(),
};
let default_id = InteractionGraph::<(), ()>::invalid_graph_index();
@@ -201,12 +198,12 @@ impl JointSet {
// NOTE: the body won't have a graph index if it does not
// have any joint attached.
if !InteractionGraph::<RigidBodyHandle, Joint>::is_graph_index_valid(graph_index1) {
if !InteractionGraph::<RigidBodyHandle, ImpulseJoint>::is_graph_index_valid(graph_index1) {
graph_index1 = self.joint_graph.graph.add_node(joint.body1);
self.rb_graph_ids.insert(joint.body1.0, graph_index1);
}
if !InteractionGraph::<RigidBodyHandle, Joint>::is_graph_index_valid(graph_index2) {
if !InteractionGraph::<RigidBodyHandle, ImpulseJoint>::is_graph_index_valid(graph_index2) {
graph_index2 = self.joint_graph.graph.add_node(joint.body2);
self.rb_graph_ids.insert(joint.body2.0, graph_index2);
}
@@ -215,7 +212,7 @@ impl JointSet {
JointHandle(handle)
}
/// Retrieve all the joints happening between two active bodies.
/// Retrieve all the impulse_joints happening between two active bodies.
// NOTE: this is very similar to the code from NarrowPhase::select_active_interactions.
pub(crate) fn select_active_interactions<Bodies>(
&self,
@@ -271,7 +268,7 @@ impl JointSet {
islands: &mut IslandManager,
bodies: &mut Bodies,
wake_up: bool,
) -> Option<Joint>
) -> Option<ImpulseJoint>
where
Bodies: ComponentSetMut<RigidBodyActivation>
+ ComponentSet<RigidBodyType>
@@ -299,11 +296,11 @@ impl JointSet {
removed_joint
}
/// Deletes all the joints attached to the given rigid-body.
/// Deletes all the impulse_joints attached to the given rigid-body.
///
/// The provided rigid-body handle is not required to identify a rigid-body that
/// is still contained by the `bodies` component set.
/// Returns the (now invalid) handles of the removed joints.
/// Returns the (now invalid) handles of the removed impulse_joints.
pub fn remove_joints_attached_to_rigid_body<Bodies>(
&mut self,
handle: RigidBodyHandle,

View File

@@ -0,0 +1,6 @@
pub use self::impulse_joint::ImpulseJoint;
pub use self::impulse_joint_set::{ImpulseJointSet, JointHandle};
pub(crate) use self::impulse_joint_set::{JointGraphEdge, JointIndex};
mod impulse_joint;
mod impulse_joint_set;

Some files were not shown because too many files have changed in this diff Show More