gltl.h
上传用户:sesekoo
上传日期:2020-07-18
资源大小:21543k
文件大小:46k
- #if (!defined __GLTL_H)
- #define __GLTL_H
- // disable warning C4201
- #pragma warning( push )
- #pragma warning( disable : 4201 )
- namespace gltl
- {
- template < class _num >
- class ntraits;
- template < class _num, class _ntr >
- class vector3;
- template < class _num, class _ntr >
- class vector4;
- template < class _num, class _ntr >
- class matrix;
- #include <math.h>
- #if (defined _DEBUG)
- #if (defined ASSERT)
- #define __gltl_assert__(__x__) ASSERT(__x__)
- #elif (defined ATLASSERT)
- #define __gltl_assert__(__x__) ATLASSERT(__x__)
- #else
- #include <assert.h>
- #define __gltl_assert__(__x__) assert(__x__)
- #endif
- #else
- #define __gltl_assert__(__x__)
- #endif // _DEBUG
- template < class _num >
- class ntraits
- {
- public:
- typedef const _num _numc;
- typedef _num & _numr;
- typedef const _num & _numrc;
- typedef _num * _nump;
- typedef const _num * _numpc;
- static _num adjust_angle_d(
- _numc _angle_degrees,
- long _l_adjust_prec = 1000L
- )
- {
- long _ang = long( _angle_degrees * ((_num)(_l_adjust_prec)) );
- long _modx360 = 360L * _l_adjust_prec;
- // long _modx180 = _modx360 >> 1; // _modx360/2
- _ang %= _modx360;
- if( _ang < 0L )
- _ang = _modx360 + _ang;
- __gltl_assert__( _ang >= 0L );
- // if( _ang > _modx180 )
- // _ang = _ang%_modx180 - _modx180;
- _num _ret_val = (_num)(_ang);
- _ret_val /= (_num)(_l_adjust_prec);
- return _ret_val;
- }
- static _numc get_pi()
- {
- return ((_num)(3.1415926535897932384626433832795));
- }
- static _numc get_safe_min()
- {
- return ((_num)(0.000001));
- }
- static _numc get_def_epsilon()
- {
- return ((_num)(0.0001));
- }
- static _num r2d( _numc _angle_radians )
- {
- return
- adjust_angle_d(
- ( _angle_radians * ((_num)180.0) )
- / get_pi()
- );
- }
- static _num d2r( _numc _angle_degrees )
- {
- return
- ( adjust_angle_d(_angle_degrees) * get_pi() )
- / ((_num)180.0)
- ;
- }
- static _num abs( _numc _val )
- {
- return (_val >= (_num)(0.0)) ? _val : (-_val);
- }
- static _num sin( _numc _val )
- {
- return ( (_num) ::sin(_val) );
- }
- static _num cos( _numc _val )
- {
- return ( (_num) ::cos(_val) );
- }
- static _num tan( _numc _val )
- {
- return ( (_num) ::tan(_val) );
- }
- static _num asin( _numc _val )
- {
- return ( (_num) ::asin(_val) );
- }
- static _num acos( _numc _val )
- {
- return ( (_num) ::acos(_val) );
- }
- static _num atan( _numc _val )
- {
- return ( (_num) ::atan(_val) );
- }
- static _num atan2( _numc _y, _numc _x )
- {
- return ( (_num) ::atan2( _y, _x ) );
- }
- static _num sqrt( _numc _val )
- {
- return ( (_num) ::sqrt(_val) );
- }
- };
- template < class _num, class _ntr >
- class vector3
- {
- public:
-
- typedef const _num _numc;
- typedef _num & _numr;
- typedef const _num & _numrc;
- typedef _num * _nump;
- typedef const _num * _numpc;
- typedef vector3<_num,_ntr> _v3t;
- typedef vector3<_num,_ntr> & _v3rt;
- typedef const vector3<_num,_ntr> & _v3rct;
- typedef vector4<_num,_ntr> _v4t;
- typedef vector4<_num,_ntr> & _v4rt;
- typedef const vector4<_num,_ntr> & _v4rct;
- typedef matrix<_num,_ntr> _mt;
- typedef matrix<_num,_ntr> & _mrt;
- typedef const matrix<_num,_ntr> & _mrct;
-
- union
- {
- struct { _num x, y, z; };
- struct { _num a, b, c; };
- _num arr[3];
- };
- vector3(
- _numc _x = ((_num)0.0),
- _numc _y = ((_num)0.0),
- _numc _z = ((_num)0.0)
- )
- : x( _x )
- , y( _y )
- , z( _z )
- {
- }
- void load_vector(
- _num _x = ((_num)0.0),
- _num _y = ((_num)0.0),
- _num _z = ((_num)0.0)
- )
- {
- x = _x;
- y = _y;
- z = _z;
- }
-
- void translate(
- _num _x = ((_num)0.0),
- _num _y = ((_num)0.0),
- _num _z = ((_num)0.0)
- )
- {
- x += _x;
- y += _y;
- z += _z;
- }
- void scale(
- _num _x = ((_num)1.0),
- _num _y = ((_num)1.0),
- _num _z = ((_num)1.0)
- )
- {
- x *= _x;
- y *= _y;
- z *= _z;
- }
- _num get_length_sq() const
- {
- return ( (_num) (x*x + y*y + z*z) );
- }
- _num get_length() const
- {
- return _ntr::sqrt( get_length_sq() );
- }
- _mt get_as_scale() const;
- _mt get_as_translation() const;
- _mt get_as_rotation_xyz() const;
- _mt get_as_rotation_quaternion() const;
- _v3rt normalize()
- {
- _num _len = get_length();
- if( ( _len < _ntr::get_safe_min() ) && ( _len > (- _ntr::get_safe_min()) ) )
- _len = 1;
- x /= _len;
- y /= _len;
- z /= _len;
- return (*this);
- }
- static inline void stat_multiplication(
- _mrct _mtx,
- _v3rct _v,
- _v3rt _ret_val
- );
- static inline _v3t stat_multiplication(
- _mrct _mtx,
- _v3rct _v
- );
- _numr operator () ( int _i )
- {
- __gltl_assert__( ( 0 <= _i ) && ( _i <= 3 ) );
- return *(((_nump)&x) + _i);
- }
-
- _numr operator [] ( int _i )
- {
- __gltl_assert__( ( 0 <= _i ) && ( _i <= 2 ) );
- return *(((_nump)&x) + _i);
- }
- _numrc operator [] ( int _i ) const
- {
- __gltl_assert__( ( 0 <= _i ) && ( _i <= 2 ) );
- return *(((_nump)&x) + _i);
- }
- bool operator == ( _v3rct _v ) const
- {
- return ( x==_v.x && y==_v.y && z==_v.z ) ? true : false;
- }
- bool operator != ( _v3rct _v ) const
- {
- return ( x==_v.x && y==_v.y && z==_v.z ) ? false : true;
- }
- _v3rt operator = ( _v3rct _v )
- {
- x = _v.x;
- y = _v.y;
- z = _v.z;
- return (*this);
- }
- _v3rt operator = ( _v4rct );
- _v3rt operator *= ( _numc _s )
- {
- x *= _s;
- y *= _s;
- z *= _s;
- return (*this);
- }
- _v3rt operator *= ( _mrct _mtx )
- {
- stat_multiplication( _mtx, *this, *this );
- return (*this);
- }
- _v3rt operator += ( _v3rct _v )
- {
- x += _v.x;
- y += _v.y;
- z += _v.z;
- return (*this);
- }
- _v3rt operator -= ( _v3rct _v )
- {
- x -= _v.x;
- y -= _v.y;
- z -= _v.z;
- return (*this);
- }
- };
- template < class _num, class _ntr >
- inline vector3<_num,_ntr> operator * (
- const vector3<_num,_ntr> & _v,
- const _num _s
- )
- {
- vector3<_num,_ntr> _ret_val;
- _ret_val.x = _v.x * _s;
- _ret_val.y = _v.y * _s;
- _ret_val.z = _v.z * _s;
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline vector3<_num,_ntr> operator * (
- const _num _s,
- const vector3<_num,_ntr> & _v
- )
- {
- vector3<_num,_ntr> _ret_val;
- _ret_val.x = _v.x * _s;
- _ret_val.y = _v.y * _s;
- _ret_val.z = _v.z * _s;
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline _num operator * (
- const vector3<_num,_ntr> & _v1,
- const vector3<_num,_ntr> & _v2
- )
- {
- return ( _v1.x*_v2.x + _v1.y*_v2.y + _v1.z*_v2.z );
- }
- template < class _num, class _ntr >
- inline vector3<_num,_ntr> operator ^ (
- const vector3<_num,_ntr> & _v1,
- const vector3<_num,_ntr> & _v2
- )
- {
- vector3<_num,_ntr> _ret_val;
- _ret_val.x = _v1.y*_v2.z - _v1.z*_v2.y;
- _ret_val.y = _v1.z*_v2.x - _v1.x*_v2.z;
- _ret_val.z = _v1.x*_v2.y - _v1.y*_v2.x;
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline vector3<_num,_ntr> operator + (
- const vector3<_num,_ntr> & _v1,
- const vector3<_num,_ntr> & _v2
- )
- {
- vector3<_num,_ntr> _ret_val;
- _ret_val.x = _v1.x + _v2.x;
- _ret_val.y = _v1.y + _v2.y;
- _ret_val.z = _v1.z + _v2.z;
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline vector3<_num,_ntr> operator - (
- const vector3<_num,_ntr> & _v1,
- const vector3<_num,_ntr> & _v2
- )
- {
- vector3<_num,_ntr> _ret_val;
- _ret_val.x = _v1.x - _v2.x;
- _ret_val.y = _v1.y - _v2.y;
- _ret_val.z = _v1.z - _v2.z;
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline vector3<_num,_ntr> operator - (
- const vector3<_num,_ntr> & _v
- )
- {
- vector3<_num,_ntr> _ret_val;
- _ret_val.x = - _v.x;
- _ret_val.y = - _v.y;
- _ret_val.z = - _v.z;
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline vector3<_num,_ntr> operator + (
- const vector3<_num,_ntr> & _v
- )
- {
- return _v;
- }
- template < class _num, class _ntr >
- inline vector3<_num,_ntr> operator ~ (
- const vector3<_num,_ntr> & _v
- )
- {
- _num _len = _v.get_length();
- vector3<_num,_ntr> _ret_val;
- _ret_val.x = _v.x / _len;
- _ret_val.y = _v.y / _len;
- _ret_val.z = _v.z / _len;
- return _ret_val;
- }
- template < class _num, class _ntr >
- class vector4
- {
- public:
- typedef const _num _numc;
- typedef _num & _numr;
- typedef const _num & _numrc;
- typedef _num * _nump;
- typedef const _num * _numpc;
- typedef vector3<_num,_ntr> _v3t;
- typedef vector3<_num,_ntr> & _v3rt;
- typedef const vector3<_num,_ntr> & _v3rct;
- typedef vector4<_num,_ntr> _v4t;
- typedef vector4<_num,_ntr> & _v4rt;
- typedef const vector4<_num,_ntr> & _v4rct;
- typedef matrix<_num,_ntr> _mt;
- typedef matrix<_num,_ntr> & _mrt;
- typedef const matrix<_num,_ntr> & _mrct;
- union
- {
- struct { _num x, y, z, w; };
- struct { _num a, b, c, d; };
- _num arr[4];
- };
- vector4(
- _numc _x = ((_num)0.0),
- _numc _y = ((_num)0.0),
- _numc _z = ((_num)0.0),
- _numc _w = ((_num)0.0)
- )
- : x( _x )
- , y( _y )
- , z( _z )
- , w( _w )
- {
- }
- void load_vector(
- _num _x = ((_num)0.0),
- _num _y = ((_num)0.0),
- _num _z = ((_num)0.0),
- _num _w = ((_num)0.0)
- )
- {
- x = _x;
- y = _y;
- z = _z;
- w = _w;
- }
- void translate(
- _num _x = ((_num)0.0),
- _num _y = ((_num)0.0),
- _num _z = ((_num)0.0),
- _num _w = ((_num)0.0)
- )
- {
- x += _x;
- y += _y;
- z += _z;
- w += _w;
- }
- void scale(
- _num _x = ((_num)1.0),
- _num _y = ((_num)1.0),
- _num _z = ((_num)1.0),
- _num _w = ((_num)1.0)
- )
- {
- x *= _x;
- y *= _y;
- z *= _z;
- w *= _w;
- }
- _num get_length_sq() const
- {
- return ( (_num) (x*x + y*y + z*z + w*w) );
- }
- _num get_length() const
- {
- return _ntr::sqrt( get_length_sq() );
- }
- _v4rt normalize()
- {
- _num _len = get_length();
- if( ( _len < _ntr::get_safe_min() ) && ( _len > (- _ntr::get_safe_min()) ) )
- _len = 1;
- x /= _len;
- y /= _len;
- z /= _len;
- w /= _len;
- return (*this);
- }
- static inline _v4t stat_multiplication(
- _mrct _mtx,
- _v4rct _v
- );
- static inline void stat_multiplication(
- _mrct _mtx,
- _v4rct _v,
- _v4rt _ret_val
- );
- _numr operator () ( int _i )
- {
- __gltl_assert__( ( 0 <= _i ) && ( _i <= 3 ) );
- return *(((_nump)&x) + _i);
- }
-
- _numr operator [] ( int _i )
- {
- __gltl_assert__( ( 0 <= _i ) && ( _i <= 3 ) );
- return *(((_nump)&x) + _i);
- }
- _numrc operator [] ( int _i ) const
- {
- __gltl_assert__( ( 0 <= _i ) && ( _i <= 3 ) );
- return *(((_nump)&x) + _i);
- }
- bool operator == ( _v4rct _v ) const
- {
- return ( x==_v.x && y==_v.y && z==_v.z && w==_v.w ) ? true : false;
- }
- bool operator != ( _v4rct _v ) const
- {
- return ( x==_v.x && y==_v.y && z==_v.z && w==_v.w ) ? false : true;
- }
- _v4rt operator = ( _v4rct _v )
- {
- x = _v.x;
- y = _v.y;
- z = _v.z;
- w = _v.w;
- return (*this);
- }
- _v4rt operator = ( _v3rct _v )
- {
- x = _v.x;
- y = _v.y;
- z = _v.z;
- w = ((_num)0.0);
- return (*this);
- }
-
- _v4rt operator *= ( _numc _s )
- {
- x *= _s;
- y *= _s;
- z *= _s;
- w *= _s;
- return (*this);
- }
- _v4rt operator *= ( _mrct _mtx )
- {
- stat_multiplication( _mtx, *this, *this );
- return (*this);
- }
- _v4rt operator += ( _v4rct _v )
- {
- x += _v.x;
- y += _v.y;
- z += _v.z;
- w += _v.w;
- return (*this);
- }
- _v4rt operator -= ( _v4rct _v )
- {
- x -= _v.x;
- y -= _v.y;
- z -= _v.z;
- w -= _v.w;
- return (*this);
- }
- };
- template < class _num, class _ntr >
- inline vector4<_num,_ntr> operator * (
- const vector4<_num,_ntr> & _v,
- const _num _s
- )
- {
- vector4<_num,_ntr> _ret_val;
- _ret_val.x = _v.x * _s;
- _ret_val.y = _v.y * _s;
- _ret_val.z = _v.z * _s;
- _ret_val.w = _v.w * _s;
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline vector4<_num,_ntr> operator * (
- const _num _s,
- const vector4<_num,_ntr> & _v
- )
- {
- vector4<_num,_ntr> _ret_val;
- _ret_val.x = _v.x * _s;
- _ret_val.y = _v.y * _s;
- _ret_val.z = _v.z * _s;
- _ret_val.w = _v.w * _s;
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline _num operator * (
- const vector4<_num,_ntr> & _v1,
- const vector4<_num,_ntr> & _v2
- )
- {
- return ( _v1.x*_v2.x + _v1.y*_v2.y + _v1.z*_v2.z + _v1.w*_v2.w );
- }
- template < class _num, class _ntr >
- inline vector4<_num,_ntr> operator + (
- const vector4<_num,_ntr> & _v1,
- const vector4<_num,_ntr> & _v2
- )
- {
- vector4<_num,_ntr> _ret_val;
- _ret_val.x = _v1.x + _v2.x;
- _ret_val.y = _v1.y + _v2.y;
- _ret_val.z = _v1.z + _v2.z;
- _ret_val.w = _v1.w + _v2.w;
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline vector4<_num,_ntr> operator - (
- const vector4<_num,_ntr> & _v1,
- const vector4<_num,_ntr> & _v2
- )
- {
- vector4<_num,_ntr> _ret_val;
- _ret_val.x = _v1.x - _v2.x;
- _ret_val.y = _v1.y - _v2.y;
- _ret_val.z = _v1.z - _v2.z;
- _ret_val.w = _v1.w - _v2.w;
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline vector4<_num,_ntr> operator - (
- const vector4<_num,_ntr> & _v
- )
- {
- vector4<_num,_ntr> _ret_val;
- _ret_val.x = - _v.x;
- _ret_val.y = - _v.y;
- _ret_val.z = - _v.z;
- _ret_val.w = - _v.w;
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline vector4<_num,_ntr> operator + (
- const vector4<_num,_ntr> & _v
- )
- {
- return _v;
- }
- template < class _num, class _ntr >
- inline vector4<_num,_ntr> operator ~ (
- const vector4<_num,_ntr> & _v
- )
- {
- _num _len = _v.get_length();
- vector4<_num,_ntr> _ret_val;
- _ret_val.x = _v.x / _len;
- _ret_val.y = _v.y / _len;
- _ret_val.z = _v.z / _len;
- _ret_val.w = _v.w / _len;
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline vector4<_num,_ntr> operator ^ (
- const vector4<_num,_ntr> & _v1,
- const vector4<_num,_ntr> & _v2
- )
- {
- vector4<_num,_ntr> _ret_val;
- _ret_val.x = _v1.y*_v2.z - _v1.z*_v2.y;
- _ret_val.y = _v1.z*_v2.x - _v1.x*_v2.z;
- _ret_val.z = _v1.x*_v2.y - _v1.y*_v2.x;
- _ret_val.w = ((_num)0.0);
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline vector3<_num,_ntr> & vector3<_num,_ntr>::operator = (
- const vector4<_num,_ntr> & _v
- )
- {
- x = _v.x;
- y = _v.y;
- z = _v.z;
- return (*this);
- }
- template < class _num, class _ntr >
- class quaternion : public vector4<_num,_ntr>
- {
- public:
- typedef quaternion<_num,_ntr> _q4t;
- typedef quaternion<_num,_ntr> & _q4rt;
- typedef const quaternion<_num,_ntr> & _q4rct;
- quaternion()
- {
- load_quaternion();
- }
- quaternion( _q4rct _q )
- {
- set_quaternion( _q );
- }
- quaternion( _numc _x, _numc _y, _numc _z )
- {
- set_quaternion( _x, _y, _z );
- }
- quaternion( _v3rct _v )
- {
- set_quaternion( _v );
- }
- quaternion( _numc _angle, _numc _x, _numc _y, _numc _z )
- {
- set_quaternion( _angle, _x, _y, _z );
- }
-
- quaternion( _numc _mtx[3][3] )
- {
- _num _tr, _s, _q[4];
- int _i, _j, _k, _nxt_val[3] = {1, 2, 0};
- _tr = _mtx[0][0] + _mtx[1][1] + _mtx[2][2];
- if( _tr > 0.0 )
- {
- _s = _ntr::sqrt( _tr + ((_num)1.0) );
- w = _s / ((_num)2.0);
- _s = ((_num)0.5) / _s;
- x = (_mtx[1][2] - _mtx[2][1]) * _s;
- y = (_mtx[2][0] - _mtx[0][2]) * _s;
- z = (_mtx[0][1] - _mtx[1][0]) * _s;
- }
- else
- {
- _i = 0;
- if( _mtx[1][1] > _mtx[0][0] )
- _i = 1;
- if( _mtx[2][2] > _mtx[_i][_i] )
- _i = 2;
- _j = _nxt_val[_i];
- _k = _nxt_val[_j];
- _s =
- _ntr::sqrt(
- ( _mtx[_i][_i] - ( _mtx[_j][_j] + _mtx[_k][_k] ) )
- + 1.0
- );
- _q[_i] = _s * ((_num)0.5);
- if( _s != ((_num)0.0) )
- _s = ((_num)0.5) / _s;
- _q[3] = (_mtx[_j][_k] - _mtx[_k][_j]) * _s;
- _q[_j] = (_mtx[_i][_j] + _mtx[_j][_i]) * _s;
- _q[_k] = (_mtx[_i][_k] + _mtx[_k][_i]) * _s;
- x = _q[0];
- y = _q[1];
- z = _q[2];
- w = _q[3];
- }
- }
- quaternion( _mrt _mtx );
- void load_quaternion(
- _numc _x = ((_num)0.0),
- _numc _y = ((_num)0.0),
- _numc _z = ((_num)0.0),
- _numc _w = ((_num)1.0)
- )
- {
- x = _x;
- y = _y;
- z = _z;
- w = _w;
- }
-
- void set_quaternion( _num _angle, _num _x, _num _y, _num _z )
- {
- _numc _fct = _x*_x+_y*_y+_z*_z;
- __gltl_assert__( _fct != 0 );
- _numc _scale_by( ((_num)1.0) / _ntr::sqrt(_fct) );
- _x = _x * _scale_by;
- _y = _y * _scale_by;
- _z = _z * _scale_by;
- w = _ntr::cos( _angle / ((_num)2.0) );
- _numc _sin_half( _ntr::sin( _angle / ((_num)2.0) ) );
- x = _x * _sin_half;
- y = _y * _sin_half;
- z = _z * _sin_half;
- }
- void set_quaternion( _numc _x, _numc _y, _numc _z )
- {
- _q4t _x_q( _x, ((_num)1.0), ((_num)0.0), ((_num)0.0) );
- _q4t _y_q( _y, ((_num)0.0), ((_num)1.0), ((_num)0.0) );
- _q4t _z_q( _z, ((_num)0.0), ((_num)0.0), ((_num)1.0) );
- set_quaternion( _x_q );
- (*this) *= _y_q;
- (*this) *= _z_q;
- }
- void set_quaternion( _v3rct _v )
- {
- set_quaternion( _v.x, _v.y, _v.z );
- }
- void set_quaternion( _q4rct _q )
- {
- x = _q.x;
- y = _q.y;
- z = _q.z;
- w = _q.w;
- }
- void normalize()
- {
- _num _fct = get_length_sq();
- __gltl_assert__( _fct != 0 );
- _num _scale_by( ((_num)1.0) / _ntr::sqrt(_fct) );
- x = x * _scale_by;
- y = y * _scale_by;
- z = z * _scale_by;
- w = w * _scale_by;
- }
- void get_as_matrix( _mrt _mtx );
- _mt get_as_matrix() const;
- void get_axis_angle( _numr axis_x, _numr axis_y, _numr axis_z, _numr _rot_angle ) const
- {
- _numc _vec_len2 = x*x + y*y + z*z;
- if( _vec_len2 < _ntr::get_def_epsilon() )
- {
- axis_x = ((_num)1.0);
- axis_y = ((_num)0.0);
- axis_z = ((_num)0.0);
- _rot_angle = ((_num)0.0);
- }
- else
- {
- _numc _len_inv = ((_num)1.0) / _ntr::sqrt(_vec_len2);
- axis_x = x * _len_inv;
- axis_y = y * _len_inv;
- axis_z = z * _len_inv;
- _rot_angle = ((_num)2.0) * _ntr::acos(w);
- }
- }
- void get_axis_angle( _v3rt _v, _numr _rot_angle ) const
- {
- get_axis_angle( _v.x, _v.y, _v.z, _rot_angle );
- }
- void get_lt_ln( _numr _angle_lat, _numr _angle_long ) const
- {
- _num _x, _y, _z;
- get_direction_vector( _x, _y, _z );
- _angle_lat = _ntr::asin( _y );
- if( _ntr::abs(_y) > ( ((_num)1.0) - _ntr::get_def_epsilon() ) )
- _angle_long = ((_num)0.0);
- else
- {
- if( _ntr::abs(_z) < _ntr::get_def_epsilon() )
- _angle_long = _x > ((_num)0.0)
- ? ( _ntr::get_pi() / ((_num)2.0) )
- : ( _ntr::get_pi() * ((_num)3.0) / ((_num)2.0) )
- ;
- else
- {
- if( _z >= ((_num)0.0) )
- _angle_long = _ntr::atan( _x / _z );
- else
- _angle_long = _ntr::get_pi() + _ntr::atan( _x / _z );
- if( _angle_long < ((_num)0.0) )
- _angle_long += _ntr::get_pi() * ((_num)2.0);
- }
- }
- }
- void get_direction_vector( _numr _x, _numr _y, _numr _z )
- {
- normalize();
- _x = ((_num)2.0) * ( x * z - w * y );
- _y = ((_num)2.0) * ( y * z + w * x );
- _z = ((_num)1.0) - ((_num)2.0) * ( x * x + y * y );
- }
- void get_direction_vector( _v3rt _v )
- {
- get_direction_vector( _v.x, _v.y, _v.z );
- }
- static _q4t stat_multiplication( _q4rct _q1, _q4rct _q2 )
- {
- _q4t _q;
- _q.x =
- _q2.w*_q1.x
- + _q2.x*_q1.w
- + _q2.y*_q1.z
- - _q2.z*_q1.y;
- _q.y =
- _q2.w*_q1.y
- - _q2.x*_q1.z
- + _q2.y*_q1.w
- + _q2.z*_q1.x;
- _q.z =
- _q2.w*_q1.z
- + _q2.x*_q1.y
- - _q2.y*_q1.x
- + _q2.z*_q1.w;
- _q.w =
- _q2.w*_q1.w
- - _q2.x*_q1.x
- - _q2.y*_q1.y
- - _q2.z*_q1.z;
- return _q;
- }
- _q4rt operator *= ( _q4rct _q2 )
- {
- _q4t _holder( *this );
- (*this) = stat_multiplication( _holder, _q2 );
- return (*this);
- }
- };
- template < class _num, class _ntr >
- class matrix
- {
- public:
- typedef const _num _numc;
- typedef _num & _numr;
- typedef const _num & _numrc;
- typedef _num * _nump;
- typedef const _num * _numpc;
- typedef vector3<_num,_ntr> _v3t;
- typedef vector3<_num,_ntr> & _v3rt;
- typedef const vector3<_num,_ntr> & _v3rct;
-
- typedef vector4<_num,_ntr> _v4t;
- typedef vector4<_num,_ntr> & _v4rt;
- typedef const vector4<_num,_ntr> & _v4rct;
- typedef quaternion<_num,_ntr> _q4t;
- typedef quaternion<_num,_ntr> & _q4rt;
- typedef const quaternion<_num,_ntr> & _q4rct;
- typedef matrix<_num,_ntr> _mt;
- typedef matrix<_num,_ntr> & _mrt;
- typedef const matrix<_num,_ntr> & _mrct;
- union
- {
- struct
- {
- _num
- m11, m21, m31, m41,
- m12, m22, m32, m42,
- m13, m23, m33, m43,
- m14, m24, m34, m44;
- };
- _num arr[16];
- _num _xx[4][4];
- };
- matrix(
- _num src11 = ((_num)1.0), _num src21 = ((_num)0.0), _num src31 = ((_num)0.0), _num src41 = ((_num)0.0),
- _num src12 = ((_num)0.0), _num src22 = ((_num)1.0), _num src32 = ((_num)0.0), _num src42 = ((_num)0.0),
- _num src13 = ((_num)0.0), _num src23 = ((_num)0.0), _num src33 = ((_num)1.0), _num src43 = ((_num)0.0),
- _num src14 = ((_num)0.0), _num src24 = ((_num)0.0), _num src34 = ((_num)0.0), _num src44 = ((_num)1.0)
- )
- : m14(src14), m13(src13), m12(src12), m11(src11)
- , m24(src24), m23(src23), m22(src22), m21(src21)
- , m34(src34), m33(src33), m32(src32), m31(src31)
- , m44(src44), m43(src43), m42(src42), m41(src41)
- {
- }
- matrix( _nump p_src )
- : m14(p_src[ 3]), m13(p_src[ 2]), m12(p_src[ 1]), m11(p_src[ 0])
- , m24(p_src[ 7]), m23(p_src[ 6]), m22(p_src[ 5]), m21(p_src[ 4])
- , m34(p_src[11]), m33(p_src[10]), m32(p_src[ 9]), m31(p_src[ 8])
- , m44(p_src[15]), m43(p_src[14]), m42(p_src[13]), m41(p_src[12])
- {
- }
- matrix( _num _mtx[3][3] )
- : m14(_mtx[0][0]), m13(_mtx[0][1]), m12(_mtx[0][2]), m11(((_num)0.0))
- , m24(_mtx[1][0]), m23(_mtx[1][1]), m22(_mtx[1][2]), m21(((_num)0.0))
- , m34(_mtx[2][0]), m33(_mtx[2][1]), m32(_mtx[2][2]), m31(((_num)0.0))
- , m44(((_num)0.0)), m43(((_num)0.0)), m42(((_num)0.0)), m41(((_num)1.0))
- {
- }
- _numr get_item_ref_xy( int _i = 0, int _j = 0 )
- {
- __gltl_assert__( (0<=_i) && (_i<=3) && (0<=_j) && (_j<=3) );
- return *(((_nump)&m11) + (_j<<2)+_i);
- }
- _numrc get_item_ref_xy( int _i = 0, int _j = 0 ) const
- {
- __gltl_assert__( (0<=_i) && (_i<=3) && (0<=_j) && (_j<=3) );
- return *(((_nump)&m11) + (_j<<2)+_i);
- }
- _nump get_item_ptr_xy( int _i = 0, int _j = 0 )
- {
- __gltl_assert__( (0<=_i) && (_i<=3) && (0<=_j) && (_j<=3) );
- return (((_nump)&m11) + (_j<<2)+_i);
- }
- _numpc get_item_ptr_xy( int _i = 0, int _j = 0 ) const
- {
- __gltl_assert__( (0<=_i) && (_i<=3) && (0<=_j) && (_j<=3) );
- return (((_nump)&m11) + (_j<<2)+_i);
- }
- _numr operator () ( int _i, int _j )
- {
- return get_item_ref_xy( _i, _j );
- }
- _numrc operator () ( int _i, int _j ) const
- {
- return get_item_ref_xy( _i, _j );
- }
- _numr get_item_ref_yx( int _i = 0, int _j = 0 )
- {
- return get_item_ref_xy( _j, _i );
- }
- _numrc get_item_ref_yx( int _i = 0, int _j = 0 ) const
- {
- return get_item_ref_xy( _j, _i );
- }
- _nump get_item_ptr_yx( int _i = 0, int _j = 0 )
- {
- return get_item_ptr_xy( _j, _i );
- }
- _numpc get_item_ptr_yx( int _i = 0, int _j = 0 ) const
- {
- return get_item_ptr_xy( _j, _i );
- }
- bool operator == ( _mrct _mtx ) const
- {
- return (
- m11 == _mtx.m11 && m12 == _mtx.m12 && m13 == _mtx.m13 && m14 == _mtx.m14
- && m21 == _mtx.m21 && m22 == _mtx.m22 && m23 == _mtx.m23 && m24 == _mtx.m24
- && m31 == _mtx.m31 && m32 == _mtx.m32 && m33 == _mtx.m33 && m34 == _mtx.m34
- && m41 == _mtx.m41 && m42 == _mtx.m42 && m43 == _mtx.m43 && m44 == _mtx.m44
- ) ? true : false;
- }
- bool operator != ( _mrct _mtx ) const
- {
- return (
- m11 == _mtx.m11 && m12 == _mtx.m12 && m13 == _mtx.m13 && m14 == _mtx.m14
- && m21 == _mtx.m21 && m22 == _mtx.m22 && m23 == _mtx.m23 && m24 == _mtx.m24
- && m31 == _mtx.m31 && m32 == _mtx.m32 && m33 == _mtx.m33 && m34 == _mtx.m34
- && m41 == _mtx.m41 && m42 == _mtx.m42 && m43 == _mtx.m43 && m44 == _mtx.m44
- ) ? false : true;
- }
-
- _mrt operator = ( _mrct _mtx )
- {
- m11 = _mtx.m11; m12 = _mtx.m12; m13 = _mtx.m13; m14 = _mtx.m14;
- m21 = _mtx.m21; m22 = _mtx.m22; m23 = _mtx.m23; m24 = _mtx.m24;
- m31 = _mtx.m31; m32 = _mtx.m32; m33 = _mtx.m33; m34 = _mtx.m34;
- m41 = _mtx.m41; m42 = _mtx.m42; m43 = _mtx.m43; m44 = _mtx.m44;
- return (*this);
- }
- static void stat_multiplication(
- _mrct _mtx1,
- _mrct _mtx2,
- _mrt _ret_val
- )
- {
- _mt _ret_val_prep;
- _ret_val_prep.m11 = _mtx1.m11*_mtx2.m11 + _mtx1.m12*_mtx2.m21 + _mtx1.m13*_mtx2.m31 + _mtx1.m14*_mtx2.m41;
- _ret_val_prep.m12 = _mtx1.m11*_mtx2.m12 + _mtx1.m12*_mtx2.m22 + _mtx1.m13*_mtx2.m32 + _mtx1.m14*_mtx2.m42;
- _ret_val_prep.m13 = _mtx1.m11*_mtx2.m13 + _mtx1.m12*_mtx2.m23 + _mtx1.m13*_mtx2.m33 + _mtx1.m14*_mtx2.m43;
- _ret_val_prep.m14 = _mtx1.m11*_mtx2.m14 + _mtx1.m12*_mtx2.m24 + _mtx1.m13*_mtx2.m34 + _mtx1.m14*_mtx2.m44;
- _ret_val_prep.m21 = _mtx1.m21*_mtx2.m11 + _mtx1.m22*_mtx2.m21 + _mtx1.m23*_mtx2.m31 + _mtx1.m24*_mtx2.m41;
- _ret_val_prep.m22 = _mtx1.m21*_mtx2.m12 + _mtx1.m22*_mtx2.m22 + _mtx1.m23*_mtx2.m32 + _mtx1.m24*_mtx2.m42;
- _ret_val_prep.m23 = _mtx1.m21*_mtx2.m13 + _mtx1.m22*_mtx2.m23 + _mtx1.m23*_mtx2.m33 + _mtx1.m24*_mtx2.m43;
- _ret_val_prep.m24 = _mtx1.m21*_mtx2.m14 + _mtx1.m22*_mtx2.m24 + _mtx1.m23*_mtx2.m34 + _mtx1.m24*_mtx2.m44;
- _ret_val_prep.m31 = _mtx1.m31*_mtx2.m11 + _mtx1.m32*_mtx2.m21 + _mtx1.m33*_mtx2.m31 + _mtx1.m34*_mtx2.m41;
- _ret_val_prep.m32 = _mtx1.m31*_mtx2.m12 + _mtx1.m32*_mtx2.m22 + _mtx1.m33*_mtx2.m32 + _mtx1.m34*_mtx2.m42;
- _ret_val_prep.m33 = _mtx1.m31*_mtx2.m13 + _mtx1.m32*_mtx2.m23 + _mtx1.m33*_mtx2.m33 + _mtx1.m34*_mtx2.m43;
- _ret_val_prep.m34 = _mtx1.m31*_mtx2.m14 + _mtx1.m32*_mtx2.m24 + _mtx1.m33*_mtx2.m34 + _mtx1.m34*_mtx2.m44;
- _ret_val_prep.m41 = _mtx1.m41*_mtx2.m11 + _mtx1.m42*_mtx2.m21 + _mtx1.m43*_mtx2.m31 + _mtx1.m44*_mtx2.m41;
- _ret_val_prep.m42 = _mtx1.m41*_mtx2.m12 + _mtx1.m42*_mtx2.m22 + _mtx1.m43*_mtx2.m32 + _mtx1.m44*_mtx2.m42;
- _ret_val_prep.m43 = _mtx1.m41*_mtx2.m13 + _mtx1.m42*_mtx2.m23 + _mtx1.m43*_mtx2.m33 + _mtx1.m44*_mtx2.m43;
- _ret_val_prep.m44 = _mtx1.m41*_mtx2.m14 + _mtx1.m42*_mtx2.m24 + _mtx1.m43*_mtx2.m34 + _mtx1.m44*_mtx2.m44;
- // for( int _i = 0; _i < 4; _i++ )
- // {
- // for( int _j = 0; _j < 4; _j++ )
- // {
- // _ret_val_prep._xx[_i][_j] = 0;
- // for( int _k = 0; _k < 4; _k++ )
- // {
- // _ret_val_prep._xx[_i][_j] +=
- // _mtx2._xx[_i][_k] * _mtx1._xx[_k][_j];
- // }
- // }
- // }
- _ret_val = _ret_val_prep;
- }
- static _mt stat_multiplication(
- _mrct _mtx1,
- _mrct _mtx2
- )
- {
- _mt _ret_val;
- _ret_val.m11 = _mtx1.m11*_mtx2.m11 + _mtx1.m12*_mtx2.m21 + _mtx1.m13*_mtx2.m31 + _mtx1.m14*_mtx2.m41;
- _ret_val.m12 = _mtx1.m11*_mtx2.m12 + _mtx1.m12*_mtx2.m22 + _mtx1.m13*_mtx2.m32 + _mtx1.m14*_mtx2.m42;
- _ret_val.m13 = _mtx1.m11*_mtx2.m13 + _mtx1.m12*_mtx2.m23 + _mtx1.m13*_mtx2.m33 + _mtx1.m14*_mtx2.m43;
- _ret_val.m14 = _mtx1.m11*_mtx2.m14 + _mtx1.m12*_mtx2.m24 + _mtx1.m13*_mtx2.m34 + _mtx1.m14*_mtx2.m44;
- _ret_val.m21 = _mtx1.m21*_mtx2.m11 + _mtx1.m22*_mtx2.m21 + _mtx1.m23*_mtx2.m31 + _mtx1.m24*_mtx2.m41;
- _ret_val.m22 = _mtx1.m21*_mtx2.m12 + _mtx1.m22*_mtx2.m22 + _mtx1.m23*_mtx2.m32 + _mtx1.m24*_mtx2.m42;
- _ret_val.m23 = _mtx1.m21*_mtx2.m13 + _mtx1.m22*_mtx2.m23 + _mtx1.m23*_mtx2.m33 + _mtx1.m24*_mtx2.m43;
- _ret_val.m24 = _mtx1.m21*_mtx2.m14 + _mtx1.m22*_mtx2.m24 + _mtx1.m23*_mtx2.m34 + _mtx1.m24*_mtx2.m44;
- _ret_val.m31 = _mtx1.m31*_mtx2.m11 + _mtx1.m32*_mtx2.m21 + _mtx1.m33*_mtx2.m31 + _mtx1.m34*_mtx2.m41;
- _ret_val.m32 = _mtx1.m31*_mtx2.m12 + _mtx1.m32*_mtx2.m22 + _mtx1.m33*_mtx2.m32 + _mtx1.m34*_mtx2.m42;
- _ret_val.m33 = _mtx1.m31*_mtx2.m13 + _mtx1.m32*_mtx2.m23 + _mtx1.m33*_mtx2.m33 + _mtx1.m34*_mtx2.m43;
- _ret_val.m34 = _mtx1.m31*_mtx2.m14 + _mtx1.m32*_mtx2.m24 + _mtx1.m33*_mtx2.m34 + _mtx1.m34*_mtx2.m44;
- _ret_val.m41 = _mtx1.m41*_mtx2.m11 + _mtx1.m42*_mtx2.m21 + _mtx1.m43*_mtx2.m31 + _mtx1.m44*_mtx2.m41;
- _ret_val.m42 = _mtx1.m41*_mtx2.m12 + _mtx1.m42*_mtx2.m22 + _mtx1.m43*_mtx2.m32 + _mtx1.m44*_mtx2.m42;
- _ret_val.m43 = _mtx1.m41*_mtx2.m13 + _mtx1.m42*_mtx2.m23 + _mtx1.m43*_mtx2.m33 + _mtx1.m44*_mtx2.m43;
- _ret_val.m44 = _mtx1.m41*_mtx2.m14 + _mtx1.m42*_mtx2.m24 + _mtx1.m43*_mtx2.m34 + _mtx1.m44*_mtx2.m44;
- // for( int _i = 0; _i < 4; _i++ )
- // {
- // for( int _j = 0; _j < 4; _j++ )
- // {
- // _ret_val._xx[_i][_j] = 0;
- // for( int _k = 0; _k < 4; _k++ )
- // {
- // _ret_val._xx[_i][_j] +=
- // _mtx2._xx[_i][_k] * _mtx1._xx[_k][_j];
- // }
- // }
- // }
- return _ret_val;
- }
- _mrt operator *= ( _q4rct _q );
- _mrt operator *= ( _mrct _mtx )
- {
- stat_multiplication( *this, _mtx, *this );
- return (*this);
- }
- _mrt operator *= ( _numc _v )
- {
- for( int _i = 0; _i < 16; _i++ )
- *(((_num*)&m11)+_i) = *(((_num*)&m11)+_i) * _v;
- return (*this);
- }
- _mrt operator += ( _mrct _mtx )
- {
- for( int _i = 0; _i < 16; _i++ )
- *(((_num*)&m11)+_i) = *(((_num*)&m11)+_i) + *(((_num*)&_mtx.m11)+_i);
- return (*this);
- }
- _mrt operator -= ( _mrct _mtx )
- {
- for( int _i = 0; _i < 16; _i++ )
- *(((_num*)&m11)+_i) = *(((_num*)&m11)+_i) - *(((_num*)&_mtx.m11)+_i);
- return (*this);
- }
- void load_transposition()
- {
- _num _swap_val;
- _swap_val = m12; m12 = m21; m21 = _swap_val;
- _swap_val = m13; m13 = m31; m31 = _swap_val;
- _swap_val = m14; m14 = m41; m41 = _swap_val;
- _swap_val = m23; m23 = m32; m32 = _swap_val;
- _swap_val = m24; m24 = m42; m42 = _swap_val;
- _swap_val = m34; m34 = m43; m43 = _swap_val;
- }
-
- _num load_inversion()
- {
- _num _dest[16], _swap[12], _src[16];
- for( int _i = 0; _i < 4; _i++ )
- {
- _src[_i] = *(((_nump)&m11) + (_i<<2));
- _src[_i + 4] = *(((_nump)&m11) + (_i<<2) + 1);
- _src[_i + 8] = *(((_nump)&m11) + (_i<<2) + 2);
- _src[_i + 12] = *(((_nump)&m11) + (_i<<2) + 3);
- }
- _swap[ 0] = _src[10] * _src[15];
- _swap[ 1] = _src[11] * _src[14];
- _swap[ 2] = _src[ 9] * _src[15];
- _swap[ 3] = _src[11] * _src[13];
- _swap[ 4] = _src[ 9] * _src[14];
- _swap[ 5] = _src[10] * _src[13];
- _swap[ 6] = _src[ 8] * _src[15];
- _swap[ 7] = _src[11] * _src[12];
- _swap[ 8] = _src[ 8] * _src[14];
- _swap[ 9] = _src[10] * _src[12];
- _swap[10] = _src[ 8] * _src[13];
- _swap[11] = _src[ 9] * _src[12];
- _dest[ 0] = _swap[0]*_src[5] + _swap[3]*_src[6] + _swap[ 4]*_src[7];
- _dest[ 0]-= _swap[1]*_src[5] + _swap[2]*_src[6] + _swap[ 5]*_src[7];
- _dest[ 1] = _swap[1]*_src[4] + _swap[6]*_src[6] + _swap[ 9]*_src[7];
- _dest[ 1]-= _swap[0]*_src[4] + _swap[7]*_src[6] + _swap[ 8]*_src[7];
- _dest[ 2] = _swap[2]*_src[4] + _swap[7]*_src[5] + _swap[10]*_src[7];
- _dest[ 2]-= _swap[3]*_src[4] + _swap[6]*_src[5] + _swap[11]*_src[7];
- _dest[ 3] = _swap[5]*_src[4] + _swap[8]*_src[5] + _swap[11]*_src[6];
- _dest[ 3]-= _swap[4]*_src[4] + _swap[9]*_src[5] + _swap[10]*_src[6];
- _dest[ 4] = _swap[1]*_src[1] + _swap[2]*_src[2] + _swap[ 5]*_src[3];
- _dest[ 4]-= _swap[0]*_src[1] + _swap[3]*_src[2] + _swap[ 4]*_src[3];
- _dest[ 5] = _swap[0]*_src[0] + _swap[7]*_src[2] + _swap[ 8]*_src[3];
- _dest[ 5]-= _swap[1]*_src[0] + _swap[6]*_src[2] + _swap[ 9]*_src[3];
- _dest[ 6] = _swap[3]*_src[0] + _swap[6]*_src[1] + _swap[11]*_src[3];
- _dest[ 6]-= _swap[2]*_src[0] + _swap[7]*_src[1] + _swap[10]*_src[3];
- _dest[ 7] = _swap[4]*_src[0] + _swap[9]*_src[1] + _swap[10]*_src[2];
- _dest[ 7]-= _swap[5]*_src[0] + _swap[8]*_src[1] + _swap[11]*_src[2];
- _swap[ 0] = _src[2]*_src[7];
- _swap[ 1] = _src[3]*_src[6];
- _swap[ 2] = _src[1]*_src[7];
- _swap[ 3] = _src[3]*_src[5];
- _swap[ 4] = _src[1]*_src[6];
- _swap[ 5] = _src[2]*_src[5];
- _swap[ 6] = _src[0]*_src[7];
- _swap[ 7] = _src[3]*_src[4];
- _swap[ 8] = _src[0]*_src[6];
- _swap[ 9] = _src[2]*_src[4];
- _swap[10] = _src[0]*_src[5];
- _swap[11] = _src[1]*_src[4];
- _dest[ 8] = _swap[ 0]*_src[13] + _swap[ 3]*_src[14] + _swap[ 4]*_src[15];
- _dest[ 8]-= _swap[ 1]*_src[13] + _swap[ 2]*_src[14] + _swap[ 5]*_src[15];
- _dest[ 9] = _swap[ 1]*_src[12] + _swap[ 6]*_src[14] + _swap[ 9]*_src[15];
- _dest[ 9]-= _swap[ 0]*_src[12] + _swap[ 7]*_src[14] + _swap[ 8]*_src[15];
- _dest[10] = _swap[ 2]*_src[12] + _swap[ 7]*_src[13] + _swap[10]*_src[15];
- _dest[10]-= _swap[ 3]*_src[12] + _swap[ 6]*_src[13] + _swap[11]*_src[15];
- _dest[11] = _swap[ 5]*_src[12] + _swap[ 8]*_src[13] + _swap[11]*_src[14];
- _dest[11]-= _swap[ 4]*_src[12] + _swap[ 9]*_src[13] + _swap[10]*_src[14];
- _dest[12] = _swap[ 2]*_src[10] + _swap[ 5]*_src[11] + _swap[ 1]*_src[ 9];
- _dest[12]-= _swap[ 4]*_src[11] + _swap[ 0]*_src[ 9] + _swap[ 3]*_src[10];
- _dest[13] = _swap[ 8]*_src[11] + _swap[ 0]*_src[ 8] + _swap[ 7]*_src[10];
- _dest[13]-= _swap[ 6]*_src[10] + _swap[ 9]*_src[11] + _swap[ 1]*_src[ 8];
- _dest[14] = _swap[ 6]*_src[ 9] + _swap[11]*_src[11] + _swap[ 3]*_src[ 8];
- _dest[14]-= _swap[10]*_src[11] + _swap[ 2]*_src[ 8] + _swap[ 7]*_src[ 9];
- _dest[15] = _swap[10]*_src[10] + _swap[ 4]*_src[ 8] + _swap[ 9]*_src[ 9];
- _dest[15]-= _swap[ 8]*_src[ 9] + _swap[11]*_src[10] + _swap[ 5]*_src[ 8];
- _num _det1 =
- _src[0]*_dest[0]
- + _src[1]*_dest[1]
- + _src[2]*_dest[2]
- + _src[3]*_dest[3];
- _num _det2 = ((_num)1.0) / _det1;
- for( int _j = 0; _j < 16; _j++ )
- {
- _dest[_j] *= _det2;
- *(((_nump)&m11) + _j) = _dest[_j];
- }
- return _det1;
- }
- _num get_determinant()
- {
- _num _src[16], _swap[12], _dest[4];
- for( int _i = 0; _i < 16; _i++ )
- _src[_i] = *(((_nump)&m11) + _i);
- _swap[ 0] = _src[10] * _src[15];
- _swap[ 1] = _src[11] * _src[14];
- _swap[ 2] = _src[ 9] * _src[15];
- _swap[ 3] = _src[11] * _src[13];
- _swap[ 4] = _src[ 9] * _src[14];
- _swap[ 5] = _src[10] * _src[13];
- _swap[ 6] = _src[ 8] * _src[15];
- _swap[ 7] = _src[11] * _src[12];
- _swap[ 8] = _src[ 8] * _src[14];
- _swap[ 9] = _src[10] * _src[12];
- _swap[10] = _src[ 8] * _src[13];
- _swap[11] = _src[ 9] * _src[12];
- _dest[ 0] = _swap[0]*_src[5] + _swap[3]*_src[6] + _swap[ 4]*_src[7];
- _dest[ 0]-= _swap[1]*_src[5] + _swap[2]*_src[6] + _swap[ 5]*_src[7];
- _dest[ 1] = _swap[1]*_src[4] + _swap[6]*_src[6] + _swap[ 9]*_src[7];
- _dest[ 1]-= _swap[0]*_src[4] + _swap[7]*_src[6] + _swap[ 8]*_src[7];
- _dest[ 2] = _swap[2]*_src[4] + _swap[7]*_src[5] + _swap[10]*_src[7];
- _dest[ 2]-= _swap[3]*_src[4] + _swap[6]*_src[5] + _swap[11]*_src[7];
- _dest[ 3] = _swap[5]*_src[4] + _swap[8]*_src[5] + _swap[11]*_src[6];
- _dest[ 3]-= _swap[4]*_src[4] + _swap[9]*_src[5] + _swap[10]*_src[6];
- _num _det =
- _src[0]*_dest[0]
- + _src[1]*_dest[1]
- + _src[2]*_dest[2]
- + _src[3]*_dest[3];
- return _det;
- }
- _v3t get_angles()
- {
- _num yy, xx, zz, _k, rd;
- rd = _ntr::sqrt( m13*m13 + m23*m23 + m33*m33 );
- _k = ( ((_num)1.0) - _ntr::get_safe_min() ) * rd;
- if( m23 > _k )
- {
- zz = ((_num)0.0);
- xx = - _ntr::get_pi() / ((_num)2.0);
- yy = _ntr::atan2( -m12, m11 );
- }
- else if( m23 < (-_k) )
- {
- zz = ((_num)0.0);
- xx = _ntr::get_pi() / ((_num)2.0);
- yy = _ntr::atan2( m12, m11 );
- }
- else
- {
- if( rd == 0)
- yy = xx = zz = ((_num)0.0);
- else
- {
- xx = - _ntr::asin( m23 / rd );
- yy = _ntr::atan2( m13, m33 );
- zz = _ntr::atan2( m21, m22 );
- }
- }
- return _v3t( xx, yy, zz );
- }
- _v3t get_position()
- {
- return _v3t( m14, m24, m34 );
- }
-
- void load_zero()
- {
- m11 = m12 = m13 = m14
- = m21 = m22 = m23 = m24
- = m31 = m32 = m33 = m34
- = m41 = m42 = m43 = m44
- = ((_num)0.0);
- }
- void load_identity()
- {
- load_zero();
- m11 = m22 = m33 = m44 = ((_num)1.0);
- }
- void load_translation(
- _numc dx,
- _numc dy,
- _numc dz
- )
- {
- load_identity();
- m14 = dx;
- m24 = dy;
- m34 = dz;
- }
- void load_translation( _v3rct _v )
- {
- load_identity();
- m14 = _v.x;
- m24 = _v.y;
- m34 = _v.z;
- }
- void load_rotation_x( _numc _angle_radians )
- {
- _num _c = _ntr::cos(_angle_radians), _s = _ntr::sin(_angle_radians);
- load_identity();
- m22 = + _c;
- m23 = - _s;
- m32 = + _s;
- m33 = + _c;
- }
- void load_rotation_y( _numc _angle_radians )
- {
- _num _c = _ntr::cos(_angle_radians), _s = _ntr::sin(_angle_radians);
- load_identity();
- m11 = + _c;
- m13 = + _s;
- m31 = - _s;
- m33 = + _c;
- }
- void load_rotation_z( _numc _angle_radians )
- {
- _num _c = _ntr::cos(_angle_radians), _s = _ntr::sin(_angle_radians);
- load_identity();
- m11 = + _c;
- m12 = - _s;
- m21 = + _s;
- m22 = + _c;
- }
- void load_rotation_xyz( _numc _x, _numc _y, _numc _z )
- {
- _mt mtx_rotation_x, mtx_rotation_y, mtx_rotation_z;
- mtx_rotation_x.load_rotation_x(_x);
- mtx_rotation_y.load_rotation_y(_y);
- mtx_rotation_z.load_rotation_z(_z);
- (*this) = mtx_rotation_x * mtx_rotation_y * mtx_rotation_z;
- }
- void load_rotation_xyz( _v3rct _v )
- {
- load_rotation_xyz( _v.x, _v.y, _v.z );
- }
- void load_scale( _numc _x, _numc _y, _numc _z )
- {
- load_identity();
- m11 = _x;
- m22 = _y;
- m33 = _z;
- }
- void load_scale( _v3rct _v )
- {
- load_identity();
- m11 = _v.x;
- m22 = _v.y;
- m33 = _v.z;
- }
- void load_scale( _numc _val )
- {
- load_identity();
- m11 = m22 = m33 = _val;
- }
- void load_perspective(
- _num fovy,
- _num aspect,
- _num znear,
- _num zfar
- )
- {
- load_identity();
- _num _ctan_fov =
- ((_num)1.0)
- /
- ( _ntr::tan( fovy / ((_num)2.0)) );
- m11 = _ctan_fov / aspect;
- m22 = _ctan_fov;
- m33 = - (zfar + znear) / (zfar - znear);
- m34 = - ((_num)2.0) * (zfar * znear) / ( zfar - znear );
- m43 = - ((_num)1.0);
- m44 = ((_num)0.0);
- }
- void load_rotation_about_vector(
- _numc _angle,
- _v3rct _vec
- )
- {
- _v3t _v( _vec );
- _v.normalize();
- _num _x = _v._x, _y = _v._y, _z = _v._z;
- _num _c = _ntr::cos(_angle);
- _num _s = _ntr::sin(_angle);
- _num xx = _x * _x;
- _num xy = _y * _x;
- _num xz = _z * _x;
- _num yy = _y * _y;
- _num yz = _y * _z;
- _num zz = _z * _z;
- _num xs = _x * _s;
- _num ys = _y * _s;
- _num zs = _z * _s;
- _num _1c = 1 - _c;
- m11 = xx*_1c+_c;
- m12 = xy*_1c+zs;
- m13 = xz*_1c-ys;
- m14 = 0;
- m21 = xy*_1c-zs;
- m22 = yy*_1c+_c;
- m23 = yz*_1c+xs;
- m24 = 0;
- m31 = xz*_1c+ys;
- m32 = yz*_1c-xs;
- m33 = zz*_1c+_c;
- m34 = 0;
- m41 = 0;
- m42 = 0;
- m43 = 0;
- m44 = 1;
- }
- void load_rotation_about_vector(
- _numc _angle,
- _numc _x,
- _numc _y,
- _numc _z
- )
- {
- load_rotation_about_vector(
- _angle,
- _v3t( _x, _y, _z )
- );
- }
- void load_rotation_about_vector(
- _numc _angle,
- _v4rct _vec
- )
- {
- load_rotation_about_vector(
- _angle,
- _v3t(_vec.x,_vec.y,_vec.z)
- );
- }
- void load_reflection(
- _numc _a,
- _numc _b,
- _numc _c,
- _numc _d
- )
- {
- get_item_ref_yx( 0, 0 ) = _numc(1.0) - _numc(2.0) * _a * _a;
- get_item_ref_yx( 1, 0 ) = - _numc(2.0) * _a * _b;
- get_item_ref_yx( 2, 0 ) = - _numc(2.0) * _a * _c;
- get_item_ref_yx( 3, 0 ) = - _numc(2.0) * _d * _a;
- get_item_ref_yx( 0, 1 ) = - _numc(2.0) * _b * _a;
- get_item_ref_yx( 1, 1 ) = _numc(1.0) - _numc(2.0) * _b * _b;
- get_item_ref_yx( 2, 1 ) = - _numc(2.0) * _b * _c;
- get_item_ref_yx( 3, 1 ) = - _numc(2.0) * _d * _b;
- get_item_ref_yx( 0, 2 ) = - _numc(2.0) * _c * _a;
- get_item_ref_yx( 1, 2 ) = - _numc(2.0) * _c * _b;
- get_item_ref_yx( 2, 2 ) = _numc(1.0) - _numc(2.0) * _c * _c;
- get_item_ref_yx( 3, 2 ) = - _numc(2.0) * _d * _c;
- get_item_ref_yx( 0, 3 ) = _numc(0.0);
- get_item_ref_yx( 1, 3 ) = _numc(0.0);
- get_item_ref_yx( 2, 3 ) = _numc(0.0);
- get_item_ref_yx( 3, 3 ) = _numc(1.0);
- }
- void load_reflection( _v4rct plane )
- {
- load_reflection( plane.a, plane.b, plane.c, plane.d );
- }
- };
- template < class _num, class _ntr >
- inline matrix<_num,_ntr> operator * (
- const matrix<_num,_ntr> &_mtx,
- const _num _v
- )
- {
- matrix<_num,_ntr> _ret_val;
- for( int _i = 0; _i < 16; _i++ )
- *(((_num*)&_ret_val.m11)+_i) = *(((_num*)&_mtx.m11)+_i) * _v;
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline matrix<_num,_ntr> operator * (
- const _num _v,
- const matrix<_num,_ntr> & _mtx
- )
- {
- matrix<_num,_ntr> _ret_val;
- for( int _i = 0; _i < 16; _i++ )
- *(((_num*)&_ret_val.m11)+_i) = *(((_num*)&_mtx.m11)+_i) * _v;
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline matrix<_num,_ntr> operator * (
- const matrix<_num,_ntr> & _mtx1,
- const matrix<_num,_ntr> & _mtx2
- )
- {
- return matrix<_num,_ntr>::stat_multiplication( _mtx1, _mtx2 );
- }
- template < class _num, class _ntr >
- inline matrix<_num,_ntr> operator + (
- const matrix<_num,_ntr> & _mtx1,
- const matrix<_num,_ntr> & _mtx2
- )
- {
- matrix<_num,_ntr> _ret_val;
- for( int _i = 0; _i < 16; _i++ )
- *(((_num*)&_ret_val.m11)+_i) = *(((_num*)&_mtx1.m11)+_i) + *(((_num*)&_mtx2.m11)+_i);
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline matrix<_num,_ntr> operator - (
- const matrix<_num,_ntr> & _mtx1,
- const matrix<_num,_ntr> & _mtx2
- )
- {
- matrix<_num,_ntr> _ret_val;
- for( int _i = 0; _i < 16; _i++ )
- *(((_num*)&_ret_val.m11)+_i) = *(((_num*)&_mtx1.m11)+_i) - *(((_num*)&_mtx2.m11)+_i);
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline matrix<_num,_ntr> operator - ( const matrix<_num,_ntr> & _mtx )
- {
- matrix<_num,_ntr> _ret_val;
- for( int _i = 0; _i < 16; _i++ )
- *(((_num*)&_ret_val.m11)+_i) = - *(((_num*)&_mtx.m11)+_i);
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline matrix<_num,_ntr> operator + ( const matrix<_num,_ntr> & _mtx )
- {
- return _mtx;
- }
- template < class _num, class _ntr >
- void inline vector3<_num,_ntr>::stat_multiplication(
- const matrix<_num,_ntr> & _mtx,
- const vector3<_num,_ntr> & _v,
- vector3<_num,_ntr> & _ret_val
- )
- {
- vector3<_num,_ntr> _ret_val_prep;
- _ret_val_prep.x = _mtx.m11*_v.x + _mtx.m12*_v.y + _mtx.m13*_v.z + _mtx.m14;
- _ret_val_prep.y = _mtx.m21*_v.x + _mtx.m22*_v.y + _mtx.m23*_v.z + _mtx.m24;
- _ret_val_prep.z = _mtx.m31*_v.x + _mtx.m32*_v.y + _mtx.m33*_v.z + _mtx.m34;
- _ret_val.x = _ret_val_prep.x;
- _ret_val.y = _ret_val_prep.y;
- _ret_val.z = _ret_val_prep.z;
- }
- template < class _num, class _ntr >
- inline vector3<_num,_ntr> vector3<_num,_ntr>::stat_multiplication(
- const matrix<_num,_ntr> & _mtx,
- const vector3<_num,_ntr> & _v
- )
- {
- vector3<_num,_ntr> _ret_val;
- _ret_val.x = _mtx.m11*_v.x + _mtx.m12*_v.y + _mtx.m13*_v.z + _mtx.m14;
- _ret_val.y = _mtx.m21*_v.x + _mtx.m22*_v.y + _mtx.m23*_v.z + _mtx.m24;
- _ret_val.z = _mtx.m31*_v.x + _mtx.m32*_v.y + _mtx.m33*_v.z + _mtx.m34;
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline vector3<_num,_ntr> operator * (
- const matrix<_num,_ntr> & _mtx,
- const vector3<_num,_ntr> & _v
- )
- {
- return vector3<_num,_ntr>::stat_multiplication( _mtx, _v );
- }
- template < class _num, class _ntr >
- inline void vector4<_num,_ntr>::stat_multiplication(
- const matrix<_num,_ntr> & _mtx,
- _v4rct _v,
- _v4rt _ret_val
- )
- {
- vector4<_num,_ntr> _ret_val_prep;
- _ret_val_prep.x = _mtx.m11*_v.x + _mtx.m12*_v.y + _mtx.m13*_v.z + _mtx.m14*_v.w;
- _ret_val_prep.y = _mtx.m21*_v.x + _mtx.m22*_v.y + _mtx.m23*_v.z + _mtx.m24*_v.w;
- _ret_val_prep.z = _mtx.m31*_v.x + _mtx.m32*_v.y + _mtx.m33*_v.z + _mtx.m34*_v.w;
- _ret_val_prep.w = _mtx.m41*_v.x + _mtx.m42*_v.y + _mtx.m43*_v.z + _mtx.m44*_v.w;
- _ret_val.x = _ret_val_prep.x;
- _ret_val.y = _ret_val_prep.y;
- _ret_val.z = _ret_val_prep.z;
- _ret_val.w = _ret_val_prep.w;
- }
- template < class _num, class _ntr >
- inline vector4<_num,_ntr> vector4<_num,_ntr>::stat_multiplication(
- const matrix<_num,_ntr> & _mtx,
- _v4rct _v
- )
- {
- vector4<_num,_ntr> _ret_val;
- _ret_val.x = _mtx.m11*_v.x + _mtx.m12*_v.y + _mtx.m13*_v.z + _mtx.m14*_v.w;
- _ret_val.y = _mtx.m21*_v.x + _mtx.m22*_v.y + _mtx.m23*_v.z + _mtx.m24*_v.w;
- _ret_val.z = _mtx.m31*_v.x + _mtx.m32*_v.y + _mtx.m33*_v.z + _mtx.m34*_v.w;
- _ret_val.w = _mtx.m41*_v.x + _mtx.m42*_v.y + _mtx.m43*_v.z + _mtx.m44*_v.w;
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline vector4<_num,_ntr> operator * (
- const matrix<_num,_ntr> & _mtx,
- const vector4<_num,_ntr> & _v
- )
- {
- return vector4<_num,_ntr>::stat_multiplication( _mtx, _v );
- }
- template < class _num, class _ntr >
- inline quaternion<_num,_ntr>::quaternion(
- matrix<_num,_ntr> & _mtx
- )
- {
- _num _tr, _s, _q[4];
- int _i, _j, _k;
- int _nxt_val[3] = { 1, 2, 0 };
- _tr = _mtx.m11 + _mtx.m22 + _mtx.m33;
- if( _tr > ((_num)0.0) )
- {
- _s = _ntr::sqrt( _tr + ((_num)1.0) );
- w = _s / ((_num)2.0);
- _s = ((_num)0.5) / _s;
- x = (_mtx.m23 - _mtx.m32) * _s;
- y = (_mtx.m31 - _mtx.m13) * _s;
- z = (_mtx.m12 - _mtx.m21) * _s;
- }
- else
- {
- _i = 0;
- if( _mtx.m22 > _mtx.m11 )
- _i = 1;
- if( _mtx.m33 > _mtx.arr[4*_i+_i] )
- _i = 2;
- _j = _nxt_val[_i];
- _k = _nxt_val[_j];
- _s =
- _ntr::sqrt(
- ( _mtx.arr[4*_i+_i] -
- ( _mtx.arr[4*_j+_j] + _mtx.arr[4*_k+_k] )
- ) + ((_num)1.0)
- );
- _q[_i] = _s * ((_num)0.5);
- if( _s != ((_num)0.0) )
- _s = ((_num)0.5) / _s;
- _q[3] = (_mtx.arr[4*_j+_k] - _mtx.arr[4*_k+_j] ) * _s;
- _q[_j] = (_mtx.arr[4*_i+_j] + _mtx.arr[4*_j+_i] ) * _s;
- _q[_k] = (_mtx.arr[4*_i+_k] + _mtx.arr[4*_k+_i] ) * _s;
- x = _q[0];
- y = _q[1];
- z = _q[2];
- w = _q[3];
- }
- }
- template < class _num, class _ntr >
- inline void quaternion<_num,_ntr>::get_as_matrix(
- matrix<_num,_ntr> & _mtx
- )
- {
- normalize();
- _num xx = x * x;
- _num yy = y * y;
- _num zz = z * z;
- _mtx.get_item_ref_yx( 0, 0 ) = ((_num)1.0) - ((_num)2.0) * ( yy + zz );
- _mtx.get_item_ref_yx( 1, 0 ) = ((_num)2.0) * ( x * y + w * z );
- _mtx.get_item_ref_yx( 2, 0 ) = ((_num)2.0) * ( x * z - w * y );
- _mtx.get_item_ref_yx( 3, 0 ) = ((_num)0.0);
- _mtx.get_item_ref_yx( 0, 1 ) = ((_num)2.0) * ( x * y - w * z );
- _mtx.get_item_ref_yx( 1, 1 ) = ((_num)1.0) - ((_num)2.0) * ( xx + zz );
- _mtx.get_item_ref_yx( 2, 1 ) = ((_num)2.0) * ( y * z + w * x );
- _mtx.get_item_ref_yx( 3, 1 ) = ((_num)0.0);
- _mtx.get_item_ref_yx( 0, 2 ) = ((_num)2.0) * ( x * z + w * y );
- _mtx.get_item_ref_yx( 1, 2 ) = ((_num)2.0) * ( y * z - w * x );
- _mtx.get_item_ref_yx( 2, 2 ) = ((_num)1.0) - ((_num)2.0) * ( xx + yy );
- _mtx.get_item_ref_yx( 3, 2 ) = ((_num)0.0);
- _mtx.get_item_ref_yx( 0, 3 ) = ((_num)0.0);
- _mtx.get_item_ref_yx( 1, 3 ) = ((_num)0.0);
- _mtx.get_item_ref_yx( 2, 3 ) = ((_num)0.0);
- _mtx.get_item_ref_yx( 3, 3 ) = ((_num)1.0);
- }
- template < class _num, class _ntr >
- inline matrix<_num,_ntr> quaternion<_num,_ntr>::
- get_as_matrix() const
- {
- _q4t _q = (*this);
- _mt _mtx;
- _q.get_as_matrix( _mtx );
- return _mtx;
- }
- template < class _num, class _ntr >
- inline matrix<_num,_ntr> &
- matrix<_num,_ntr>::operator *= (
- const quaternion<_num,_ntr> & _q
- )
- {
- (*this) *= _q.get_as_matrix();
- return (*this);
- }
- template < class _num, class _ntr >
- inline matrix<_num,_ntr> operator * (
- const matrix<_num,_ntr> & _mtx,
- const quaternion<_num,_ntr> & _q
- )
- {
- matrix<_num,_ntr> _ret_val = _mtx;
- _ret_val *= _q;
- return _ret_val;
- }
- template < class _num, class _ntr >
- inline matrix<_num,_ntr>
- vector3<_num,_ntr>::get_as_scale() const
- {
- _mt _mtx;
- _mtx.load_scale( *this );
- return _mtx;
- }
- template < class _num, class _ntr >
- inline matrix<_num,_ntr>
- vector3<_num,_ntr>::get_as_translation() const
- {
- _mt _mtx;
- _mtx.load_translation( *this );
- return _mtx;
- }
- template < class _num, class _ntr >
- inline matrix<_num,_ntr>
- vector3<_num,_ntr>::get_as_rotation_xyz() const
- {
- _mt _mtx;
- _mtx.load_rotation_xyz( *this );
- return _mtx;
- }
- template < class _num, class _ntr >
- inline matrix<_num,_ntr>
- vector3<_num,_ntr>::get_as_rotation_quaternion() const
- {
- quaternion<_num,_ntr> _q( *this );
- return _q.get_as_matrix();
- }
- }; // namespace gltl
- // rollback warning C4201
- #pragma warning( pop )
- #endif // __GLTL_H