Move Kinematic Rigidbodies In Code

Yo @Cedric … I am having an issue trying to move a physics object with mass = 0 (Should be static or kinematic)…

If i set position of transform in babylon code, does not move :frowning:

If i set the ammo btTransform with setOrigin, also does not move :frowning:

How do you move around a static or kinematic physics object ?

Let me check that …

You just have to move the mesh and it works.
See line 24 in this PG:

Babylon.js Playground

2 Likes

Yo @Cedric … Are these functions descriptions backwards… This function sure looks to me that its updateing the babylon mesh from the physics body… But these descriptions says otherwise

    /**
     * Sets the physics body position/rotation from the babylon mesh's position/rotation
     * @param impostor imposter containing the physics body and babylon object
     */
    public setTransformationFromPhysicsBody(impostor: PhysicsImpostor) {
        impostor.physicsBody.getMotionState().getWorldTransform(this._tmpAmmoTransform);
        impostor.object.position.set(this._tmpAmmoTransform.getOrigin().x(), this._tmpAmmoTransform.getOrigin().y(), this._tmpAmmoTransform.getOrigin().z());

        if (!impostor.object.rotationQuaternion) {
            if (impostor.object.rotation) {
                this._tmpQuaternion.set(this._tmpAmmoTransform.getRotation().x(), this._tmpAmmoTransform.getRotation().y(), this._tmpAmmoTransform.getRotation().z(), this._tmpAmmoTransform.getRotation().w());
                this._tmpQuaternion.toEulerAnglesToRef(impostor.object.rotation);
            }
        } else {
            impostor.object.rotationQuaternion.set(this._tmpAmmoTransform.getRotation().x(), this._tmpAmmoTransform.getRotation().y(), this._tmpAmmoTransform.getRotation().z(), this._tmpAmmoTransform.getRotation().w());
        }
    }

Same thing for

/**
     * Sets the babylon object's position/rotation from the physics body's position/rotation
     * @param impostor imposter containing the physics body and babylon object
     * @param newPosition new position
     * @param newRotation new rotation
     */
    public setPhysicsBodyTransformation(impostor: PhysicsImpostor, newPosition: Vector3, newRotation: Quaternion) {
        var trans = impostor.physicsBody.getWorldTransform();

        // If rotation/position has changed update and activate rigged body
        if (
            Math.abs(trans.getOrigin().x() - newPosition.x) > Epsilon ||
            Math.abs(trans.getOrigin().y() - newPosition.y) > Epsilon ||
            Math.abs(trans.getOrigin().z() - newPosition.z) > Epsilon ||
            Math.abs(trans.getRotation().x() - newRotation.x) > Epsilon ||
            Math.abs(trans.getRotation().y() - newRotation.y) > Epsilon ||
            Math.abs(trans.getRotation().z() - newRotation.z) > Epsilon ||
            Math.abs(trans.getRotation().w() - newRotation.w) > Epsilon
        ) {
            this._tmpAmmoVectorA.setValue(newPosition.x, newPosition.y, newPosition.z);
            trans.setOrigin(this._tmpAmmoVectorA);

            this._tmpAmmoQuaternion.setValue(newRotation.x, newRotation.y, newRotation.z, newRotation.w);
            trans.setRotation(this._tmpAmmoQuaternion);
            impostor.physicsBody.setWorldTransform(trans);

            if (impostor.mass == 0) {
                // Kinematic objects must be updated using motion state
                var motionState = impostor.physicsBody.getMotionState();
                if (motionState) {
                    motionState.setWorldTransform(trans);
                }
            } else {
                impostor.physicsBody.activate();
            }
        }
    }

It looks to me that this is setting the physics body from the babylon mesh position, but the descript says the opposite … or am i just plain reading this wrong

I found the problem… If you are NOT using Quaternion Rotations… You CANNOT update the physics impostor transform… My component is using node.rotation instead of node.rotationQuaternion

I found the issue in beforeStep function of the physicsImpostor class

if (!this._options.disableBidirectionalTransformation) {
            this.object.rotationQuaternion && this._physicsEngine.getPhysicsPlugin().setPhysicsBodyTransformation(this, /*bInfo.boundingBox.centerWorld*/ this.object.getAbsolutePosition(), this._tmpQuat);
}

That does not seem right to only support setPhysicsBodyTransformation if using quaternions… What about folks for whatever reason needs to use regular Euler Rotations ???

3 Likes