PixelLightAPI
.
|
00001 /*********************************************************\ 00002 * File: Vector3.h * 00003 * 00004 * Copyright (C) 2002-2012 The PixelLight Team (http://www.pixellight.org/) 00005 * 00006 * This file is part of PixelLight. 00007 * 00008 * PixelLight is free software: you can redistribute it and/or modify 00009 * it under the terms of the GNU Lesser General Public License as published by 00010 * the Free Software Foundation, either version 3 of the License, or 00011 * (at your option) any later version. 00012 * 00013 * PixelLight is distributed in the hope that it will be useful, 00014 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00015 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00016 * GNU Lesser General Public License for more details. 00017 * 00018 * You should have received a copy of the GNU Lesser General Public License 00019 * along with PixelLight. If not, see <http://www.gnu.org/licenses/>. 00020 \*********************************************************/ 00021 00022 00023 #ifndef __PLMATH_VECTOR3_H__ 00024 #define __PLMATH_VECTOR3_H__ 00025 #pragma once 00026 00027 00028 //[-------------------------------------------------------] 00029 //[ Includes ] 00030 //[-------------------------------------------------------] 00031 #include <PLCore/String/String.h> 00032 #include "PLMath/PLMath.h" 00033 00034 00035 //[-------------------------------------------------------] 00036 //[ Namespace ] 00037 //[-------------------------------------------------------] 00038 namespace PLMath { 00039 00040 00041 //[-------------------------------------------------------] 00042 //[ Forward declarations ] 00043 //[-------------------------------------------------------] 00044 class Vector2; 00045 class Vector4; 00046 class Matrix3x3; 00047 class Matrix3x4; 00048 class Matrix4x4; 00049 class Rectangle; 00050 class Quaternion; 00051 00052 00053 //[-------------------------------------------------------] 00054 //[ Classes ] 00055 //[-------------------------------------------------------] 00056 /** 00057 * @brief 00058 * 3D vector 00059 */ 00060 class Vector3 { 00061 00062 00063 //[-------------------------------------------------------] 00064 //[ Public definitions ] 00065 //[-------------------------------------------------------] 00066 public: 00067 /** 00068 * @brief 00069 * Vector component 00070 */ 00071 enum Component { 00072 X = 0, /**< X component */ 00073 Y = 1, /**< Y component */ 00074 Z = 2 /**< Z component */ 00075 }; 00076 00077 00078 //[-------------------------------------------------------] 00079 //[ Public static data ] 00080 //[-------------------------------------------------------] 00081 public: 00082 static PLMATH_API const Vector3 Zero; /**< 0.0, 0.0, 0.0 */ 00083 static PLMATH_API const Vector3 One; /**< 1.0, 1.0, 1.0 */ 00084 static PLMATH_API const Vector3 NegativeOne; /**< -1.0, -1.0, -1.0 */ 00085 static PLMATH_API const Vector3 UnitX; /**< 1.0, 0.0, 0.0 */ 00086 static PLMATH_API const Vector3 UnitY; /**< 0.0, 1.0, 0.0 */ 00087 static PLMATH_API const Vector3 UnitZ; /**< 0.0, 0.0, 1.0 */ 00088 static PLMATH_API const Vector3 NegativeUnitX; /**< -1.0, 0.0, 0.0 */ 00089 static PLMATH_API const Vector3 NegativeUnitY; /**< 0.0, -1.0, 0.0 */ 00090 static PLMATH_API const Vector3 NegativeUnitZ; /**< 0.0, 0.0, -1.0 */ 00091 00092 00093 //[-------------------------------------------------------] 00094 //[ Public data ] 00095 //[-------------------------------------------------------] 00096 public: 00097 /** 00098 * @brief 00099 * Some direct vertex element accesses 00100 */ 00101 union { 00102 /** 00103 * @brief 00104 * Vertex element array access 00105 */ 00106 float fV[3]; 00107 00108 /** 00109 * @brief 00110 * Known vertex element names when dealing with positions or directions 00111 */ 00112 struct { 00113 float x, y, z; 00114 }; 00115 00116 /** 00117 * @brief 00118 * Known vertex element names when dealing with texture coordinates 00119 */ 00120 struct { 00121 float u, v, w; 00122 }; 00123 00124 /** 00125 * @brief 00126 * Known vertex element names when dealing with rotations 00127 * 00128 * @note 00129 * - X rotation axis: Pitch (also called 'bank') change is moving the nose down and the tail up (or vice-versa) 00130 * - Y rotation axis: Yaw (also called 'heading') change is turning to the left or right 00131 * - Z rotation axis: Roll (also called 'attitude') change is moving one wingtip up and the other down 00132 */ 00133 struct { 00134 float fPitch, fYaw, fRoll; 00135 }; 00136 }; 00137 00138 00139 //[-------------------------------------------------------] 00140 //[ Public functions ] 00141 //[-------------------------------------------------------] 00142 public: 00143 //[-------------------------------------------------------] 00144 //[ Constructors ] 00145 //[-------------------------------------------------------] 00146 /** 00147 * @brief 00148 * Default constructor setting all components to 0 00149 */ 00150 inline Vector3(); 00151 00152 inline Vector3(float fX, float fY, float fZ = 0.0f); 00153 inline Vector3(const float fV[]); 00154 PLMATH_API Vector3(const Vector2 &vV, float fZ = 0.0f); 00155 inline Vector3(const Vector3 &vV); 00156 PLMATH_API Vector3(const Vector4 &vV); 00157 inline Vector3(const PLCore::String &sString); 00158 00159 //[-------------------------------------------------------] 00160 //[ Destructor ] 00161 //[-------------------------------------------------------] 00162 inline ~Vector3(); 00163 00164 //[-------------------------------------------------------] 00165 //[ Assignment operators ] 00166 //[-------------------------------------------------------] 00167 inline Vector3 &operator =(const float fV[]); 00168 PLMATH_API Vector3 &operator =(const Vector2 &vV); 00169 inline Vector3 &operator =(const Vector3 &vV); 00170 PLMATH_API Vector3 &operator =(const Vector4 &vV); 00171 00172 //[-------------------------------------------------------] 00173 //[ Comparison ] 00174 //[-------------------------------------------------------] 00175 /** 00176 * @brief 00177 * Compares two vectors 00178 * 00179 * @param[in] vV 00180 * Vector to compare with 00181 * 00182 * @return 00183 * 'true' if all components are equal, else 'false' 00184 */ 00185 inline bool operator ==(const Vector3 &vV) const; 00186 00187 /** 00188 * @brief 00189 * Compares two vectors 00190 * 00191 * @param[in] vV 00192 * Vector to compare with 00193 * 00194 * @return 00195 * 'false' if all components are equal, else 'true' 00196 */ 00197 inline bool operator !=(const Vector3 &vV) const; 00198 00199 /** 00200 * @brief 00201 * Compares two vectors lexicographically 00202 * 00203 * @param[in] vV 00204 * Vector to compare with 00205 * 00206 * @return 00207 * 'true' if ALL components of this vector are less, else 'false' 00208 * 00209 * @note 00210 * - A lexicographical order for 3-dimensional vectors is used (see http://en.wikipedia.org/wiki/Ordered_vector_space) 00211 */ 00212 inline bool operator <(const Vector3 &vV) const; 00213 00214 /** 00215 * @brief 00216 * Compares two vectors lexicographically 00217 * 00218 * @param[in] vV 00219 * Vector to compare with 00220 * 00221 * @return 00222 * 'true' if ALL components of this vector are greater, else 'false' 00223 * 00224 * @see 00225 * - "operator <" 00226 */ 00227 inline bool operator >(const Vector3 &vV) const; 00228 00229 /** 00230 * @brief 00231 * Compares two vectors lexicographically 00232 * 00233 * @param[in] vV 00234 * Vector to compare with 00235 * 00236 * @return 00237 * 'true' if ALL components of this vector are less or equal, else 'false' 00238 * 00239 * @see 00240 * - "operator <" 00241 */ 00242 inline bool operator <=(const Vector3 &vV) const; 00243 00244 /** 00245 * @brief 00246 * Compares two vectors lexicographically 00247 * 00248 * @param[in] vV 00249 * Vector to compare with 00250 * 00251 * @return 00252 * 'true' if ALL components of this vector are greater or equal, else 'false' 00253 * 00254 * @see 00255 * - "operator <" 00256 */ 00257 inline bool operator >=(const Vector3 &vV) const; 00258 00259 //[-------------------------------------------------------] 00260 //[ Vector ] 00261 //[-------------------------------------------------------] 00262 inline Vector3 operator +(const Vector3 &vV) const; 00263 inline Vector3 operator +(float fN) const; 00264 inline Vector3 &operator +=(const Vector3 &vV); 00265 inline Vector3 &operator +=(float fN); 00266 inline Vector3 operator -() const; 00267 inline Vector3 operator -(const Vector3 &vV) const; 00268 inline Vector3 operator -(float fN) const; 00269 inline Vector3 &operator -=(const Vector3 &vV); 00270 inline Vector3 &operator -=(float fN); 00271 00272 /** 00273 * @brief 00274 * Per component multiplication 00275 * 00276 * @param[in] vV 00277 * Vector to multiplicate with 00278 * 00279 * @return 00280 * The resulting vector 00281 */ 00282 inline Vector3 operator *(const Vector3 &vV) const; 00283 inline Vector3 operator *(float fS) const; 00284 00285 /** 00286 * @brief 00287 * Per component multiplication 00288 * 00289 * @param[in] vV 00290 * Vector to multiplicate with 00291 * 00292 * @return 00293 * This vector which is now the resulting vector 00294 */ 00295 inline Vector3 &operator *=(const Vector3 &vV); 00296 inline Vector3 &operator *=(float fS); 00297 00298 /** 00299 * @brief 00300 * Rotates the vector 00301 * 00302 * @param[in] mRot 00303 * Matrix which rotates the vector 00304 * 00305 * @return 00306 * This vector which is now the resulting vector 00307 */ 00308 PLMATH_API Vector3 &operator *=(const Matrix3x3 &mRot); 00309 00310 /** 00311 * @brief 00312 * Transforms the vector 00313 * 00314 * @param[in] mTrans 00315 * Matrix which transforms the vector 00316 * 00317 * @return 00318 * This vector which is now the resulting vector 00319 */ 00320 PLMATH_API Vector3 &operator *=(const Matrix3x4 &mTrans); 00321 00322 /** 00323 * @brief 00324 * Transforms the vector 00325 * 00326 * @param[in] mTrans 00327 * Matrix which transforms the vector 00328 * 00329 * @return 00330 * This vector which is now the resulting vector 00331 */ 00332 PLMATH_API Vector3 &operator *=(const Matrix4x4 &mTrans); 00333 00334 /** 00335 * @brief 00336 * Rotates the vector 00337 * 00338 * @param[in] qQ 00339 * Quaternion which rotates the vector 00340 * 00341 * @return 00342 * This vector which is now the resulting vector 00343 */ 00344 PLMATH_API Vector3 &operator *=(const Quaternion &qQ); 00345 00346 /** 00347 * @brief 00348 * Per component division 00349 * 00350 * @param[in] vV 00351 * Vector to divide through 00352 * 00353 * @return 00354 * The resulting vector 00355 */ 00356 inline Vector3 operator /(const Vector3 &vV) const; 00357 inline Vector3 operator /(float fS) const; 00358 00359 /** 00360 * @brief 00361 * Per component division 00362 * 00363 * @param[in] vV 00364 * Vector to divide through 00365 * 00366 * @return 00367 * This vector which is now the resulting vector 00368 */ 00369 inline Vector3 &operator /=(const Vector3 &vV); 00370 inline Vector3 &operator /=(float fS); 00371 00372 //[-------------------------------------------------------] 00373 //[ Get and set ] 00374 //[-------------------------------------------------------] 00375 inline operator float *(); 00376 inline operator const float *() const; 00377 inline float &operator [](int nIndex); 00378 inline const float &operator [](int nIndex) const; 00379 inline void GetXYZ(float &fX, float &fY, float &fZ) const; 00380 inline float GetX() const; 00381 inline float GetY() const; 00382 inline float GetZ() const; 00383 inline void SetXYZ(float fX = 0.0f, float fY = 0.0f, float fZ = 0.0f); 00384 inline void SetXYZ(const float fV[]); 00385 inline void SetX(float fX = 0.0f); 00386 inline void SetY(float fY = 0.0f); 00387 inline void SetZ(float fZ = 0.0f); 00388 inline void IncXYZ(float fX = 0.0f, float fY = 0.0f, float fZ = 0.0f); 00389 inline void IncXYZ(const float fV[]); 00390 inline void IncX(float fX); 00391 inline void IncY(float fY); 00392 inline void IncZ(float fZ); 00393 00394 //[-------------------------------------------------------] 00395 //[ Misc ] 00396 //[-------------------------------------------------------] 00397 /** 00398 * @brief 00399 * Returns whether the vector is null or not 00400 * 00401 * @return 00402 * 'true' if the vector is null, else 'false' 00403 */ 00404 inline bool IsNull() const; 00405 00406 /** 00407 * @brief 00408 * Returns whether the vector is packed (within range of 0-1) or not 00409 * 00410 * @return 00411 * 'true' if the vector is packed, else 'false' 00412 */ 00413 inline bool IsPacked() const; 00414 00415 /** 00416 * @brief 00417 * Packs/clamps the vector into a range of 0-1 00418 * 00419 * @remarks 00420 * First, the vector is normalized - now each component is between -1 and 1. 00421 * This normalized vector is scaled by 0.5 and 0.5 is added. 00422 */ 00423 inline void PackTo01(); 00424 00425 /** 00426 * @brief 00427 * Returns a vector which is packed/clamped into the range of 0-1 00428 * 00429 * @return 00430 * The packed vector 00431 * 00432 * @see 00433 * - PackTo01() 00434 */ 00435 inline Vector3 GetPackedTo01() const; 00436 00437 /** 00438 * @brief 00439 * Unpacks the packed vector into a range of -1 to 1 00440 * 00441 * @remarks 00442 * The vector is scaled by 2 and 1 is subtracted. 00443 * 00444 * @note 00445 * - There's no internal check whether the vector is packed or not, you can do this 00446 * by yourself using the IsPacked() function 00447 */ 00448 inline void UnpackFrom01(); 00449 00450 /** 00451 * @brief 00452 * Returns a unpacked vector of the range of -1 to 1 00453 * 00454 * @return 00455 * The unpacked vector 00456 * 00457 * @see 00458 * - UnpackFrom01() 00459 */ 00460 inline Vector3 GetUnpackedFrom01() const; 00461 00462 /** 00463 * @brief 00464 * Returns the smallest component 00465 * 00466 * @return 00467 * The smallest component 00468 * 00469 * @remarks 00470 * If x is 1, y is 2 and z is 3, this function will return the x component. 00471 */ 00472 inline Component GetSmallestComponent() const; 00473 00474 /** 00475 * @brief 00476 * Returns the value of the smallest component 00477 * 00478 * @return 00479 * The value of the smallest component 00480 * 00481 * @see 00482 * - GetSmallestComponent() above 00483 */ 00484 inline float GetSmallestValue() const; 00485 00486 /** 00487 * @brief 00488 * Returns the greatest component 00489 * 00490 * @return 00491 * The greatest component 00492 * 00493 * @remarks 00494 * If x is 1, y is 2 and z is 3, this function will return the z component. 00495 */ 00496 inline Component GetGreatestComponent() const; 00497 00498 /** 00499 * @brief 00500 * Returns the value of the greatest component 00501 * 00502 * @return 00503 * The value of the greatest component 00504 * 00505 * @see 00506 * - GetGreatestComponent() above 00507 */ 00508 inline float GetGreatestValue() const; 00509 00510 /** 00511 * @brief 00512 * Inverts the vector 00513 * 00514 * @remarks 00515 * v'.x = -v.x\n 00516 * v'.y = -v.y\n 00517 * v'.z = -v.z 00518 */ 00519 inline void Invert(); 00520 00521 /** 00522 * @brief 00523 * Returns the inverted vector 00524 * 00525 * @return 00526 * Inverted vector 00527 * 00528 * @see 00529 * - Invert() 00530 */ 00531 inline Vector3 GetInverted() const; 00532 00533 /** 00534 * @brief 00535 * Returns the length of the vector (also called magnitude) 00536 * 00537 * @return 00538 * Vector length 00539 * 00540 * @remarks 00541 * l = sqrt(x*x + y*y + z*z) 00542 */ 00543 inline float GetLength() const; 00544 00545 /** 00546 * @brief 00547 * Returns the squared length of the vector (also called norm) 00548 * 00549 * @return 00550 * Squared vector length 00551 * 00552 * @remarks 00553 * l = x*x + y*y + z*z 00554 * 00555 * @note 00556 * - For better performance, use this function instead of GetLength() whenever 00557 * possible. You can often work with squared lengths instead of the 'real' ones. 00558 */ 00559 inline float GetSquaredLength() const; 00560 00561 /** 00562 * @brief 00563 * Sets the vector to the given length 00564 * 00565 * @param[in] fLength 00566 * Length to set 00567 * 00568 * @remarks 00569 * v' = v*l/sqrt(x*x + y*y + z*z) 00570 */ 00571 inline void SetLength(float fLength = 1.0f); 00572 00573 /** 00574 * @brief 00575 * Normalizes the vector 00576 * 00577 * @return 00578 * This instance 00579 * 00580 * @remarks 00581 * v' = v*1/sqrt(x*x + y*y + z*z) 00582 * 00583 * @note 00584 * - This will set the vector to a length of 1 (same as SetLength(1.0f) :) 00585 * - A normalized vector is called 'unit vector' 00586 */ 00587 inline Vector3 &Normalize(); 00588 00589 /** 00590 * @brief 00591 * Returns the normalized vector 00592 * 00593 * @return 00594 * Normalized vector 00595 * 00596 * @see 00597 * - Normalize() 00598 */ 00599 inline Vector3 GetNormalized() const; 00600 00601 /** 00602 * @brief 00603 * Returns the distance to another vector 00604 * 00605 * @param[in] vV 00606 * The other vector 00607 * 00608 * @return 00609 * Distance to the other vector 00610 * 00611 * @remarks 00612 * dx = v2.x-v1.x\n 00613 * dy = v2.y-v1.y\n 00614 * dz = v2.z-v1.z\n 00615 * d = sqrt(dx*dx + dy*dy + dz*dz) 00616 */ 00617 inline float GetDistance(const Vector3 &vV) const; 00618 00619 /** 00620 * @brief 00621 * Returns the squared distance to another vector 00622 * 00623 * @param[in] vV 00624 * The other vector 00625 * 00626 * @return 00627 * Distance to the other vector 00628 * 00629 * @remarks 00630 * dx = v2.x-v1.x\n 00631 * dy = v2.y-v1.y\n 00632 * dz = v2.z-v1.z\n 00633 * d = dx*dx + dy*dy + dz*dz 00634 * 00635 * @note 00636 * - For better performance, use this function instead of GetDistance() whenever 00637 * possible. You can often work with squared distances instead of the 'real' ones. 00638 */ 00639 inline float GetSquaredDistance(const Vector3 &vV) const; 00640 00641 /** 00642 * @brief 00643 * Returns the dot product of two vectors 00644 * 00645 * @param[in] vV 00646 * Second vector 00647 * 00648 * @return 00649 * Dot product of the vectors 00650 * 00651 * @remarks 00652 * d = this->x*vV.x + this->y*vV.y + this->z*vV.z 00653 * 00654 * @note 00655 * - The dot product is also known as 'scalar product' or 'inner product' 00656 * - The dot product of a vector with itself is equal to it's squared length, so it's possible to 00657 * use GetSquaredLength() instead of v.DotProduct(v) 00658 * - The dot product is commutative 00659 * - If the two vectors are perpendicular, their dot product equals zero 00660 * - If the angle between the two vectors is acute (< 90 degrees) the dot product will be positive, 00661 * if the angle is obtuse (> 90 degrees) the dot product will be negative 00662 * - Geometric definition: a.DotProduct(b) = a.GetLength() * b.GetLength() * cos(r) 00663 * 00664 * @see 00665 * - GetAngle() 00666 */ 00667 inline float DotProduct(const Vector3 &vV) const; 00668 00669 /** 00670 * @brief 00671 * Project vector a onto another vector b 00672 * 00673 * @param[in] vA 00674 * Vector to project 00675 * @param[in] vB 00676 * Vector to project onto 00677 * 00678 * @remarks 00679 * @code 00680 * ^. 00681 * / . 00682 * / . 00683 * a / . 00684 * / . a.DotProduct(b) 00685 * / . projb(a) = b * ----------------- 00686 * / . b.DotProduct(b) 00687 * / . 00688 * --->____. 00689 * b ^= projb(a) 00690 * @endcode 00691 * 00692 * @return 00693 * The resulting projection vector 00694 */ 00695 inline Vector3 ProjectVector(const Vector3 &vA, const Vector3 &vB) const; 00696 00697 /** 00698 * @brief 00699 * Calculates the angle between two vectors 00700 * 00701 * @param[in] vV 00702 * Second vector 00703 * 00704 * @return 00705 * The angle between the two vectors (in radians) 00706 * 00707 * @remarks 00708 * @code 00709 * v1.DotProduct(v2) 00710 * cos A = -------------------------------- 00711 * v1.GetLength() * v2.GetLength() 00712 * @endcode 00713 * 00714 * @note 00715 * - If the two vectors are normalized, you can also use acos(DotProduct()) which is 00716 * in this case more performant 00717 */ 00718 inline float GetAngle(const Vector3 &vV) const; 00719 00720 /** 00721 * @brief 00722 * Returns the cross product of this vector with another 00723 * 00724 * @param[in] vV 00725 * Vector to calculate the cross product with 00726 * 00727 * @remarks 00728 * @code 00729 * c (a = this, b = vV) 00730 * ^ a 00731 * | ^ | ax | | bx | | ay*bz - az*by | 00732 * | / c = a x b = | ay | x | by | = | az*bx - ax*bz | 00733 * | / | az | | bz | | ax*by - ay*bx | 00734 * | / 00735 * |/--------> b 00736 * @endcode 00737 * 00738 * @return 00739 * The calculated vector which is perpendicular to the given two vectors 00740 * 00741 * @remarks 00742 * The length of the cross product is the lengths of the individual vectors, multiplied together 00743 * with the sine of the angle between them. This means you can use the cross product to tell when 00744 * two vectors are parallel, because if they are parallel their cross product will be zero. 00745 * 00746 * @note 00747 * - The cross product is also known as the 'vector product' or 'outer product' 00748 * - Unlike the dot product, the cross product is only defined for 3-dimensional 00749 * vectors (and not for 2-dimensional, 4-dimensional and so on) 00750 * - The cross product is anti commutative (a x b = -(b x a) ... means that the order is important) 00751 */ 00752 inline Vector3 CrossProduct(const Vector3 &vV) const; 00753 00754 /** 00755 * @brief 00756 * Calculates the cross product of two vectors 00757 * 00758 * @param[in] vV1 00759 * First of the two vectors to calculate the cross product from 00760 * @param[in] vV2 00761 * Second of the two vectors to calculate the cross product from 00762 * 00763 * @return 00764 * Reference to the vector itself which is now perpendicular (and not normalized) 00765 * to the two vectors 00766 * 00767 * @see 00768 * - CrossProduct() above 00769 */ 00770 inline Vector3 &CrossProduct(const Vector3 &vV1, const Vector3 &vV2); 00771 00772 /** 00773 * @brief 00774 * Calculates the right/up vectors of the vector 00775 * 00776 * @param[out] vRight 00777 * The resulting right vectors which are perpendicular to the source vector 00778 * @param[out] vUp 00779 * The resulting up vectors which are perpendicular to the source vector 00780 */ 00781 PLMATH_API void GetRightUp(Vector3 &vRight, Vector3 &vUp) const; 00782 PLMATH_API void GetRightUp(float fRight[], float fUp[]) const; 00783 00784 /** 00785 * @brief 00786 * Calculates a face/plane normal 00787 * 00788 * @param[in] vV1 00789 * First of the three vectors which describes the face/plane 00790 * @param[in] vV2 00791 * Second of the three vectors which describes the face/plane 00792 * @param[in] vV3 00793 * Third of the three vectors which describes the face/plane 00794 * 00795 * @remarks 00796 * GetNormalized(CrossProduct(vV1-vV2, vV1-vV3)) 00797 */ 00798 inline void GetFaceNormal(const Vector3 &vV1, const Vector3 &vV2, const Vector3 &vV3); 00799 00800 /** 00801 * @brief 00802 * Rotates two vectors around it's axis 00803 * 00804 * @param[in] vV 00805 * Other vector to rotate 00806 * @param[in] fAngle 00807 * Angle the two vectors should be rotated 00808 * 00809 * @return 00810 * Reference to this vector 00811 */ 00812 PLMATH_API Vector3 &RotateAxis(Vector3 &vV, float fAngle); 00813 00814 /** 00815 * @brief 00816 * Returns a rotation quaternion to the destination vector 00817 * 00818 * @param[in] vDest 00819 * Destination vector 00820 * 00821 * @return 00822 * Rotation quaternion 00823 */ 00824 PLMATH_API Quaternion GetRotationTo(const Vector3 &vDest) const; 00825 00826 /** 00827 * @brief 00828 * Calculates a normalized projection vector 00829 * 00830 * @param[in] vX 00831 * The first vector to calculate the projection from 00832 * @param[in] vN 00833 * The second vector to calculate the projection from 00834 * 00835 * @return 00836 * Reference to the vector itself which is now the resulting projection 00837 */ 00838 PLMATH_API Vector3 &GetProjection(const Vector3 &vX, const Vector3 &vN); 00839 00840 /** 00841 * @brief 00842 * Project the vector on to the plane created by two direction vectors 00843 * 00844 * @param[in] vV1 00845 * First of the two direction vectors creating the plane 00846 * @param[in] vV2 00847 * Second of the two direction vectors creating the plane 00848 * 00849 * @return 00850 * Reference to the vector itself which is now the resulting projection vector 00851 * 00852 * @note 00853 * - vV1 and vV2 MUST be perpendicular to each other 00854 */ 00855 PLMATH_API Vector3 &ProjectPlane(const Vector3 &vV1, const Vector3 &vV2); 00856 00857 /** 00858 * @brief 00859 * Calculates a reflection vector 00860 * 00861 * @param[in] vIncidentNormal 00862 * Incident normal 00863 * @param[in] vNormal 00864 * Plane normal which reflects the incident vector (must be normalized) 00865 * 00866 * @return 00867 * Reference to the vector itself which is now the resulting reflection vector 00868 * 00869 * @remarks 00870 * If I is the incident vector and N a normalized normal vector, then 00871 * the reflection vector R is computed as: R = I - 2*N*(N*I) (N*I results in a scalar...) 00872 * @code 00873 * Plane normal N 00874 * | 00875 * Incident ray I | Reflected ray R 00876 * \ | / 00877 * \ | / 00878 * ________________\|/________________ Plane 00879 * @endcode 00880 * 00881 * @note 00882 * - The reflection vector has the same length as the incident vector 00883 */ 00884 PLMATH_API Vector3 &Reflect(const Vector3 &vIncidentNormal, const Vector3 &vNormal); 00885 00886 /** 00887 * @brief 00888 * Calculates a refraction vector 00889 * 00890 * @param[in] vIncidentNormal 00891 * Incident normal 00892 * @param[in] vNormal 00893 * Plane normal which refracts the incident vector (must be normalized) 00894 * @param[in] fEtaRatio 00895 * Index of refraction ratio 00896 * 00897 * @return 00898 * Reference to the vector itself which is now the resulting refraction vector 00899 * 00900 * @remarks 00901 * Calculates a refraction vector using Snell's Law. 00902 * @code 00903 * Plane normal N 00904 * | 00905 * Incident ray I | 00906 * \ | 00907 * \ | 00908 * ________________\|_________________ Plane 00909 * \ 00910 * \ 00911 * \ 00912 * Refracted ray R 00913 * @endcode 00914 * \n 00915 * Here are some indices of refraction: 00916 * Vacuum = 1.0, Air = 1.003, Water = 1.3333, Glass = 1.5, Plastic = 1.5, 00917 * Diamond = 2.417 00918 * 00919 * @note 00920 * - The refraction vector has the same length as the incident vector 00921 */ 00922 PLMATH_API Vector3 &Refract(const Vector3 &vIncidentNormal, const Vector3 &vNormal, float fEtaRatio); 00923 00924 /** 00925 * @brief 00926 * Finds the closest point on a line to this point 00927 * 00928 * @param[in] vV1 00929 * Line start position 00930 * @param[in] vV2 00931 * Line end position 00932 * 00933 * @return 00934 * The closest point on line 00935 */ 00936 PLMATH_API Vector3 ClosestPointOnLine(const Vector3 &vV1, const Vector3 &vV2) const; 00937 00938 /** 00939 * @brief 00940 * Check if a point is in a triangle 00941 * 00942 * @param[in] vV1 00943 * First triangle point 00944 * @param[in] vV2 00945 * Second triangle point 00946 * @param[in] vV3 00947 * Third triangle point 00948 * 00949 * @return 00950 * 'true' if the point is in the triangle, else 'false' 00951 */ 00952 PLMATH_API bool IsPointInTriangle(const Vector3 &vV1, const Vector3 &vV2, const Vector3 &vV3) const; 00953 00954 /** 00955 * @brief 00956 * Find the closest point on a triangle to this point 00957 * 00958 * @param[in] vV1 00959 * First triangle point 00960 * @param[in] vV2 00961 * Second triangle point 00962 * @param[in] vV3 00963 * Third triangle point 00964 * 00965 * @return 00966 * The closest point on triangle 00967 */ 00968 PLMATH_API Vector3 ClosestPointOnTriangle(const Vector3 &vV1, const Vector3 &vV2, const Vector3 &vV3) const; 00969 00970 /** 00971 * @brief 00972 * Find the closest point on a triangle to this point 00973 * 00974 * @param[in] vV1 00975 * First triangle point 00976 * @param[in] vV2 00977 * Second triangle point 00978 * @param[in] vV3 00979 * Third triangle point 00980 * @param[in] fRadius 00981 * Point test radius 00982 * @param[out] vClosest 00983 * Will receive the closest point 00984 * 00985 * @return 00986 * 'true' if closest point is valid, else 'false' 00987 */ 00988 PLMATH_API bool ClosestPointOnTriangle(const Vector3 &vV1, const Vector3 &vV2, 00989 const Vector3 &vV3, float fRadius, Vector3 &vClosest) const; 00990 00991 /** 00992 * @brief 00993 * Returns the 2D screen coordinate corresponding to this 3D coordinate 00994 * 00995 * @param[in] mWorldViewProjection 00996 * World view projection matrix to use 00997 * @param[in] cViewportRectangle 00998 * Viewport rectangle to use 00999 * @param[in] fDepthRangeMin 01000 * Depth range minimum 01001 * @param[in] fDepthRangeMax 01002 * Depth range maximum 01003 * @param[in] pfHomogeneousDivide 01004 * If not a null pointer, this receives the homogeneous divide 01005 * 01006 * @return 01007 * The corresponding 2D screen coordinate (x, y, z depth) 01008 */ 01009 PLMATH_API Vector3 To2DCoordinate(const Matrix4x4 &mWorldViewProjection, const Rectangle &cViewportRectangle, 01010 float fDepthRangeMin = 0.0f, float fDepthRangeMax = 1.0f, float *pfHomogeneousDivide = nullptr) const; 01011 01012 /** 01013 * @brief 01014 * Returns the 3D coordinate corresponding to this 2D screen coordinate 01015 * 01016 * @param[in] mClipSpaceToObjectSpace 01017 * The clip space to object space matrix to use 01018 * @param[in] cViewportRectangle 01019 * Viewport rectangle to use 01020 * 01021 * @return 01022 * The corresponding 3D coordinate 01023 * 01024 * @remarks 01025 * The depth value stored within the z component of this vector should be between 0.0-1.0. 01026 * Try to avoid using 0.0 & 1.0, instead add a small value like 0.0001 - else 01027 * wrong results may be returned, especially if an infinite projection matrix is used. 01028 */ 01029 PLMATH_API Vector3 To3DCoordinate(const Matrix4x4 &mClipSpaceToObjectSpace, const Rectangle &cViewportRectangle) const; 01030 01031 /** 01032 * @brief 01033 * To string 01034 * 01035 * @return 01036 * String with the data 01037 */ 01038 PLMATH_API PLCore::String ToString() const; 01039 01040 /** 01041 * @brief 01042 * From string 01043 * 01044 * @param[in] sString 01045 * String with the data 01046 */ 01047 PLMATH_API bool FromString(const PLCore::String &sString); 01048 01049 01050 }; 01051 01052 01053 //[-------------------------------------------------------] 01054 //[ Namespace ] 01055 //[-------------------------------------------------------] 01056 } // PLMath 01057 01058 01059 //[-------------------------------------------------------] 01060 //[ Implementation ] 01061 //[-------------------------------------------------------] 01062 #include "PLMath/Vector3.inl" 01063 #include "PLMath/TypeVector3.inl" 01064 01065 01066 #endif // __PLMATH_VECTOR3_H__
|