Momentum transfer

Hi,

I’m testing the physics engine with simple use cases.
One of them is 2 spheres colliding, A and B , with equal masses and B at rest.
In theory, after collision, A should stop and B should move, but they both move in the same direction.
What am I missing? Here’s the code, thanks :

package jme3test.bullet.dc;

import com.jme3.app.SimpleApplication;
import com.jme3.bullet.BulletAppState;
import com.jme3.bullet.PhysicsSpace;
import com.jme3.bullet.collision.PhysicsCollisionEvent;
import com.jme3.bullet.collision.PhysicsCollisionListener;
import com.jme3.bullet.collision.shapes.SphereCollisionShape;
import com.jme3.bullet.control.RigidBodyControl;
import com.jme3.math.Vector3f;
import com.jme3.scene.Node;
import jme3test.bullet.PhysicsTestHelper;

public class POCCollisionResolution extends SimpleApplication implements PhysicsCollisionListener
{
    private BulletAppState bulletAppState;
    private static Node shapeA;
    private static Node shapeB;

    public static void main(String[] args)
    {
        POCCollisionResolution app = new POCCollisionResolution();
        app.start();

    }

    private void setupKeys()
    {

    }

    @Override
    public void simpleInitApp()
    {

        bulletAppState = new BulletAppState();
        stateManager.attach(bulletAppState);
//        bulletAppState.getPhysicsSpace().setAccuracy(1f / 3600f);

        flyCam.setMoveSpeed(20);
        bulletAppState.getPhysicsSpace().setGravity(new Vector3f(0, 0, 0));

        bulletAppState.getPhysicsSpace().enableDebug(assetManager);
        setupKeys();
        setupShapes();

        shapeA.getControl(RigidBodyControl.class).applyImpulse(new Vector3f(1, 0, 0), Vector3f.ZERO);
//        shapeA.getControl(RigidBodyControl.class).setLinearVelocity(new Vector3f(1,0,0));

    }

    private PhysicsSpace getPhysicsSpace()
    {
        return bulletAppState.getPhysicsSpace();
    }

    public void setupShapes()
    {
//        shapeA = PhysicsTestHelper.createPhysicsTestNode(assetManager, new BoxCollisionShape(new Vector3f(.001f, .001f, .1f)),1);
        shapeA = PhysicsTestHelper.createPhysicsTestNode(assetManager, new SphereCollisionShape(0.1F), 1);
        shapeA.getControl(RigidBodyControl.class).setPhysicsLocation(new Vector3f(0f, 0, 0f));
        shapeA.setName("AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA");
        shapeA.getControl(RigidBodyControl.class).setSleepingThresholds(0, 0);


        rootNode.attachChild(shapeA);
        getPhysicsSpace().add(shapeA);


//        shapeB = PhysicsTestHelper.createPhysicsTestNode(assetManager, new BoxCollisionShape(new Vector3f( .3f, .3f, .3f)),1);
        shapeB = PhysicsTestHelper.createPhysicsTestNode(assetManager, new SphereCollisionShape(0.1F), 1);
        shapeB.getControl(RigidBodyControl.class).setPhysicsLocation(new Vector3f(2, 0, 0f));
        shapeB.getControl(RigidBodyControl.class).setSleepingThresholds(0, 0);

        rootNode.attachChild(shapeB);
        getPhysicsSpace().add(shapeB);


        getPhysicsSpace().addCollisionListener(this);
    }

    @Override
    public void simpleUpdate(float tpf)
    {

    }


    public void collision(PhysicsCollisionEvent event)
    {

    }


}

Set restitution for both to 1

Great, now it’s behaving much better.

Although, sometimes it’s perfect : Sphere A ends up with 0 velocity, and the applied impulse is 1.

But often it doesn’t quite work : Sphere A ends up with (-0.1,0,0) Velocity, and the applied impulse is 1.1
In those cases, it’s always 10% too much.
It looks like this happens when during the collision detection, the sphere ended up a little inside of the other.
And it’s as if Bullet applied impulses to first separate the spheres on top of the collision. Is that possible?

Thanks

I tried your code with added restitution of 1, couldn’t get this to happen at all. I don’t know how it handles collisions so I’m not sure tbh.

One piece of advice (probably the only) I can give is to try scaling everything up, I’ve noticed this has increased the accuracy of my physics programs but I stand to be corrected if it has the opposite effect :stuck_out_tongue:
Try ×10 for everything

I’m using bullet native on jme3, are you?

If you play with the distance between the spheres, you should get the effect.
Scaling didnt help.
Maybe there’s something wrong in my config. Have you seen quirks of this magnitude in bullet?

Ah, no I have a much older JME version, using JBullet. I still cannot create the problem with my setup.

Tbh no, I don’t have much experience with bullet. Out of interest, are you thinking of using it for a pool like game/simulation? I’ve read that it’s best to avoid bullet if that is the case.

@pspeed Maybe you can confirm that my setup is the problem?

Jester, which version do you use?
I want to use it for combat simulation, so there will be lots of collisions. Where did you read about bullet’s limitations? It’s good to know what you can expect.

Why me? I’ve never used bullet, never plan to use bullet… I can spell bullet. Do you need help with spelling it?

You are the fount of all knowledge, that’s why. I use JME 3.0 so whatever was with that. Pretty sure it was after that version it went over from JBullet. I read that advice on multiple stack exchange posts about bullet physics.

Might be best just to wait until it actually happens in game in a way that you consider unacceptable before trying to tackle it.

Hey Jester,
Thanks for your help. It’s actually the physics library. When I use jBullet, the glitch isn’t there.
But there are many others, so I’ll stick with Bullet Native.
FYI, they have completely different outcomes for collision.