【问题标题】:matrix rotation multiple times矩阵旋转多次
【发布时间】:2014-12-16 04:00:53
【问题描述】:

我在理解矩阵时遇到了问题。如果我将矩阵围绕 X 轴旋转 90 度,它工作正常,但是,如果我将它围绕 Y 轴旋转 90 度,它实际上会在 Z 轴上旋转它。我猜每次旋转后轴都会移动。如何使用原始轴进行第二次(或更多次)旋转?这叫局部和全局旋转吗?

【问题讨论】:

    标签: opengl matrix rotation


    【解决方案1】:

    在旋转之间添加“glLoadIdentity”。

    【讨论】:

    • 但是我不会合并这两个旋转。
    • 如果您使用 glRotate 应该可以,但很高兴您找到了自己的解决方案。
    • glLoadIdentity 根本没有帮助。这会将矩阵清除为单位,然后下一次旋转将乘以该单位矩阵。实际上,这意味着唯一能做任何事情的转换将是最后一次执行的转换。
    • 你说的都是对的。我又一次不知道自己在想什么。
    【解决方案2】:

    您不会“旋转”矩阵。您通过乘法应用旋转变换矩阵。是的,每次调用 OpenGL 矩阵操作函数时,结果都将用作下一次变换乘法的输入。

    绕 X 轴旋转 90° 会将 Y 轴映射到 Z,将 Z 轴映射到 -Y,这就是您所观察到的。所以接下来发生的任何转变都是从这个开始的。

    要么使用 glLoadIdentity 重新为每个对象构建整个转换以重置为标识,要么使用 glPushMatrix / glPopMatrix 创建“转换块”的层次结构。或者更好的是,完全放弃 OpenGL 内置矩阵堆栈,并将其替换为适当的矩阵数学库,如 GLM、Eigen 或类似库。

    【讨论】:

    • 我不使用 opengl 来做数学。我使用自己的图书馆。一旦我计算了我的矩阵,我就用 glUniformMatrix...() 加载它
    【解决方案3】:

    在实践中,克服这个问题的最佳方法是使用四元数,这有点数学。你是对的;如果你将它围绕 Y 旋转 90 度,而不是你想围绕 Z 旋转它,你将围绕 X 旋转。

    这是一个将欧拉角转换为四元数的好来源:http://www.euclideanspace.com/maths/geometry/rotations/conversions/eulerToQuaternion/

    下面是如何用四元数制作一个旋转矩阵: http://www.euclideanspace.com/maths/geometry/rotations/conversions/quaternionToMatrix/

    填满矩阵后,可以调用glMultMatrix( qMatrix);进行乘法运算。

    【讨论】:

    • 我以前看过四元数,很复杂。但我想我会坚持使用矩阵。
    【解决方案4】:

    昨晚想了想找到了答案(我好像总是这样……)

    我有一个名为 GLMatrix 的对象来保存矩阵:

      class GLMatrix {
        public float m[] = new float[16];
        ...includes many methods to deal with matrix...
      }
    

    并且它有一个添加旋转的功能:

      public void addRotate2(float angle, float ax, float ay, float az) {
        GLMatrix tmp = new GLMatrix();
        tmp.setAA(angle, ax, ay, az);
        mult4x4(tmp);
      }
    

    如您所见,我使用轴角 (AA),它使用 setAA() 应用于临时矩阵,然后乘以当前矩阵。 昨晚我想如果我将AA的输入向量旋转当前矩阵然后创建临时矩阵和倍数。

    所以它看起来像这样:

      public void addRotate4(float angle, float ax, float ay, float az) {
        GLMatrix tmp = new GLMatrix();
        GLVector3 vec = new GLVector3();
        vec.v[0] = ax;
        vec.v[1] = ay;
        vec.v[2] = az;
        mult(vec);  //multiple vector by current matrix
        tmp.setAA(angle, vec.v[0], vec.v[1], vec.v[2]);
        mult4x4(tmp);
      }
    

    它按预期工作! addRotate4() 函数现在在原始轴上旋转。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-02-08
      • 2011-05-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多