Skip to content

Commit

Permalink
feat: add Matrix3, implement Matrix4 Adj Inverse ... functions.
Browse files Browse the repository at this point in the history
  • Loading branch information
zzxzzk115 committed Nov 2, 2023
1 parent b76f1ac commit 03c1d82
Show file tree
Hide file tree
Showing 5 changed files with 334 additions and 0 deletions.
1 change: 1 addition & 0 deletions Renderer/VGL/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ add_library(${TARGET_NAME} src/Line.cpp
src/Matrix4.cpp
src/Texture2D.cpp
src/VGL.cpp
src/Matrix3.cpp
)

set_target_properties(${TARGET_NAME} PROPERTIES CXX_STANDARD 17)
Expand Down
56 changes: 56 additions & 0 deletions Renderer/VGL/include/VGL/Matrix3.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
//
// Matrix3.h
//
// Created or modified by Kexuan Zhang on 2023/11/2 17:41.
//

#pragma once

#include "VGL/Vector3.h"

#include <iostream>
#include <vector>

namespace VGL
{
class Matrix3
{
public:
Matrix3();

std::vector<float>& operator [] (int i);
Matrix3 operator + (Matrix3& other) const;
Matrix3 operator - (Matrix3& other) const;
Matrix3 operator * (Matrix3& other) const;
Matrix3 operator * (float scalar) const;
Matrix3 operator / (float scalar) const;

friend std::ostream& operator << (std::ostream& s, Matrix3& m);

template<typename T>
Vector3<T> operator * (const Vector3<T>& other) const
{
Vector3<T> productVector;

for (int row = 0; row < 3; row++)
{
for (int col = 0; col < 3; col++)
{
productVector[row] += m_Matrix[row][col] * other[col];
}
}

return productVector;
}

void SetIdentity();
Matrix3 Transpose() const;

float Determinant() const;

static Matrix3 Identity();

private:
std::vector<std::vector<float>> m_Matrix;
};
} // namespace VGL
7 changes: 7 additions & 0 deletions Renderer/VGL/include/VGL/Matrix4.h
Original file line number Diff line number Diff line change
Expand Up @@ -54,6 +54,13 @@ namespace VGL
void SetIdentity();
Matrix4 Transpose() const;

Matrix4 Adjugate() const;
float AlgebraicCofactor(int i, int j) const;
float Determinant() const;

Matrix4 InverseTranspose() const;
Matrix4 Inverse() const;

static Matrix4 Identity();

private:
Expand Down
179 changes: 179 additions & 0 deletions Renderer/VGL/src/Matrix3.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,179 @@
//
// Matrix3.cpp
//
// Created or modified by Kexuan Zhang on 2023/11/2 17:44.
//

#include "VGL/Matrix3.h"

