PhysicsBody with PhysicsShapeMesh doesn't follow specific animated mesh (disablePreStep=false)

Hi everyone,

I’m developing a game using BabylonJS and encountering an issue with physics synchronization for a specific mesh within an animated GLB model.

My usual workflow for handling collision on animated meshes involves these steps:

  1. Import the GLB model.
  2. Find the target mesh within the model’s hierarchy that requires collision detection.
  3. Create a PhysicsBody for this mesh (typically PhysicsBody.STATIC).
  4. Create a PhysicsShapeMesh using the target mesh’s geometry to get accurate collision bounds.
  5. Set physicsBody.disablePreStep = false. My understanding is that this tells the physics engine to update the body’s transform based on the mesh’s transform before each physics step, which is necessary for animations that move the mesh.

This approach has been successful for several models. However, I’ve run into a problem with a particular GLB model. When I apply this exact procedure to certain meshes within this model, like head or body, the PhysicsBody correctly follows the mesh’s animation as expected.

The issue arises when I try to do the same for a specific mesh named hand_primitive2. Even though I follow the same steps and ensure physicsBody.disablePreStep = false is set, the PhysicsBody for hand_primitive2 does not follow the animated mesh. It remains static at its initial position/orientation, while the visual mesh animates correctly.

To demonstrate this clearly, I’ve prepared a Playground example. It loads the model, sets up the physics for hand_primitive2 as described, starts an animation, and enables the physics viewer. You can see the hand mesh moving, but its physics shape (visualized by the viewer) stays behind:

Playground Link: https://playground.babylonjs.com/#P9N31W

I’m puzzled as to why this specific mesh (hand_primitive2) behaves differently from others (head, body) in the same model using the same setup.

  • Could there be something specific about hand_primitive2? Perhaps its place in the hierarchy, its skinning/bone weights, or how the animation updates its final world matrix?
  • Is PhysicsShapeMesh combined with disablePreStep = false the correct approach for skinned/animated sub-meshes like this?
  • Is there another factor I might be overlooking?

I did search the forums but couldn’t find a similar case where the method works selectively within the same animated asset.

Any insights or suggestions on what might be causing this discrepancy and how to resolve it would be incredibly helpful!

Thanks in advance for your time and expertise.

Following up on this issue:

To further investigate and rule out potential issues with the original model file itself, I created a new, similar GLB model from scratch and tested it with the same setup.

Interestingly, I’m observing different but still incorrect behavior now. With this new model, specifically in the Playground environment:

  1. For the first few moments after the scene loads, the PhysicsBody for the hand mesh appears static at the world origin (0,0,0), even though the visual mesh is already animating correctly in its proper place.
  2. After this initial delay, the PhysicsBody does start attempting to follow the mesh, but it does so very sporadically. It seems to update its position/orientation only once every few seconds (the interval seems inconsistent), lagging significantly behind the actual mesh animation instead of synchronizing smoothly each frame.

Crucially, this sporadic synchronization behavior seems specific to the Playground. In my actual game project using the exact same model and physics setup code, the PhysicsBody for the hand mesh never updates its position after initialization. It remains completely static at its starting coordinates throughout the animation, showing no attempt to follow the mesh at all, unlike the occasional jumps seen in the Playground.

You can see this baseline sporadic behavior (in the Playground) with the new model here:
Playground Link (New Model - No Fix): https://playground.babylonjs.com/#P9N31W#1


