home *** CD-ROM | disk | FTP | other *** search
/ Computer Shopper 275 / DPCS0111DVD.ISO / Toolkit / Audio-Visual / VirtualDub / Source / VirtualDub-1.9.10-src.7z / src / h / vd2 / system / vectors.h < prev    next >
Encoding:
C/C++ Source or Header  |  2009-09-14  |  13.3 KB  |  569 lines

  1. //    VirtualDub - Video processing and capture application
  2. //    System library component
  3. //    Copyright (C) 1998-2004 Avery Lee, All Rights Reserved.
  4. //
  5. //    Beginning with 1.6.0, the VirtualDub system library is licensed
  6. //    differently than the remainder of VirtualDub.  This particular file is
  7. //    thus licensed as follows (the "zlib" license):
  8. //
  9. //    This software is provided 'as-is', without any express or implied
  10. //    warranty.  In no event will the authors be held liable for any
  11. //    damages arising from the use of this software.
  12. //
  13. //    Permission is granted to anyone to use this software for any purpose,
  14. //    including commercial applications, and to alter it and redistribute it
  15. //    freely, subject to the following restrictions:
  16. //
  17. //    1.    The origin of this software must not be misrepresented; you must
  18. //        not claim that you wrote the original software. If you use this
  19. //        software in a product, an acknowledgment in the product
  20. //        documentation would be appreciated but is not required.
  21. //    2.    Altered source versions must be plainly marked as such, and must
  22. //        not be misrepresented as being the original software.
  23. //    3.    This notice may not be removed or altered from any source
  24. //        distribution.
  25.  
  26. #ifndef f_VD2_SYSTEM_VECTORS_H
  27. #define f_VD2_SYSTEM_VECTORS_H
  28.  
  29. #ifdef _MSC_VER
  30.     #pragma once
  31. #endif
  32.  
  33. #include <vd2/system/vdtypes.h>
  34. #include <math.h>
  35. #include <limits>
  36.  
  37. #ifndef VDFORCEINLINE
  38.     #define VDFORCEINLINE __forceinline
  39. #endif
  40.  
  41. ///////////////////////////////////////////////////////////////////////////
  42.  
  43. bool VDSolveLinearEquation(double *src, int n, ptrdiff_t stride_elements, double *b, double tolerance = 1e-5);
  44.  
  45. ///////////////////////////////////////////////////////////////////////////
  46.  
  47. #include <vd2/system/vectors_float.h>
  48. #include <vd2/system/vectors_int.h>
  49.  
  50. ///////////////////////////////////////////////////////////////////////////
  51.  
  52. class vdfloat2x2 {
  53. public:
  54.     enum zero_type { zero };
  55.     enum identity_type { identity };
  56.  
  57.     typedef float            value_type;
  58.     typedef vdfloat2        vector_type;
  59.     typedef vdfloat2c        vector_ctor_type;
  60.     typedef vdfloat2x2        self_type;
  61.  
  62.     vdfloat2x2() {}
  63.     vdfloat2x2(zero_type) { m[0] = m[1] = vector_ctor_type(0, 0); }
  64.     vdfloat2x2(identity_type) {
  65.         m[0] = vector_ctor_type(1, 0);
  66.         m[1] = vector_ctor_type(0, 1);
  67.     }
  68.  
  69.     vector_type& operator[](int k) { return m[k]; }
  70.     const vector_type& operator[](int k) const { return m[k]; }
  71.  
  72.     self_type operator*(const self_type& v) const {
  73.         self_type result;
  74.  
  75. #define DO(i,j) result.m[i].v[j] = m[i].v[0]*v.m[0].v[j] + m[i].v[1]*v.m[1].v[j]
  76.         DO(0,0);
  77.         DO(0,1);
  78.         DO(1,0);
  79.         DO(1,1);
  80. #undef DO
  81.  
  82.         return result;
  83.     }
  84.  
  85.     vector_type operator*(const vector_type& r) const {
  86.         return vector_ctor_type(
  87.                 m[0].v[0]*r.v[0] + m[0].v[1]*r.v[1],
  88.                 m[1].v[0]*r.v[0] + m[1].v[1]*r.v[1]);
  89.     }
  90.  
  91.     self_type transpose() const {
  92.         self_type res;
  93.  
  94.         res.m[0].v[0] = m[0].v[0];
  95.         res.m[0].v[1] = m[1].v[0];
  96.         res.m[1].v[0] = m[0].v[1];
  97.         res.m[1].v[1] = m[1].v[1];
  98.  
  99.         return res;
  100.     }
  101.  
  102.     self_type adjunct() const {
  103.         self_type res;
  104.         
  105.         res.m[0].set(m[1].v[1], -m[0].v[1]);
  106.         res.m[1].set(-m[1].v[0], -m[0].v[0]);
  107.  
  108.         return res;
  109.     }
  110.  
  111.     value_type det() const {
  112.         return m[0].v[0]*m[1].v[1] - m[1].v[0]*m[0].v[1];
  113.     }
  114.  
  115.     self_type operator~() const {
  116.         return adjunct() / det();
  117.     }
  118.  
  119.     self_type& operator*=(const value_type factor) {
  120.         m[0] *= factor;
  121.         m[1] *= factor;
  122.  
  123.         return *this;
  124.     }
  125.  
  126.     self_type& operator/=(const value_type factor) {
  127.         return operator*=(value_type(1)/factor);
  128.     }
  129.  
  130.     self_type operator*(const value_type factor) const {
  131.         return self_type(*this) *= factor;
  132.     }
  133.  
  134.     self_type operator/(const value_type factor) const {
  135.         return self_type(*this) /= factor;
  136.     }
  137.  
  138.     vector_type m[2];
  139. };
  140.  
  141. class vdfloat3x3 {
  142. public:
  143.     enum zero_type { zero };
  144.     enum identity_type { identity };
  145.     enum rotation_x_type { rotation_x };
  146.     enum rotation_y_type { rotation_y };
  147.     enum rotation_z_type { rotation_z };
  148.  
  149.     typedef float            value_type;
  150.     typedef vdfloat3        vector_type;
  151.     typedef vdfloat3c        vector_ctor_type;
  152.     typedef vdfloat3x3        self_type;
  153.  
  154.     vdfloat3x3() {}
  155.     vdfloat3x3(zero_type) { m[0] = m[1] = m[2] = vector_ctor_type(0, 0, 0); }
  156.     vdfloat3x3(identity_type) {
  157.         m[0].set(1, 0, 0);
  158.         m[1].set(0, 1, 0);
  159.         m[2].set(0, 0, 1);
  160.     }
  161.     vdfloat3x3(rotation_x_type, value_type angle) {
  162.         const value_type s(sin(angle));
  163.         const value_type c(cos(angle));
  164.  
  165.         m[0].set( 1, 0, 0);
  166.         m[1].set( 0, c,-s);
  167.         m[2].set( 0, s, c);
  168.     }
  169.  
  170.     vdfloat3x3(rotation_y_type, value_type angle) {
  171.         const value_type s(sin(angle));
  172.         const value_type c(cos(angle));
  173.  
  174.         m[0].set( c, 0, s);
  175.         m[1].set( 0, 1, 0);
  176.         m[2].set(-s, 0, c);
  177.     }
  178.     vdfloat3x3(rotation_z_type, value_type angle) {
  179.         const value_type s(sin(angle));
  180.         const value_type c(cos(angle));
  181.  
  182.         m[0].set( c,-s, 0);
  183.         m[1].set( s, c, 0);
  184.         m[2].set( 0, 0, 1);
  185.     }
  186.  
  187.     vector_type& operator[](int k) { return m[k]; }
  188.     const vector_type& operator[](int k) const { return m[k]; }
  189.  
  190.     self_type operator*(const self_type& v) const {
  191.         self_type result;
  192.  
  193. #define DO(i,j) result.m[i].v[j] = m[i].v[0]*v.m[0].v[j] + m[i].v[1]*v.m[1].v[j] + m[i].v[2]*v.m[2].v[j]
  194.         DO(0,0);
  195.         DO(0,1);
  196.         DO(0,2);
  197.         DO(1,0);
  198.         DO(1,1);
  199.         DO(1,2);
  200.         DO(2,0);
  201.         DO(2,1);
  202.         DO(2,2);
  203. #undef DO
  204.  
  205.         return result;
  206.     }
  207.  
  208.     vector_type operator*(const vector_type& r) const {
  209.         return vector_ctor_type(
  210.                 m[0].v[0]*r.v[0] + m[0].v[1]*r.v[1] + m[0].v[2]*r.v[2],
  211.                 m[1].v[0]*r.v[0] + m[1].v[1]*r.v[1] + m[1].v[2]*r.v[2],
  212.                 m[2].v[0]*r.v[0] + m[2].v[1]*r.v[1] + m[2].v[2]*r.v[2]);
  213.     }
  214.  
  215.     self_type transpose() const {
  216.         self_type res;
  217.  
  218.         res.m[0].v[0] = m[0].v[0];
  219.         res.m[0].v[1] = m[1].v[0];
  220.         res.m[0].v[2] = m[2].v[0];
  221.         res.m[1].v[0] = m[0].v[1];
  222.         res.m[1].v[1] = m[1].v[1];
  223.         res.m[1].v[2] = m[2].v[1];
  224.         res.m[2].v[0] = m[0].v[2];
  225.         res.m[2].v[1] = m[1].v[2];
  226.         res.m[2].v[2] = m[2].v[2];
  227.  
  228.         return res;
  229.     }
  230.  
  231.     self_type adjunct() const {
  232.         using namespace nsVDMath;
  233.  
  234.         self_type res;
  235.  
  236.         res.m[0] = cross(m[1], m[2]);
  237.         res.m[1] = cross(m[2], m[0]);
  238.         res.m[2] = cross(m[0], m[1]);
  239.  
  240.         return res.transpose();
  241.     }
  242.  
  243.     value_type det() const {
  244.         return    + m[0].v[0] * m[1].v[1] * m[2].v[2]
  245.                 + m[1].v[0] * m[2].v[1] * m[0].v[2]
  246.                 + m[2].v[0] * m[0].v[1] * m[1].v[2]
  247.                 - m[0].v[0] * m[2].v[1] * m[1].v[2]
  248.                 - m[1].v[0] * m[0].v[1] * m[2].v[2]
  249.                 - m[2].v[0] * m[1].v[1] * m[0].v[2];
  250.     }
  251.  
  252.     self_type operator~() const {
  253.         return adjunct() / det();
  254.     }
  255.  
  256.     self_type& operator*=(const value_type factor) {
  257.         m[0] *= factor;
  258.         m[1] *= factor;
  259.         m[2] *= factor;
  260.  
  261.         return *this;
  262.     }
  263.  
  264.     self_type& operator/=(const value_type factor) {
  265.         return operator*=(value_type(1)/factor);
  266.     }
  267.  
  268.     self_type operator*(const value_type factor) const {
  269.         return self_type(*this) *= factor;
  270.     }
  271.  
  272.     self_type operator/(const value_type factor) const {
  273.         return self_type(*this) /= factor;
  274.     }
  275.  
  276.     vector_type m[3];
  277. };
  278.  
  279. class vdfloat4x4 {
  280. public:
  281.     enum zero_type { zero };
  282.     enum identity_type { identity };
  283.     enum rotation_x_type { rotation_x };
  284.     enum rotation_y_type { rotation_y };
  285.     enum rotation_z_type { rotation_z };
  286.  
  287.     typedef float            value_type;
  288.     typedef vdfloat4        vector_type;
  289.     typedef vdfloat4c        vector_ctor_type;
  290.  
  291.     vdfloat4x4() {}
  292.     vdfloat4x4(const vdfloat3x3& v) {
  293.         m[0].set(v.m[0].x, v.m[0].y, v.m[0].z, 0.0f);
  294.         m[1].set(v.m[1].x, v.m[1].y, v.m[1].z, 0.0f);
  295.         m[2].set(v.m[2].x, v.m[2].y, v.m[2].z, 0.0f);
  296.         m[3].set(0, 0, 0, 1);
  297.     }
  298.  
  299.     vdfloat4x4(zero_type) {
  300.         m[0].setzero();
  301.         m[1].setzero();
  302.         m[2].setzero();
  303.         m[3].setzero();
  304.     }
  305.  
  306.     vdfloat4x4(identity_type) {
  307.         m[0].set(1, 0, 0, 0);
  308.         m[1].set(0, 1, 0, 0);
  309.         m[2].set(0, 0, 1, 0);
  310.         m[3].set(0, 0, 0, 1);
  311.     }
  312.     vdfloat4x4(rotation_x_type, value_type angle) {
  313.         const value_type s(sin(angle));
  314.         const value_type c(cos(angle));
  315.  
  316.         m[0].set( 1, 0, 0, 0);
  317.         m[1].set( 0, c,-s, 0);
  318.         m[2].set( 0, s, c, 0);
  319.         m[3].set( 0, 0, 0, 1);
  320.     }
  321.     vdfloat4x4(rotation_y_type, value_type angle) {
  322.         const value_type s(sin(angle));
  323.         const value_type c(cos(angle));
  324.  
  325.         m[0].set( c, 0, s, 0);
  326.         m[1].set( 0, 1, 0, 0);
  327.         m[2].set(-s, 0, c, 0);
  328.         m[3].set( 0, 0, 0, 1);
  329.     }
  330.     vdfloat4x4(rotation_z_type, value_type angle) {
  331.         const value_type s(sin(angle));
  332.         const value_type c(cos(angle));
  333.  
  334.         m[0].set( c,-s, 0, 0);
  335.         m[1].set( s, c, 0, 0);
  336.         m[2].set( 0, 0, 1, 0);
  337.         m[3].set( 0, 0, 0, 1);
  338.     }
  339.  
  340.     const value_type *data() const { return &m[0][0]; }
  341.  
  342.     vector_type& operator[](int n) { return m[n]; }
  343.     const vector_type& operator[](int n) const { return m[n]; }
  344.  
  345.     vdfloat4x4 operator*(const vdfloat4x4& v) const {
  346.         vdfloat4x4 result;
  347.  
  348. #define DO(i,j) result.m[i].v[j] = m[i].v[0]*v.m[0].v[j] + m[i].v[1]*v.m[1].v[j] + m[i].v[2]*v.m[2].v[j] + m[i].v[3]*v.m[3].v[j]
  349.         DO(0,0);
  350.         DO(0,1);
  351.         DO(0,2);
  352.         DO(0,3);
  353.         DO(1,0);
  354.         DO(1,1);
  355.         DO(1,2);
  356.         DO(1,3);
  357.         DO(2,0);
  358.         DO(2,1);
  359.         DO(2,2);
  360.         DO(2,3);
  361.         DO(3,0);
  362.         DO(3,1);
  363.         DO(3,2);
  364.         DO(3,3);
  365. #undef DO
  366.  
  367.         return result;
  368.     }
  369.  
  370.     vdfloat4x4& operator*=(const vdfloat4x4& v) {
  371.         return operator=(operator*(v));
  372.     }
  373.  
  374.     vector_type operator*(const vdfloat3& r) const {
  375.         return vector_ctor_type(
  376.                 m[0].v[0]*r.v[0] + m[0].v[1]*r.v[1] + m[0].v[2]*r.v[2] + m[0].v[3],
  377.                 m[1].v[0]*r.v[0] + m[1].v[1]*r.v[1] + m[1].v[2]*r.v[2] + m[1].v[3],
  378.                 m[2].v[0]*r.v[0] + m[2].v[1]*r.v[1] + m[2].v[2]*r.v[2] + m[2].v[3],
  379.                 m[3].v[0]*r.v[0] + m[3].v[1]*r.v[1] + m[3].v[2]*r.v[2] + m[3].v[3]);
  380.     }
  381.  
  382.     vector_type operator*(const vector_type& r) const {
  383.         return vector_ctor_type(
  384.                 m[0].v[0]*r.v[0] + m[0].v[1]*r.v[1] + m[0].v[2]*r.v[2] + m[0].v[3]*r.v[3],
  385.                 m[1].v[0]*r.v[0] + m[1].v[1]*r.v[1] + m[1].v[2]*r.v[2] + m[1].v[3]*r.v[3],
  386.                 m[2].v[0]*r.v[0] + m[2].v[1]*r.v[1] + m[2].v[2]*r.v[2] + m[2].v[3]*r.v[3],
  387.                 m[3].v[0]*r.v[0] + m[3].v[1]*r.v[1] + m[3].v[2]*r.v[2] + m[3].v[3]*r.v[3]);
  388.     }
  389.  
  390.     vector_type m[4];
  391. };
  392.  
  393. template<class T>
  394. struct VDSize {
  395.     typedef T value_type;
  396.  
  397.     int w, h;
  398.  
  399.     VDSize() {}
  400.     VDSize(int _w, int _h) : w(_w), h(_h) {}
  401.  
  402.     bool operator==(const VDSize& s) const { return w==s.w && h==s.h; }
  403.     bool operator!=(const VDSize& s) const { return w!=s.w || h!=s.h; }
  404.  
  405.     VDSize& operator+=(const VDSize& s) {
  406.         w += s.w;
  407.         h += s.h;
  408.         return *this;
  409.     }
  410.  
  411.     T area() const { return w*h; }
  412.  
  413.     void include(const VDSize& s) {
  414.         if (w < s.w)
  415.             w = s.w;
  416.         if (h < s.h)
  417.             h = s.h;
  418.     }
  419. };
  420.  
  421. template<class T>
  422. class VDRect {
  423. public:
  424.     typedef T value_type;
  425.  
  426.     VDRect();
  427.     VDRect(T left_, T top_, T right_, T bottom_);
  428.  
  429.     bool empty() const;
  430.     bool valid() const;
  431.  
  432.     void clear();
  433.     void invalidate();
  434.     void set(T l, T t, T r, T b);
  435.  
  436.     void add(T x, T y);
  437.     void add(const VDRect& r);
  438.     void translate(T x, T y);
  439.     void scale(T x, T y);
  440.     void transform(T scaleX, T scaleY, T offsetX, T offsety);
  441.  
  442.     bool operator==(const VDRect& r) const;
  443.     bool operator!=(const VDRect& r) const;
  444.  
  445.     T width() const;
  446.     T height() const;
  447.     T area() const;
  448.     VDSize<T> size() const;
  449.  
  450. public:
  451.     T left, top, right, bottom;
  452. };
  453.  
  454. template<class T>
  455. VDRect<T>::VDRect() {
  456. }
  457.  
  458. template<class T>
  459. VDRect<T>::VDRect(T left_, T top_, T right_, T bottom_)
  460.     : left(left_)
  461.     , top(top_)
  462.     , right(right_)
  463.     , bottom(bottom_)
  464. {
  465. }
  466.  
  467. template<class T>
  468. bool VDRect<T>::empty() const {
  469.     return left >= right || top >= bottom;
  470. }
  471.  
  472. template<class T>
  473. bool VDRect<T>::valid() const {
  474.     return left <= right;
  475. }
  476.  
  477. template<class T>
  478. void VDRect<T>::clear() {
  479.     left = top = right = bottom = 0;
  480. }
  481.  
  482. template<class T>
  483. void VDRect<T>::invalidate() {
  484.     left = top = (std::numeric_limits<T>::max)();
  485.     right = bottom = std::numeric_limits<T>::is_signed ? -(std::numeric_limits<T>::max)() : T(0);
  486. }
  487.  
  488. template<class T>
  489. void VDRect<T>::set(T l, T t, T r, T b) {
  490.     left = l;
  491.     top = t;
  492.     right = r;
  493.     bottom = b;
  494. }
  495.  
  496. template<class T>
  497. void VDRect<T>::add(T x, T y) {
  498.     if (left > x)
  499.         left = x;
  500.     if (top > y)
  501.         top = y;
  502.     if (right < x)
  503.         right = x;
  504.     if (bottom < y)
  505.         bottom = y;
  506. }
  507.  
  508. template<class T>
  509. void VDRect<T>::add(const VDRect& src) {
  510.     if (left > src.left)
  511.         left = src.left;
  512.     if (top > src.top)
  513.         top = src.top;
  514.     if (right < src.right)
  515.         right = src.right;
  516.     if (bottom < src.bottom)
  517.         bottom = src.bottom;
  518. }
  519.  
  520. template<class T>
  521. void VDRect<T>::translate(T x, T y) {
  522.     left += x;
  523.     top += y;
  524.     right += x;
  525.     bottom += y;
  526. }
  527.  
  528. template<class T>
  529. void VDRect<T>::scale(T x, T y) {
  530.     left *= x;
  531.     top *= y;
  532.     right *= x;
  533.     bottom *= y;
  534. }
  535.  
  536. template<class T>
  537. void VDRect<T>::transform(T scaleX, T scaleY, T offsetX, T offsetY) {
  538.     left    = left        * scaleX + offsetX;
  539.     top        = top        * scaleY + offsetY;
  540.     right    = right        * scaleX + offsetX;
  541.     bottom    = bottom    * scaleY + offsetY;
  542. }
  543.  
  544. template<class T>
  545. bool VDRect<T>::operator==(const VDRect& r) const { return left==r.left && top==r.top && right==r.right && bottom==r.bottom; }
  546.  
  547. template<class T>
  548. bool VDRect<T>::operator!=(const VDRect& r) const { return left!=r.left || top!=r.top || right!=r.right || bottom!=r.bottom; }
  549.  
  550. template<class T>
  551. T VDRect<T>::width() const { return right-left; }
  552.  
  553. template<class T>
  554. T VDRect<T>::height() const { return bottom-top; }
  555.  
  556. template<class T>
  557. T VDRect<T>::area() const { return (right-left)*(bottom-top); }
  558.  
  559. template<class T>
  560. VDSize<T> VDRect<T>::size() const { return VDSize<T>(right-left, bottom-top); }
  561.  
  562. ///////////////////////////////////////////////////////////////////////////////
  563. typedef VDSize<sint32>    vdsize32;
  564. typedef VDSize<float>    vdsize32f;
  565. typedef    VDRect<sint32>    vdrect32;
  566. typedef    VDRect<float>    vdrect32f;
  567.  
  568. #endif
  569.