mPoint3.h

Engine/source/math/mPoint3.h

More...

Classes:

class
class
class

3D integer point

Public Typedefs

EulerF 
VectorF 

Public Functions

bool

Returns true if the point is NaN.

Returns the vector normalized.

mPerp(const Point3F & normal)

Returns a perpendicular vector to the unit length input vector.

Returns a copy of the vector reflected by a normal.

operator*(F32 mul, const Point3F & multiplicand)
operator*(F64 mul, const Point3D & multiplicand)
operator*(S32 mul, const Point3I & multiplicand)

Detailed Description

Public Typedefs

typedef Point3F EulerF 
typedef Point3F VectorF 

Public Functions

mCross(const Point3D & a, const Point3D & b)

mCross(const Point3D & a, const Point3D & b, Point3D * res)

mCross(const Point3F & a, const Point3F & b)

mCross(const Point3F & a, const Point3F & b, Point3F * res)

mDot(const Point3D & p1, const Point3D & p2)

mDot(const Point3F & p1, const Point3F & p2)

mIsNaN(const Point3F & p)

Returns true if the point is NaN.

mNormalize(const Point3F & vec)

Returns the vector normalized.

mPerp(const Point3F & normal)

Returns a perpendicular vector to the unit length input vector.

mReflect(const Point3F & v, const Point3F & n)

Returns a copy of the vector reflected by a normal.

operator*(F32 mul, const Point3F & multiplicand)

operator*(F64 mul, const Point3D & multiplicand)

