Guest User

Apache Commons Math3 bug in Rotation / mat2quat

a guest
Jan 8th, 2017
173
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Java 3.83 KB | None | 0 0
  1. package org.example.bug.mat2quat;
  2.  
  3. import com.sun.javafx.geom.Matrix3f;
  4. import com.sun.javafx.geom.Quat4f;
  5. import org.apache.commons.lang.NotImplementedException;
  6. import org.apache.commons.math3.geometry.euclidean.threed.Rotation;
  7. import org.apache.commons.math3.linear.Array2DRowRealMatrix;
  8. import org.apache.commons.math3.linear.RealMatrix;
  9. import org.junit.Test;
  10. import org.slf4j.Logger;
  11. import org.slf4j.LoggerFactory;
  12.  
  13. import javax.vecmath.Matrix4d;
  14. import javax.vecmath.Quat4d;
  15. import java.util.Locale;
  16.  
  17. public class MatrixToQuaternionUnitTest
  18. {
  19.     private static final Logger log = LoggerFactory.getLogger(MatrixToQuaternionUnitTest.class);
  20.  
  21.     @Test
  22.     public void commonsMathTest()
  23.     {
  24.         testCommonsMath(Math.PI / 2, 0);      // branch 1 in Rotation#mat2quat(final double[][])
  25.         testCommonsMath(Math.PI / 10 * 9, 2); // branch 2
  26.         testCommonsMath(Math.PI / 10 * 9, 1); // branch 3
  27.         testCommonsMath(Math.PI / 10 * 9, 0); // branch 4
  28.  
  29.         /*
  30.             Output:
  31.                 [ 0.7  0.0  0.0 -0.7] (Commons Math)
  32.                 [ 0.7  0.0  0.0  0.7] (JavaFX)
  33.                 [ 0.7  0.0  0.0  0.7] (JavaX Vecmath)
  34.                 [ 0.7  0.0  0.0  0.7] (NumPy + transformations.py)
  35.  
  36.                 [-0.2  1.0  0.0  0.0] (Commons Math)
  37.                 [ 0.2  1.0  0.0  0.0] (JavaFX)
  38.                 [ 0.2  1.0  0.0  0.0] (JavaX Vecmath)
  39.                 [ 0.2  1.0  0.0  0.0] (NumPy + transformations.py)
  40.  
  41.                 [ 0.2  0.0  1.0  0.0] (Commons Math)
  42.                 [ 0.2  0.0 -1.0  0.0] (JavaFX)
  43.                 [ 0.2  0.0 -1.0  0.0] (JavaX Vecmath)
  44.                 [-0.2  0.0  1.0  0.0] (NumPy + transformations.py)
  45.  
  46.                 [-0.2  0.0  0.0  1.0] (Commons Math)
  47.                 [ 0.2  0.0  0.0  1.0] (JavaFX)
  48.                 [ 0.2  0.0  0.0  1.0] (JavaX Vecmath)
  49.                 [ 0.2  0.0  0.0  1.0] (NumPy + transformations.py)
  50.          */
  51.     }
  52.  
  53.     private static void testCommonsMath(double angle, int id)
  54.     {
  55.         Rotation rot = new Rotation(makeMatrix(angle, id).getData(), 1e-10);
  56.         log.info(String.format((Locale)null, "[%4.1f %4.1f %4.1f %4.1f] (Commons Math)", rot.getQ0(), rot.getQ1(), rot.getQ2(), rot.getQ3()));
  57.  
  58.         Quat4f quatFx = new Quat4f();
  59.         quatFx.set(makeJavaFxMatrix(angle, id));
  60.         log.info(String.format((Locale)null, "[%4.1f %4.1f %4.1f %4.1f] (JavaFX)", quatFx.w, quatFx.x, quatFx.y, quatFx.z));
  61.  
  62.         Quat4d quatX = new Quat4d();
  63.         makeJavaXMatrix(angle, id).get(quatX);
  64.         log.info(String.format((Locale)null, "[%4.1f %4.1f %4.1f %4.1f] (JavaX Vecmath)", quatX.w, quatX.x, quatX.y, quatX.z));
  65.     }
  66.  
  67.     private static RealMatrix makeMatrix(double angle, int id)
  68.     {
  69.         double[][] data;
  70.         double c = Math.cos(angle);
  71.         double s = Math.sin(angle);
  72.  
  73.         switch(id)
  74.         {
  75.             case 0: data = new double[][] { {c, -s, 0}, {s, c,  0}, {0, 0, 1} }; break;
  76.             case 1: data = new double[][] { {c, 0, -s}, {0, 1,  0}, {s, 0, c} }; break;
  77.             case 2: data = new double[][] { {1, 0,  0}, {0, c, -s}, {0, s, c} }; break;
  78.             default: throw new NotImplementedException();
  79.         }
  80.         return new Array2DRowRealMatrix(data);
  81.     }
  82.  
  83.     private static Matrix3f makeJavaFxMatrix(double angle, int id)
  84.     {
  85.         float[] data;
  86.         float c = (float)Math.cos(angle);
  87.         float s = (float)Math.sin(angle);
  88.  
  89.         switch(id)
  90.         {
  91.             case 0: data = new float[] {c, -s, 0,  s, c,  0,  0, 0, 1}; break;
  92.             case 1: data = new float[] {c, 0, -s,  0, 1,  0,  s, 0, c}; break;
  93.             case 2: data = new float[] {1, 0,  0,  0, c, -s,  0, s, c}; break;
  94.             default: throw new NotImplementedException();
  95.         }
  96.         return new Matrix3f(data);
  97.     }
  98.  
  99.     private static Matrix4d makeJavaXMatrix(double angle, int id)
  100.     {
  101.         double[] data;
  102.         double c = Math.cos(angle);
  103.         double s = Math.sin(angle);
  104.  
  105.         switch(id)
  106.         {
  107.             case 0: data = new double[] {c, -s, 0, 0, s,  c,  0, 0,  0, 0, 1, 0,  0, 0, 0, 1}; break;
  108.             case 1: data = new double[] {c, 0, -s, 0, 0,  1,  0, 0,  s, 0, c, 0,  0, 0, 0, 1}; break;
  109.             case 2: data = new double[] {1, 0,  0, 0, 0,  c, -s, 0,  0, s, c, 0,  0, 0, 0, 1}; break;
  110.             default: throw new NotImplementedException();
  111.         }
  112.         return new Matrix4d(data);
  113.     }
  114. }
Advertisement
Add Comment
Please, Sign In to add comment