00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00046
00047
00048
00049
00050
00051
00052 #ifndef OPENMESH_GEOMETRY_QUADRIC_HH
00053 #define OPENMESH_GEOMETRY_QUADRIC_HH
00054
00055
00056
00057
00058 #include "Config.hh"
00059 #include <OpenMesh/Core/Geometry/VectorT.hh>
00060 #include <OpenMesh/Core/Utils/GenProg.hh>
00061
00062
00063
00064 namespace OpenMesh {
00065 namespace Geometry {
00066
00067
00068
00069
00070
00077 template <class Scalar>
00078 class QuadricT
00079 {
00080 public:
00081 typedef Scalar value_type;
00082 typedef QuadricT<Scalar> type;
00083 typedef QuadricT<Scalar> Self;
00084
00085
00086
00087
00088
00090 QuadricT(Scalar _a, Scalar _b, Scalar _c, Scalar _d,
00091 Scalar _e, Scalar _f, Scalar _g,
00092 Scalar _h, Scalar _i,
00093 Scalar _j)
00094 : a_(_a), b_(_b), c_(_c), d_(_d),
00095 e_(_e), f_(_f), g_(_g),
00096 h_(_h), i_(_i),
00097 j_(_j)
00098 {
00099 }
00100
00101
00103 QuadricT( Scalar _a=0.0, Scalar _b=0.0, Scalar _c=0.0, Scalar _d=0.0 )
00104 : a_(_a*_a), b_(_a*_b), c_(_a*_c), d_(_a*_d),
00105 e_(_b*_b), f_(_b*_c), g_(_b*_d),
00106 h_(_c*_c), i_(_c*_d),
00107 j_(_d*_d)
00108 {}
00109
00110 template <class _Point>
00111 QuadricT(const _Point& _pt)
00112 {
00113 set_distance_to_point(_pt);
00114 }
00115
00116 template <class _Normal, class _Point>
00117 QuadricT(const _Normal& _n, const _Point& _p)
00118 {
00119 set_distance_to_plane(_n,_p);
00120 }
00121
00122
00123 void set(Scalar _a, Scalar _b, Scalar _c, Scalar _d,
00124 Scalar _e, Scalar _f, Scalar _g,
00125 Scalar _h, Scalar _i,
00126 Scalar _j)
00127 {
00128 a_ = _a; b_ = _b; c_ = _c; d_ = _d;
00129 e_ = _e; f_ = _f; g_ = _g;
00130 h_ = _h; i_ = _i;
00131 j_ = _j;
00132 }
00133
00134
00135 template <class _Point>
00136 void set_distance_to_point(const _Point& _pt)
00137 {
00138 set(1, 0, 0, -_pt[0],
00139 1, 0, -_pt[1],
00140 1, -_pt[2],
00141 dot(_pt,_pt));
00142 }
00143
00144
00145 void set_distance_to_plane(Scalar _a, Scalar _b, Scalar _c, Scalar _d)
00146 {
00147 a_ = _a*_a; b_ = _a*_b; c_ = _a*_c; d_ = _a*_d;
00148 e_ = _b*_b; f_ = _b*_c; g_ = _b*_d;
00149 h_ = _c*_c; i_ = _c*_d;
00150 j_ = _d*_d;
00151 }
00152
00153
00154
00155 template <class _Normal, class _Point>
00156 void set_distance_to_plane(const _Normal& _n, const _Point& _p)
00157 {
00158 set_distance_to_plane(_n[0], _n[1], _n[2], -dot(_n,_p));
00159 }
00160
00162 void clear() { a_ = b_ = c_ = d_ = e_ = f_ = g_ = h_ = i_ = j_ = 0.0; }
00163
00165 QuadricT<Scalar>& operator+=( const QuadricT<Scalar>& _q )
00166 {
00167 a_ += _q.a_; b_ += _q.b_; c_ += _q.c_; d_ += _q.d_;
00168 e_ += _q.e_; f_ += _q.f_; g_ += _q.g_;
00169 h_ += _q.h_; i_ += _q.i_;
00170 j_ += _q.j_;
00171 return *this;
00172 }
00173
00174
00176 QuadricT<Scalar>& operator*=( Scalar _s)
00177 {
00178 a_ *= _s; b_ *= _s; c_ *= _s; d_ *= _s;
00179 e_ *= _s; f_ *= _s; g_ *= _s;
00180 h_ *= _s; i_ *= _s;
00181 j_ *= _s;
00182 return *this;
00183 }
00184
00185
00187 template <class _Vec4>
00188 _Vec4 operator*(const _Vec4& _v) const
00189 {
00190 Scalar x(_v[0]), y(_v[1]), z(_v[2]), w(_v[3]);
00191 return _Vec4(x*a_ + y*b_ + z*c_ + w*d_,
00192 x*b_ + y*e_ + z*f_ + w*g_,
00193 x*c_ + y*f_ + z*h_ + w*i_,
00194 x*d_ + y*g_ + z*i_ + w*j_);
00195 }
00196
00198 template <class _Vec>
00199 Scalar operator()(const _Vec& _v) const
00200 {
00201 return evaluate(_v, GenProg::Int2Type<_Vec::size_>());
00202 }
00203
00204 Scalar a() const { return a_; }
00205 Scalar b() const { return b_; }
00206 Scalar c() const { return c_; }
00207 Scalar d() const { return d_; }
00208 Scalar e() const { return e_; }
00209 Scalar f() const { return f_; }
00210 Scalar g() const { return g_; }
00211 Scalar h() const { return h_; }
00212 Scalar i() const { return i_; }
00213 Scalar j() const { return j_; }
00214
00215 Scalar xx() const { return a_; }
00216 Scalar xy() const { return b_; }
00217 Scalar xz() const { return c_; }
00218 Scalar xw() const { return d_; }
00219 Scalar yy() const { return e_; }
00220 Scalar yz() const { return f_; }
00221 Scalar yw() const { return g_; }
00222 Scalar zz() const { return h_; }
00223 Scalar zw() const { return i_; }
00224 Scalar ww() const { return j_; }
00225
00226 protected:
00227
00229 template <class _Vec3>
00230 Scalar evaluate(const _Vec3& _v, GenProg::Int2Type<3>) const
00231 {
00232 Scalar x(_v[0]), y(_v[1]), z(_v[2]);
00233 return a_*x*x + 2.0*b_*x*y + 2.0*c_*x*z + 2.0*d_*x
00234 + e_*y*y + 2.0*f_*y*z + 2.0*g_*y
00235 + h_*z*z + 2.0*i_*z
00236 + j_;
00237 }
00238
00240 template <class _Vec4>
00241 Scalar evaluate(const _Vec4& _v, GenProg::Int2Type<4>) const
00242 {
00243 Scalar x(_v[0]), y(_v[1]), z(_v[2]), w(_v[3]);
00244 return a_*x*x + 2.0*b_*x*y + 2.0*c_*x*z + 2.0*d_*x*w
00245 + e_*y*y + 2.0*f_*y*z + 2.0*g_*y*w
00246 + h_*z*z + 2.0*i_*z*w
00247 + j_*w*w;
00248 }
00249
00250 private:
00251
00252 Scalar a_, b_, c_, d_,
00253 e_, f_, g_,
00254 h_, i_,
00255 j_;
00256 };
00257
00258
00260 typedef QuadricT<float> Quadricf;
00261
00263 typedef QuadricT<double> Quadricd;
00264
00265
00266
00267 }
00268 }
00269
00270 #endif // OPENMESH_GEOMETRY_HH defined
00271