operator*(S32 mul, const Point3I & multiplicand)

   1
   2//-----------------------------------------------------------------------------
   3// Copyright (c) 2012 GarageGames, LLC
   4//
   5// Permission is hereby granted, free of charge, to any person obtaining a copy
   6// of this software and associated documentation files (the "Software"), to
   7// deal in the Software without restriction, including without limitation the
   8// rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
   9// sell copies of the Software, and to permit persons to whom the Software is
  10// furnished to do so, subject to the following conditions:
  11//
  12// The above copyright notice and this permission notice shall be included in
  13// all copies or substantial portions of the Software.
  14//
  15// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  16// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  17// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  18// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  19// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
  20// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
  21// IN THE SOFTWARE.
  22//-----------------------------------------------------------------------------
  23
  24#ifndef _MPOINT3_H_
  25#define _MPOINT3_H_
  26
  27#ifndef _MMATHFN_H_
  28#include "math/mMathFn.h"
  29#endif
  30#ifndef _MPOINT2_H_
  31#include "math/mPoint2.h"
  32#endif
  33
  34//------------------------------------------------------------------------------
  35/// 3D integer point
  36///
  37/// Uses S32 internally.
  38class Point3I
  39{
  40   //-------------------------------------- Public data
  41  public:
  42   S32 x;                                                   ///< X co-ordinate
  43   S32 y;                                                   ///< Y co-ordinate
  44   S32 z;                                                   ///< Z co-ordinate
  45
  46   //-------------------------------------- Public interface
  47  public:
  48   Point3I();               ///< Create an uninitialized point.
  49   Point3I(const Point3I&); ///< Copy constructor.
  50   explicit Point3I(S32 xyz);        ///< Initializes all elements to the same value.
  51   Point3I(S32 in_x, S32 in_y, S32 in_z); ///< Create a point from co-ordinates.
  52
  53   //-------------------------------------- Non-math mutators and misc functions
  54   void set(S32 xyz);           ///< Initializes all elements to the same value.
  55   void set(S32 in_x, S32 in_y, S32 in_z); ///< Set co-ordinates.
  56   void setMin(const Point3I&); ///< Store lesser co-ordinates in this point.
  57   void setMax(const Point3I&); ///< Store greater co-ordinates in this point.
  58   void zero();                 ///< Zero all values
  59
  60   //-------------------------------------- Math mutators
  61   void neg();                      ///< Invert co-ordinate's signs.
  62   void convolve(const Point3I&);   ///< Convolve by parameter.
  63
  64   //-------------------------------------- Queries
  65   bool isZero() const;             ///< Check for point at origin. (No epsilon.)
  66   F32  len() const;                ///< Get length.
  67
  68   //-------------------------------------- Overloaded operators
  69  public:
  70   operator S32*() { return &x; }
  71   operator const S32*() const { return &x; }
  72
  73   // Comparison operators
  74   bool operator==(const Point3I&) const;
  75   bool operator!=(const Point3I&) const;
  76
  77   // Arithmetic w/ other points
  78   Point3I  operator+(const Point3I&) const;
  79   Point3I  operator-(const Point3I&) const;
  80   Point3I& operator+=(const Point3I&);
  81   Point3I& operator-=(const Point3I&);
  82
  83   // Arithmetic w/ scalars
  84   Point3I  operator*(S32) const;
  85   Point3I& operator*=(S32);
  86   Point3I  operator/(S32) const;
  87   Point3I& operator/=(S32);
  88
  89   // Unary operators
  90   Point3I operator-() const;
  91
  92   //-------------------------------------- Public static constants
  93public:
  94   const static Point3I One;
  95   const static Point3I Zero;
  96};
  97
  98class Point3D;
  99
 100//------------------------------------------------------------------------------
 101class Point3F
 102{
 103   //-------------------------------------- Public data
 104  public:
 105   F32 x;
 106   F32 y;
 107   F32 z;
 108
 109  public:
 110   Point3F();
 111   Point3F(const Point3F&);
 112   Point3F(F32 _x, F32 _y, F32 _z);
 113   explicit Point3F(F32 xyz);
 114
 115   //-------------------------------------- Non-math mutators and misc functions
 116  public:
 117   void set(F32 xyz);
 118   void set(F32 _x, F32 _y, F32 _z);
 119   void set(const Point3F&);
 120
 121   void setMin(const Point3F&);
 122   void setMax(const Point3F&);
 123
 124   void interpolate(const Point3F&, const Point3F&, F32);
 125   void zero();
 126
 127   /// Returns the smallest absolute value.
 128   F32 least() const;
 129
 130   /// Returns the greatest absolute value.
 131   F32 most() const;
 132
 133   operator F32*() { return &x; }
 134   operator const F32*() const { return &x; }
 135
 136   /// Returns the x and y coords as a Point2F.
 137   Point2F asPoint2F() const { return Point2F( x, y ); }
 138
 139   //-------------------------------------- Queries
 140  public:
 141   bool  isZero() const;
 142   bool  isUnitLength() const;
 143   F32   len()    const;
 144   F32   lenSquared() const;
 145   F32   magnitudeSafe() const;
 146   bool  equal( const Point3F &compare, F32 epsilon = POINT_EPSILON ) const;
 147   U32   getLeastComponentIndex() const;
 148   U32   getGreatestComponentIndex() const;
 149
 150   //-------------------------------------- Mathematical mutators
 151  public:
 152   void neg();
 153   void normalize();
 154   void normalizeSafe();
 155   void normalize(F32 val);
 156   void convolve(const Point3F&);
 157   void convolveInverse(const Point3F&);
 158
 159   //-------------------------------------- Overloaded operators
 160  public:
 161   // Comparison operators
 162   bool operator==(const Point3F&) const;
 163   bool operator!=(const Point3F&) const;
 164
 165   // Arithmetic w/ other points
 166   Point3F  operator+(const Point3F&) const;
 167   Point3F  operator-(const Point3F&) const;
 168   Point3F& operator+=(const Point3F&);
 169   Point3F& operator-=(const Point3F&);
 170
 171   // Arithmetic w/ scalars
 172   Point3F  operator*(F32) const;
 173   Point3F  operator/(F32) const;
 174   Point3F& operator*=(F32);
 175   Point3F& operator/=(F32);
 176
 177   Point3F  operator*(const Point3F&) const;
 178   Point3F& operator*=(const Point3F&);
 179   Point3F  operator/(const Point3F&) const;
 180   Point3F& operator/=(const Point3F&);
 181
 182   // Unary operators
 183   Point3F operator-() const;
 184
 185   Point3F& operator=(const Point3D&);
 186
 187   //-------------------------------------- Public static constants
 188public:
 189   const static Point3F One;
 190   const static Point3F Zero;
 191   const static Point3F Max;
 192   const static Point3F Min;
 193   const static Point3F UnitX;
 194   const static Point3F UnitY;
 195   const static Point3F UnitZ;
 196};
 197
 198typedef Point3F VectorF;
 199typedef Point3F EulerF;
 200
 201
 202//------------------------------------------------------------------------------
 203class Point3D
 204{
 205   //-------------------------------------- Public data
 206  public:
 207   F64 x;
 208   F64 y;
 209   F64 z;
 210
 211  public:
 212   Point3D();
 213   Point3D(const Point3D&);
 214   Point3D(const Point3F&);
 215   explicit Point3D(F64 xyz);
 216   Point3D(F64 _x, F64 _y, F64 _z);
 217
 218   //-------------------------------------- Non-math mutators and misc functions
 219  public:
 220   void set(F64 xyz);
 221   void set(F64 _x, F64 _y, F64 _z);
 222
 223   void setMin(const Point3D&);
 224   void setMax(const Point3D&);
 225
 226   void interpolate(const Point3D&, const Point3D&, F64);
 227   void zero();
 228
 229   operator F64*() { return (&x); }
 230   operator const F64*() const { return &x; }
 231
 232   //-------------------------------------- Queries
 233  public:
 234   bool  isZero() const;
 235   F64 len()    const;
 236   F64 lenSquared() const;
 237   F64 magnitudeSafe() const;
 238
 239   //-------------------------------------- Mathematical mutators
 240  public:
 241   void neg();
 242   void normalize();
 243   void normalizeSafe();
 244   void normalize(F64 val);
 245   void convolve(const Point3D&);
 246   void convolveInverse(const Point3D&);
 247
 248   //-------------------------------------- Overloaded operators
 249  public:
 250   Point3F toPoint3F() const;
 251   // Comparison operators
 252   bool operator==(const Point3D&) const;
 253   bool operator!=(const Point3D&) const;
 254
 255   // Arithmetic w/ other points
 256   Point3D  operator+(const Point3D&) const;
 257   Point3D  operator-(const Point3D&) const;
 258   Point3D& operator+=(const Point3D&);
 259   Point3D& operator-=(const Point3D&);
 260
 261   // Arithmetic w/ scalars
 262   Point3D  operator*(F64) const;
 263   Point3D  operator/(F64) const;
 264   Point3D& operator*=(F64);
 265   Point3D& operator/=(F64);
 266
 267   // Unary operators
 268   Point3D operator-() const;
 269
 270   //-------------------------------------- Public static constants
 271public:
 272   const static Point3D One;
 273   const static Point3D Zero;
 274};
 275
 276//------------------------------------------------------------------------------
 277//-------------------------------------- Point3I
 278//
 279inline Point3I::Point3I()
 280{
 281   //
 282}
 283
 284inline Point3I::Point3I(const Point3I& _copy)
 285 : x(_copy.x), y(_copy.y), z(_copy.z)
 286{
 287   //
 288}
 289
 290inline Point3I::Point3I(S32 xyz)
 291 : x(xyz), y(xyz), z(xyz)
 292{
 293   //
 294}
 295
 296inline Point3I::Point3I(S32 _x, S32 _y, S32 _z)
 297 : x(_x), y(_y), z(_z)
 298{
 299   //
 300}
 301
 302inline void Point3I::set(S32 xyz)
 303{
 304   x = y = z = xyz;
 305}
 306
 307inline void Point3I::set(S32 _x, S32 _y, S32 _z)
 308{
 309   x = _x;
 310   y = _y;
 311   z = _z;
 312}
 313
 314inline void Point3I::setMin(const Point3I& _test)
 315{
 316   x = (_test.x < x) ? _test.x : x;
 317   y = (_test.y < y) ? _test.y : y;
 318   z = (_test.z < z) ? _test.z : z;
 319}
 320
 321inline void Point3I::setMax(const Point3I& _test)
 322{
 323   x = (_test.x > x) ? _test.x : x;
 324   y = (_test.y > y) ? _test.y : y;
 325   z = (_test.z > z) ? _test.z : z;
 326}
 327
 328inline void Point3I::zero()
 329{
 330   x = y = z = 0;
 331}
 332
 333inline void Point3I::neg()
 334{
 335   x = -x;
 336   y = -y;
 337   z = -z;
 338}
 339
 340inline F32 Point3I::len() const
 341{
 342   return mSqrt(F32(x*x + y*y + z*z));
 343}
 344
 345inline void Point3I::convolve(const Point3I& c)
 346{
 347   x *= c.x;
 348   y *= c.y;
 349   z *= c.z;
 350}
 351
 352inline bool Point3I::isZero() const
 353{
 354   return ((x == 0) && (y == 0) && (z == 0));
 355}
 356
 357inline bool Point3I::operator==(const Point3I& _test) const
 358{
 359   return ((x == _test.x) && (y == _test.y) && (z == _test.z));
 360}
 361
 362inline bool Point3I::operator!=(const Point3I& _test) const
 363{
 364   return (operator==(_test) == false);
 365}
 366
 367inline Point3I Point3I::operator+(const Point3I& _add) const
 368{
 369   return Point3I(x + _add.x, y + _add.y, z + _add.z);
 370}
 371
 372inline Point3I Point3I::operator-(const Point3I& _rSub) const
 373{
 374   return Point3I(x - _rSub.x, y - _rSub.y, z - _rSub.z);
 375}
 376
 377inline Point3I& Point3I::operator+=(const Point3I& _add)
 378{
 379   x += _add.x;
 380   y += _add.y;
 381   z += _add.z;
 382
 383   return *this;
 384}
 385
 386inline Point3I& Point3I::operator-=(const Point3I& _rSub)
 387{
 388   x -= _rSub.x;
 389   y -= _rSub.y;
 390   z -= _rSub.z;
 391
 392   return *this;
 393}
 394
 395inline Point3I Point3I::operator-() const
 396{
 397   return Point3I(-x, -y, -z);
 398}
 399
 400inline Point3I Point3I::operator*(S32 mul) const
 401{
 402   return Point3I(x * mul, y * mul, z * mul);
 403}
 404
 405inline Point3I Point3I::operator/(S32 div) const
 406{
 407   AssertFatal(div != 0, "Error, div by zero attempted");
 408   return Point3I(x/div, y/div, z/div);
 409}
 410
 411inline Point3I& Point3I::operator*=(S32 mul)
 412{
 413   x *= mul;
 414   y *= mul;
 415   z *= mul;
 416
 417   return *this;
 418}
 419
 420inline Point3I& Point3I::operator/=(S32 div)
 421{
 422   AssertFatal(div != 0, "Error, div by zero attempted");
 423
 424   x /= div;
 425   y /= div;
 426   z /= div;
 427
 428   return *this;
 429}
 430
 431//------------------------------------------------------------------------------
 432//-------------------------------------- Point3F
 433//
 434inline Point3F::Point3F()
 435#if defined(TORQUE_OS_LINUX)
 436 : x(0.f), y(0.f), z(0.f)
 437#endif
 438{
 439// Uninitialized points are definitely a problem.
 440// Enable the following code to see how often they crop up.
 441#ifdef DEBUG_MATH
 442   *(U32 *)&x = 0x7FFFFFFA;
 443   *(U32 *)&y = 0x7FFFFFFB;
 444   *(U32 *)&z = 0x7FFFFFFC;
 445#endif
 446}
 447
 448
 449inline Point3F::Point3F(const Point3F& _copy)
 450 : x(_copy.x), y(_copy.y), z(_copy.z)
 451{
 452   //
 453}
 454
 455inline Point3F::Point3F(F32 _x, F32 _y, F32 _z)
 456 : x(_x), y(_y), z(_z)
 457{
 458   //
 459}
 460
 461inline Point3F::Point3F(F32 xyz)
 462 : x(xyz), y(xyz), z(xyz)
 463{
 464   //
 465}
 466
 467inline void Point3F::set(F32 xyz)
 468{
 469   x = y = z = xyz;
 470}
 471
 472inline void Point3F::set(F32 _x, F32 _y, F32 _z)
 473{
 474   x = _x;
 475   y = _y;
 476   z = _z;
 477}
 478
 479inline void Point3F::set(const Point3F& copy)
 480{
 481   x = copy.x;
 482   y = copy.y;
 483   z = copy.z;
 484}
 485
 486inline void Point3F::setMin(const Point3F& _test)
 487{
 488   x = (_test.x < x) ? _test.x : x;
 489   y = (_test.y < y) ? _test.y : y;
 490   z = (_test.z < z) ? _test.z : z;
 491}
 492
 493inline void Point3F::setMax(const Point3F& _test)
 494{
 495   x = (_test.x > x) ? _test.x : x;
 496   y = (_test.y > y) ? _test.y : y;
 497   z = (_test.z > z) ? _test.z : z;
 498}
 499
 500inline void Point3F::interpolate(const Point3F& _from, const Point3F& _to, F32 _factor)
 501{
 502   AssertFatal(_factor >= 0.0f && _factor <= 1.0f, "Out of bound interpolation factor");
 503   m_point3F_interpolate( _from, _to, _factor, *this);
 504}
 505
 506inline void Point3F::zero()
 507{
 508   x = y = z = 0.0f;
 509}
 510
 511inline bool Point3F::isZero() const
 512{
 513   return ((x*x) <= POINT_EPSILON) && ((y*y) <= POINT_EPSILON) && ((z*z) <= POINT_EPSILON );
 514}
 515
 516inline bool Point3F::isUnitLength() const
 517{
 518   return ( mFabs( 1.0f - ( x*x + y*y + z*z ) ) < POINT_EPSILON );
 519}
 520
 521inline bool Point3F::equal( const Point3F &compare, F32 epsilon ) const
 522{
 523   return( ( mFabs( x - compare.x ) < epsilon ) &&
 524           ( mFabs( y - compare.y ) < epsilon ) &&
 525           ( mFabs( z - compare.z ) < epsilon ) );
 526}
 527
 528inline U32 Point3F::getLeastComponentIndex() const
 529{
 530   U32 idx;
 531
 532   if ( mFabs( x ) < mFabs( y ) )
 533   {
 534      if ( mFabs( x ) < mFabs( z ) )
 535         idx = 0;
 536      else
 537         idx = 2;
 538   }
 539   else
 540   {
 541      if ( mFabs( y ) < mFabs( z ) )
 542         idx = 1;  
 543      else
 544         idx = 2;
 545   }
 546
 547   return idx;
 548}
 549
 550inline U32 Point3F::getGreatestComponentIndex() const
 551{
 552   U32 idx;
 553
 554   if ( mFabs( x ) > mFabs( y ) )
 555   {
 556      if ( mFabs( x ) > mFabs( z ) )
 557         idx = 0;
 558      else
 559         idx = 2;
 560   }
 561   else
 562   {
 563      if ( mFabs( y ) > mFabs( z ) )
 564         idx = 1;  
 565      else
 566         idx = 2;
 567   }
 568
 569   return idx;
 570}
 571
 572inline F32 Point3F::least() const
 573{
 574   return getMin( mFabs( x ), getMin( mFabs( y ), mFabs( z ) ) );
 575}
 576
 577inline F32 Point3F::most() const
 578{
 579   return getMax( mFabs( x ), getMax( mFabs( y ), mFabs( z ) ) );
 580}
 581
 582inline void Point3F::neg()
 583{
 584   x = -x;
 585   y = -y;
 586   z = -z;
 587}
 588
 589inline void Point3F::convolve(const Point3F& c)
 590{
 591   x *= c.x;
 592   y *= c.y;
 593   z *= c.z;
 594}
 595
 596inline void Point3F::convolveInverse(const Point3F& c)
 597{
 598   x /= c.x;
 599   y /= c.y;
 600   z /= c.z;
 601}
 602
 603inline F32 Point3F::lenSquared() const
 604{
 605   return (x * x) + (y * y) + (z * z);
 606}
 607
 608inline F32 Point3F::len() const
 609{
 610   return mSqrt(x*x + y*y + z*z);
 611}
 612
 613inline void Point3F::normalize()
 614{
 615   m_point3F_normalize(*this);
 616}
 617
 618inline F32 Point3F::magnitudeSafe() const
 619{
 620   if( isZero() )
 621   {
 622      return 0.0f;
 623   }
 624   else
 625   {
 626      return len();
 627   }
 628}
 629
 630inline void Point3F::normalizeSafe()
 631{
 632   F32 vmag = magnitudeSafe();
 633
 634   if( vmag > POINT_EPSILON )
 635   {
 636      *this *= F32(1.0 / vmag);
 637   }
 638}
 639
 640
 641inline void Point3F::normalize(F32 val)
 642{
 643   m_point3F_normalize_f(*this, val);
 644}
 645
 646inline bool Point3F::operator==(const Point3F& _test) const
 647{
 648   return (x == _test.x) && (y == _test.y) && (z == _test.z);
 649}
 650
 651inline bool Point3F::operator!=(const Point3F& _test) const
 652{
 653   return operator==(_test) == false;
 654}
 655
 656inline Point3F Point3F::operator+(const Point3F& _add) const
 657{
 658   return Point3F(x + _add.x, y + _add.y,  z + _add.z);
 659}
 660
 661inline Point3F Point3F::operator-(const Point3F& _rSub) const
 662{
 663   return Point3F(x - _rSub.x, y - _rSub.y, z - _rSub.z);
 664}
 665
 666inline Point3F& Point3F::operator+=(const Point3F& _add)
 667{
 668   x += _add.x;
 669   y += _add.y;
 670   z += _add.z;
 671
 672   return *this;
 673}
 674
 675inline Point3F& Point3F::operator-=(const Point3F& _rSub)
 676{
 677   x -= _rSub.x;
 678   y -= _rSub.y;
 679   z -= _rSub.z;
 680
 681   return *this;
 682}
 683
 684inline Point3F Point3F::operator*(F32 _mul) const
 685{
 686   return Point3F(x * _mul, y * _mul, z * _mul);
 687}
 688
 689inline Point3F Point3F::operator/(F32 _div) const
 690{
 691   AssertFatal(_div != 0.0f, "Error, div by zero attempted");
 692
 693   F32 inv = 1.0f / _div;
 694
 695   return Point3F(x * inv, y * inv, z * inv);
 696}
 697
 698inline Point3F& Point3F::operator*=(F32 _mul)
 699{
 700   x *= _mul;
 701   y *= _mul;
 702   z *= _mul;
 703
 704   return *this;
 705}
 706
 707inline Point3F& Point3F::operator/=(F32 _div)
 708{
 709   AssertFatal(_div != 0.0f, "Error, div by zero attempted");
 710
 711   F32 inv = 1.0f / _div;
 712   x *= inv;
 713   y *= inv;
 714   z *= inv;
 715
 716   return *this;
 717}
 718
 719inline Point3F Point3F::operator*(const Point3F &_vec) const
 720{
 721   return Point3F(x * _vec.x, y * _vec.y, z * _vec.z);
 722}
 723
 724inline Point3F& Point3F::operator*=(const Point3F &_vec)
 725{
 726   x *= _vec.x;
 727   y *= _vec.y;
 728   z *= _vec.z;
 729   return *this;
 730}
 731
 732inline Point3F Point3F::operator/(const Point3F &_vec) const
 733{
 734   AssertFatal(_vec.x != 0.0f && _vec.y != 0.0f && _vec.z != 0.0f, "Error, div by zero attempted");
 735   return Point3F(x / _vec.x, y / _vec.y, z / _vec.z);
 736}
 737
 738inline Point3F& Point3F::operator/=(const Point3F &_vec)
 739{
 740   AssertFatal(_vec.x != 0.0f && _vec.y != 0.0f && _vec.z != 0.0f, "Error, div by zero attempted");
 741   x /= _vec.x;
 742   y /= _vec.y;
 743   z /= _vec.z;
 744   return *this;
 745}
 746
 747inline Point3F Point3F::operator-() const
 748{
 749   return Point3F(-x, -y, -z);
 750}
 751
 752
 753inline Point3F& Point3F::operator=(const Point3D &_vec)
 754{
 755   x = (F32)_vec.x;
 756   y = (F32)_vec.y;
 757   z = (F32)_vec.z;
 758   return *this;
 759}
 760
 761//------------------------------------------------------------------------------
 762//-------------------------------------- Point3D
 763//
 764inline Point3D::Point3D()
 765{
 766   //
 767}
 768
 769inline Point3D::Point3D(const Point3D& _copy)
 770 : x(_copy.x), y(_copy.y), z(_copy.z)
 771{
 772   //
 773}
 774
 775inline Point3D::Point3D(const Point3F& _copy)
 776 : x(_copy.x), y(_copy.y), z(_copy.z)
 777{
 778   //
 779}
 780
 781inline Point3D::Point3D(F64 xyz)
 782 : x(xyz), y(xyz), z(xyz)
 783{
 784   //
 785}
 786
 787inline Point3D::Point3D(F64 _x, F64 _y, F64 _z)
 788 : x(_x), y(_y), z(_z)
 789{
 790   //
 791}
 792
 793inline void Point3D::set( F64 xyz )
 794{
 795   x = y = z = xyz;
 796}
 797
 798inline void Point3D::set(F64 _x, F64 _y, F64 _z)
 799{
 800   x = _x;
 801   y = _y;
 802   z = _z;
 803}
 804
 805inline void Point3D::setMin(const Point3D& _test)
 806{
 807   x = (_test.x < x) ? _test.x : x;
 808   y = (_test.y < y) ? _test.y : y;
 809   z = (_test.z < z) ? _test.z : z;
 810}
 811
 812inline void Point3D::setMax(const Point3D& _test)
 813{
 814   x = (_test.x > x) ? _test.x : x;
 815   y = (_test.y > y) ? _test.y : y;
 816   z = (_test.z > z) ? _test.z : z;
 817}
 818
 819inline void Point3D::interpolate(const Point3D& _from, const Point3D& _to, F64 _factor)
 820{
 821   AssertFatal(_factor >= 0.0f && _factor <= 1.0f, "Out of bound interpolation factor");
 822   m_point3D_interpolate( _from, _to, _factor, *this);
 823}
 824
 825inline void Point3D::zero()
 826{
 827   x = y = z = 0.0;
 828}
 829
 830inline bool Point3D::isZero() const
 831{
 832   return (x == 0.0f) && (y == 0.0f) && (z == 0.0f);
 833}
 834
 835inline void Point3D::neg()
 836{
 837   x = -x;
 838   y = -y;
 839   z = -z;
 840}
 841
 842inline void Point3D::convolve(const Point3D& c)
 843{
 844   x *= c.x;
 845   y *= c.y;
 846   z *= c.z;
 847}
 848
 849inline void Point3D::convolveInverse(const Point3D& c)
 850{
 851   x /= c.x;
 852   y /= c.y;
 853   z /= c.z;
 854}
 855
 856inline F64 Point3D::lenSquared() const
 857{
 858   return (x * x) + (y * y) + (z * z);
 859}
 860
 861inline F64 Point3D::len() const
 862{
 863   F64 temp = x*x + y*y + z*z;
 864   return (temp > 0.0) ? mSqrtD(temp) : 0.0;
 865}
 866
 867inline void Point3D::normalize()
 868{
 869   m_point3D_normalize(*this);
 870}
 871
 872inline F64 Point3D::magnitudeSafe() const
 873{
 874   if( isZero() )
 875   {
 876      return 0.0;
 877   }
 878   else
 879   {
 880      return len();
 881   }
 882}
 883
 884inline void Point3D::normalizeSafe()
 885{
 886   F64 vmag = magnitudeSafe();
 887
 888   if( vmag > POINT_EPSILON )
 889   {
 890      *this *= F64(1.0 / vmag);
 891   }
 892}
 893
 894inline void Point3D::normalize(F64 val)
 895{
 896   m_point3D_normalize_f(*this, val);
 897}
 898
 899inline bool Point3D::operator==(const Point3D& _test) const
 900{
 901   return (x == _test.x) && (y == _test.y) && (z == _test.z);
 902}
 903
 904inline bool Point3D::operator!=(const Point3D& _test) const
 905{
 906   return operator==(_test) == false;
 907}
 908
 909inline Point3D Point3D::operator+(const Point3D& _add) const
 910{
 911   return Point3D(x + _add.x, y + _add.y,  z + _add.z);
 912}
 913
 914
 915inline Point3D Point3D::operator-(const Point3D& _rSub) const
 916{
 917   return Point3D(x - _rSub.x, y - _rSub.y, z - _rSub.z);
 918}
 919
 920inline Point3D& Point3D::operator+=(const Point3D& _add)
 921{
 922   x += _add.x;
 923   y += _add.y;
 924   z += _add.z;
 925
 926   return *this;
 927}
 928
 929inline Point3D& Point3D::operator-=(const Point3D& _rSub)
 930{
 931   x -= _rSub.x;
 932   y -= _rSub.y;
 933   z -= _rSub.z;
 934
 935   return *this;
 936}
 937
 938inline Point3D Point3D::operator*(F64 _mul) const
 939{
 940   return Point3D(x * _mul, y * _mul, z * _mul);
 941}
 942
 943inline Point3D Point3D::operator/(F64 _div) const
 944{
 945   AssertFatal(_div != 0.0f, "Error, div by zero attempted");
 946
 947   F64 inv = 1.0f / _div;
 948
 949   return Point3D(x * inv, y * inv, z * inv);
 950}
 951
 952inline Point3D& Point3D::operator*=(F64 _mul)
 953{
 954   x *= _mul;
 955   y *= _mul;
 956   z *= _mul;
 957
 958   return *this;
 959}
 960
 961inline Point3D& Point3D::operator/=(F64 _div)
 962{
 963   AssertFatal(_div != 0.0f, "Error, div by zero attempted");
 964
 965   F64 inv = 1.0f / _div;
 966   x *= inv;
 967   y *= inv;
 968   z *= inv;
 969
 970   return *this;
 971}
 972
 973inline Point3D Point3D::operator-() const
 974{
 975   return Point3D(-x, -y, -z);
 976}
 977
 978inline Point3F Point3D::toPoint3F() const
 979{
 980   return Point3F((F32)x,(F32)y,(F32)z);
 981}
 982
 983//-------------------------------------------------------------------
 984// Non-Member Operators
 985//-------------------------------------------------------------------
 986
 987inline Point3I operator*(S32 mul, const Point3I& multiplicand)
 988{
 989   return multiplicand * mul;
 990}
 991
 992inline Point3F operator*(F32 mul, const Point3F& multiplicand)
 993{
 994   return multiplicand * mul;
 995}
 996
 997inline Point3D operator*(F64 mul, const Point3D& multiplicand)
 998{
 999   return multiplicand * mul;
1000}
1001
1002inline F32 mDot(const Point3F &p1, const Point3F &p2)
1003{
1004   return (p1.x*p2.x + p1.y*p2.y + p1.z*p2.z);
1005}
1006
1007inline F64 mDot(const Point3D &p1, const Point3D &p2)
1008{
1009   return (p1.x*p2.x + p1.y*p2.y + p1.z*p2.z);
1010}
1011
1012inline void mCross(const Point3F &a, const Point3F &b, Point3F *res)
1013{
1014   res->x = (a.y * b.z) - (a.z * b.y);
1015   res->y = (a.z * b.x) - (a.x * b.z);
1016   res->z = (a.x * b.y) - (a.y * b.x);
1017}
1018
1019inline void mCross(const Point3D &a, const Point3D &b, Point3D *res)
1020{
1021   res->x = (a.y * b.z) - (a.z * b.y);
1022   res->y = (a.z * b.x) - (a.x * b.z);
1023   res->z = (a.x * b.y) - (a.y * b.x);
1024}
1025
1026inline Point3F mCross(const Point3F &a, const Point3F &b)
1027{
1028   Point3F r;
1029   mCross( a, b, &r );
1030   return r;
1031}
1032
1033inline Point3D mCross(const Point3D &a, const Point3D &b)
1034{
1035   Point3D r;
1036   mCross( a, b, &r );
1037   return r;
1038}
1039
1040/// Returns the vector normalized.
1041inline Point3F mNormalize( const Point3F &vec )
1042{
1043   Point3F out( vec );
1044   out.normalize();
1045   return out;
1046}
1047
1048/// Returns true if the point is NaN.
1049inline bool mIsNaN( const Point3F &p )
1050{
1051   return mIsNaN_F( p.x ) || mIsNaN_F( p.y ) || mIsNaN_F( p.z );
1052}
1053
1054/// Returns a copy of the vector reflected by a normal
1055inline Point3F mReflect( const Point3F &v, const Point3F &n )
1056{
1057   return v - 2 * n * mDot( v, n );
1058}
1059
1060/// Returns a perpendicular vector to the unit length input vector.
1061extern Point3F mPerp( const Point3F &normal );
1062
1063#endif // _MPOINT3_H_
1064