在OpenGL中我的四元数旋转有什么问题?

在互联网上写下笔记有助于正确构建四元数课程。 我的问题是将它们用于实际使用,并将它们用于原始OpenGL中的旋转。

在我的输入事件中,我有以下几点:

Quaternion<float> qPrev = qRot;
qRot = qRot.UnitQuaternion(); // #1.
Quaternion<float> axis(5., 0., 1., 0.);
qRot = qPrev*axis;
qRot *= qPrev.conjugate();
//#2. qRot = qRot.UnitQuaternion();

如果我使用#1旋转结果单元,它会旋转几秒钟,加速然后完全消失。

如果我使用#2作为单位结果框“摇摆”并且从不旋转。

另外,我使用这个基于其他实现:

Quaternion<float> qPrev = qRot;
Quaternion<float> axis(-5./100, 0., 1., 0.); // #3.
axis = axis.UnitQuaternion();
qRot = qPrev*axis;
// #4. qRot *= qPrev.conjugate();

哪里#3。 最有意义的是,以一个非单位四元组的单位,并最初乘以身份四元组; 将所有内容都保存在单位中。

在哪里#4。 根据我对等式旋转定义的理解,尝试乘以共轭。

所有这些产生了一个小摆动,#1是我得​​到的最接近的; 盒子旋转,然后很快,然后消失。


我的理解是,我有一个轴,我可以绕w旋转多少(以弧度表示的角度)。 我只是乘以方向,并乘以方向的负面结果; 例如缀合物。


渲染代码(这可能是罪魁祸首):

// Apply some transformations
glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
glTranslatef(0, 0, -100.f);
glRotatef(qRot.x, 1., 0, 0);
glRotatef(qRot.y, 0, 1., 0);
glRotatef(qRot.z, 0, 0, 1.);

// Draw the cube
glDrawArrays(GL_TRIANGLES, 0, 36);

// Draw some text on top of our OpenGL object
window.pushGLStates();

我很感激帮助


编辑:非常感谢@ybungalobill帮忙

我从四元数中得到的东西是四元数学方面非常具体的应用。 我想要一个旋转轴,而在我的示例中,我使用直接值创建四元数。 这不是如何导出旋转矩阵的。 我需要更多步骤:

void FromAxisAngle(_Tp theta, _Tp x, _Tp y, _Tp z)
{
    //Angle should be in radians
    this->w = cos(theta/2);

    //Axes
    this->x = x * sin(theta/2);
    this->y = y * sin(theta/2);
    this->z = z * sin(theta/2);
    //Normalize
    *this = this->UnitQuaternion();
}

再次,获得旋转矩阵是一个非常具体的应用程序,具有非常特定的步骤。 四元数不会“开箱即用”。

旋转逻辑也有一些小的改变:

   Quaternion<float> qPrev = qRot;
   Quaternion<float> axis;
   axis.FromAxisAngle(-5./100, 1., 0., 0.);
   qRot = qPrev*axis;

所以现在我创建了一个数学上正确的四元数从我的旋转轴。 然后乘。

最后,我必须做的最后一件事就是从我的四元数中创建一个OpenGL可以使用的矩阵。 所以我们有更多的数学方法来使它在旋转事物的符号中出现:

void GetMatrix(_Tp matrix[16])
{
   Quaternion<_Tp> temp(this->UnitQuaternion());
  _Tp qw = temp.w;
  _Tp qx = temp.x;
  _Tp qy = temp.y;
  _Tp qz = temp.z;

  matrix[0] = 1.0f - 2.0f*qy*qy - 2.0f*qz*qz;
  matrix[1] = 2.0f*qx*qy - 2.0f*qz*qw;
  matrix[2] = 2.0f*qx*qz + 2.0f*qy*qw;
  matrix[3] = 0;

  matrix[4] = 2.0f*qx*qy + 2.0f*qz*qw;
  matrix[5] = 1.0f - 2.0f*qx*qx - 2.0f*qz*qz;
  matrix[6] = 2.0f*qy*qz - 2.0f*qx*qw;
  matrix[7] = 0;

  matrix[8] = 2.0f*qx*qz - 2.0f*qy*qw;
  matrix[9] = 2.0f*qy*qz + 2.0f*qx*qw;
  matrix[10] = 1.0f - 2.0f*qx*qx - 2.0f*qy*qy;
  matrix[11] = 0;

  matrix[12] = 0;
  matrix[13] = 0;
  matrix[14] = 0;
  matrix[15] = 1;
}

使用glMultMatrix多维数据集旋转。


glRotatef(qRot.x, 1., 0, 0);
glRotatef(qRot.y, 0, 1., 0);
glRotatef(qRot.z, 0, 0, 1.);

这不是如何将四元数旋转应用于总帐状态。 你必须将它转化成一个矩阵从这里公式如下,然后调用glMultMatrixglMultTransposeMatrix 。 之后,第3号方法将按预期工作。


从Stannum库中将任何非零四元数转换为矩阵的代码:

template<class T>
mat<T,3,3> mat_rotation(const quat<T> &x)
{
    T s = 2/norm2(x); // cheap renormalization even of non-unit quaternions
    T wx = x.w*x.x, wy = x.w*x.y, wz = x.w*x.z;
    T xx = x.x*x.x, xy = x.x*x.y, xz = x.x*x.z;
    T yy = x.y*x.y, yz = x.y*x.z;
    T zz = x.z*x.z;

    return mat<T,3,3>(
        1 - s*(yy+zz),  s*(xy-wz),  s*(xz+wy),
        s*(xy+wz),  1 - s*(xx+zz),  s*(yz-wx),
        s*(xz-wy),  s*(yz+wx),  1 - s*(xx+yy)
    );
}
链接地址: http://www.djcxy.com/p/14359.html

上一篇: What is wrong with my Quaternion rotation in OpenGL?

下一篇: Quaternion to Rotation Matrix, incorrect values using Eigen Library