AmmoJS forceUpdate does not stop sphere movement

Hey Guys,

I wanted to signal a bug with the AmmoJS plugin ( perhaps? ) or just physics in general. I have noticed this while trying to switch my game https://gcapsarena.com ( does not work on chrome now) to the latest version of babylonjs ( I have to since I get an webgl error on chrome).

GCaps is a ball game, I have developed it in 4.0.0.alpha.21 and it worked great. When migrating to the latest version I notice that the ball never stops movement even after setting velocities to 0 or calling forceUpdate on the Impostor. Since GCaps is a multiplayer game you realize that is almost hell to make deterministic. I do not seem to find a solution for this. Luckily, I think I have it reproduced here :

https://www.babylonjs-playground.com/#B5BDU#66

If you open the console, you will see that even after calling forceUpdate the spheres position is always changing. forceUpdate resets the impostor so logically it should also reset the forces, something not right.

Pinging @Cedric

I bet it’s “Brownian jitter”. Friggin’ Brownians… can never sit still. :slight_smile:

Me thinks maybe… IF AmmoJS has allowSleep and sleepDelay… etc, it’s not activating.

(like I have a clue) :slight_smile:

It’s much much worse in my game. There is no jitter, full movement / rotation in force. It used to work in 4.0.0.alpha.21. There is a sleep functionality in ammojs but, as you mentioned, for some reason it is not activated / does nothing. Updating the impostor though re-initializes it, maybe for GC purposes the same physics body is reused?

I’m taking a look!

https://www.babylonjs-playground.com/#B5BDU#71

I can get that sphere to dead-stop… SOMETIMES. (needs full reloads sometimes?)

MASSIVE code within dual setTimeouts… gruesome! Its got some impostor.setMass(0) calls, which I know Cedric LOVES. :wink:

Notice line 29 where I added a few more 9’s to one of the damping values, too. Maybe relevant, maybe not. I think not.

2 Likes

@Wingnut These are workarounds. This used to work by setting linear and angular velocities to 0. Also forceUpdate should be the absolute reseter in my opinion. The body should turn to absolute rest when calling it. If not, is there another way to reset the impostor / physicsbody?

@Cedric Thank you so much for having a look!

1 Like

Yeah, you bet. I just do them… to attempt to find the actual problem area. They’re just garbage “feeling-around-in-the-dark”… but they sure are fun. :slight_smile: Diggin’ for clues, gettin’ all muddy.

Yep, actual reason for recent functionality changes/differences… needs finding and bug-stomp. :slight_smile:

Calling forceUpdate will recreate the ammojs rigidbody and collision shape.
So, setting mass=0 then calling forceUpdate will replace the dynamic body with a kinematic one.
If you don’t change the mass, I think it’s like setting velocity/angular velocity to 0. So gravity keeps being applied.
But even with a zero mass, the Y position is updated by the physics engine which is really strange.
I tried to set the body to sleep without success. I will investigate more on that point.

1 Like

Apparently, the delta I get on Y when body has mass == 0 is because of float precision. the difference between 2 frames is < 10e-5. So, it’s a kinematic object. No need to worry about that.
But, when in kinematic mode, the impostor will not receive forces from collisions with other bodies.
That means that other impostors will bounce on it with it will not move. It will be static.

The body doesn’t go to sleeping mode by itself. I don’t know why yet and it may takes time to figure that out. My guess is that some process keeps touching the body preventing it to sleep.
Anyway, you can force it to sleep mode:

https://www.babylonjs-playground.com/#B5BDU#72

Check line 50.

The position reported will not be the same between two frames. Because of float precision, you’ll get something like 10e-5 delta.

1 Like

Wanna see something “weird” in that #72 playground? Try repeated re-RUNS (play button) while watching console.

For me, approximately 1 in 8 re-runs… makes the sphere dead-stop, with no “floaty-floats” at console. Go fig. hmm.

I suppose… Null and I… should help Cedric deep-dive Ammo, if we can. Null, I need you to collect all the “What’s New” lists since 4.0.0.alpha.21. See if you can see anything in the list(s)… that might have caused AmmoJS forceUpdate() to change.

Do you know how to query github… to see all framework PR’s since 4.0.0.alpha.21? That might be worth a tour, too.

Have your report on my desk by Sunday morning, ok? :smiley:

@trevordev , @RaananW , @JohnK, @Raggar … shall we go digging native Ammo-poop with Cedric?

The more ideas/eyes, the better. Great/Easy physics is a bigtime crowd-drawer for BJS… a very important future-shaper.

Me, I’ll be here, watching you guys… REALLY HARD, and cooking pancakes for us. :slight_smile:

@Wingnut Once in a while, I get the exact same values between 2 frames. Maybe that’s what you get. It looks like it’s not outputting values.

https://www.babylonjs-playground.com/#B5BDU#73

I’m still getting approx 1-in-8 re-runs… where sphere gets dead-stopped. I’m printing values at 1-second intervals… with time-stamp before each.

I don’t know if this proves/disproves anything, but what the heck… I give it a try. :slight_smile:

I’m seeing various oddness. I tested with .getAbsolutePosition() instead-of .position, too. Oddness. Sometimes X and Z at stopped, but Y is floaty. Then after a few more outputs, Z goes floaty, too, but X still holds-solid. I can’t seem to find a consistent pattern.

Brownian movement… from broken auto-sleep issue, ya think? hmm. Or maybe it CAN’T sleep with those micro-movements happening?

https://www.babylonjs-playground.com/#B5BDU#75

I tried some things. lockedTarget to sphere, changed ground from plane to box, tried less/more impulse power, added texture to ground and zoomed cam… to see if I could see any jitter.

No change. Darn. Still… console numbers show sphere dead stop… 1-in-8 or 1-in-10 re-runs, approx. Floaty-floats the rest of the time. hmm. I don’t know how to help find this issue.

Lines 61/62… I’m not real sure what they do. I’ve “visited” disableBidirectionalTransformation before, which is a fairly new impostor-level property, I think. (within the last 3 years - arrived when transformNodes arrived?)

physicsBody.setActivationState(2)… that’s native Cannon level… I have no idea what it does. Maybe @null knows.

Actually, the sphere has stopped, from an ammojs view. The delta you see is related to float precision.
The range is 10e-5 and non linear. if the unit is meter, the delta is around 1% of a millimeter.

But why sometimes dead stop, why other times floaty?

And we still must acknowledge OP. Something changed since 4.0.0.alpha.21… that is making null’s (home project) sphere bounce-around quite severely after the forceUpdate() call, or after the velocities kill, or after a combo of both. He/she says working fine @ 4.0.0.alpha.21.

Something changed… and it’s killing Null’s project. Want to label this as “expected behavior”?

1 Like

It might be a good idea to post this same example using 4.0.0.alpha.21. You could use jsfiddle.

For me the problems are bigger. The sphere does not stop at all but for some reason I am unable to reproduce it in the playground. Even with Cedric suggestions ( Thank you so much for them ). Unfortunately I have not been able to understand where the problem is. I have checked the code between BJS versions and it is almost identical. The jitter in this example is not what I am experiencing so I don’t think this is even the case.

I am convinced this is some sort of bug since it used to work before and somehow I am the only one being able to reproduce it. It might be a specific usecase but honestly I am not sure anymore. The same code stops the sphere here and it doesn’t in my project. I will try to set up a scenario as close as mine to be able to reproduce the same thing but to be fair I am losing hope :confused:

1 Like

Or at least, can you make a video capture of the result and the output values?It might give me some clues on what’s happening.

1 Like