I came across another forum thread (https://forum.babylonjs.com/t/physicsbody-controlled-by-animation/42652/4) where a user experienced lag and mentioned forcing matrix updates. Based on that, I tried adding the following code in both environments:

scene.onBeforePhysicsObservable.add(() => {
    // Assuming 'thisMesh' is the hand mesh
    thisMesh.computeWorldMatrix(true);
});

My hope was that explicitly forcing the world matrix computation just before the physics step would ensure the physics body gets the most up-to-date transform.

Unfortunately, this did not resolve the issue in either the Playground or my game. The behavior remained the same as described above (sporadic updates in PG, completely static in my game).

Here is the Playground link demonstrating that the computeWorldMatrix call didn’t change the outcome:
Updated Playground Link (New Model - With computeWorldMatrix): https://playground.babylonjs.com/#P9N31W#2


Does this difference between the Playground behavior and my actual game environment, along with the fact that computeWorldMatrix doesn’t help, offer any more clues? Could it be related to timing differences, the rendering loop, or perhaps how skinned mesh matrices are updated or accessed by the physics engine under slightly different conditions, even when disablePreStep is false?

Any further insights would be greatly appreciated!

In principle, this should work as I do something similar in my project, too. I am dragging along hit boxes parented under a skeleton ( / rig) as well as parented under a gltf root node.

My guess is there is something off with your animation (I used this pg).

The scalings change over time. I cannot quite remember exactly but there were some cases where Havok had problems with scalings (but might just be scaling < 0).

Anyway, if you get the arm mesh out of the hierarchy and animate it manually, it works: https://playground.babylonjs.com/#P9N31W#4 Therefore I would try to change the animation so that it only affects rotation and see ift his fixes it.

Hi @Joe_Kerr,

Thank you so much for your analysis and suggestions! You were absolutely right about the scaling.

Following your advice, I modified the animation to ensure no scaling is applied to the relevant bones or the mesh itself during the animation sequence. I’ve updated the model accordingly.

This change has made a significant difference! The physics body is no longer stuck at the origin or jumping sporadically as it was in the previous examples. It now generally follows the hand mesh much more closely. Thank you for spotting that!

However, there’s still a noticeable, albeit different, issue remaining:

  • The PhysicsBody perfectly synchronizes with the Right-hand_primitive1 mesh when the mesh momentarily pauses in its animation cycle (e.g., at the highest and lowest points of the hand’s movement in the example animation).
  • But, during the transition – while the hand is actively moving between these pause points – the PhysicsBody visibly lags behind the mesh. It seems to desynchronize during the motion phase and then catches up and snaps back into correct alignment once the mesh pauses again.

I’ve updated the Playground to demonstrate this specific behavior with the new model/animation (no scaling):

Updated Playground Link: https://playground.babylonjs.com/#P9N31W#5

You can observe the physics shape aligning correctly when the hand stops briefly at the top and bottom, but falling behind during the up/down swing.

Given that scaling is no longer a factor, could this remaining lag during movement be related to something else?

  • Perhaps a subtle timing issue between when the final world matrix (affected by the skeleton animation) is fully computed/updated and when the physics engine reads it via disablePreStep = false?
  • Is a certain degree of lag expected for relatively fast bone-driven animations even with the pre-step enabled, and perhaps my previous issue (scaling) was just masking this secondary effect?
  • Could the complexity of the hierarchy above the hand mesh play a role?

Any further thoughts or insights based on this new behavior would be fantastic! Thanks again for your valuable help pinpointing the scaling issue.

Just adding another thought to the mix while investigating the remaining animation lag (from playground #P9N31W#5):

I’ve realized that these physics synchronization issues seemed to start cropping up after I switched my modeling workflow from an older Blender version (around 3.x) to Blender 4.0.2.

Previously, on older Blender versions, I remember using similarly complex animations (sometimes involving non-uniform scaling, which I’ve now removed as per Joe_Kerr’s suggestion) on skinned meshes without encountering this specific type of physics desynchronization lag during movement in BabylonJS. Animations involving primarily simple rotationQuaternion updates always seemed fine.

Interestingly, if I take a .blend file created in 4.0.2 and simply open and re-export it using a newer Blender version (on a different machine), the exported GLB still exhibits the same physics lag issue in BabylonJS. This makes me wonder if the way animation data (especially bone influences affecting vertex positions) is fundamentally structured or saved by Blender 4.0.2 might be slightly different in a way that affects how BabylonJS’s physics engine reads the final mesh transform via disablePreStep = false, even after the scaling issue was fixed.

(My primary modeling machine struggles with newer Blender versions, hence sticking with 4.0.2 for now).

My next step is to try creating a simple test model from scratch on both an older Blender version (< 4.0) and a much newer one (> 4.0.2, on a different PC) to see if the issue is tied to the Blender version used for creation.

However, before I dive into that, I wanted to ask the community: Are there any known issues or subtle behavioral changes specifically with Blender 4.0.2’s GLTF exporter (or animation system) that might affect how skinned mesh animations interact with physics engines like BabylonJS’s Havok implementation, particularly concerning the synchronization during active movement?

Any pointers or shared experiences related to Blender 4.0.2 exports and BabylonJS physics would be very helpful. Thanks!

This way it seems to work: https://playground.babylonjs.com/#P9N31W#6

I downloaded your model, loaded it in Blender and normalized the scalings of all nodes and re-exported. Note that the model is sort of collapsed but this already happened on import. Anyway, the important point is, I think, that the physics syncing seems alright.

1 Like

I’m late to the party! Also set motion type as ANIMATED. It doesn’t make a (visual) difference in the last PG but it’s conceptually the expected.
In previous PG, I can see non uniform scaling values. It might explain the lag and weird behavior. Non uniform scaling should not be allowed by international laws. :smiley:

1 Like

Cedric for president!! :prince:

3 Likes

Where should I sign???