namespace VGL
{
Matrix3::Matrix3()
{
m_Matrix = std::vector<std::vector<float>>(3, std::vector<float>(3, 0));
}

std::vector<float>& Matrix3::operator[](int i)
{
return m_Matrix[i];
}

Matrix3 Matrix3::operator + (Matrix3& other) const
{
Matrix3 matrix3 = *this;

for (int row = 0; row < 3; ++row)
{
for (int col = 0; col < 3; ++col)
{
matrix3[row][col] += other[row][col];
}
}

return matrix3;
}

Matrix3 Matrix3::operator - (Matrix3& other) const
{
Matrix3 matrix3 = *this;

for (int row = 0; row < 3; ++row)
{
for (int col = 0; col < 3; ++col)
{
matrix3[row][col] -= other[row][col];
}
}

return matrix3;
}

Matrix3 Matrix3::operator * (float scalar) const
{
Matrix3 matrix3 = *this;

for (int row = 0; row < 3; ++row)
{
for (int col = 0; col < 3; ++col)
{
matrix3[row][col] *= scalar;
}
}

return matrix3;
}

Matrix3 Matrix3::operator / (float scalar) const
{
if (std::abs(scalar) < 1e-6)
{
throw std::runtime_error("Divided by Zero!!!");
}

Matrix3 matrix3 = *this;

for (int row = 0; row < 3; ++row)
{
for (int col = 0; col < 3; ++col)
{
matrix3[row][col] /= scalar;
}
}

return matrix3;
}

Matrix3 Matrix3::operator * (Matrix3& other) const
{
Matrix3 matrix3;

for (int row = 0; row < 3; ++row)
{
for (int col = 0; col < 3; ++col)
{
for (int entry = 0; entry < 4; ++entry)
{
matrix3.m_Matrix[row][col] += m_Matrix[row][entry] * other.m_Matrix[entry][col];
}
}
}

return matrix3;
}

std::ostream& operator << (std::ostream& s, Matrix3& m)
{
for (int row = 0; row < 3; ++row)
{
for (int col = 0; col < 3; col++)
{
s << m[row][col];
if (col < 2) s << "\t";
}
s << std::endl;
}
return s;
}

void Matrix3::SetIdentity()
{
for (int i = 0; i < 3; ++i)
{
for (int j = 0; j < 3; ++j)
{
m_Matrix[i][j] = i==j ? 1 : 0;
}
}
}

Matrix3 Matrix3::Transpose() const
{
Matrix3 transposeMatrix;

for (int row = 0; row < 4; row++)
{
for (int col = 0; col < 4; col++)
{
transposeMatrix.m_Matrix[row][col] = m_Matrix[col][row];
}
}

return transposeMatrix;
}

float Matrix3::Determinant() const
{
Matrix3 matrix3 = *this;
float det = 1.0f;

for (int col = 0; col < 3; col++)
{
for (int row = col + 1; row < 3; row++)
{
float factor = matrix3.m_Matrix[row][col] / matrix3.m_Matrix[col][col];
for (int i = col; i < 3; i++)
{
matrix3.m_Matrix[row][i] -= matrix3.m_Matrix[col][i] * factor;
}
}
}

for (int i = 0; i < 3; i++)
{
det *= matrix3.m_Matrix[i][i];
}

return det;
}

Matrix3 Matrix3::Identity()
{
Matrix3 result;
result.m_Matrix = {
{1, 0, 0},
{0, 1, 0},
{0, 0, 1},
};
return result;
}
} // namespace VGL
91 changes: 91 additions & 0 deletions Renderer/VGL/src/Matrix4.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
//

#include "VGL/Matrix4.h"
#include "VGL/Matrix3.h"

namespace VGL
{
Expand Down Expand Up @@ -141,6 +142,96 @@ namespace VGL
return transposeMatrix;
}

Matrix4 Matrix4::Adjugate() const
{
Matrix4 result;

for (int i = 0; i < 4; ++i)
{
for (int j = 0; j < 4; ++j)
{
result[i][j] = AlgebraicCofactor(i, j);
}
}

return result.Transpose();
}

float Matrix4::AlgebraicCofactor(int i, int j) const
{
Matrix3 subMatrix;

int subRow = 0, subCol = 0;
for (int row = 0; row < 4; row++)
{
if (row == i)
{
continue;
}
for (int col = 0; col < 4; col++)
{
if (col == j)
{
continue;
}
subMatrix[subRow][subCol] = m_Matrix[row][col];
subCol++;
}
subRow++;
subCol = 0;
}

float subDeterminant = subMatrix.Determinant();

float cofactor = subDeterminant * ((i + j) % 2 == 0 ? 1 : -1);

return cofactor;
}

float Matrix4::Determinant() const
{
Matrix4 matrix4 = *this;
float det = 1.0f;

for (int col = 0; col < 4; col++)
{
for (int row = col + 1; row < 4; row++)
{
float factor = matrix4.m_Matrix[row][col] / matrix4.m_Matrix[col][col];
for (int i = col; i < 4; i++)
{
matrix4.m_Matrix[row][i] -= matrix4.m_Matrix[col][i] * factor;
}
}
}

for (int i = 0; i < 4; i++)
{
det *= matrix4.m_Matrix[i][i];
}

return det;
}

Matrix4 Matrix4::InverseTranspose() const
{
return Inverse().Transpose();
}

Matrix4 Matrix4::Inverse() const
{
float determinant = Determinant();

if (determinant == 0)
{
throw std::runtime_error("Determinant is Zero!!!");
}

Matrix4 adjugate = Adjugate();
return adjugate * (1.0f / determinant);
}


Matrix4 Matrix4::Identity()
{
Matrix4 result;
Expand Down

0 comments on commit 03c1d82

Please sign in to comment.