Implement Matrix3x3 missing members and documentation (More!!!)
All checks were successful
Build Docs With Doxygen / Explore-Gitea-Actions (push) Successful in 1m3s
All checks were successful
Build Docs With Doxygen / Explore-Gitea-Actions (push) Successful in 1m3s
This commit is contained in:
@@ -383,6 +383,8 @@ namespace J3ML::LinearAlgebra {
|
||||
/// Performs a batch transformation of the given array.
|
||||
void BatchTransform(Vector3 *pointArray, int numPoints) const;
|
||||
void BatchTransform(Vector3 *pointArray, int numPoints, int stride) const;
|
||||
void BatchTransform(Vector4 *vectorArray, int numVectors) const;
|
||||
void BatchTransform(Vector4 *vectorArray, int numVectors, int stride) const;
|
||||
|
||||
/// Returns the sum of the diagonal elements of this matrix.
|
||||
float Trace() const;
|
||||
@@ -393,19 +395,32 @@ namespace J3ML::LinearAlgebra {
|
||||
|
||||
Vector3 operator[](int row) const;
|
||||
|
||||
/// Transforms the given vector by this matrix (in the order M * v).
|
||||
Vector2 operator * (const Vector2& rhs) const;
|
||||
Vector3 operator * (const Vector3& rhs) const;
|
||||
/// Transforms the given vector by this matrix (in the order M * v).
|
||||
/// This function ignores the W component of the given input vector. This component is assumed to be either 0 or 1.
|
||||
Vector4 operator * (const Vector4& rhs) const;
|
||||
|
||||
/// Multiplies the two matrices.
|
||||
Matrix3x3 operator * (const Matrix3x3& rhs) const;
|
||||
Matrix4x4 operator * (const Matrix4x4& rhs) const;
|
||||
Matrix3x3 Mul(const Matrix3x3& rhs) const;
|
||||
/// Multiplies the two matrices.
|
||||
Matrix4x4 operator * (const Matrix4x4& rhs) const;
|
||||
Matrix4x4 Mul(const Matrix4x4& rhs) const;
|
||||
|
||||
Vector2 Mul(const Vector2& rhs) const;
|
||||
Vector3 Mul(const Vector3& rhs) const;
|
||||
Vector4 Mul(const Vector4& rhs) const;
|
||||
|
||||
/// Converts the quaternion to a M3x3 and multiplies the two matrices together.
|
||||
Matrix3x3 operator *(const Quaternion& rhs) const;
|
||||
|
||||
Quaternion Mul(const Quaternion& rhs) const;
|
||||
|
||||
// Returns true if the column vectors of this matrix are all perpendicular to each other.
|
||||
bool IsColOrthogonal(float epsilon = 1e-3f) const;
|
||||
bool IsColOrthogonal3(float epsilon = 1e-3f) const { return IsColOrthogonal(epsilon);}
|
||||
// Returns true if the row vectors of this matrix are all perpendicular to each other.
|
||||
bool IsRowOrthogonal(float epsilon = 1e-3f) const;
|
||||
|
||||
@@ -414,6 +429,51 @@ namespace J3ML::LinearAlgebra {
|
||||
|
||||
Vector3 ExtractScale() const;
|
||||
|
||||
|
||||
/// Tests if this matrix does not contain any NaNs or infs
|
||||
/// @return Returns true if the entries of this M3x3 are all finite.
|
||||
bool IsFinite() const;
|
||||
|
||||
/// Tests if this is the identity matrix.
|
||||
/// @return Returns true if this matrix is the identity matrix, up to the given epsilon.
|
||||
bool IsIdentity(float epsilon = 1e-3f) const;
|
||||
/// Tests if this matrix is in lower triangular form.
|
||||
/// @return Returns true if this matrix is in lower triangular form, up to the given epsilon.
|
||||
bool IsLowerTriangular(float epsilon = 1e-3f) const;
|
||||
/// Tests if this matrix is in upper triangular form.
|
||||
/// @return Returns true if this matrix is in upper triangular form, up to the given epsilon.
|
||||
bool IsUpperTriangular(float epsilon = 1e-3f) const;
|
||||
/// Tests if this matrix has an inverse.
|
||||
/// @return Returns true if this matrix can be inverted, up to the given epsilon.
|
||||
bool IsInvertible(float epsilon = 1e-3f) const;
|
||||
/// Tests if this matrix is symmetric (M == M^T).
|
||||
/// The test compares the elements for equality. Up to the given epsilon. A matrix is symmetric if it is its own transpose.
|
||||
bool IsSymmetric(float epsilon = 1e-3f) const;
|
||||
/// Tests if this matrix is skew-symmetric (M == -M^T).
|
||||
/// The test compares the elements of this matrix up to the given epsilon. A matrix M is skew-symmetric if the identity M=-M^T holds.
|
||||
bool IsSkewSymmetric(float epsilon = 1e-3f) const;
|
||||
/// Returns true if this matrix does not perform any scaling,
|
||||
/** A matrix does not do any scaling if the column vectors of this matrix are normalized in length,
|
||||
compared to the given epsilon. Note that this matrix may still perform reflection,
|
||||
i.e. it has a -1 scale along some axis.
|
||||
@note This function only examines the upper 3-by-3 part of this matrix.
|
||||
@note This function assumes that this matrix does not contain projection (the fourth row of this matrix is [0,0,0,1] */
|
||||
bool HasUnitaryScale(float epsilon = 1e-3f) const;
|
||||
/// Returns true if this matrix performs a reflection along some plane.
|
||||
/** In 3D space, an even number of reflections corresponds to a rotation about some axis, so a matrix consisting of
|
||||
an odd number of consecutive mirror operations can only reflect about one axis. A matrix that contains reflection reverses
|
||||
the handedness of the coordinate system. This function tests if this matrix does perform mirroring.
|
||||
This occurs if this matrix has a negative determinant.*/
|
||||
bool HasNegativeScale() const;
|
||||
|
||||
/// Returns true if the column and row vectors of this matrix form an orthonormal set.
|
||||
/// @note In math terms, there does not exist such a thing as an 'orthonormal matrix'. In math terms, a matrix
|
||||
/// is orthogonal if the column and row vectors are orthogonal *unit* vectors.
|
||||
/// In terms of this library however, a matrix is orthogonal if its column and row vectors are orthogonal. (no need to be unitary),
|
||||
/// and a matrix is orthonormal if the column and row vectors are orthonormal.
|
||||
bool IsOrthonormal(float epsilon = 1e-3f) const;
|
||||
|
||||
|
||||
protected: /// Member values
|
||||
float elems[3][3];
|
||||
};
|
||||
|
@@ -529,5 +529,88 @@ namespace J3ML::LinearAlgebra {
|
||||
|
||||
}
|
||||
|
||||
bool Matrix3x3::IsFinite() const {
|
||||
for (int y = 0; y < Rows; y++)
|
||||
for (int x = 0; x < Cols; ++x)
|
||||
if (!std::isfinite(elems[y][x]))
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
/** Compares the two values for equality, allowing the given amount of absolute error. */
|
||||
bool EqualAbs(float a, float b, float epsilon)
|
||||
{
|
||||
return std::abs(a-b) < epsilon;
|
||||
}
|
||||
|
||||
bool Matrix3x3::IsIdentity(float epsilon) const
|
||||
{
|
||||
for (int y = 0; y < Rows; ++y)
|
||||
for (int x = 0; x < Cols; ++x)
|
||||
if (!EqualAbs(elems[y][x], (x == y) ? 1.f : 0.f, epsilon))
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
|
||||
bool Matrix3x3::IsLowerTriangular(float epsilon) const
|
||||
{
|
||||
return EqualAbs(elems[0][1], 0.f, epsilon)
|
||||
&& EqualAbs(elems[0][2], 0.f, epsilon)
|
||||
&& EqualAbs(elems[1][2], 0.f, epsilon);
|
||||
}
|
||||
|
||||
|
||||
bool Matrix3x3::IsUpperTriangular(float epsilon) const
|
||||
{
|
||||
return EqualAbs(elems[1][0], 0.f, epsilon)
|
||||
&& EqualAbs(elems[2][0], 0.f, epsilon)
|
||||
&& EqualAbs(elems[2][1], 0.f, epsilon);
|
||||
}
|
||||
|
||||
bool Matrix3x3::IsInvertible(float epsilon) const
|
||||
{
|
||||
float d = Determinant();
|
||||
bool isSingular = EqualAbs(d, 0.f, epsilon);
|
||||
//assert(Inverse(epsilon) == isSingular);
|
||||
return !isSingular;
|
||||
}
|
||||
|
||||
bool Matrix3x3::IsSymmetric(float epsilon) const
|
||||
{
|
||||
return EqualAbs(elems[0][1], elems[1][0], epsilon)
|
||||
&& EqualAbs(elems[0][2], elems[2][0], epsilon)
|
||||
&& EqualAbs(elems[1][2], elems[2][1], epsilon);
|
||||
}
|
||||
|
||||
bool Matrix3x3::IsSkewSymmetric(float epsilon) const
|
||||
{
|
||||
return EqualAbs(elems[0][0], 0.f, epsilon)
|
||||
&& EqualAbs(elems[1][1], 0.f, epsilon)
|
||||
&& EqualAbs(elems[2][2], 0.f, epsilon)
|
||||
&& EqualAbs(elems[0][1], -elems[1][0], epsilon)
|
||||
&& EqualAbs(elems[0][2], -elems[2][0], epsilon)
|
||||
&& EqualAbs(elems[1][2], -elems[2][1], epsilon);
|
||||
}
|
||||
|
||||
|
||||
bool Matrix3x3::HasUnitaryScale(float epsilon) const {
|
||||
Vector3 scale = ExtractScale();
|
||||
return scale.Equals(1.f, 1.f, 1.f, epsilon);
|
||||
}
|
||||
|
||||
bool Matrix3x3::HasNegativeScale() const
|
||||
{
|
||||
return Determinant() < 0.f;
|
||||
}
|
||||
|
||||
|
||||
bool Matrix3x3::IsOrthonormal(float epsilon) const
|
||||
{
|
||||
///@todo Epsilon magnitudes don't match.
|
||||
return IsColOrthogonal(epsilon) && Row(0).IsNormalized(epsilon) && Row(1).IsNormalized(epsilon) && Row(2).IsNormalized(epsilon);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
Reference in New Issue
Block a user