Set Mass and Local Inertia of Ammo.js Rigid Body

This article explains how to set the mass and calculate the local inertia of a new rigid body in Ammo.js. You will learn how to initialize these physical properties using a collision shape, calculate the inertia vector, and apply them during the creation of a rigid body, as well as how to update them dynamically on an existing body.

Setting Mass and Inertia During Creation

In Ammo.js (the JavaScript port of the Bullet Physics engine), you cannot simply assign a mass value directly to a rigid body upon instantiation. Instead, you must calculate the local inertia based on the body’s collision shape and mass, and then pass both values to the rigid body construction helper.

Here is the step-by-step process to set the mass and local inertia of a new rigid body:

1. Define the Mass and Create an Inertia Vector

First, define your mass as a float. If the mass is 0, the object is treated as static (immovable). For dynamic objects, use a value greater than 0. You also need to instantiate a btVector3 to store the calculated local inertia.

const mass = 1.0; // Dynamic body
const localInertia = new Ammo.btVector3(0, 0, 0);

2. Calculate the Local Inertia

Use the collision shape’s calculateLocalInertia method. This method populates your localInertia vector with the correct values based on the geometry of the shape and the specified mass.

const geometry = new Ammo.btBoxShape(new Ammo.btVector3(1, 1, 1)); // 2x2x2 box
geometry.calculateLocalInertia(mass, localInertia);

3. Create the Rigid Body Construction Info

Pass the mass and the calculated local inertia into the btRigidBodyConstructionInfo object along with your motion state and shape.

const startTransform = new Ammo.btTransform();
startTransform.setIdentity();
startTransform.setOrigin(new Ammo.btVector3(0, 5, 0));
const motionState = new Ammo.btDefaultMotionState(startTransform);

const rbInfo = new Ammo.btRigidBodyConstructionInfo(
    mass, 
    motionState, 
    geometry, 
    localInertia
);
const body = new Ammo.btRigidBody(rbInfo);

4. Add the Body to the Physics World

Finally, add the newly constructed rigid body to your dynamics world.

physicsWorld.addRigidBody(body);

Modifying Mass and Inertia Dynamically

If you need to change the mass and local inertia of a rigid body after it has already been added to the physics world, you can use the setMassProps method directly on the rigid body instance.

const newMass = 5.0;
const newLocalInertia = new Ammo.btVector3(0, 0, 0);

// Recalculate inertia for the new mass
body.getCollisionShape().calculateLocalInertia(newMass, newLocalInertia);

// Apply the new mass and inertia properties
body.setMassProps(newMass, newLocalInertia);

// Force the physics engine to update the body's status
body.activate();

When updating physics properties dynamically, always call body.activate() to ensure that the physics simulation does not leave the body in a “sleeping” state.