Skip to content
22 changes: 22 additions & 0 deletions jme3-core/src/main/java/com/jme3/scene/Spatial.java
Original file line number Diff line number Diff line change
Expand Up @@ -986,6 +986,28 @@ public Vector3f worldToLocal(final Vector3f in, final Vector3f store) {
return worldTransform.transformInverseVector(in, store);
}

/**
* Transforms the given quaternion from world space to local space relative to this object's transform.
*
* @param in the input quaternion in world space that needs to be transformed
* @param store an optional Quaternion to store the result; if null, a new Quaternion will be created
* @return the transformed quaternion in local space, either stored in the provided Quaternion or a new one
*/
public Quaternion worldToLocal(final Quaternion in, Quaternion store){
checkDoTransformUpdate();
if(store == null){
store=new Quaternion(in);
}else{
store.set(in);
}
TempVars tempVars = TempVars.get();
Quaternion worldRotation = tempVars.quat1.set(getWorldRotation());
worldRotation.inverseLocal();
store.multLocal(worldRotation);
tempVars.release();
return store;
}

/**
* <code>getParent</code> retrieves this node's parent. If the parent is
* null this is the root node.
Expand Down
32 changes: 32 additions & 0 deletions jme3-core/src/test/java/com/jme3/scene/SpatialTest.java
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,9 @@
*/
package com.jme3.scene;

import com.jme3.math.FastMath;
import com.jme3.math.Quaternion;
import com.jme3.math.Vector3f;
import com.jme3.scene.control.UpdateControl;
import org.junit.Assert;
import org.junit.Test;
Expand Down Expand Up @@ -119,4 +122,33 @@ public void testAddControlAt() {
Assert.assertEquals(testSpatial, control1.getSpatial());
Assert.assertEquals(testSpatial, control2.getSpatial());
}

@Test
public void testTransferToOtherNode(){
Node nodeA = new Node("nodeA");
Node nodeB = new Node("nodeB");
Node testNode=new Node("testNode");
nodeA.setLocalTranslation(-1,0,0);
nodeB.setLocalTranslation(1,0,0);
nodeB.rotate(0,90* FastMath.DEG_TO_RAD,0);
testNode.setLocalTranslation(1,0,0);
nodeA.attachChild(testNode);
Vector3f worldTranslation = testNode.getWorldTranslation().clone();
Quaternion worldRotation = testNode.getWorldRotation().clone();

Assert.assertTrue(worldTranslation.isSimilar(testNode.getWorldTranslation(),1e-6f));
Assert.assertTrue(worldRotation.isSimilar(testNode.getWorldRotation(),1e-6f));

nodeB.attachChild(testNode);

Assert.assertFalse(worldTranslation.isSimilar(testNode.getWorldTranslation(),1e-6f));
Assert.assertFalse(worldRotation.isSimilar(testNode.getWorldRotation(),1e-6f));

testNode.setLocalTranslation(nodeB.worldToLocal(worldTranslation,null));
Assert.assertTrue(worldTranslation.isSimilar(testNode.getWorldTranslation(),1e-6f));

testNode.setLocalRotation(nodeB.worldToLocal(worldRotation,null));
System.out.println(testNode.getWorldRotation());
Assert.assertTrue(worldRotation.isSimilar(testNode.getWorldRotation(),1e-6f));
}
}
Loading