Getting started

Bevy is an efficient, simple-to-use, and fast-to-compile data-driven game engine written in Rust. It is based on the ECS (Entity-Component-System) paradigm and allows the definition of plugins, i.e., sets of components, systems, and resources that share a common objective.

The bevy_rapier2d and bevy_rapier3d crates which integrate Rapier to Bevy using their plugin system. To get the best of bevy-rapier multiple features can be enabled optionally:

  • simd-stable: enables explicit SIMD optimizations using the wide crate. Has limited cross-platform support but can be used with a stable version of the Rust compiler.
  • simd-nightly: enables explicit SIMD optimizations using the packed_simd crate. Has a great cross-platform support but requires a nightly version of the Rust compiler.
  • parallel: enables parallelism of the physics pipeline with the rayon crate.
  • serde-serialize: enables serialization of the physics components with serde.
  • enhanced-determinism: enables cross-platform determinism (assuming the rest of your code is also deterministic) across all 32-bit and 64-bit platforms that implements the IEEE 754-2008 standard strictly. This includes most modern processors as well as WASM targets.
  • wasm-bindgen: enables usage of rapier as a dependency of a WASM crate that is compiled with wasm-bindgen.

Cargo example#

To use these crates, the first step is to add a dependency to your Cargo.toml:

[dependencies]
# TODO: Replace the * by the latest version numbers.
bevy_rapier2d = *

If you need to enable some Rapier features like SIMD, parallelism, serialization, or determinism, you can enable them on bevy_rapier directly.

[dependencies]
# TODO: Replace the * by the latest version numbers.
bevy_rapier2d = { version = "*", features = [ "simd-stable" ] }

Basic simulation example#

Here is a basic example of main.rs file. This creates a ball bouncing on a static ground. Details about the elements used in this examples are given in subsequent pages of this guide.

info

The use bevy_rapier2d::prelude::* or use bevy_rapier3d::prelude::* will import all the most common types needed to work with bevy_rapier.

use bevy::prelude::*;
use bevy_rapier2d::prelude::*;
fn main() {
App::build()
.add_plugins(DefaultPlugins)
.add_plugin(RapierPhysicsPlugin::<NoUserData>::default())
.add_startup_system(setup_physics.system())
.add_system(print_ball_altitude.system())
.run();
}
fn setup_physics(mut commands: Commands) {
/* Create the ground. */
let collider = ColliderBundle {
shape: ColliderShape::cuboid(100.0, 0.1),
..Default::default()
};
commands.spawn_bundle(collider);
/* Create the bouncing ball. */
let rigid_body = RigidBodyBundle {
position: Vec2::new(0.0, 10.0).into(),
..Default::default()
};
let collider = ColliderBundle {
shape: ColliderShape::ball(0.5),
material: ColliderMaterial {
restitution: 0.7,
..Default::default()
},
..Default::default()
};
commands.spawn_bundle(rigid_body)
.insert_bundle(collider);
}
fn print_ball_altitude(positions: Query<&RigidBodyPosition>) {
for rb_pos in positions.iter() {
println!("Ball altitude: {}", rb_pos.position.translation.vector.y);
}
}

The debug renderer#

warning

The debug-renderer is very limited right now. It won't be able to render every shape type, and doesn't render other elements like contacts, rigid-body frames, etc. Contributions are welcome!

The bevy_rapier plugin comes with a debug-render to help debugging physics bugs. This can be enabled by:

  1. Enabling the render cargo feature of bevy-rapier.
  2. Adding the plugin RapierRenderPlugin to the Bevy app.
  3. Adding the ColliderDebugRender component to an entity containing a collider. Please note that this will only work if the entity doesn't have a mesh already attached to it.
  4. (optional) Adding the ColliderPositionSync component to the same entity. This is not needed if you have your own way of synchronizing the collider's position with the entity's Transform.
[dependencies]
# Make sure the "render" feature is enabled.
bevy_rapier2d = { version = "*", features = [ "simd-stable", "render" ] }
bevy_rapier3d = { version = "*", features = [ "simd-stable", "render" ] }
use bevy::prelude::*;
use bevy_rapier3d::prelude::*;
fn main() {
App::build()
...
.add_plugin(RapierRenderPlugin)
...
.run();
}
fn setup_physics() {
let collider = ColliderBundle {
shape: ColliderShape::ball(0.4),
..Default::default()
};
commands.spawn_bundle(collider)
.insert(ColliderPositionSync::Discrete)
.insert(ColliderDebugRender::with_id(1)); // The id selects one of the predefined colors.
}