Jbullet-jme - PhysicsCharacterNode, Animation and WorldRotation

Hello,



I'm trying to use PhysicsCharacterNode on a imported model that has animation.



Everything works fine when using the model as a PhysicsNode (static or dynamic), but not with the PhysicsCharacterNode.

Something very strange is happening to the world rotation of the animation bones during the physics update, and by strange, I mean something that I'm pretty sure should not be happening.



The WorldTranslation and WorldRotation of the bones mysteriously changes after the second physics space update, while their LocalTranslation does not. This results in the world location of the mountpoint (a bone) being wrong, which is no good as it's need …as a mountpoint  :(



Here's the result after a few s.o.p lines:


PhysicsSpace.update()
PhysicsGhostNode - setWorldTranslation: (0.0, 0.99, 0.0)
PhysicsGhostNode - setWorldRotation: [x=0.0 y=0.0 z=0.0 w=0.5]
Mountpoint:            [x=-1.4901161E-7 y=-0.99999887 z=-5.811453E-7 w=-6.2584877E-7]        [x=0.49089 y=0.553379 z=0.446544 w=0.503386]
Mountpoint parent:     [x=0.44654325 y=-0.5033847 z=-0.49088922 w=-0.5533788]        [x=0.018487 y=-0.015465 z=-0.001465 w=0.999708]
Mountpoint parent:     [x=0.46349767 y=-0.50337523 z=-0.49395728 w=-0.53645843]        [x=0.048764 y=-0.727602 z=0.045756 w=0.682732]
PhysicsSpace.update()
PhysicsGhostNode - setWorldTranslation: (0.0, 0.98, 0.0)
PhysicsGhostNode - setWorldRotation: [x=0.0 y=0.0 z=0.0 w=0.5]
Mountpoint:            [x=-7.4505806E-8 y=-0.49999943 z=-2.9057264E-7 w=-3.1292439E-7]        [x=0.49089 y=0.553379 z=0.446544 w=0.503386]
Mountpoint parent:     [x=0.22327162 y=-0.25169235 z=-0.24544461 w=-0.2766894]        [x=0.018487 y=-0.015465 z=-0.001465 w=0.999708]
Mountpoint parent:     [x=0.23174883 y=-0.25168762 z=-0.24697864 w=-0.26822922]        [x=0.048764 y=-0.727602 z=0.045756 w=0.682732]


(The rotations and translations remain constant after the second update())

The mountpoint's WorldRotation and LocalRotation is below that
The mountpoint's immendiate parent is outputted (there are a few of them)  

The good news is that I've narrowed down the problem to either with jbullet-jme, jbullet, bullet or the way I'm using the jbullet-jme API.

If you know the solution to this problem I would appreciate some pointers, as it is: I'm rather stuck  :?

In general PhysicsCharacterNodes should not rotate at all, their rotation is set to zero each physics update. I could not check your problem myself yet, but if theres a problem with applying rotation values maybe I will change jbullet-jme in a way that the physics updates do not modify the rotation at all in character nodes, as its not supported by bullet anyway…

normen said:

In general PhysicsCharacterNodes should not rotate at all, their rotation is set to zero each physics update. I could not check your problem myself yet, but if theres a problem with applying rotation values maybe I will change jbullet-jme in a way that the physics updates do not modify the rotation at all in character nodes, as its not supported by bullet anyway..

Actually this is a bug with JBullet itself. I have had the same issue and I spoke about it in pm's to normen awhile back here are some of my quote from it in how I hackishly solved it. 

Problem:
SomethingNew said:

One issue I'm having right now that maybe you could help with is when I add my PhysicsCharacterNode to the PhysicsSpace it messes up the character.  My character is an OgreXML mesh and is in this order: PhysicsCharacterNode->Player(Node)->BodyMesh(OgreNode)->HeadAttachNode(OgreAttachNode)->HeadMesh(OgreNode).  I don't know what's happening, but as soon as I add the PhysicsCharacterNode with this hierarchy to PhysicsSpace it moves the Head to the center of the body and sets that as the physics bounding box.  It's sorta hard to describe because I can't really understand what's going on, or why the physics engine is messing up my node hierarchy.  Any ideas, or is there is any code that I don't know about that's changing the spatial added to the PhysicsCharacterNode?


Solution:
SomethingNew said:

Ahh ok I understand now.  :D

I sorta have fixed my issue so far, it seems there's an error with JBullet itself!  When you create a JBullet GhostObject with its included Transform the default Transform that's created creates a new javax.vecmath.Matrix3f() for rotation, this matrix that it creates is not the identity Matrix, it's actually a matrix with all values at zero.  This ripples down to my character and rotates the head weirdly.  I fixed it by patching it in your code, but really it should be fixed in JBullet.  Is JBullet still being actively ported?  Here's what I added to buildObject in PhysicsGhostNode of your code:

        gObject.getWorldTransform(tempTrans);
        tempTrans.basis.setIdentity();
        gObject.setWorldTransform(tempTrans);

  This really sucks because it's not elegant and something that can be fixed easily, without committing to JBullet.

Now that I fixed that though, I still having an issue because my PhysicsCharacter is sinking halfway in the floor when I move it.  I don't really think you can help me solve this one though, I just have to keep looking.  ;)


You were actually showing the correct info, as you can see the quaternion for the ghostnode is (0, 0, 0, .5):
monkey_scratches_head said:


PhysicsGhostNode - setWorldRotation: [x=0.0 y=0.0 z=0.0 w=0.5]



