From b81b77b1c95de8fda430a0bd428dd551c89db380 Mon Sep 17 00:00:00 2001 From: Pascal Serrarens Date: Wed, 31 Jul 2024 11:44:23 +0200 Subject: [PATCH] Extend AngleOf support --- Angle.cpp | 31 +++++++++++++++------ Angle.h | 24 ++++++++++------- Angle16.cpp | 74 +++++++++++++++++++++++++++++++++++++++++++++++++++ Angle16.h | 34 +++++++++++------------ Angle32.h | 36 +++++++++++++------------ Angle8.cpp | 24 +++++++++++++++++ Angle8.h | 36 ++++++++++++------------- AngleUsing.h | 11 +++++--- Polar.cpp | 40 ++++++++++++++-------------- Polar.h | 40 +++++++++++++++++----------- Spherical.cpp | 55 +++++++++++++++++++------------------- Spherical.h | 47 +++++++++++++++++++------------- Vector2.cpp | 74 ++++++++++++++++++++++++++++----------------------- Vector2.h | 49 +++++++++++++++++++--------------- Vector3.cpp | 71 +++++++++++++++++++++++++----------------------- Vector3.h | 63 +++++++++++++++++++++++++------------------ 16 files changed, 441 insertions(+), 268 deletions(-) create mode 100644 Angle16.cpp create mode 100644 Angle8.cpp diff --git a/Angle.cpp b/Angle.cpp index 180db0f..4e69f45 100644 --- a/Angle.cpp +++ b/Angle.cpp @@ -3,8 +3,8 @@ // file, You can obtain one at https ://mozilla.org/MPL/2.0/. #include "Angle.h" -#include "FloatSingle.h" #include +#include "FloatSingle.h" /* const float Angle::Rad2Deg = 57.29578F; @@ -73,17 +73,29 @@ float Angle::SineRuleAngle(float a, float beta, float b) { */ //---------------------- -template <> AngleOf AngleOf::pi = 3.1415927410125732421875F; +template <> +AngleOf::AngleOf(float angle) : value(angle) {} -template <> AngleOf AngleOf::Rad2Deg = 360.0f / (pi * 2); -template <> AngleOf AngleOf::Deg2Rad = (pi * 2) / 360.0f; +template <> +AngleOf::operator float() const { + return value; +} + +template <> +AngleOf AngleOf::pi = 3.1415927410125732421875F; + +template <> +AngleOf AngleOf::Rad2Deg = 360.0f / (pi * 2); +template <> +AngleOf AngleOf::Deg2Rad = (pi * 2) / 360.0f; template <> bool Passer::LinearAlgebra::AngleOf::operator==(AngleOf a) { return (float)*this == (float)a; } -template <> AngleOf AngleOf::Normalize(AngleOf angle) { +template <> +AngleOf AngleOf::Normalize(AngleOf angle) { float angleValue = angle; if (!isfinite(angleValue)) return angleValue; @@ -96,7 +108,8 @@ template <> AngleOf AngleOf::Normalize(AngleOf angle) { } template <> -AngleOf AngleOf::Clamp(AngleOf angle, AngleOf min, +AngleOf AngleOf::Clamp(AngleOf angle, + AngleOf min, AngleOf max) { float normalizedAngle = Normalize(angle); float r = Float::Clamp(normalizedAngle, min, max); @@ -120,7 +133,8 @@ AngleOf AngleOf::MoveTowards(AngleOf fromAngle, } template <> -AngleOf AngleOf::CosineRuleSide(float a, float b, +AngleOf AngleOf::CosineRuleSide(float a, + float b, AngleOf gamma) { float a2 = a * a; float b2 = b * b; @@ -150,7 +164,8 @@ AngleOf AngleOf::CosineRuleAngle(float a, float b, float c) { } template <> -AngleOf AngleOf::SineRuleAngle(float a, AngleOf beta, +AngleOf AngleOf::SineRuleAngle(float a, + AngleOf beta, float b) { float alpha = asin(a * sin(beta * Angle::Deg2Rad) / b); return alpha; diff --git a/Angle.h b/Angle.h index 3c55e48..8be0583 100644 --- a/Angle.h +++ b/Angle.h @@ -8,11 +8,15 @@ namespace Passer { namespace LinearAlgebra { -template class AngleOf { -public: - AngleOf(){}; - AngleOf(T v) : value(v) {} - operator T() const { return value; } +template +class AngleOf { + public: + AngleOf() {}; + AngleOf(float f); + // AngleOf(T v) : value(v) {} + // operator T() const; // { return value; } + operator float() const; + inline T GetBinary() const { return this->value; } static AngleOf Rad2Deg; static AngleOf Deg2Rad; @@ -27,7 +31,8 @@ public: AngleOf r = Normalize(b - a); return r; }; - static AngleOf MoveTowards(AngleOf fromAngle, AngleOf toAngle, + static AngleOf MoveTowards(AngleOf fromAngle, + AngleOf toAngle, AngleOf maxAngle); static AngleOf CosineRuleSide(float a, float b, AngleOf gamma); @@ -35,14 +40,15 @@ public: static AngleOf SineRuleAngle(float a, AngleOf beta, float c); -private: + private: T value; }; using Angle = AngleOf; +// using Angle = AngleOf; -} // namespace LinearAlgebra -} // namespace Passer +} // namespace LinearAlgebra +} // namespace Passer using namespace Passer::LinearAlgebra; #endif \ No newline at end of file diff --git a/Angle16.cpp b/Angle16.cpp new file mode 100644 index 0000000..d30e208 --- /dev/null +++ b/Angle16.cpp @@ -0,0 +1,74 @@ +// This Source Code Form is subject to the terms of the Mozilla Public +// License, v. 2.0.If a copy of the MPL was not distributed with this +// file, You can obtain one at https ://mozilla.org/MPL/2.0/. + +#include +#include "Angle.h" + +template <> +AngleOf::AngleOf(float angle) { + if (!isfinite(angle)) { + value = 0; + return; + } + + // map float [-180..180) to integer [-32768..32767] + this->value = (signed short)((angle / 360.0F) * 65536.0F); +} + +template <> +AngleOf::operator float() const { + float f = ((this->value * 180) / 32768.0F); + return f; +} + +// This should not exist... +// template <> +// AngleOf AngleOf::pi = 3.1415927410125732421875F; + +// template <> +// AngleOf AngleOf::Rad2Deg = 360.0f / (pi * 2); +// template <> +// AngleOf AngleOf::Deg2Rad = (pi * 2) / 360.0f; + +// template <> +// AngleOf AngleOf::Normalize( +// AngleOf angle) { +// return angle; +// } + +// Not correct!!! just for syntactical compilation ATM +template <> +AngleOf AngleOf::CosineRuleSide( + float a, + float b, + AngleOf gamma) { + float a2 = a * a; + float b2 = b * b; + float d = a2 + b2 - 2 * a * b * cos(gamma * AngleOf::Deg2Rad); + // Catch edge cases where float inacuracies lead tot nans + if (d < 0) + return 0; + + float c = sqrtf(d); + return c; +} + +// Not correct!!! just for syntactical compilation ATM +template <> +AngleOf AngleOf::CosineRuleAngle(float a, + float b, + float c) { + float a2 = a * a; + float b2 = b * b; + float c2 = c * c; + float d = (a2 + b2 - c2) / (2 * a * b); + // Catch edge cases where float inacuracies lead tot nans + if (d >= 1) + return 0; + if (d <= -1) + return 180; + + float gamma = acos(d) * Angle::Rad2Deg; + return gamma; +} diff --git a/Angle16.h b/Angle16.h index 511ab63..c3f55e9 100644 --- a/Angle16.h +++ b/Angle16.h @@ -1,28 +1,28 @@ -#include "AngleUsing.h" +// #include "AngleUsing.h" -#include "Angle.h" #include +#include "Angle.h" namespace Passer { namespace LinearAlgebra { -typedef AngleUsing Angle16; +typedef AngleOf Angle16; -template <> Angle16::AngleUsing(float angle) { - if (!isfinite(angle)) { - value = 0; - return; - } +// template <> Angle16::AngleOf(float angle) { +// if (!isfinite(angle)) { +// value = 0; +// return; +// } - // map float [-180..180) to integer [-32768..32767] - this->value = (signed short)((angle / 360.0F) * 65536.0F); -} +// // map float [-180..180) to integer [-32768..32767] +// this->value = (signed short)((angle / 360.0F) * 65536.0F); +// } -template <> float Angle16::ToFloat() const { - float f = ((this->value * 180) / 32768.0F); - return f; -} +// template <> float Angle16::ToFloat() const { +// float f = ((this->value * 180) / 32768.0F); +// return f; +// } -} // namespace LinearAlgebra -} // namespace Passer +} // namespace LinearAlgebra +} // namespace Passer using namespace Passer::LinearAlgebra; \ No newline at end of file diff --git a/Angle32.h b/Angle32.h index 72b135b..75a6e24 100644 --- a/Angle32.h +++ b/Angle32.h @@ -1,28 +1,30 @@ -#include "AngleUsing.h" +// #include "AngleUsing.h" -#include "Angle.h" #include +#include "Angle.h" namespace Passer { namespace LinearAlgebra { -typedef AngleUsing Angle32; +typedef AngleOf Angle32; -template <> Angle32::AngleUsing(float angle) { - if (!isfinite(angle)) { - value = 0; - return; - } +// template <> +// Angle32::AngleOf(float angle) { +// if (!isfinite(angle)) { +// value = 0; +// return; +// } - // map float [-180..180) to integer [-2147483648..2147483647] - this->value = (signed long)((angle / 360.0F) * 4294967295.0F); -} +// // map float [-180..180) to integer [-2147483648..2147483647] +// this->value = (signed long)((angle / 360.0F) * 4294967295.0F); +// } -template <> float Angle32::ToFloat() const { - float f = ((this->value * 180) / 2147483648.0F); - return f; -} +// template <> +// float Angle32::ToFloat() const { +// float f = ((this->value * 180) / 2147483648.0F); +// return f; +// } -} // namespace LinearAlgebra -} // namespace Passer +} // namespace LinearAlgebra +} // namespace Passer using namespace Passer::LinearAlgebra; \ No newline at end of file diff --git a/Angle8.cpp b/Angle8.cpp new file mode 100644 index 0000000..a992466 --- /dev/null +++ b/Angle8.cpp @@ -0,0 +1,24 @@ +// This Source Code Form is subject to the terms of the Mozilla Public +// License, v. 2.0.If a copy of the MPL was not distributed with this +// file, You can obtain one at https ://mozilla.org/MPL/2.0/. + +#include +#include "Angle.h" + +template <> +AngleOf::AngleOf(float angle) { + if (!isfinite(angle)) { + value = 0; + return; + } + + // map float [-180..180) to integer [-128..127] + float f = angle / 360.0F; + this->value = (signed char)(f * 256.0F); +} + +template <> +AngleOf::operator float() const { + float f = (this->value * 180) / 128.0F; + return f; +} diff --git a/Angle8.h b/Angle8.h index 53ba7d2..580c0af 100644 --- a/Angle8.h +++ b/Angle8.h @@ -1,29 +1,29 @@ -#include "AngleUsing.h" +// #include "AngleUsing.h" -#include "Angle.h" #include +#include "Angle.h" namespace Passer { namespace LinearAlgebra { -typedef AngleUsing Angle8; +typedef AngleOf Angle8; -template <> Angle8::AngleUsing(float angle) { - if (!isfinite(angle)) { - value = 0; - return; - } +// template <> Angle8::AngleOf(float angle) { +// if (!isfinite(angle)) { +// value = 0; +// return; +// } - // map float [-180..180) to integer [-128..127] - float f = angle / 360.0F; - this->value = (signed char)(f * 256.0F); -} +// // map float [-180..180) to integer [-128..127] +// float f = angle / 360.0F; +// this->value = (signed char)(f * 256.0F); +// } -template <> float Angle8::ToFloat() const { - float f = (this->value * 180) / 128.0F; - return f; -} +// template <> float Angle8::ToFloat() const { +// float f = (this->value * 180) / 128.0F; +// return f; +// } -} // namespace LinearAlgebra -} // namespace Passer +} // namespace LinearAlgebra +} // namespace Passer using namespace Passer::LinearAlgebra; \ No newline at end of file diff --git a/AngleUsing.h b/AngleUsing.h index 7afe51d..f2bc80e 100644 --- a/AngleUsing.h +++ b/AngleUsing.h @@ -1,3 +1,4 @@ +/* #ifndef DISCRETEANGLE_H #define DISCRETEANGLE_H @@ -9,8 +10,9 @@ namespace LinearAlgebra { // A fixed angle between (-180..180] -template class AngleUsing { -public: +template +class AngleUsing { + public: AngleUsing(T sourceValue) { this->value = sourceValue; } AngleUsing(float f); float ToFloat() const; @@ -42,8 +44,9 @@ public: T value; }; -} // namespace LinearAlgebra -} // namespace Passer +} // namespace LinearAlgebra +} // namespace Passer using namespace Passer::LinearAlgebra; #endif +*/ \ No newline at end of file diff --git a/Polar.cpp b/Polar.cpp index 2be9547..8bebaf1 100644 --- a/Polar.cpp +++ b/Polar.cpp @@ -37,11 +37,11 @@ const Polar Polar::back = Polar(1.0, 180.0f); const Polar Polar::right = Polar(1.0, 90.0f); const Polar Polar::left = Polar(1.0, -90.0f); -bool Polar::operator==(const Polar &v) const { +bool Polar::operator==(const Polar& v) const { return (this->distance == v.distance && this->angle == v.angle); } -Polar Polar::Normalize(const Polar &v) { +Polar Polar::Normalize(const Polar& v) { Polar r = Polar(1, v.angle); return r; } @@ -55,15 +55,15 @@ Polar Polar::operator-() const { return v; } -Polar Polar::operator-(const Polar &v) const { +Polar Polar::operator-(const Polar& v) const { Polar r = -v; return *this + r; } -Polar Polar::operator-=(const Polar &v) { +Polar Polar::operator-=(const Polar& v) { *this = *this - v; return *this; } -Polar Polar::operator+(const Polar &v) const { +Polar Polar::operator+(const Polar& v) const { if (v.distance == 0) return Polar(this->distance, this->angle); if (this->distance == 0.0f) @@ -89,39 +89,39 @@ Polar Polar::operator+(const Polar &v) const { Polar vector = Polar(newDistance, newAngle); return vector; } -Polar Polar::operator+=(const Polar &v) { +Polar Polar::operator+=(const Polar& v) { *this = *this + v; return *this; } -Polar Passer::LinearAlgebra::operator*(const Polar &v, float f) { - return Polar(v.distance * f, v.angle); -} -Polar Passer::LinearAlgebra::operator*(float f, const Polar &v) { - return Polar(v.distance * f, v.angle); -} +// Polar Passer::LinearAlgebra::operator*(const Polar &v, float f) { +// return Polar(v.distance * f, v.angle); +// } +// Polar Passer::LinearAlgebra::operator*(float f, const Polar &v) { +// return Polar(v.distance * f, v.angle); +// } Polar Polar::operator*=(float f) { this->distance *= f; return *this; } -Polar Passer::LinearAlgebra::operator/(const Polar &v, float f) { - return Polar(v.distance / f, v.angle); -} -Polar Passer::LinearAlgebra::operator/(float f, const Polar &v) { - return Polar(v.distance / f, v.angle); -} +// Polar Passer::LinearAlgebra::operator/(const Polar& v, float f) { +// return Polar(v.distance / f, v.angle); +// } +// Polar Passer::LinearAlgebra::operator/(float f, const Polar& v) { +// return Polar(v.distance / f, v.angle); +// } Polar Polar::operator/=(float f) { this->distance /= f; return *this; } -float Polar::Distance(const Polar &v1, const Polar &v2) { +float Polar::Distance(const Polar& v1, const Polar& v2) { float d = Angle::CosineRuleSide(v1.distance, v2.distance, (float)v2.angle - (float)v1.angle); return d; } -Polar Polar::Rotate(const Polar &v, Angle angle) { +Polar Polar::Rotate(const Polar& v, Angle angle) { Angle a = Angle::Normalize(v.angle + angle); Polar r = Polar(v.distance, a); return r; diff --git a/Polar.h b/Polar.h index ec9a2c7..d6eb5ff 100644 --- a/Polar.h +++ b/Polar.h @@ -17,7 +17,7 @@ struct Spherical; /// @details This will use the polar coordinate system consisting of a angle /// from a reference direction and a distance. struct Polar { -public: + public: /// @brief The distance in meters /// @remark The distance shall never be negative float distance; @@ -59,12 +59,12 @@ public: /// @return true: if it is identical to the given vector /// @note This uses float comparison to check equality which may have /// strange effects. Equality on floats should be avoided. - bool operator==(const Polar &v) const; + bool operator==(const Polar& v) const; /// @brief The vector length /// @param v The vector for which you need the length /// @return The vector length; - inline static float Magnitude(const Polar &v) { return v.distance; } + inline static float Magnitude(const Polar& v) { return v.distance; } /// @brief The vector length /// @return The vector length inline float magnitude() const { return this->distance; } @@ -72,7 +72,7 @@ public: /// @brief Convert the vector to a length of 1 /// @param v The vector to convert /// @return The vector normalized to a length of 1 - static Polar Normalize(const Polar &v); + static Polar Normalize(const Polar& v); /// @brief Convert the vector to a length of a /// @return The vector normalized to a length of 1 Polar normalized() const; @@ -85,45 +85,53 @@ public: /// @brief Subtract a polar vector from this vector /// @param v The vector to subtract /// @return The result of the subtraction - Polar operator-(const Polar &v) const; - Polar operator-=(const Polar &v); + Polar operator-(const Polar& v) const; + Polar operator-=(const Polar& v); /// @brief Add a polar vector to this vector /// @param v The vector to add /// @return The result of the addition - Polar operator+(const Polar &v) const; - Polar operator+=(const Polar &v); + Polar operator+(const Polar& v) const; + Polar operator+=(const Polar& v); /// @brief Scale the vector uniformly up /// @param f The scaling factor /// @return The scaled vector /// @remark This operation will scale the distance of the vector. The angle /// will be unaffected. - friend Polar operator*(const Polar &v, float f); - friend Polar operator*(float f, const Polar &v); + friend Polar operator*(const Polar& v, float f) { + return Polar(v.distance * f, v.angle); + } + friend Polar operator*(float f, const Polar& v) { + return Polar(f * v.distance, v.angle); + } Polar operator*=(float f); /// @brief Scale the vector uniformly down /// @param f The scaling factor /// @return The scaled factor /// @remark This operation will scale the distance of the vector. The angle /// will be unaffected. - friend Polar operator/(const Polar &v, float f); - friend Polar operator/(float f, const Polar &v); + friend Polar operator/(const Polar& v, float f) { + return Polar(v.distance / f, v.angle); + } + friend Polar operator/(float f, const Polar& v) { + return Polar(f / v.distance, v.angle); + } Polar operator/=(float f); /// @brief The distance between two vectors /// @param v1 The first vector /// @param v2 The second vector /// @return The distance between the two vectors - static float Distance(const Polar &v1, const Polar &v2); + static float Distance(const Polar& v1, const Polar& v2); /// @brief Rotate a vector /// @param v The vector to rotate /// @param a The angle in degreesto rotate /// @return The rotated vector - static Polar Rotate(const Polar &v, Angle a); + static Polar Rotate(const Polar& v, Angle a); }; -} // namespace LinearAlgebra -} // namespace Passer +} // namespace LinearAlgebra +} // namespace Passer using namespace Passer::LinearAlgebra; #include "Spherical.h" diff --git a/Spherical.cpp b/Spherical.cpp index b09fda0..860b621 100644 --- a/Spherical.cpp +++ b/Spherical.cpp @@ -17,7 +17,8 @@ Spherical::Spherical(Polar polar) { this->verticalAngle = 0.0f; } -Spherical::Spherical(float distance, Angle horizontalAngle, +Spherical::Spherical(float distance, + Angle horizontalAngle, Angle verticalAngle) { if (distance < 0) { this->distance = -distance; @@ -50,13 +51,13 @@ const Spherical Spherical::left = Spherical(1.0f, -90.0f, 0.0f); const Spherical Spherical::up = Spherical(1.0f, 0.0f, 90.0f); const Spherical Spherical::down = Spherical(1.0f, 0.0f, -90.0f); -bool Spherical::operator==(const Spherical &v) const { +bool Spherical::operator==(const Spherical& v) const { return (this->distance == v.distance && this->horizontalAngle == v.horizontalAngle && this->verticalAngle == v.verticalAngle); } -Spherical Spherical::Normalize(const Spherical &v) { +Spherical Spherical::Normalize(const Spherical& v) { Spherical r = Spherical(1, v.horizontalAngle, v.verticalAngle); return r; } @@ -71,7 +72,7 @@ Spherical Spherical::operator-() const { return v; } -Spherical Spherical::operator-(const Spherical &s2) const { +Spherical Spherical::operator-(const Spherical& s2) const { // let's do it the easy way... Vector3 v1 = Vector3(*this); Vector3 v2 = Vector3(s2); @@ -79,12 +80,12 @@ Spherical Spherical::operator-(const Spherical &s2) const { Spherical r = Spherical(v); return r; } -Spherical Spherical::operator-=(const Spherical &v) { +Spherical Spherical::operator-=(const Spherical& v) { *this = *this - v; return *this; } -Spherical Spherical::operator+(const Spherical &s2) const { +Spherical Spherical::operator+(const Spherical& s2) const { // let's do it the easy way... Vector3 v1 = Vector3(*this); Vector3 v2 = Vector3(s2); @@ -138,28 +139,28 @@ Spherical Spherical::operator+(const Spherical &s2) const { Spherical v = Spherical(newDistance, newHorizontalAngle, newVerticalAngle); */ } -Spherical Spherical::operator+=(const Spherical &v) { +Spherical Spherical::operator+=(const Spherical& v) { *this = *this + v; return *this; } -Spherical Passer::LinearAlgebra::operator*(const Spherical &v, float f) { - return Spherical(v.distance * f, v.horizontalAngle, v.verticalAngle); -} -Spherical Passer::LinearAlgebra::operator*(float f, const Spherical &v) { - return Spherical(v.distance * f, v.horizontalAngle, v.verticalAngle); -} +// Spherical Passer::LinearAlgebra::operator*(const Spherical &v, float f) { +// return Spherical(v.distance * f, v.horizontalAngle, v.verticalAngle); +// } +// Spherical Passer::LinearAlgebra::operator*(float f, const Spherical &v) { +// return Spherical(v.distance * f, v.horizontalAngle, v.verticalAngle); +// } Spherical Spherical::operator*=(float f) { this->distance *= f; return *this; } -Spherical Passer::LinearAlgebra::operator/(const Spherical &v, float f) { - return Spherical(v.distance / f, v.horizontalAngle, v.verticalAngle); -} -Spherical Passer::LinearAlgebra::operator/(float f, const Spherical &v) { - return Spherical(v.distance / f, v.horizontalAngle, v.verticalAngle); -} +// Spherical Passer::LinearAlgebra::operator/(const Spherical &v, float f) { +// return Spherical(v.distance / f, v.horizontalAngle, v.verticalAngle); +// } +// Spherical Passer::LinearAlgebra::operator/(float f, const Spherical &v) { +// return Spherical(v.distance / f, v.horizontalAngle, v.verticalAngle); +// } Spherical Spherical::operator/=(float f) { this->distance /= f; return *this; @@ -183,12 +184,11 @@ Spherical Spherical::operator/=(float f) { const float epsilon = 1E-05f; const float Rad2Deg = 57.29578F; -Angle Spherical::AngleBetween(const Spherical &v1, const Spherical &v2) { - +Angle Spherical::AngleBetween(const Spherical& v1, const Spherical& v2) { // float denominator = sqrtf(v1_3.sqrMagnitude() * v2_3.sqrMagnitude()); float denominator = - v1.distance * v2.distance; // sqrtf(v1.distance * v1.distance * - // v2.distance * v2.distance); + v1.distance * v2.distance; // sqrtf(v1.distance * v1.distance * + // v2.distance * v2.distance); if (denominator < epsilon) return 0; @@ -197,24 +197,25 @@ Angle Spherical::AngleBetween(const Spherical &v1, const Spherical &v2) { float dot = Vector3::Dot(v1_3, v2_3); float fraction = dot / denominator; if (isnan(fraction)) - return fraction; // short cut to returning NaN universally + return fraction; // short cut to returning NaN universally float cdot = Float::Clamp(fraction, -1.0, 1.0); float r = ((float)acos(cdot)) * Rad2Deg; return r; } -Spherical Spherical::Rotate(const Spherical &v, Angle horizontalAngle, +Spherical Spherical::Rotate(const Spherical& v, + Angle horizontalAngle, Angle verticalAngle) { Spherical r = Spherical(v.distance, v.horizontalAngle + horizontalAngle, v.verticalAngle + verticalAngle); return r; } -Spherical Spherical::RotateHorizontal(const Spherical &v, Angle a) { +Spherical Spherical::RotateHorizontal(const Spherical& v, Angle a) { Spherical r = Spherical(v.distance, v.horizontalAngle + a, v.verticalAngle); return r; } -Spherical Spherical::RotateVertical(const Spherical &v, Angle a) { +Spherical Spherical::RotateVertical(const Spherical& v, Angle a) { Spherical r = Spherical(v.distance, v.horizontalAngle, v.verticalAngle + a); return r; } \ No newline at end of file diff --git a/Spherical.h b/Spherical.h index 4e285e3..112f5e0 100644 --- a/Spherical.h +++ b/Spherical.h @@ -19,7 +19,7 @@ struct Vector3; /// reference direction. The reference direction is typically thought of /// as a forward direction. struct Spherical { -public: + public: /// @brief The distance in meters /// @remark The distance should never be negative float distance; @@ -66,12 +66,12 @@ public: /// @return true: if it is identical to the given vector /// @note This uses float comparison to check equality which may have strange /// effects. Equality on floats should be avoided. - bool operator==(const Spherical &v) const; + bool operator==(const Spherical& v) const; /// @brief The vector length /// @param v The vector for which you need the length /// @return The vector length; - inline static float Magnitude(const Spherical &v) { return v.distance; } + inline static float Magnitude(const Spherical& v) { return v.distance; } /// @brief The vector length /// @return The vector length inline float magnitude() const { return this->distance; } @@ -79,7 +79,7 @@ public: /// @brief Convert the vector to a length of 1 /// @param v The vector to convert /// @return The vector normalized to a length of 1 - static Spherical Normalize(const Spherical &v); + static Spherical Normalize(const Spherical& v); /// @brief Convert the vector to a length of a /// @return The vector normalized to a length of 1 Spherical normalized() const; @@ -93,29 +93,39 @@ public: /// @brief Subtract a spherical vector from this vector /// @param v The vector to subtract /// @return The result of the subtraction - Spherical operator-(const Spherical &v) const; - Spherical operator-=(const Spherical &v); + Spherical operator-(const Spherical& v) const; + Spherical operator-=(const Spherical& v); /// @brief Add a spherical vector to this vector /// @param v The vector to add /// @return The result of the addition - Spherical operator+(const Spherical &v) const; - Spherical operator+=(const Spherical &v); + Spherical operator+(const Spherical& v) const; + Spherical operator+=(const Spherical& v); /// @brief Scale the vector uniformly up /// @param f The scaling factor /// @return The scaled vector /// @remark This operation will scale the distance of the vector. The angle /// will be unaffected. - friend Spherical operator*(const Spherical &v, float f); - friend Spherical operator*(float f, const Spherical &v); + friend Spherical operator*(const Spherical& v, float f) { + return Spherical(v.distance * f, v.horizontalAngle, v.verticalAngle); + } + friend Spherical operator*(float f, const Spherical& v) { + return Spherical(v.distance * f, v.horizontalAngle, + v.verticalAngle); // not correct, should be f * v.distance + } Spherical operator*=(float f); /// @brief Scale the vector uniformly down /// @param f The scaling factor /// @return The scaled factor /// @remark This operation will scale the distance of the vector. The angle /// will be unaffected. - friend Spherical operator/(const Spherical &v, float f); - friend Spherical operator/(float f, const Spherical &v); + friend Spherical operator/(const Spherical& v, float f) { + return Spherical(v.distance / f, v.horizontalAngle, v.verticalAngle); + } + friend Spherical operator/(float f, const Spherical& v) { + return Spherical(v.distance / f, v.horizontalAngle, + v.verticalAngle); // not correct, should be f / v.distance + } Spherical operator/=(float f); /// @@ -126,16 +136,17 @@ public: /// The distance between the two vectors // static float Distance(const Spherical &s1, const Spherical &s2); - static Angle AngleBetween(const Spherical &v1, const Spherical &v2); + static Angle AngleBetween(const Spherical& v1, const Spherical& v2); - static Spherical Rotate(const Spherical &v, Angle horizontalAngle, + static Spherical Rotate(const Spherical& v, + Angle horizontalAngle, Angle verticalAngle); - static Spherical RotateHorizontal(const Spherical &v, Angle angle); - static Spherical RotateVertical(const Spherical &v, Angle angle); + static Spherical RotateHorizontal(const Spherical& v, Angle angle); + static Spherical RotateVertical(const Spherical& v, Angle angle); }; -} // namespace LinearAlgebra -} // namespace Passer +} // namespace LinearAlgebra +} // namespace Passer using namespace Passer::LinearAlgebra; #include "Vector3.h" diff --git a/Vector2.cpp b/Vector2.cpp index 9c94fae..a7ded06 100644 --- a/Vector2.cpp +++ b/Vector2.cpp @@ -26,8 +26,8 @@ Vector2::Vector2(float _x, float _y) { // y = v.y; // } Vector2::Vector2(Vector3 v) { - x = v.Right(); // x; - y = v.Forward(); // z; + x = v.Right(); // x; + y = v.Forward(); // z; } Vector2::Vector2(Polar p) { float horizontalRad = p.angle * Angle::Deg2Rad; @@ -49,18 +49,24 @@ const Vector2 Vector2::down = Vector2(0, -1); const Vector2 Vector2::forward = Vector2(0, 1); const Vector2 Vector2::back = Vector2(0, -1); -bool Vector2::operator==(const Vector2 &v) { +bool Vector2::operator==(const Vector2& v) { return (this->x == v.x && this->y == v.y); } -float Vector2::Magnitude(const Vector2 &v) { +float Vector2::Magnitude(const Vector2& v) { return sqrtf(v.x * v.x + v.y * v.y); } -float Vector2::magnitude() const { return (float)sqrtf(x * x + y * y); } -float Vector2::SqrMagnitude(const Vector2 &v) { return v.x * v.x + v.y * v.y; } -float Vector2::sqrMagnitude() const { return (x * x + y * y); } +float Vector2::magnitude() const { + return (float)sqrtf(x * x + y * y); +} +float Vector2::SqrMagnitude(const Vector2& v) { + return v.x * v.x + v.y * v.y; +} +float Vector2::sqrMagnitude() const { + return (x * x + y * y); +} -Vector2 Vector2::Normalize(const Vector2 &v) { +Vector2 Vector2::Normalize(const Vector2& v) { float num = Vector2::Magnitude(v); Vector2 result = Vector2::zero; if (num > Float::epsilon) { @@ -77,63 +83,65 @@ Vector2 Vector2::normalized() const { return result; } -Vector2 Vector2::operator-() { return Vector2(-this->x, -this->y); } +Vector2 Vector2::operator-() { + return Vector2(-this->x, -this->y); +} -Vector2 Vector2::operator-(const Vector2 &v) const { +Vector2 Vector2::operator-(const Vector2& v) const { return Vector2(this->x - v.x, this->y - v.y); } -Vector2 Vector2::operator-=(const Vector2 &v) { +Vector2 Vector2::operator-=(const Vector2& v) { this->x -= v.x; this->y -= v.y; return *this; } -Vector2 Vector2::operator+(const Vector2 &v) const { +Vector2 Vector2::operator+(const Vector2& v) const { return Vector2(this->x + v.x, this->y + v.y); } -Vector2 Vector2::operator+=(const Vector2 &v) { +Vector2 Vector2::operator+=(const Vector2& v) { this->x += v.x; this->y += v.y; return *this; } -Vector2 Vector2::Scale(const Vector2 &v1, const Vector2 &v2) { +Vector2 Vector2::Scale(const Vector2& v1, const Vector2& v2) { return Vector2(v1.x * v2.x, v1.y * v2.y); } -Vector2 Passer::LinearAlgebra::operator*(const Vector2 &v, float f) { - return Vector2(v.x * f, v.y * f); -} -Vector2 Passer::LinearAlgebra::operator*(float f, const Vector2 &v) { - return Vector2(v.x * f, v.y * f); -} +// Vector2 Passer::LinearAlgebra::operator*(const Vector2 &v, float f) { +// return Vector2(v.x * f, v.y * f); +// } +// Vector2 Passer::LinearAlgebra::operator*(float f, const Vector2 &v) { +// return Vector2(v.x * f, v.y * f); +// } Vector2 Vector2::operator*=(float f) { this->x *= f; this->y *= f; return *this; } -Vector2 Passer::LinearAlgebra::operator/(const Vector2 &v, float f) { - return Vector2(v.x / f, v.y / f); -} -Vector2 Passer::LinearAlgebra::operator/(float f, const Vector2 &v) { - return Vector2(v.x / f, v.y / f); -} +// Vector2 Passer::LinearAlgebra::operator/(const Vector2 &v, float f) { +// return Vector2(v.x / f, v.y / f); +// } +// Vector2 Passer::LinearAlgebra::operator/(float f, const Vector2 &v) { +// return Vector2(v.x / f, v.y / f); +// } Vector2 Vector2::operator/=(float f) { this->x /= f; this->y /= f; return *this; } -float Vector2::Dot(const Vector2 &v1, const Vector2 &v2) { +float Vector2::Dot(const Vector2& v1, const Vector2& v2) { return v1.x * v2.x + v1.y * v2.y; } -float Vector2::Distance(const Vector2 &v1, const Vector2 &v2) { +float Vector2::Distance(const Vector2& v1, const Vector2& v2) { return Magnitude(v1 - v2); } -float Vector2::Angle(const Vector2 &v1, const Vector2 &v2) { +float Vector2::Angle(const Vector2& v1, const Vector2& v2) { return (float)fabs(SignedAngle(v1, v2)); } -float Vector2::SignedAngle(const Vector2 &v1, const Vector2 &v2) { +float Vector2::SignedAngle(const Vector2& v1, const Vector2& v2) { float sqrMagFrom = v1.sqrMagnitude(); float sqrMagTo = v2.sqrMagnitude(); @@ -151,11 +159,11 @@ float Vector2::SignedAngle(const Vector2 &v1, const Vector2 &v2) { return -(angleTo - angleFrom) * Angle::Rad2Deg; } -Vector2 Vector2::Rotate(const Vector2 &v, Passer::LinearAlgebra::Angle a) { +Vector2 Vector2::Rotate(const Vector2& v, Passer::LinearAlgebra::Angle a) { float angleRad = a * Angle::Deg2Rad; #if defined(AVR) float sinValue = sin(angleRad); - float cosValue = cos(angleRad); // * Angle::Deg2Rad); + float cosValue = cos(angleRad); // * Angle::Deg2Rad); #else float sinValue = (float)sinf(angleRad); float cosValue = (float)cosf(angleRad); @@ -168,7 +176,7 @@ Vector2 Vector2::Rotate(const Vector2 &v, Passer::LinearAlgebra::Angle a) { return r; } -Vector2 Vector2::Lerp(const Vector2 &v1, const Vector2 &v2, float f) { +Vector2 Vector2::Lerp(const Vector2& v1, const Vector2& v2, float f) { Vector2 v = v1 + (v2 - v1) * f; return v; } diff --git a/Vector2.h b/Vector2.h index aeca26b..97d6c79 100644 --- a/Vector2.h +++ b/Vector2.h @@ -38,7 +38,7 @@ struct Polar; struct Vector2 : Vec2 { friend struct Vec2; -public: + public: /// @brief A new 2-dimensional zero vector Vector2(); /// @brief A new 2-dimensional vector @@ -80,12 +80,12 @@ public: /// @return true if it is identical to the given vector /// @note This uses float comparison to check equality which may have strange /// effects. Equality on floats should be avoided. - bool operator==(const Vector2 &v); + bool operator==(const Vector2& v); /// @brief The vector length /// @param v The vector for which you need the length /// @return The vector length - static float Magnitude(const Vector2 &v); + static float Magnitude(const Vector2& v); /// @brief The vector length /// @return The vector length float magnitude() const; @@ -95,7 +95,7 @@ public: /// @remark The squared length is computationally simpler than the real /// length. Think of Pythagoras A^2 + B^2 = C^2. This prevents the calculation /// of the squared root of C. - static float SqrMagnitude(const Vector2 &v); + static float SqrMagnitude(const Vector2& v); /// @brief The squared vector length /// @return The squared vector length /// @remark The squared length is computationally simpler than the real @@ -106,7 +106,7 @@ public: /// @brief Convert the vector to a length of 1 /// @param v The vector to convert /// @return The vector normalized to a length of 1 - static Vector2 Normalize(const Vector2 &v); + static Vector2 Normalize(const Vector2& v); /// @brief Convert the vector to a length 1 /// @return The vector normalized to a length of 1 Vector2 normalized() const; @@ -118,13 +118,13 @@ public: /// @brief Subtract a vector from this vector /// @param v The vector to subtract from this vector /// @return The result of the subtraction - Vector2 operator-(const Vector2 &v) const; - Vector2 operator-=(const Vector2 &v); + Vector2 operator-(const Vector2& v) const; + Vector2 operator-=(const Vector2& v); /// @brief Add a vector to this vector /// @param v The vector to add to this vector /// @return The result of the addition - Vector2 operator+(const Vector2 &v) const; - Vector2 operator+=(const Vector2 &v); + Vector2 operator+(const Vector2& v) const; + Vector2 operator+=(const Vector2& v); /// @brief Scale the vector using another vector /// @param v1 The vector to scale @@ -132,34 +132,39 @@ public: /// @return The scaled vector /// @remark Each component of the vector v1 will be multiplied with the /// matching component from the scaling vector v2. - static Vector2 Scale(const Vector2 &v1, const Vector2 &v2); + static Vector2 Scale(const Vector2& v1, const Vector2& v2); /// @brief Scale the vector uniformly up /// @param f The scaling factor /// @return The scaled vector /// @remark Each component of the vector will be multipled with the same /// factor f. - friend Vector2 operator*(const Vector2 &v, float f); - friend Vector2 operator*(float f, const Vector2 &v); + friend Vector2 operator*(const Vector2& v, float f) { + return Vector2(v.x * f, v.y * f); + } + friend Vector2 operator*(float f, const Vector2& v) { + return Vector2(v.x * f, v.y * f); + // return Vector2(f * v.x, f * v.y); + } Vector2 operator*=(float f); /// @brief Scale the vector uniformly down /// @param f The scaling factor /// @return The scaled vector /// @remark Each componet of the vector will be divided by the same factor. - friend Vector2 operator/(const Vector2 &v, float f); - friend Vector2 operator/(float f, const Vector2 &v); + friend Vector2 operator/(const Vector2& v, float f); + friend Vector2 operator/(float f, const Vector2& v); Vector2 operator/=(float f); /// @brief The dot product of two vectors /// @param v1 The first vector /// @param v2 The second vector /// @return The dot product of the two vectors - static float Dot(const Vector2 &v1, const Vector2 &v2); + static float Dot(const Vector2& v1, const Vector2& v2); /// @brief The distance between two vectors /// @param v1 The first vector /// @param v2 The second vector /// @return The distance between the two vectors - static float Distance(const Vector2 &v1, const Vector2 &v2); + static float Distance(const Vector2& v1, const Vector2& v2); /// @brief The angle between two vectors /// @param v1 The first vector @@ -168,18 +173,18 @@ public: /// @remark This reterns an unsigned angle which is the shortest distance /// between the two vectors. Use Vector2::SignedAngle if a signed angle is /// needed. - static float Angle(const Vector2 &v1, const Vector2 &v2); + static float Angle(const Vector2& v1, const Vector2& v2); /// @brief The signed angle between two vectors /// @param v1 The starting vector /// @param v2 The ending vector /// @return The signed angle between the two vectors - static float SignedAngle(const Vector2 &v1, const Vector2 &v2); + static float SignedAngle(const Vector2& v1, const Vector2& v2); /// @brief Rotate the vector /// @param v The vector to rotate /// @param a The angle in degrees to rotate /// @return The rotated vector - static Vector2 Rotate(const Vector2 &v, Passer::LinearAlgebra::Angle a); + static Vector2 Rotate(const Vector2& v, Passer::LinearAlgebra::Angle a); /// @brief Lerp (linear interpolation) between two vectors /// @param v1 The starting vector @@ -189,11 +194,11 @@ public: /// @remark The factor f is unclamped. Value 0 matches the vector *v1*, Value /// 1 matches vector *v2*. Value -1 is vector *v1* minus the difference /// between *v1* and *v2* etc. - static Vector2 Lerp(const Vector2 &v1, const Vector2 &v2, float f); + static Vector2 Lerp(const Vector2& v1, const Vector2& v2, float f); }; -} // namespace LinearAlgebra -} // namespace Passer +} // namespace LinearAlgebra +} // namespace Passer using namespace Passer::LinearAlgebra; #include "Polar.h" diff --git a/Vector3.cpp b/Vector3.cpp index da894f8..50829d7 100644 --- a/Vector3.cpp +++ b/Vector3.cpp @@ -65,17 +65,21 @@ const Vector3 Vector3::back = Vector3(0, 0, -1); // return Vector3(v.x, 0, v.y); // } -float Vector3::Magnitude(const Vector3 &v) { +float Vector3::Magnitude(const Vector3& v) { return sqrtf(v.x * v.x + v.y * v.y + v.z * v.z); } -float Vector3::magnitude() const { return (float)sqrtf(x * x + y * y + z * z); } +float Vector3::magnitude() const { + return (float)sqrtf(x * x + y * y + z * z); +} -float Vector3::SqrMagnitude(const Vector3 &v) { +float Vector3::SqrMagnitude(const Vector3& v) { return v.x * v.x + v.y * v.y + v.z * v.z; } -float Vector3::sqrMagnitude() const { return (x * x + y * y + z * z); } +float Vector3::sqrMagnitude() const { + return (x * x + y * y + z * z); +} -Vector3 Vector3::Normalize(const Vector3 &v) { +Vector3 Vector3::Normalize(const Vector3& v) { float num = Vector3::Magnitude(v); Vector3 result = Vector3::zero; if (num > epsilon) { @@ -96,46 +100,46 @@ Vector3 Vector3::operator-() const { return Vector3(-this->x, -this->y, -this->z); } -Vector3 Vector3::operator-(const Vector3 &v) const { +Vector3 Vector3::operator-(const Vector3& v) const { return Vector3(this->x - v.x, this->y - v.y, this->z - v.z); } -Vector3 Vector3::operator-=(const Vector3 &v) { +Vector3 Vector3::operator-=(const Vector3& v) { this->x -= v.x; this->y -= v.y; this->z -= v.z; return *this; } -Vector3 Vector3::operator+(const Vector3 &v) const { +Vector3 Vector3::operator+(const Vector3& v) const { return Vector3(this->x + v.x, this->y + v.y, this->z + v.z); } -Vector3 Vector3::operator+=(const Vector3 &v) { +Vector3 Vector3::operator+=(const Vector3& v) { this->x += v.x; this->y += v.y; this->z += v.z; return *this; } -Vector3 Vector3::Scale(const Vector3 &v1, const Vector3 &v2) { +Vector3 Vector3::Scale(const Vector3& v1, const Vector3& v2) { return Vector3(v1.x * v2.x, v1.y * v2.y, v1.z * v2.z); } -Vector3 Passer::LinearAlgebra::operator*(const Vector3 &v, float f) { - return Vector3(v.x * f, v.y * f, v.z * f); -} -Vector3 Passer::LinearAlgebra::operator*(float f, const Vector3 &v) { - return Vector3(v.x * f, v.y * f, v.z * f); -} +// Vector3 Passer::LinearAlgebra::operator*(const Vector3 &v, float f) { +// return Vector3(v.x * f, v.y * f, v.z * f); +// } +// Vector3 Passer::LinearAlgebra::operator*(float f, const Vector3 &v) { +// return Vector3(v.x * f, v.y * f, v.z * f); +// } Vector3 Vector3::operator*=(float f) { this->x *= f; this->y *= f; this->z *= f; return *this; } -Vector3 Passer::LinearAlgebra::operator/(const Vector3 &v, float f) { - return Vector3(v.x / f, v.y / f, v.z / f); -} -Vector3 Passer::LinearAlgebra::operator/(float f, const Vector3 &v) { - return Vector3(v.x / f, v.y / f, v.z / f); -} +// Vector3 Passer::LinearAlgebra::operator/(const Vector3 &v, float f) { +// return Vector3(v.x / f, v.y / f, v.z / f); +// } +// Vector3 Passer::LinearAlgebra::operator/(float f, const Vector3 &v) { +// return Vector3(v.x / f, v.y / f, v.z / f); +// } Vector3 Vector3::operator/=(float f) { this->x /= f; this->y /= f; @@ -143,24 +147,24 @@ Vector3 Vector3::operator/=(float f) { return *this; } -float Vector3::Dot(const Vector3 &v1, const Vector3 &v2) { +float Vector3::Dot(const Vector3& v1, const Vector3& v2) { return v1.x * v2.x + v1.y * v2.y + v1.z * v2.z; } -bool Vector3::operator==(const Vector3 &v) { +bool Vector3::operator==(const Vector3& v) { return (this->x == v.x && this->y == v.y && this->z == v.z); } -float Vector3::Distance(const Vector3 &v1, const Vector3 &v2) { +float Vector3::Distance(const Vector3& v1, const Vector3& v2) { return Magnitude(v1 - v2); } -Vector3 Vector3::Cross(const Vector3 &v1, const Vector3 &v2) { +Vector3 Vector3::Cross(const Vector3& v1, const Vector3& v2) { return Vector3(v1.y * v2.z - v1.z * v2.y, v1.z * v2.x - v1.x * v2.z, v1.x * v2.y - v1.y * v2.x); } -Vector3 Vector3::Project(const Vector3 &v, const Vector3 &n) { +Vector3 Vector3::Project(const Vector3& v, const Vector3& n) { float sqrMagnitude = Dot(n, n); if (sqrMagnitude < epsilon) return Vector3::zero; @@ -171,7 +175,7 @@ Vector3 Vector3::Project(const Vector3 &v, const Vector3 &n) { } } -Vector3 Vector3::ProjectOnPlane(const Vector3 &v, const Vector3 &n) { +Vector3 Vector3::ProjectOnPlane(const Vector3& v, const Vector3& n) { Vector3 r = v - Project(v, n); return r; } @@ -182,7 +186,7 @@ float clamp(float x, float lower, float upper) { return upperClamp; } -float Vector3::Angle(const Vector3 &v1, const Vector3 &v2) { +float Vector3::Angle(const Vector3& v1, const Vector3& v2) { float denominator = sqrtf(v1.sqrMagnitude() * v2.sqrMagnitude()); if (denominator < epsilon) return 0; @@ -190,15 +194,16 @@ float Vector3::Angle(const Vector3 &v1, const Vector3 &v2) { float dot = Vector3::Dot(v1, v2); float fraction = dot / denominator; if (isnan(fraction)) - return fraction; // short cut to returning NaN universally + return fraction; // short cut to returning NaN universally float cdot = clamp(fraction, -1.0, 1.0); float r = ((float)acos(cdot)) * Rad2Deg; return r; } -float Vector3::SignedAngle(const Vector3 &v1, const Vector3 &v2, - const Vector3 &axis) { +float Vector3::SignedAngle(const Vector3& v1, + const Vector3& v2, + const Vector3& axis) { // angle in [0,180] float angle = Vector3::Angle(v1, v2); @@ -212,7 +217,7 @@ float Vector3::SignedAngle(const Vector3 &v1, const Vector3 &v2, return signed_angle; } -Vector3 Vector3::Lerp(const Vector3 &v1, const Vector3 &v2, float f) { +Vector3 Vector3::Lerp(const Vector3& v1, const Vector3& v2, float f) { Vector3 v = v1 + (v2 - v1) * f; return v; } diff --git a/Vector3.h b/Vector3.h index 27db549..f17eae8 100644 --- a/Vector3.h +++ b/Vector3.h @@ -19,7 +19,7 @@ extern "C" { /// This is a C-style implementation /// This uses the right-handed coordinate system. typedef struct Vec3 { -protected: + protected: /// /// The right axis of the vector /// @@ -42,7 +42,7 @@ protected: struct Vector3 : Vec3 { friend struct Vec3; -public: + public: /// @brief A new 3-dimensional zero vector Vector3(); /// @brief A new 3-dimensional vector @@ -88,12 +88,12 @@ public: /// @return true if it is identical to the given vector /// @note This uses float comparison to check equality which may have strange /// effects. Equality on floats should be avoided. - bool operator==(const Vector3 &v); + bool operator==(const Vector3& v); /// @brief The vector length /// @param v The vector for which you need the length /// @return The vector length - static float Magnitude(const Vector3 &v); + static float Magnitude(const Vector3& v); /// @brief The vector length /// @return The vector length float magnitude() const; @@ -103,7 +103,7 @@ public: /// @remark The squared length is computationally simpler than the real /// length. Think of Pythagoras A^2 + B^2 = C^2. This leaves out the /// calculation of the squared root of C. - static float SqrMagnitude(const Vector3 &v); + static float SqrMagnitude(const Vector3& v); /// @brief The squared vector length /// @return The squared vector length /// @remark The squared length is computationally simpler than the real @@ -114,7 +114,7 @@ public: /// @brief Convert the vector to a length of 1 /// @param v The vector to convert /// @return The vector normalized to a length of 1 - static Vector3 Normalize(const Vector3 &v); + static Vector3 Normalize(const Vector3& v); /// @brief Convert the vector to a length of 1 /// @return The vector normalized to a length of 1 Vector3 normalized() const; @@ -126,13 +126,13 @@ public: /// @brief Subtract a vector from this vector /// @param v The vector to subtract from this vector /// @return The result of this subtraction - Vector3 operator-(const Vector3 &v) const; - Vector3 operator-=(const Vector3 &v); + Vector3 operator-(const Vector3& v) const; + Vector3 operator-=(const Vector3& v); /// @brief Add a vector to this vector /// @param v The vector to add to this vector /// @return The result of the addition - Vector3 operator+(const Vector3 &v) const; - Vector3 operator+=(const Vector3 &v); + Vector3 operator+(const Vector3& v) const; + Vector3 operator+=(const Vector3& v); /// @brief Scale the vector using another vector /// @param v1 The vector to scale @@ -140,52 +140,62 @@ public: /// @return The scaled vector /// @remark Each component of the vector v1 will be multiplied with the /// matching component from the scaling vector v2. - static Vector3 Scale(const Vector3 &v1, const Vector3 &v2); + static Vector3 Scale(const Vector3& v1, const Vector3& v2); /// @brief Scale the vector uniformly up /// @param f The scaling factor /// @return The scaled vector /// @remark Each component of the vector will be multipled with the same /// factor f. - friend Vector3 operator*(const Vector3 &v, float f); - friend Vector3 operator*(float f, const Vector3 &v); + friend Vector3 operator*(const Vector3& v, float f) { + return Vector3(v.x * f, v.y * f, v.z * f); + } + friend Vector3 operator*(float f, const Vector3& v) { + // return Vector3(f * v.x, f * v.y, f * v.z); + return Vector3(v.x * f, v.y * f, v.z * f); + } Vector3 operator*=(float f); /// @brief Scale the vector uniformly down /// @param f The scaling factor /// @return The scaled vector /// @remark Each componet of the vector will be divided by the same factor. - friend Vector3 operator/(const Vector3 &v, float f); - friend Vector3 operator/(float f, const Vector3 &v); + friend Vector3 operator/(const Vector3& v, float f) { + return Vector3(v.x / f, v.y / f, v.z / f); + } + friend Vector3 operator/(float f, const Vector3& v) { + // return Vector3(f / v.x, f / v.y, f / v.z); + return Vector3(v.x / f, v.y / f, v.z / f); + } Vector3 operator/=(float f); /// @brief The distance between two vectors /// @param v1 The first vector /// @param v2 The second vector /// @return The distance between the two vectors - static float Distance(const Vector3 &v1, const Vector3 &v2); + static float Distance(const Vector3& v1, const Vector3& v2); /// @brief The dot product of two vectors /// @param v1 The first vector /// @param v2 The second vector /// @return The dot product of the two vectors - static float Dot(const Vector3 &v1, const Vector3 &v2); + static float Dot(const Vector3& v1, const Vector3& v2); /// @brief The cross product of two vectors /// @param v1 The first vector /// @param v2 The second vector /// @return The cross product of the two vectors - static Vector3 Cross(const Vector3 &v1, const Vector3 &v2); + static Vector3 Cross(const Vector3& v1, const Vector3& v2); /// @brief Project the vector on another vector /// @param v The vector to project /// @param n The normal vecto to project on /// @return The projected vector - static Vector3 Project(const Vector3 &v, const Vector3 &n); + static Vector3 Project(const Vector3& v, const Vector3& n); /// @brief Project the vector on a plane defined by a normal orthogonal to the /// plane. /// @param v The vector to project /// @param n The normal of the plane to project on /// @return Teh projected vector - static Vector3 ProjectOnPlane(const Vector3 &v, const Vector3 &n); + static Vector3 ProjectOnPlane(const Vector3& v, const Vector3& n); /// @brief The angle between two vectors /// @param v1 The first vector @@ -194,14 +204,15 @@ public: /// @remark This reterns an unsigned angle which is the shortest distance /// between the two vectors. Use Vector3::SignedAngle if a signed angle is /// needed. - static float Angle(const Vector3 &v1, const Vector3 &v2); + static float Angle(const Vector3& v1, const Vector3& v2); /// @brief The signed angle between two vectors /// @param v1 The starting vector /// @param v2 The ending vector /// @param axis The axis to rotate around /// @return The signed angle between the two vectors - static float SignedAngle(const Vector3 &v1, const Vector3 &v2, - const Vector3 &axis); + static float SignedAngle(const Vector3& v1, + const Vector3& v2, + const Vector3& axis); /// @brief Lerp (linear interpolation) between two vectors /// @param v1 The starting vector @@ -211,11 +222,11 @@ public: /// @remark The factor f is unclamped. Value 0 matches the vector *v1*, Value /// 1 matches vector *v2*. Value -1 is vector *v1* minus the difference /// between *v1* and *v2* etc. - static Vector3 Lerp(const Vector3 &v1, const Vector3 &v2, float f); + static Vector3 Lerp(const Vector3& v1, const Vector3& v2, float f); }; -} // namespace LinearAlgebra -} // namespace Passer +} // namespace LinearAlgebra +} // namespace Passer using namespace Passer::LinearAlgebra; #include "Spherical.h"