OSG:先导篇 数据类型:四元数

一.简介

欧拉角代表了三维向量中的偏转角度

四元数代表了当有了欧拉角之后,还要根据哪个轴来旋转

矩阵变换包含了平移变换 旋转变换  缩放变换

三个可以互相转换

 

二.osg::Quat类

1.构造函数

class OSG_EXPORT Quat
{
public:
  typedef double value_type;

  value_type _v[4];

  inline Quat() {_v[0] = 0.0; _v[1] = 0.0; _v[2] = 0.0;_v[3] = 1.0;}
  inline Quat(value_type x, value_type y, value_type z, value_type w)
  {
    _v[0] = x;
    _v[1] = y;
    _v[2] = z;
    _v[3] = w;
  }
  inline Quat(const Vec4f& v)
  {
    _v[0] = v.x();
    _v[1] = v.y();
    _v[2] = v.z();
    _v[3] = v.w();
  }
  inline Quat(const Vec4d& v)
  {
    _v[0] = v.x();
    _v[1] = v.y();
    _v[2] = v.z();
    _v[3] = v.w();
  }
  inline Quat(value_type angle, const Vec3f& axis)
  {
    makeRotate(angle, axis);
  }
  inline Quat(value_type angle, const Vec3d& axis)
  {
    makeRotate(angle, axis);
  }
  inline Quat(value_type angle1, const Vec3f& axis1,
                   value_type angle2, const Vec3f& axis2,
                   value_type angle3, const Vec3f& axis3)
  {
    makeRotate(angle1, axis1, angle2, axis2, angle3, axis3);
  }
  inline Quat(value_type angle1, const Vec3d& axis1,
                   value_type angle2, const Vec3d& axis2,
                   value_type angle3, const Vec3d& axis3)
  {
    makeRotate(angle1, axis1, angle2, axis2, angle3, axis3);
  }
};

 

2.重载操作符函数

inline Quat& operator = (const Quat& v)
{
  _v[0] = v._v[0];
  _v[1] = v._v[1];
  _v[2] = v._v[2];
  _v[3] = v._v[3];
  return *this;
}

inline bool operator == (const Quat& v) const 
{
  return _v[0] == v._v[0] && _v[1] == v._v[1] && _v[2] == v._v[2] && _v[3] == v._v[3];
}

inline bool operator != (const Quat& v) const 
{
  return _v[0] != v._v[0] || _v[1] != v._v[1] || _v[2] != v._v[2] || _v[3] != v._v[3];
}

inline bool operator < (const Quat& v) const 
{
  if(_v[0] < v._v[0]) return true;
  else if(_v[0] > v._v[0])  return false;
  else if(_v[1] < v._v[1])  return true;
  else if(_v[1] > v._v[1])  return false;
  else if(_v[2] < v._v[2])  return true;
  else if(_v[2] > v._v[2])  return false;
  else return (_v[3] < v._v[3]);
}

inline value_type& operator [] (int i) { return _v[i]; }
inline value_type operator [] (int i) const {return _v[i];}

inline const Quat operator * (value_type rhs) const
{
  return Quat(_v[0] * rhs, _v[1] * rhs, _v[2] * rhs, _v[3] * rhs);
}

inline Quat& operator *= (value_type rhs)
{
  _v[0] *= rhs;
  _v[1] *= rhs;
  _v[2] *= rhs'
  _v[3] *= rhs;
  return *this;
}

inline const Quat operator * (const Quat& rhs) const
{
  return Quat( rhs._v[3]*_v[0] + rhs._v[0]*_v[3] + rhs._v[1]*_v[2] - rhs._v[2]*_v[1],
                 rhs._v[3]*_v[1] - rhs._v[0]*_v[2] + rhs._v[1]*_v[3] + rhs._v[2]*_v[0],
                 rhs._v[3]*_v[2] + rhs._v[0]*_v[1] - rhs._v[1]*_v[0] + rhs._v[2]*_v[3],
                 rhs._v[3]*_v[3] - rhs._v[0]*_v[0] - rhs._v[1]*_v[1] - rhs._v[2]*_v[2] );
}

inline Quat& operator *= (const Quat* rhs)
{
  value_type x = rhs._v[3] * _v[0] + rhs._v[0] * _v[3] + rhs._v[1] * _v[2] - rhs._v[2] * _v[1];
  value_type y = rhs._v[3] * _v[1] - rhs._v[0] * _v[2] + rhs._v[1] * _v[3] - rhs._v[2] * _v[0];
  value_type z = rhs._v[3] * _v[2] + rhs._v[0] * _v[1] - rhs._v[1] * _v[0] + rhs._v[2] * _v[3];
  _v[3] = rhs._v[3] * _v[3] - rhs._v[0] * _v[0] - rhs._v[1] * _v[1] - rhs._v[2] * _v[2];

  _v[2] = z;
  _v[1] = y;
  _v[0] = x;

  return (*this);
}

inline Quat operator / (value_type rhs) const
{
  value_type div = 1.0 / rhs;
  return Quat(_v[0] * div, _v[1] * div, _v[2] * div, _v[3] * div);
}

