00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019 #ifndef GEOM_MAT3_HH
00020 #define GEOM_MAT3_HH
00021
00022 #include <cstddef>
00023 #include <ostream>
00024 #include <cassert>
00025 #include <stdexcept>
00026
00027 #include <boost/operators.hpp>
00028
00029 #include <ost/geom/module_config.hh>
00030 #include <ost/geom/mat2.hh>
00031 namespace geom {
00032
00033 class Vec3;
00034
00035 class DLLEXPORT_OST_GEOM Mat3:
00036 private boost::equality_comparable<Mat3>,
00037 private boost::additive1<Mat3>,
00038 private boost::multiplicative2<Mat3, Real>
00039 {
00040 public:
00042 Mat3()
00043 {
00044 this->set(1.0,0.0,0.0, 0.0,1.0,0.0, 0.0,0.0,1.0);
00045 }
00047
00056 Mat3(Real i00, Real i01, Real i02,
00057 Real i10, Real i11, Real i12,
00058 Real i20, Real i21, Real i22)
00059 {
00060 this->set(i00,i01,i02,i10,i11,i12,i20,i21,i22);
00061 }
00062
00063 Mat3(const Mat3& m)
00064 {
00065 this->set(m(0,0),m(0,1),m(0,2),m(1,0),m(1,1),m(1,2),m(2,0),m(2,1),m(2,2));
00066 }
00067
00068 Mat3(const Mat2& m)
00069 {
00070 this->set(m(0, 0), m(0, 1), Real(0.0),
00071 m(1, 0), m(1, 1), Real(0.0),
00072 Real(0.0), Real(0.0), Real(1.0));
00073 }
00074
00075 explicit Mat3(const Real arr[9])
00076 {
00077 this->set(arr[0],arr[1],arr[2],arr[3],arr[4],arr[5],arr[6],arr[7],arr[8]);
00078 }
00079
00080 explicit Mat3(Real x, Real y, Real z)
00081 {
00082 this->set(x, 0.0, 0.0, 0.0, y, 0.0, 0.0, 0.0, z);
00083 }
00085 Real& At(std::size_t r, std::size_t c)
00086 {
00087 if (r>2 || c>2) {
00088 throw std::out_of_range("indices must be smaller than 3");
00089 }
00090 return data_[r][c];
00091 }
00093 const Real& At(std::size_t r, std::size_t c) const
00094 {
00095 if (r>2 || c>2) {
00096 throw std::out_of_range("indices must be smaller than 3");
00097 }
00098 return data_[r][c];
00099 }
00101 Real& operator()(std::size_t r, std::size_t c)
00102 {
00103 assert(r<3 && c<3);
00104 return data_[r][c];
00105 }
00107 const Real& operator()(std::size_t r, std::size_t c) const
00108 {
00109 assert(r<3 && c<3);
00110 return data_[r][c];
00111 }
00112
00113 Mat3& operator=(const Mat3& m)
00114 {
00115 if(&m!=this) {
00116 this->set(m(0,0),m(0,1),m(0,2),m(1,0),m(1,1),m(1,2),m(2,0),m(2,1),m(2,2));
00117 }
00118 return *this;
00119 }
00120
00121 static Mat3 Identity()
00122 {
00123 static Mat3 i(1.0,0.0,0.0,
00124 0.0,1.0,0.0,
00125 0.0,0.0,1.0);
00126 return i;
00127 }
00128
00129 bool operator==(const Mat3& rhs) const
00130 {
00131 return data_[0][0] == rhs.data_[0][0] &&
00132 data_[1][0] == rhs.data_[1][0] &&
00133 data_[2][0] == rhs.data_[2][0] &&
00134 data_[0][1] == rhs.data_[0][1] &&
00135 data_[1][1] == rhs.data_[1][1] &&
00136 data_[2][1] == rhs.data_[2][1] &&
00137 data_[0][2] == rhs.data_[0][2] &&
00138 data_[1][2] == rhs.data_[1][2] &&
00139 data_[2][2] == rhs.data_[2][2];
00140 }
00141
00142 Mat3& operator+=(const Mat3& rhs)
00143 {
00144 data_[0][0]+=rhs(0,0);
00145 data_[0][1]+=rhs(0,1);
00146 data_[0][2]+=rhs(0,2);
00147 data_[1][0]+=rhs(1,0);
00148 data_[1][1]+=rhs(1,1);
00149 data_[1][2]+=rhs(1,2);
00150 data_[2][0]+=rhs(2,0);
00151 data_[2][1]+=rhs(2,1);
00152 data_[2][2]+=rhs(2,2);
00153 return *this;
00154 }
00155 Mat3& operator-=(const Mat3& rhs)
00156 {
00157 data_[0][0]-=rhs(0,0);
00158 data_[0][1]-=rhs(0,1);
00159 data_[0][2]-=rhs(0,2);
00160 data_[1][0]-=rhs(1,0);
00161 data_[1][1]-=rhs(1,1);
00162 data_[1][2]-=rhs(1,2);
00163 data_[2][0]-=rhs(2,0);
00164 data_[2][1]-=rhs(2,1);
00165 data_[2][2]-=rhs(2,2);
00166 return *this;
00167 }
00168 Mat3& operator*=(const Real d)
00169 {
00170 data_[0][0]*=d;
00171 data_[0][1]*=d;
00172 data_[0][2]*=d;
00173 data_[1][0]*=d;
00174 data_[1][1]*=d;
00175 data_[1][2]*=d;
00176 data_[2][0]*=d;
00177 data_[2][1]*=d;
00178 data_[2][2]*=d;
00179 return *this;
00180 }
00181 Mat3& operator/=(const Real d)
00182 {
00183 data_[0][0]/=d;
00184 data_[0][1]/=d;
00185 data_[0][2]/=d;
00186 data_[1][0]/=d;
00187 data_[1][1]/=d;
00188 data_[1][2]/=d;
00189 data_[2][0]/=d;
00190 data_[2][1]/=d;
00191 data_[2][2]/=d;
00192 return *this;
00193 }
00194
00195 Mat3& operator*=(const Mat3& m)
00196 {
00197 (*this)=Mat3((*this)(0,0)*m(0,0)+(*this)(0,1)*m(1,0)+(*this)(0,2)*m(2,0),
00198 (*this)(0,0)*m(0,1)+(*this)(0,1)*m(1,1)+(*this)(0,2)*m(2,1),
00199 (*this)(0,0)*m(0,2)+(*this)(0,1)*m(1,2)+(*this)(0,2)*m(2,2),
00200 (*this)(1,0)*m(0,0)+(*this)(1,1)*m(1,0)+(*this)(1,2)*m(2,0),
00201 (*this)(1,0)*m(0,1)+(*this)(1,1)*m(1,1)+(*this)(1,2)*m(2,1),
00202 (*this)(1,0)*m(0,2)+(*this)(1,1)*m(1,2)+(*this)(1,2)*m(2,2),
00203 (*this)(2,0)*m(0,0)+(*this)(2,1)*m(1,0)+(*this)(2,2)*m(2,0),
00204 (*this)(2,0)*m(0,1)+(*this)(2,1)*m(1,1)+(*this)(2,2)*m(2,1),
00205 (*this)(2,0)*m(0,2)+(*this)(2,1)*m(1,2)+(*this)(2,2)*m(2,2));
00206 return *this;
00207 }
00208
00209 Real* Data() {return &data_[0][0];}
00210 const Real* Data() const {return &data_[0][0];}
00211
00212 geom::Vec3 GetCol(int index) const;
00213 geom::Vec3 GetRow(int index) const;
00214 private:
00215 Real data_[3][3];
00216
00217 void set(Real i00, Real i01, Real i02,
00218 Real i10, Real i11, Real i12,
00219 Real i20, Real i21, Real i22)
00220 {
00221 data_[0][0]=i00; data_[0][1]=i01; data_[0][2]=i02;
00222 data_[1][0]=i10; data_[1][1]=i11; data_[1][2]=i12;
00223 data_[2][0]=i20; data_[2][1]=i21; data_[2][2]=i22;
00224 }
00225 };
00226
00227 DLLEXPORT_OST_GEOM std::ostream& operator<<(std::ostream& o, const Mat3& m);
00228
00229 }
00230
00231
00232 #endif