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 #ifndef __UT_Vector4_h__
00027 #define __UT_Vector4_h__
00028
00029 #include "UT_API.h"
00030 #include <math.h>
00031 #include <limits.h>
00032 #include <iostream.h>
00033 #include "UT_Assert.h"
00034 #include "UT_Math.h"
00035 #include <vector>
00036
00037 class UT_Matrix4;
00038 class UT_IStream;
00039 class UT_DMatrix4;
00040 class UT_Vector3;
00041 class UT_Vector4;
00042
00043
00044
00045
00046
00047
00048
00049
00050 inline UT_Vector4 operator*(const UT_Vector4 &v, const UT_Matrix4 &m);
00051 inline UT_Vector4 operator*(const UT_Vector4 &v, const UT_DMatrix4 &m);
00052 inline UT_Vector4 operator+(const UT_Vector4 &v1, const UT_Vector4 &v2);
00053 inline UT_Vector4 operator-(const UT_Vector4 &v1, const UT_Vector4 &v2);
00054 inline UT_Vector4 operator+(const UT_Vector4 &v, fpreal scalar);
00055 inline UT_Vector4 operator-(const UT_Vector4 &v, fpreal scalar);
00056 inline UT_Vector4 operator*(const UT_Vector4 &v, fpreal scalar);
00057 inline UT_Vector4 operator/(const UT_Vector4 &v, fpreal scalar);
00058 inline UT_Vector4 operator+(fpreal scalar, const UT_Vector4 &v);
00059 inline UT_Vector4 operator-(fpreal scalar, const UT_Vector4 &v);
00060 inline UT_Vector4 operator*(fpreal scalar, const UT_Vector4 &v);
00061 inline UT_Vector4 operator/(fpreal scalar, const UT_Vector4 &v);
00062
00063
00064
00065
00066 UT_API UT_Vector3 cross(const UT_Vector4 &v1, const UT_Vector4 &v2);
00067
00068
00069
00070 inline fpreal dot(const UT_Vector4 &v1, const UT_Vector4 &v2);
00071 inline fpreal dot(const UT_Vector4 &v1, const UT_Vector3 &v2);
00072 inline fpreal dot(const UT_Vector3 &v1, const UT_Vector4 &v2);
00073
00074
00075
00076
00077
00078
00079
00080
00081
00082
00083
00084
00085
00086
00087
00088
00089
00090
00091
00092 UT_API UT_Vector4 rowVecMult(const UT_Vector4 &v, const UT_Matrix4 &m);
00093 UT_API UT_Vector4 rowVecMult(const UT_Vector4 &v, const UT_DMatrix4 &m);
00094 UT_API UT_Vector4 colVecMult(const UT_Matrix4 &m, const UT_Vector4 &v);
00095 UT_API UT_Vector4 colVecMult(const UT_DMatrix4 &m, const UT_Vector4 &v);
00096
00097 UT_API UT_Vector4 rowVecMult3(const UT_Vector4 &v, const UT_Matrix4 &m);
00098 UT_API UT_Vector4 rowVecMult3(const UT_Vector4 &v, const UT_DMatrix4 &m);
00099 UT_API UT_Vector4 colVecMult3(const UT_Matrix4 &m, const UT_Vector4 &v);
00100 UT_API UT_Vector4 colVecMult3(const UT_DMatrix4 &m, const UT_Vector4 &v);
00101
00102
00103
00104
00105 inline fpreal distance4(const UT_Vector4 &p1, const UT_Vector4 &p2);
00106 inline fpreal distance3(const UT_Vector4 &p1, const UT_Vector4 &p2);
00107
00108
00109
00110 class UT_API UT_Vector4 {
00111 public:
00112
00113
00114 inline UT_Vector4(void)
00115 {
00116 UT_ASSERT_COMPILETIME(sizeof(UT_Vector4) ==
00117 4 * sizeof(float));
00118 }
00119 inline UT_Vector4(fpreal vx, fpreal vy, fpreal vz, fpreal vw = 1.0f)
00120 {
00121 vec[0] = vx; vec[1] = vy; vec[2] = vz; vec[3] = vw;
00122 }
00123 inline UT_Vector4(const fpreal32 v[4])
00124 {
00125 vec[0] = v[0]; vec[1] = v[1]; vec[2] = v[2]; vec[3] = v[3];
00126 }
00127 inline UT_Vector4(const fpreal64 v[4])
00128 {
00129 vec[0] = (fpreal) v[0];
00130 vec[1] = (fpreal) v[1];
00131 vec[2] = (fpreal) v[2];
00132 vec[3] = (fpreal) v[3];
00133 }
00134 inline
00135 explicit UT_Vector4(const UT_Vector3 &v, float w = 1.f);
00136
00137
00138 ~UT_Vector4(void) {}
00139
00140
00141
00142
00143
00144
00145
00146
00147
00148
00149
00150 UT_Vector4 &operator=(const UT_Vector3 &v);
00151
00152
00153
00154
00155
00156
00157 inline
00158 UT_Vector4 &operator+=(const UT_Vector4 &v)
00159 {
00160 vec[0] += v.vec[0];
00161 vec[1] += v.vec[1];
00162 vec[2] += v.vec[2];
00163 vec[3] += v.vec[3];
00164 return *this;
00165 }
00166 inline
00167 UT_Vector4 &operator-=(const UT_Vector4 &v)
00168 {
00169 vec[0] -= v.vec[0];
00170 vec[1] -= v.vec[1];
00171 vec[2] -= v.vec[2];
00172 vec[3] -= v.vec[3];
00173 return *this;
00174 }
00175 unsigned operator==(const UT_Vector4 &v) const
00176 {
00177 return (vec[0] == v.vec[0] && vec[1] == v.vec[1] &&
00178 vec[2] == v.vec[2] && vec[3] == v.vec[3] );
00179
00180 }
00181 unsigned operator!=(const UT_Vector4 &v) const
00182 { return !(*this == v); }
00183 int equalZero(fpreal tol = 0.00001f) const
00184 {
00185 return (vec[0] >= -tol && vec[0] <= tol) &&
00186 (vec[1] >= -tol && vec[1] <= tol) &&
00187 (vec[2] >= -tol && vec[2] <= tol) &&
00188 (vec[3] >= -tol && vec[3] <= tol);
00189 }
00190 int equalZero3(fpreal tol = 0.00001f) const
00191 {
00192 return (vec[0] >= -tol && vec[0] <= tol) &&
00193 (vec[1] >= -tol && vec[1] <= tol) &&
00194 (vec[2] >= -tol && vec[2] <= tol);
00195 }
00196
00197 void clampZero(fpreal tol = 0.00001f)
00198 {
00199 if (vec[0] >= -tol && vec[0] <= tol) vec[0] = 0;
00200 if (vec[1] >= -tol && vec[1] <= tol) vec[1] = 0;
00201 if (vec[2] >= -tol && vec[2] <= tol) vec[2] = 0;
00202 if (vec[3] >= -tol && vec[3] <= tol) vec[3] = 0;
00203 }
00204
00205 void clampZero3(fpreal tol = 0.00001f)
00206 {
00207 if (vec[0] >= -tol && vec[0] <= tol) vec[0] = 0;
00208 if (vec[1] >= -tol && vec[1] <= tol) vec[1] = 0;
00209 if (vec[2] >= -tol && vec[2] <= tol) vec[2] = 0;
00210 }
00211
00212 void negate3()
00213 { vec[0]= -vec[0]; vec[1]= -vec[1]; vec[2]= -vec[2]; }
00214 void negate() { vec[0]= -vec[0]; vec[1]= -vec[1]; vec[2]= -vec[2];
00215 vec[3] = -vec[3]; }
00216
00217 void multiplyComponents(const UT_Vector4 &v)
00218 {
00219 vec[0] *= v.vec[0];
00220 vec[1] *= v.vec[1];
00221 vec[2] *= v.vec[2];
00222 vec[3] *= v.vec[3];
00223 }
00224
00225 int isEqual(const UT_Vector4 &v, fpreal tol = 0.00001f) const
00226 {
00227 return ((vec[0]>=v.vec[0]-tol) && (vec[0]<=v.vec[0]+tol) &&
00228 (vec[1]>=v.vec[1]-tol) && (vec[1]<=v.vec[1]+tol) &&
00229 (vec[2]>=v.vec[2]-tol) && (vec[2]<=v.vec[2]+tol) &&
00230 (vec[3]>=v.vec[3]-tol) && (vec[3]<=v.vec[3]+tol));
00231 }
00232 int isEqual(const UT_Vector3 &vect, fpreal tol = 0.00001f) const;
00233
00234
00235
00236
00237
00238
00239 inline void rowVecMult(const UT_Matrix4 &m)
00240 { operator=(::rowVecMult(*this, m)); }
00241 void rowVecMult(const UT_DMatrix4 &m)
00242 { operator=(::rowVecMult(*this, m)); }
00243 void colVecMult(const UT_Matrix4 &m)
00244 { operator=(::colVecMult(m, *this)); }
00245 void colVecMult(const UT_DMatrix4 &m)
00246 { operator=(::colVecMult(m, *this)); }
00247
00248
00249
00250
00251
00252
00253
00254 void rowVecMult3(const UT_Matrix4 &m)
00255 { operator=(::rowVecMult3(*this, m)); }
00256 void rowVecMult3(const UT_DMatrix4 &m)
00257 { operator=(::rowVecMult3(*this, m)); }
00258
00259
00260
00261
00262
00263
00264
00265 inline
00266 UT_Vector4 &operator*=(const UT_Matrix4 &mat)
00267 { rowVecMult(mat); return *this; }
00268 UT_Vector4 &operator*=(const UT_DMatrix4 &mat)
00269 { rowVecMult(mat); return *this; }
00270
00271 void multiply3(const UT_Matrix4 &mat)
00272 { rowVecMult3(mat); }
00273 void multiply3(const UT_DMatrix4 &mat)
00274 { rowVecMult3(mat); }
00275 void multiply3(UT_Vector4 &dest, const UT_Matrix4 &mat) const
00276 { dest = ::rowVecMult3(*this, mat); }
00277
00278
00279 UT_Vector4 &operator=(fpreal scalar)
00280 {
00281 vec[0] = vec[1] = vec[2] = vec[3] = scalar;
00282 return *this;
00283 }
00284 UT_Vector4 &operator+=(fpreal scalar)
00285 {
00286 vec[0] += scalar; vec[1] += scalar;
00287 vec[2] += scalar; vec[3] += scalar;
00288 return *this;
00289 }
00290 UT_Vector4 &operator-=(fpreal scalar)
00291 {
00292 return operator+=(-scalar);
00293 }
00294 inline
00295 UT_Vector4 &operator*=(fpreal scalar)
00296 {
00297 vec[0] *= scalar; vec[1] *= scalar;
00298 vec[2] *= scalar; vec[3] *= scalar;
00299 return *this;
00300 }
00301 inline
00302 UT_Vector4 &operator*=(const UT_Vector4 &v)
00303 {
00304 vec[0] *= v.vec[0];
00305 vec[1] *= v.vec[1];
00306 vec[2] *= v.vec[2];
00307 vec[3] *= v.vec[3];
00308 return *this;
00309 }
00310 inline
00311 UT_Vector4 &operator/=(fpreal scalar)
00312 {
00313 return operator*=( 1.0f/scalar );
00314 }
00315 inline
00316 UT_Vector4 &operator/=(const UT_Vector4 &v)
00317 {
00318 vec[0] /= v.vec[0];
00319 vec[1] /= v.vec[1];
00320 vec[2] /= v.vec[2];
00321 vec[3] /= v.vec[3];
00322 return *this;
00323 }
00324
00325 fpreal maxComponent() const
00326 {
00327 fpreal m = vec[0];
00328 if (vec[1] > m) m = vec[1];
00329 if (vec[2] > m) m = vec[2];
00330 if (vec[3] > m) m = vec[3];
00331 return m;
00332 }
00333 fpreal minComponent() const
00334 {
00335 fpreal m = vec[0];
00336 if (vec[1] < m) m = vec[1];
00337 if (vec[2] < m) m = vec[2];
00338 if (vec[3] < m) m = vec[3];
00339 return m;
00340 }
00341 fpreal avgComponent() const
00342 {
00343 return (vec[0]+vec[1]+vec[2]+vec[3])*0.25F;
00344 }
00345
00346
00347
00348 int findMinAbsAxis() const
00349 {
00350 if (SYSabs(x()) < SYSabs(y()))
00351 if (SYSabs(z()) < SYSabs(x()))
00352 if (SYSabs(w()) < SYSabs(z()))
00353 return 3;
00354 else
00355 return 2;
00356 else
00357 if (SYSabs(w()) < SYSabs(x()))
00358 return 3;
00359 else
00360 return 0;
00361 else
00362 if (SYSabs(z()) < SYSabs(y()))
00363 if (SYSabs(w()) < SYSabs(z()))
00364 return 3;
00365 else
00366 return 2;
00367 else
00368 if (SYSabs(w()) < SYSabs(y()))
00369 return 3;
00370 else
00371 return 1;
00372 }
00373 int findMaxAbsAxis() const
00374 {
00375 if (SYSabs(x()) >= SYSabs(y()))
00376 if (SYSabs(z()) >= SYSabs(x()))
00377 if (SYSabs(w()) >= SYSabs(z()))
00378 return 3;
00379 else
00380 return 2;
00381 else
00382 if (SYSabs(w()) >= SYSabs(x()))
00383 return 3;
00384 else
00385 return 0;
00386 else
00387 if (SYSabs(z()) >= SYSabs(y()))
00388 if (SYSabs(w()) >= SYSabs(z()))
00389 return 3;
00390 else
00391 return 2;
00392 else
00393 if (SYSabs(w()) >= SYSabs(y()))
00394 return 3;
00395 else
00396 return 1;
00397 }
00398
00399
00400 inline
00401 fpreal dot(const UT_Vector4 &v) const
00402 {
00403 return ::dot(*this, v);
00404 }
00405 void normalize (void)
00406 {
00407 fpreal dn = vec[0]*vec[0] + vec[1]*vec[1] +
00408 vec[2]*vec[2] + vec[3]*vec[3];
00409 if (dn > FLT_MIN)
00410 (*this) *= (((fpreal)1.)/SYSsqrt(dn) );
00411 }
00412
00413
00414 inline
00415 fpreal length(void) const
00416 { return SYSsqrt(dot(*this)); }
00417
00418 inline
00419 fpreal length2(void) const
00420 { return dot(*this); }
00421
00422
00423
00424
00425 const float *data(void) const { return &vec[0]; }
00426 float *data(void) { return &vec[0]; }
00427 inline float&x(void) { return vec[0]; }
00428 inline float x(void) const { return vec[0]; }
00429 inline float&y(void) { return vec[1]; }
00430 inline float y(void) const { return vec[1]; }
00431 inline float&z(void) { return vec[2]; }
00432 inline float z(void) const { return vec[2]; }
00433 inline float&w(void) { return vec[3]; }
00434 inline float w(void) const { return vec[3]; }
00435 inline float&operator()(unsigned i)
00436 {
00437 UT_ASSERT_P(i < 4);
00438 return vec[i];
00439 }
00440 inline float operator()(unsigned i) const
00441 {
00442 UT_ASSERT_P(i < 4);
00443 return vec[i];
00444 }
00445 inline float&operator[](unsigned i)
00446 {
00447 UT_ASSERT_P(i < 4);
00448 return vec[i];
00449 }
00450 inline float operator[](unsigned i) const
00451 {
00452 UT_ASSERT_P(i < 4);
00453 return vec[i];
00454 }
00455 std::vector<float> asStdVector() const;
00456
00457
00458
00459
00460
00461 void assign(fpreal xx = 0.0f, fpreal yy = 0.0f, fpreal zz = 0.0f,
00462 fpreal ww = 1.0f)
00463 {
00464 vec[0] = xx; vec[1] = yy; vec[2] = zz; vec[3] = ww;
00465 }
00466
00467 void assign(const float *v, int size = 4)
00468 {
00469 vec[0] = v[0];
00470 vec[1] = v[1];
00471 vec[2] = v[2];
00472 if (size == 4) vec[3] = v[3];
00473 }
00474
00475
00476
00477 void homogenize(void)
00478 {
00479 vec[0] *= vec[3];
00480 vec[1] *= vec[3];
00481 vec[2] *= vec[3];
00482 }
00483 void dehomogenize(void)
00484 {
00485 fpreal denom = 1.0f / vec[3];
00486 vec[0] *= denom;
00487 vec[1] *= denom;
00488 vec[2] *= denom;
00489 }
00490
00491
00492 void save(ostream &os, int binary=0) const;
00493 bool load(UT_IStream &is);
00494
00495 private:
00496
00497
00498 friend ostream &operator<<(ostream &os, const UT_Vector4 &v)
00499 {
00500 v.save(os);
00501 return os;
00502 }
00503
00504
00505
00506 float vec[4];
00507 };
00508
00509 #include "UT_Vector3.h"
00510
00511 inline UT_Vector4::UT_Vector4(const UT_Vector3 &v, float vw)
00512 {
00513 vec[0] = v.x();
00514 vec[1] = v.y();
00515 vec[2] = v.z();
00516 vec[3] = vw;
00517 }
00518
00519 inline int
00520 UT_Vector4::isEqual(const UT_Vector3 &vect, fpreal tol) const
00521 {
00522 return ((vec[0]>=vect.x()-tol) && (vec[0]<=vect.x()+tol) &&
00523 (vec[1]>=vect.y()-tol) && (vec[1]<=vect.y()+tol) &&
00524 (vec[2]>=vect.z()-tol) && (vec[2]<=vect.z()+tol));
00525 }
00526
00527
00528 inline UT_Vector4 operator+(const UT_Vector4 &v1, const UT_Vector4 &v2)
00529 {
00530 return UT_Vector4(v1.x()+v2.x(), v1.y()+v2.y(),
00531 v1.z()+v2.z(), v1.w()+v2.w());
00532 }
00533 inline UT_Vector4 operator-(const UT_Vector4 &v1, const UT_Vector4 &v2)
00534 {
00535 return UT_Vector4(v1.x()-v2.x(), v1.y()-v2.y(),
00536 v1.z()-v2.z(), v1.w()-v2.w());
00537 }
00538 inline UT_Vector4 operator*(const UT_Vector4 &v1, const UT_Vector4 &v2)
00539 {
00540 return UT_Vector4(v1.x()*v2.x(), v1.y()*v2.y(), v1.z()*v2.z(), v1.w()*v2.w());
00541 }
00542
00543 inline UT_Vector4 operator/(const UT_Vector4 &v1, const UT_Vector4 &v2)
00544 {
00545 return UT_Vector4(v1.x()/v2.x(), v1.y()/v2.y(), v1.z()/v2.z(), v1.w()/v2.w());
00546 }
00547
00548 inline UT_Vector4 operator+(const UT_Vector4 &v, fpreal scalar)
00549 {
00550 return UT_Vector4(v.x()+scalar, v.y()+scalar, v.z()+scalar, v.w()+scalar);
00551 }
00552 inline UT_Vector4 operator+(fpreal scalar, const UT_Vector4 &v)
00553 {
00554 return UT_Vector4(v.x()+scalar, v.y()+scalar, v.z()+scalar, v.w()+scalar);
00555 }
00556 inline UT_Vector4 operator-(const UT_Vector4 &v, fpreal scalar)
00557 {
00558 return UT_Vector4(v.x()-scalar, v.y()-scalar, v.z()-scalar, v.w()-scalar);
00559 }
00560 inline UT_Vector4 operator-(fpreal scalar, const UT_Vector4 &v)
00561 {
00562 return UT_Vector4(scalar-v.x(), scalar-v.y(), scalar-v.z(), v.w()-scalar);
00563 }
00564 inline UT_Vector4 operator*(const UT_Vector4 &v, fpreal scalar)
00565 {
00566 return UT_Vector4(v.x()*scalar, v.y()*scalar, v.z()*scalar, v.w()*scalar);
00567 }
00568 inline UT_Vector4 operator*(fpreal scalar, const UT_Vector4 &v)
00569 {
00570 return UT_Vector4(v.x()*scalar, v.y()*scalar, v.z()*scalar, v.w()*scalar);
00571 }
00572 inline UT_Vector4 operator/(const UT_Vector4 &v, fpreal scalar)
00573 {
00574 return UT_Vector4(v.x()/scalar, v.y()/scalar, v.z()/scalar, v.w()/scalar);
00575 }
00576 inline UT_Vector4 operator/(fpreal scalar, const UT_Vector4 &v)
00577 {
00578 return UT_Vector4(scalar/v.x(), scalar/v.y(), scalar/v.z(), scalar/v.w());
00579 }
00580 inline fpreal dot(const UT_Vector4 &v1, const UT_Vector4 &v2)
00581 {
00582 return v1.x()*v2.x() + v1.y()*v2.y() + v1.z()*v2.z() + v1.w()*v2.w();
00583 }
00584 inline fpreal dot(const UT_Vector4 &v1, const UT_Vector3 &v2)
00585 {
00586 return v1.x()*v2.x() + v1.y()*v2.y() + v1.z()*v2.z();
00587 }
00588 inline fpreal dot(const UT_Vector3 &v1, const UT_Vector4 &v2)
00589 {
00590 return v1.x()*v2.x() + v1.y()*v2.y() + v1.z()*v2.z();
00591 }
00592
00593 inline UT_Vector4 operator*(const UT_Vector4 &v, const UT_Matrix4 &m)
00594 {
00595 return rowVecMult(v, m);
00596 }
00597 inline UT_Vector4 operator*(const UT_Vector4 &v, const UT_DMatrix4 &m)
00598 {
00599 return rowVecMult(v, m);
00600 }
00601 inline fpreal distance(const UT_Vector4 &v1, const UT_Vector4 &v2)
00602 {
00603 fpreal x = v1.x()-v2.x();
00604 fpreal y = v1.y()-v2.y();
00605 fpreal z = v1.z()-v2.z();
00606 fpreal w = v1.w()-v2.w();
00607 return SYSsqrt(x*x + y*y + z*z + w*w);
00608 }
00609 inline fpreal distance3(const UT_Vector4 &v1, const UT_Vector4 &v2)
00610 {
00611 fpreal x = v1.x()-v2.x();
00612 fpreal y = v1.y()-v2.y();
00613 fpreal z = v1.z()-v2.z();
00614 return SYSsqrt(x*x + y*y + z*z);
00615 }
00616
00617 #endif