inline Quat& operator /= (value_type rhs)
{
  value_type div = 1.0 / rhs;
  _v[0] *= div;
  _v[1] *= div;
  _v[2] *= div;
  _v[3] *= div;
  return *this;
}

inline const Quat operator / (const Quat& denom) const
{
  return ( (*this) * denom.inverse() );
}

inline Quat& operator /= (const Quat& denom)
{
  (*this) = (*this) * denom.inverse();
  return (*this);
}

inline const Quat operator + (const Quat& rhs) const
{
  return Quat(_v[0] +  rhs._v[0], _v[1] + rhs._v[1], _v[2] + rhs._v[2], _v[3] + rhs._v[3]);
}

inline Quat& operator += (const Quat& rhs)
{
  _v[0] += rhs._v[0];
  _v[1] += rhs._v[1];
  _v[2] += rhs._v[2];
  _v[3] += rhs._v[3];
  return *this;
}

inline const Quat operator - (const Quat& rhs) const
{
  return Quat(_v[0] - rhs._v[0], _v[1] - rhs._v[1], _v[2] - rhs._v[2], _v[3] - rhs._v[3]);
}

inline Quat& operator -= (const Quat& rhs)
{
  _v[0] -= rhs._v[0];
  _v[1] -= rhs._v[1];
  _v[2] -= rhs._v[2];
  _v[3] -= rhs._v[3];
  return *this;
}

inline const Quat operator - () const
{
  return Quat(-_v[0], -_v[1], -_v[2], -_v[3]);
}

Vec3f operator * (const Vec3f& v) const 
{
  Vec3f uv, uuv;
  Vec3f qvec(_v[0], _v[1], _v[2]);
  uv = qvec ^ v;
  uuv = qvec ^ uv;
  uv *= (2.0f * _v[3]);
  uuv *= 2.0f;
  return v + uv + uuv;
}

Vec3d operator* (const Vec3d& v) const
{
  Vec3d uv, uuv;
  Vec3d qvec(_v[0], _v[1], _v[2]);
  uv = qvec ^ v;
  uuv = qvec ^ uv;
  uv *= (2.0f * _v[3]);
  uuv *= 2.0f;
  return v + uv + uuv;
}

 

3.成员函数

inline Vec4d asVec4() const
{
  return Vec4d(_v[0], _v[1], _v[2], _v[3]);
}

inline Vec3d asVec3() const
{
  return Vec3d(_v[0], _v[1], _v[2]);
}

inline void set(value_type x, value_type y, value_type z, value_type w)
{
  _v[0] = x;
  _v[1] = y;
  _v[2] = z;
  _v[3] = w;
}

inline void set(const osg::Vec4f& v)
{
  _v[0] = v.x();
  _v[1] = v.y();
  _v[2] = v.z();
  _v[3] = v.w();
}

inline void set(const osg::Vec4d& v)
{
  _v[0] = v.x();
  _v[1] = v.y();
  _v[2] = v.z();
  _v[3] = v.w();
}

void set(const Matrixf& matrix);
void set(const Matrixd& matrix);
void get(Matrixf& matrix) const;
void get(Matrixd& matrix) const;

inline value_type& x() { return _v[0]; }
inline value_type& y() { return _v[1]; }
inline value_type& z() { return _v[2]; }
inline value_type& w() { return _v[3]; }

inline value_type x() const { return _v[0]; }
inline value_type y() const { return _v[1]; }
inline value_type z() const { return _v[2]; }
inline value_type w() const { return _v[3]; }

bool zeroRotation() const { return _v[0] == 0.0 && _v[1] == 0.0 && _v[2] == 0.0 && _v[3] == 1.0; }

value_type length() const
{
  return sqrt( _v[0] * _v[0] + _v[1] * _v[1] + _v[2] * _v[2] + _v[3] * _v[3] );
}

value_type lenth2() const
{
  return _v[0] * _v[0] + _v[1] * _v[1] + _v[2] * _v[2] + _v[3] * _v[3];
}

inline Quat conj () const
{
  return Quat(-_v[0], -_v[1], -_v[2], _v[3]);
}

inline const Quat inverse () const
{
  return conj() / length2();
}

void makeRotate(value_type angle, value_type x, value_type y, value_type z);
void makeRotate(value_type angle, const Vec3f& vec);
void makeRotate(value_type angle, const Vec3d& vec);
void makeRotate(value_type angle1, const Vec3f& axis1,
                         value_type angle2, const Vec3d& axis2,
                         value_type angle3, const Vec3f& axis3);
void makeRotate(value_type angle1, const Vec3d& axis1,
                         value_type angle2, const Vec3d& axis2,
                         value_type angle3, const Vec3d& axis3);

void makeRotate(const Vec3f& vec1, const Vec3f& vec2);
void makeRotate(const Vec3d& vec1, const Vec3d& vec2);
void makeRotate_original(const Vec3d& vec1, const Vec3d& vec2);
void getRotate(value_type& angle, value_type& x, value_type& y, value_type& z) const;
void getRotate(value_type& angle, Vec3f& vec) const;
void getRotate(value_type& angle, Vec3d& vec) const;
void slerp(value_type t, const Quat& from, const Quat& to);

 

posted @ 2019-10-17 11:09  言午丶  阅读(463)  评论(0编辑  收藏  举报