The real identity for a quaternion is (0, 0, 0, 1) so the worldRotation is rotating your model when it shouldn't.  Hopefully this will explain this problem a bit.  ;)

@Norman, thanks for the prompt reply, as per usual!



@SomethingNew thanks, you were spot on with the Quaterion being the problem. (I compiled this reply before seeing your post)



Anyway… gathered more data, outputting the rotations for all the nodes from the mountpoint upto the PhysicsCharacterNode:


PhysicsSpace.update()
PhysicsGhostNode - setWorldRotation: [x=0.0 y=0.0 z=0.0 w=0.5]
Mountpoint: [x=-1.4901161E-7 y=-0.99999887 z=-5.811453E-7 w=-6.2584877E-7]        [x=0.49089 y=0.553379 z=0.446544 w=0.503386]
Mountpoint parent:   [x=0.44654325 y=-0.5033847 z=-0.49088922 w=-0.5533788]        [x=0.018487 y=-0.015465 z=-0.001465 w=0.999708]
Mountpoint parent +2: [x=0.46349767 y=-0.50337523 z=-0.49395728 w=-0.53645843]        [x=0.048764 y=-0.727602 z=0.045756 w=0.682732]
Mountpoint parent +3: [x=0.7250419 y=-0.6887041 z=9.99996E-7 w=-2.791E-9]        [x=0.723117 y=-0.690725 z=1.0E-6 w=0.0]
Mountpoint parent +4: [x=0.0 y=0.0 z=0.002791 w=0.999996]        [x=0.0 y=0.0 z=0.002791 w=0.999996]
Mountpoint parent +5: [x=0.0 y=0.0 z=0.0 w=1.0]        [x=0.0 y=0.0 z=0.0 w=1.0]
Mountpoint parent +6: [x=0.0 y=0.0 z=0.0 w=1.0]        [x=0.0 y=0.0 z=0.0 w=1.0]
Mountpoint parent +7: [x=0.0 y=0.0 z=0.0 w=1.0]        [x=0.0 y=0.0 z=0.0 w=0.5]
Mountpoint parent +7 class: class com.jmex.jbullet.nodes.PhysicsCharacterNode
PhysicsSpace.update()
PhysicsGhostNode - setWorldRotation: [x=0.0 y=0.0 z=0.0 w=0.5]
Mountpoint: [x=-7.4505806E-8 y=-0.49999943 z=-2.9057264E-7 w=-3.1292439E-7]        [x=0.49089 y=0.553379 z=0.446544 w=0.503386]
Mountpoint parent:   [x=0.22327162 y=-0.25169235 z=-0.24544461 w=-0.2766894]        [x=0.018487 y=-0.015465 z=-0.001465 w=0.999708]
Mountpoint parent +2: [x=0.23174883 y=-0.25168762 z=-0.24697864 w=-0.26822922]        [x=0.048764 y=-0.727602 z=0.045756 w=0.682732]
Mountpoint parent +3: [x=0.36252096 y=-0.34435204 z=4.99998E-7 w=-1.3955E-9]        [x=0.723117 y=-0.690725 z=1.0E-6 w=0.0]
Mountpoint parent +4: [x=0.0 y=0.0 z=0.0013955 w=0.499998]        [x=0.0 y=0.0 z=0.002791 w=0.999996]
Mountpoint parent +5: [x=0.0 y=0.0 z=0.0 w=0.5]        [x=0.0 y=0.0 z=0.0 w=1.0]
Mountpoint parent +6: [x=0.0 y=0.0 z=0.0 w=0.5]        [x=0.0 y=0.0 z=0.0 w=1.0]
Mountpoint parent +7: [x=0.0 y=0.0 z=0.0 w=0.5]        [x=0.0 y=0.0 z=0.0 w=0.5]
Mountpoint parent +7 class: class com.jmex.jbullet.nodes.PhysicsCharacterNode



Although I'm not great with Quaterions, it does look like the problem is caused by the w value going from 1.0 to 0.5.
The localRotation of the PhysicsCharacterNode in the first PhysicsSpace.update() chages to 0.5, which is then propagated to the WorldRotation on the subsequent update, affecting the child nodes.

I tried removing rotation applied by commenting out the setWorldRotation() in PhysicsGhostNode on my local copy of bullet-jme ...and it worked! Everything was positioned where it should be :)

I checked out the TestPhysicsCharacter from the jbullet-jme tests and that does the same thing, the WorldRotation for the PhysicsCharacterNode is [0, 0, 0, 0.5].
The problem I'm experiencing will only be encountered when there are children that have rotations.


Summary
The cause is the 0.5 'w' value in the given Quaterion rotation for setWorldRotation() in PhysicsGhostNode.
The identity for a Quaterion would be [0,0,0,1], with: w == 1.

Ending Question
From a performance viewpoint, as PhysicsCharacterNode is not to be rotated, then why apply a rotation at all?
Basically every update a Quaterion multiplcation is applied to the PhysicsCharacterNode where the goal is to achieve no rotation
monkey_scratches_head said:

Ending Question
From a performance viewpoint, as PhysicsCharacterNode is not to be rotated, then why apply a rotation at all?
Basically every update a Quaterion multiplcation is applied to the PhysicsCharacterNode where the goal is to achieve no rotation
norman wrote:
Edit: new constructor with CollisionShape is in svn, have also overridden setWorldRotation() in PhysicsCharacterNode, still have to check if that leads to problems somehow, but I think it should not.

Just to let you know, I've just updated the svn and tested the changes out with my code
monkey_scratches_head said:

Just to let you know, I've just updated the svn and tested the changes out with my code