Add finite check for normalize() in vector classes
This commit is contained in:
+2
-1
@@ -54,7 +54,8 @@ void Basis::invert() {
|
||||
}
|
||||
|
||||
void Basis::orthonormalize() {
|
||||
// Gram-Schmidt Process
|
||||
// Orthonormalizable check is done in Vector3 class below.
|
||||
// Gram-Schmidt Process:
|
||||
|
||||
Vector3 x = get_column(0);
|
||||
Vector3 y = get_column(1);
|
||||
|
||||
+7
-1
@@ -38,9 +38,15 @@ void Plane::set_normal(const Vector3 &p_normal) {
|
||||
}
|
||||
|
||||
void Plane::normalize() {
|
||||
#ifdef MATH_CHECKS
|
||||
if (!is_finite()) {
|
||||
WARN_PRINT("Plane cannot be normalized, the distance and the normal should be finite.");
|
||||
}
|
||||
#endif // MATH_CHECKS
|
||||
|
||||
real_t l = normal.length();
|
||||
if (l == 0) {
|
||||
*this = Plane(0, 0, 0, 0);
|
||||
zero();
|
||||
return;
|
||||
}
|
||||
normal /= l;
|
||||
|
||||
@@ -45,6 +45,11 @@ struct [[nodiscard]] Plane {
|
||||
void set_normal(const Vector3 &p_normal);
|
||||
_FORCE_INLINE_ Vector3 get_normal() const { return normal; }
|
||||
|
||||
void zero() {
|
||||
normal.zero();
|
||||
d = 0;
|
||||
}
|
||||
|
||||
void normalize();
|
||||
Plane normalized() const;
|
||||
|
||||
|
||||
@@ -63,6 +63,11 @@ real_t Quaternion::length() const {
|
||||
}
|
||||
|
||||
void Quaternion::normalize() {
|
||||
#ifdef MATH_CHECKS
|
||||
if (!is_finite()) {
|
||||
WARN_PRINT("Quaternion cannot be normalized, the elements should be finite.");
|
||||
}
|
||||
#endif // MATH_CHECKS
|
||||
*this /= length();
|
||||
}
|
||||
|
||||
|
||||
@@ -145,7 +145,8 @@ void Transform2D::translate_local(const Vector2 &p_translation) {
|
||||
}
|
||||
|
||||
void Transform2D::orthonormalize() {
|
||||
// Gram-Schmidt Process
|
||||
// Orthonormalizable check is done in Vector2 class below.
|
||||
// Gram-Schmidt Process:
|
||||
|
||||
Vector2 x = columns[0];
|
||||
Vector2 y = columns[1];
|
||||
|
||||
@@ -150,6 +150,7 @@ Transform3D Transform3D::translated_local(const Vector3 &p_translation) const {
|
||||
}
|
||||
|
||||
void Transform3D::orthonormalize() {
|
||||
// Orthonormalizable check is done in Basis class below.
|
||||
basis.orthonormalize();
|
||||
}
|
||||
|
||||
|
||||
+12
-2
@@ -50,8 +50,18 @@ real_t Vector2::length_squared() const {
|
||||
}
|
||||
|
||||
void Vector2::normalize() {
|
||||
real_t l = x * x + y * y;
|
||||
if (l != 0) {
|
||||
if (!is_finite()) {
|
||||
#ifdef MATH_CHECKS
|
||||
WARN_PRINT("Vector2 cannot be normalized, the elements must be finite. Making (0, 0) as a fallback.");
|
||||
#endif // MATH_CHECKS
|
||||
zero();
|
||||
return;
|
||||
}
|
||||
|
||||
real_t l = length_squared();
|
||||
if (l == 0) {
|
||||
zero();
|
||||
} else {
|
||||
l = Math::sqrt(l);
|
||||
x /= l;
|
||||
y /= l;
|
||||
|
||||
@@ -91,6 +91,8 @@ struct [[nodiscard]] Vector2 {
|
||||
real_t length_squared() const;
|
||||
Vector2 limit_length(real_t p_len = 1.0) const;
|
||||
|
||||
void zero() { x = y = 0; }
|
||||
|
||||
Vector2 min(const Vector2 &p_vector2) const {
|
||||
return Vector2(MIN(x, p_vector2.x), MIN(y, p_vector2.y));
|
||||
}
|
||||
|
||||
+15
-7
@@ -546,14 +546,22 @@ real_t Vector3::length_squared() const {
|
||||
}
|
||||
|
||||
void Vector3::normalize() {
|
||||
real_t lengthsq = length_squared();
|
||||
if (lengthsq == 0) {
|
||||
x = y = z = 0;
|
||||
if (!is_finite()) {
|
||||
#ifdef MATH_CHECKS
|
||||
WARN_PRINT("Vector3 cannot be normalized, the elements must be finite. Making (0, 0, 0) as a fallback.");
|
||||
#endif // MATH_CHECKS
|
||||
zero();
|
||||
return;
|
||||
}
|
||||
|
||||
real_t l = length_squared();
|
||||
if (l == 0) {
|
||||
zero();
|
||||
} else {
|
||||
real_t length = Math::sqrt(lengthsq);
|
||||
x /= length;
|
||||
y /= length;
|
||||
z /= length;
|
||||
l = Math::sqrt(l);
|
||||
x /= l;
|
||||
y /= l;
|
||||
z /= l;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+16
-8
@@ -79,15 +79,23 @@ real_t Vector4::length() const {
|
||||
}
|
||||
|
||||
void Vector4::normalize() {
|
||||
real_t lengthsq = length_squared();
|
||||
if (lengthsq == 0) {
|
||||
x = y = z = w = 0;
|
||||
if (!is_finite()) {
|
||||
#ifdef MATH_CHECKS
|
||||
WARN_PRINT("Vector4 cannot be normalized, the elements must be finite. Making (0, 0, 0, 0) as a fallback.");
|
||||
#endif // MATH_CHECKS
|
||||
zero();
|
||||
return;
|
||||
}
|
||||
|
||||
real_t l = length_squared();
|
||||
if (l == 0) {
|
||||
zero();
|
||||
} else {
|
||||
real_t length = Math::sqrt(lengthsq);
|
||||
x /= length;
|
||||
y /= length;
|
||||
z /= length;
|
||||
w /= length;
|
||||
l = Math::sqrt(l);
|
||||
x /= l;
|
||||
y /= l;
|
||||
z /= l;
|
||||
w /= l;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -98,6 +98,8 @@ struct [[nodiscard]] Vector4 {
|
||||
Vector4 normalized() const;
|
||||
bool is_normalized() const;
|
||||
|
||||
void zero() { x = y = z = w = 0; }
|
||||
|
||||
real_t distance_to(const Vector4 &p_to) const;
|
||||
real_t distance_squared_to(const Vector4 &p_to) const;
|
||||
Vector4 direction_to(const Vector4 &p_to) const;
|
||||
|
||||
Reference in New Issue
Block a user