Compare commits

..

10 Commits

12 changed files with 1885 additions and 1608 deletions

View File

@@ -21,7 +21,9 @@ clang-analyzer-*,
-modernize-avoid-c-arrays, -modernize-avoid-c-arrays,
-cppcoreguidelines-pro-bounds-array-to-pointer-decay, -cppcoreguidelines-pro-bounds-array-to-pointer-decay,
-readability-named-parameter, -readability-named-parameter,
-cert-env33-c -cert-env33-c,
-readability-identifier-length,
-cppcoreguidelines-pro-type-union-access
' '

32
.vscode/launch.json vendored
View File

@@ -1,32 +0,0 @@
{
// Use IntelliSense to learn about possible attributes.
// Hover to view descriptions of existing attributes.
// For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387
"version": "0.2.0",
"configurations": [
{
"name": "Debug MathTestFPU (gdb)",
"type": "cppdbg",
"request": "launch",
"program": "${workspaceFolder}/bin/1.0.0/Debug/MathTestFPU/MathTestFPU",
"args": [],
"stopAtEntry": false,
"cwd": "${fileDirname}",
"environment": [],
"externalConsole": false,
"MIMode": "gdb",
"setupCommands": [
{
"description": "Enable pretty-printing for gdb",
"text": "-enable-pretty-printing",
"ignoreFailures": true
},
{
"description": "Set Disassembly Flavor to Intel",
"text": "-gdb-set disassembly-flavor intel",
"ignoreFailures": true
}
]
}
]
}

152
.vscode/settings.json vendored
View File

@@ -1,152 +0,0 @@
{
"C_Cpp.formatting": "clangFormat",
"C_Cpp.loggingLevel": "Error",
"C_Cpp.default.cppStandard": "c++20",
"C_Cpp.default.includePath": [
"${workspaceFolder}/Engine/Source/Runtime/",
"${workspaceFolder}/Engine/Source/ThirdParty/"
],
"C_Cpp.default.browse.path": [
"${workspaceFolder}/Engine/Source/Runtime",
"${workspaceFolder}/Engine/Source/ThirdParty"
],
"C_Cpp.default.browse.databaseFilename": "${workspaceFolder}/.vscode/browse.vc.db",
"files.associations": {
"cstdint": "cpp",
"chrono": "cpp",
"string": "cpp",
"cctype": "cpp",
"clocale": "cpp",
"cmath": "cpp",
"cstdarg": "cpp",
"cstddef": "cpp",
"cstdio": "cpp",
"cstdlib": "cpp",
"cstring": "cpp",
"ctime": "cpp",
"cwchar": "cpp",
"cwctype": "cpp",
"any": "cpp",
"array": "cpp",
"atomic": "cpp",
"bit": "cpp",
"*.tcc": "cpp",
"bitset": "cpp",
"charconv": "cpp",
"cinttypes": "cpp",
"codecvt": "cpp",
"compare": "cpp",
"complex": "cpp",
"concepts": "cpp",
"condition_variable": "cpp",
"deque": "cpp",
"forward_list": "cpp",
"list": "cpp",
"map": "cpp",
"set": "cpp",
"unordered_map": "cpp",
"unordered_set": "cpp",
"vector": "cpp",
"exception": "cpp",
"expected": "cpp",
"algorithm": "cpp",
"functional": "cpp",
"iterator": "cpp",
"memory": "cpp",
"memory_resource": "cpp",
"numeric": "cpp",
"optional": "cpp",
"random": "cpp",
"ratio": "cpp",
"regex": "cpp",
"source_location": "cpp",
"string_view": "cpp",
"system_error": "cpp",
"tuple": "cpp",
"type_traits": "cpp",
"utility": "cpp",
"hash_map": "cpp",
"hash_set": "cpp",
"format": "cpp",
"fstream": "cpp",
"future": "cpp",
"initializer_list": "cpp",
"iomanip": "cpp",
"iosfwd": "cpp",
"iostream": "cpp",
"istream": "cpp",
"limits": "cpp",
"mutex": "cpp",
"new": "cpp",
"numbers": "cpp",
"ostream": "cpp",
"semaphore": "cpp",
"shared_mutex": "cpp",
"span": "cpp",
"sstream": "cpp",
"stdexcept": "cpp",
"stdfloat": "cpp",
"stop_token": "cpp",
"streambuf": "cpp",
"text_encoding": "cpp",
"thread": "cpp",
"cfenv": "cpp",
"typeindex": "cpp",
"typeinfo": "cpp",
"valarray": "cpp",
"variant": "cpp"
},
"C_Cpp.default.defines": [
"P_LINUX_BUILD",
"__SSE__",
],
"C_Cpp.default.configurationProvider": "ms-vscode.cmake-tools",
"editor.tokenColorCustomizations": {
"[*Light*]": {
"textMateRules": [
{
"scope": "ref.matchtext",
"settings": {
"foreground": "#000"
}
}
]
},
"[*Dark*]": {
"textMateRules": [
{
"scope": "ref.matchtext",
"settings": {
"foreground": "#fff"
}
}
]
},
"textMateRules": [
{
"scope": "googletest.failed",
"settings": {
"foreground": "#f00"
}
},
{
"scope": "googletest.passed",
"settings": {
"foreground": "#0f0"
}
},
{
"scope": "googletest.run",
"settings": {
"foreground": "#0f0"
}
}
]
},
"gtest-adapter.debugConfig": [
"Debug MathTestFPU (gdb)"
],
"gtest-adapter.supportLocation": true,
"premake.version": "Premake 5.0-beta5",
}

28
.vscode/tasks.json vendored
View File

@@ -1,28 +0,0 @@
{
"tasks": [
{
"type": "cppbuild",
"label": "C/C++: g++ build active file",
"command": "/sbin/g++",
"args": [
"-fdiagnostics-color=always",
"-g",
"${file}",
"-o",
"${fileDirname}/${fileBasenameNoExtension}"
],
"options": {
"cwd": "${fileDirname}"
},
"problemMatcher": [
"$gcc"
],
"group": {
"kind": "build",
"isDefault": true
},
"detail": "Task generated by Debugger."
}
],
"version": "2.0.0"
}

View File

@@ -1,52 +1,95 @@
#pragma once #pragma once
#ifdef P_BUILD_LIB #ifdef P_BUILD_LIB
#include "PhanesEnginePCH.h" # include "PhanesEnginePCH.h"
#else #else
#include <vector> # include <vector>
#endif #endif
#ifndef MATH_FWD_H #ifndef MATH_FWD_H
#define MATH_FWD_H # define MATH_FWD_H
#include "Core/Math/Boilerplate.h" # include "Core/Math/Boilerplate.h"
#include "Core/Math/SIMD/PhanesSIMDTypes.h" # include "Core/Math/SIMD/PhanesSIMDTypes.h"
/** /**
* Includes forward declarations, as well as certain useful typedefs. * Includes forward declarations, as well as certain useful usings.
* *
* @ref OSAL/PlatformTypes.h * @ref OSAL/PlatformTypes.h
*/ */
namespace Phanes::Core::Math
namespace Phanes::Core::Math { {
/** /**
* Template forward declarations. * Template forward declarations.
*/ */
template<RealType T> struct TColor; template <RealType T>
template<RealType T> struct TLinearColor; struct TColor;
template<RealType T> struct TLine;
template<RealType T> struct TQuaternion; template <RealType T>
template<RealType T> struct TTransform; struct TLinearColor;
template<RealType T> struct TPoint2;
template<RealType T> struct TPoint3; template <RealType T>
template<RealType T> struct TPoint4; struct TLine;
template<IntType T> struct TIntPoint2;
template<IntType T> struct TIntPoint3; template <RealType T>
template<IntType T> struct TIntPoint4; struct TTransform;
template<RealType T> struct TMatrix2;
template<RealType T, bool S> struct TMatrix3; template <RealType T>
template<RealType T, bool S> struct TMatrix4; struct TPoint2;
template<RealType T, bool S> struct TVector2;
template<RealType T, bool S> struct TVector3; template <RealType T>
template<RealType T, bool S> struct TVector4; struct TPoint3;
template<IntType T, bool S> struct TIntVector2;
template<IntType T, bool S> struct TIntVector3; template <RealType T>
template<IntType T, bool S> struct TIntVector4; struct TPoint4;
template<RealType T, bool S> struct TPlane;
template<RealType T, bool S> struct TRay; template <IntType T>
struct TIntPoint2;
template <IntType T>
struct TIntPoint3;
template <IntType T>
struct TIntPoint4;
template <RealType T>
struct TMatrix2;
template <RealType T, bool S>
struct TQuaternion;
template <RealType T, bool S>
struct TMatrix3;
template <RealType T, bool S>
struct TMatrix4;
template <RealType T, bool S>
struct TVector2;
template <RealType T, bool S>
struct TVector3;
template <RealType T, bool S>
struct TVector4;
template <IntType T, bool S>
struct TIntVector2;
template <IntType T, bool S>
struct TIntVector3;
template <IntType T, bool S>
struct TIntVector4;
template <RealType T, bool S>
struct TPlane;
template <RealType T, bool S>
struct TRay;
/** /**
* Specific instantiation of forward declarations. * Specific instantiation of forward declarations.
@@ -54,148 +97,142 @@ namespace Phanes::Core::Math {
// TPoint2 // TPoint2
typedef TPoint2<float> Point2; using Point2 = TPoint2<float>;
typedef TPoint2<float> Point2f; using Point2f = TPoint2<float>;
typedef TPoint2<double> Point2d; using Point2d = TPoint2<double>;
// TPoint3 // TPoint3
typedef TPoint3<float> Point3; using Point3 = TPoint3<float>;
typedef TPoint3<float> Point3f; using Point3f = TPoint3<float>;
typedef TPoint3<double> Point3d; using Point3d = TPoint3<double>;
// TPoint4 // TPoint4
typedef TPoint4<float> Point4; using Point4 = TPoint4<float>;
typedef TPoint4<float> Point4f; using Point4f = TPoint4<float>;
typedef TPoint4<double> Point4d; using Point4d = TPoint4<double>;
// TIntPoint2 // TIntPoint2
typedef TIntPoint2<int> IntPoint2; using IntPoint2 = TIntPoint2<int>;
typedef TIntPoint2<int> IntPoint2i; using IntPoint2i = TIntPoint2<int>;
typedef TIntPoint2<long> IntPoint2l; using IntPoint2l = TIntPoint2<long>;
// TIntPoint3 // TIntPoint3
typedef TIntPoint3<int> IntPoint3; using IntPoint3 = TIntPoint3<int>;
typedef TIntPoint3<int> IntPoint3i; using IntPoint3i = TIntPoint3<int>;
typedef TIntPoint3<long> IntPoint3l; using IntPoint3l = TIntPoint3<long>;
// TIntPoint4 // TIntPoint4
typedef TIntPoint4<int> IntPoint4; using IntPoint4 = TIntPoint4<int>;
typedef TIntPoint4<int> IntPoint4i; using IntPoint4i = TIntPoint4<int>;
typedef TIntPoint4<long> IntPoint4l; using IntPoint4l = TIntPoint4<long>;
// IntVetor2 // IntVetor2
typedef TIntVector2<int, false> IntVector2; using IntVector2 = TIntVector2<int, false>;
typedef TIntVector2<int, false> Vector2i; using Vector2i = TIntVector2<int, false>;
typedef TIntVector2<long, false> LongVector2; using LongVector2 = TIntVector2<long, false>;
typedef TIntVector2<long, false> Vector2l; using Vector2l = TIntVector2<long, false>;
// IntVetor3 // IntVetor3
typedef TIntVector3<int, false> IntVector3; using IntVector3 = TIntVector3<int, false>;
typedef TIntVector3<int, false> Vector3i; using Vector3i = TIntVector3<int, false>;
typedef TIntVector3<long, false> LongVector3; using LongVector3 = TIntVector3<long, false>;
typedef TIntVector3<long, false> Vector3l; using Vector3l = TIntVector3<long, false>;
// IntVetor4 // IntVetor4
typedef TIntVector4<int, false> IntVector4; using IntVector4 = TIntVector4<int, false>;
typedef TIntVector4<int, false> Vector4i; using Vector4i = TIntVector4<int, false>;
typedef TIntVector4<long, false> LongVector4; using LongVector4 = TIntVector4<long, false>;
typedef TIntVector4<long, false> Vector4l; using Vector4l = TIntVector4<long, false>;
// Vector2 // Vector2
typedef TVector2<float, false> Vector2; using Vector2 = TVector2<float, false>;
typedef TVector2<float, false> Vector2f; using Vector2f = TVector2<float, false>;
typedef TVector2<double, false> Vector2d; using Vector2d = TVector2<double, false>;
typedef TVector2<double, SIMD::use_simd<double, 2, true>::value> Vector2Regf64;
typedef TVector2<double, SIMD::use_simd<double, 2, true>::value> Vector2Reg;
typedef TVector2<double, SIMD::use_simd<double, 2, true>::value> Vector2Regd;
using Vector2Regf64 = TVector2<double, SIMD::use_simd<double, 2, true>::value>;
using Vector2Reg = TVector2<double, SIMD::use_simd<double, 2, true>::value>;
using Vector2Regd = TVector2<double, SIMD::use_simd<double, 2, true>::value>;
// Vector3 // Vector3
typedef TVector3<float, false> Vector3; using Vector3 = TVector3<float, false>;
typedef TVector3<float, false> Vector3f; using Vector3f = TVector3<float, false>;
typedef TVector3<double, false> Vector3d; using Vector3d = TVector3<double, false>;
typedef TVector3<float, SIMD::use_simd<float, 3, true>::value> Vector3Reg;
typedef TVector3<float, SIMD::use_simd<float, 3, true>::value> Vector3Regf32;
typedef TVector3<double, SIMD::use_simd<double, 3, true>::value> Vector3Regd;
typedef TVector3<double, SIMD::use_simd<double, 3, true>::value> Vector3Regf64;
using Vector3Reg = TVector3<float, SIMD::use_simd<float, 3, true>::value>;
using Vector3Regf32 = TVector3<float, SIMD::use_simd<float, 3, true>::value>;
using Vector3Regd = TVector3<double, SIMD::use_simd<double, 3, true>::value>;
using Vector3Regf64 = TVector3<double, SIMD::use_simd<double, 3, true>::value>;
// Vector4 // Vector4
typedef TVector4<float, false> Vector4; using Vector4 = TVector4<float, false>;
typedef TVector4<float, false> Vector4f; using Vector4f = TVector4<float, false>;
typedef TVector4<double, false> Vector4d; using Vector4d = TVector4<double, false>;
typedef TVector4<float, SIMD::use_simd<float, 4, true>::value> Vector4Reg; using Vector4Reg = TVector4<float, SIMD::use_simd<float, 4, true>::value>;
typedef TVector4<float, SIMD::use_simd<float, 4, true>::value> Vector4Regf32; using Vector4Regf32 = TVector4<float, SIMD::use_simd<float, 4, true>::value>;
typedef TVector4<double, SIMD::use_simd<double, 4, true>::value> Vector4Regd; using Vector4Regd = TVector4<double, SIMD::use_simd<double, 4, true>::value>;
typedef TVector4<double, SIMD::use_simd<double, 4, true>::value> Vector4Regf64; using Vector4Regf64 = TVector4<double, SIMD::use_simd<double, 4, true>::value>;
// Matrix2 // Matrix2
typedef TMatrix2<float> Matrix2; using Matrix2 = TMatrix2<float>;
typedef TMatrix2<float> Matrix2f; using Matrix2f = TMatrix2<float>;
typedef TMatrix2<double> Matrix2d; using Matrix2d = TMatrix2<double>;
// Matrix3 // Matrix3
typedef TMatrix3<float, false> Matrix3; using Matrix3 = TMatrix3<float, false>;
typedef TMatrix3<float, false> Matrix3f; using Matrix3f = TMatrix3<float, false>;
typedef TMatrix3<double, false> Matrix3d; using Matrix3d = TMatrix3<double, false>;
typedef TMatrix3<float, SIMD::use_simd<float, 3, true>::value> Matrix3Reg; using Matrix3Reg = TMatrix3<float, SIMD::use_simd<float, 3, true>::value>;
typedef TMatrix3<float, SIMD::use_simd<float, 3, true>::value> Matrix3Regf; using Matrix3Regf = TMatrix3<float, SIMD::use_simd<float, 3, true>::value>;
typedef TMatrix3<double, SIMD::use_simd<double, 3, true>::value> Matrix3Regd; using Matrix3Regd = TMatrix3<double, SIMD::use_simd<double, 3, true>::value>;
typedef TMatrix3<double, SIMD::use_simd<double, 3, true>::value> Matrix3Regf64; using Matrix3Regf64 = TMatrix3<double, SIMD::use_simd<double, 3, true>::value>;
// Matrix4 // Matrix4
typedef TMatrix4<float, false> Matrix4; using Matrix4 = TMatrix4<float, false>;
typedef TMatrix4<float, false> Matrix4f; using Matrix4f = TMatrix4<float, false>;
typedef TMatrix4<double, false> Matrix4d; using Matrix4d = TMatrix4<double, false>;
typedef TMatrix3<float, SIMD::use_simd<float, 4, true>::value> Matrix4Reg;
typedef TMatrix3<float, SIMD::use_simd<float, 4, true>::value> Matrix4Regf;
typedef TMatrix3<double, SIMD::use_simd<double, 4, true>::value> Matrix4Regd;
typedef TMatrix3<double, SIMD::use_simd<double, 4, true>::value> Matrix4Regf64;
using Matrix4Reg = TMatrix3<float, SIMD::use_simd<float, 4, true>::value>;
using Matrix4Regf = TMatrix3<float, SIMD::use_simd<float, 4, true>::value>;
using Matrix4Regd = TMatrix3<double, SIMD::use_simd<double, 4, true>::value>;
using Matrix4Regf64 = TMatrix3<double, SIMD::use_simd<double, 4, true>::value>;
// TPlane // TPlane
typedef TPlane<float, false> Plane; using Plane = TPlane<float, false>;
typedef TPlane<float, false> Planef; using Planef = TPlane<float, false>;
typedef TPlane<double, false> Planed; using Planed = TPlane<double, false>;
typedef TPlane<float, SIMD::use_simd<float, 4, true>::value> PlaneReg; using PlaneReg = TPlane<float, SIMD::use_simd<float, 4, true>::value>;
typedef TPlane<float, SIMD::use_simd<double, 4, true>::value> PlaneRegd; using PlaneRegd = TPlane<float, SIMD::use_simd<double, 4, true>::value>;
} // namespace Phanes::Core::Math
} // Phanes::Core::Math::coretypes
namespace Phanes::Core::Math::Internal namespace Phanes::Core::Math::Internal
{ {
// Internal types // Internal types
template <typename T, unsigned int D> struct AVector; template <typename T, unsigned int D>
struct AVector;
template <typename T, unsigned int n, unsigned int> struct AMatrix;
}
template <typename T, unsigned int n, unsigned int>
struct AMatrix;
} // namespace Phanes::Core::Math::Internal
#endif // !MATH_FWD_H #endif // !MATH_FWD_H

View File

@@ -7,18 +7,18 @@
#include "Core/Math/Vector2.hpp" #include "Core/Math/Vector2.hpp"
#ifndef MATRIX2_H #ifndef MATRIX2_H
#define MATRIX2_H # define MATRIX2_H
namespace Phanes::Core::Math { namespace Phanes::Core::Math
{
// 2x2 Matrix defined in column-major order. // 2x2 Matrix defined in column-major order.
// Accessed by M[Row][Col]. // Accessed by M[Col][Row].
template<RealType T> template <RealType T>
struct TMatrix2 struct TMatrix2
{ {
public: public:
union union
{ {
struct struct
@@ -38,7 +38,6 @@ namespace Phanes::Core::Math {
}; };
public: public:
TMatrix2() = default; TMatrix2() = default;
/** /**
@@ -59,25 +58,29 @@ namespace Phanes::Core::Math {
TMatrix2(T fields[2][2]) TMatrix2(T fields[2][2])
{ {
this->data[0][0] = fields[0][0]; this->data[1][0] = fields[1][0]; this->data[0][0] = fields[0][0];
this->data[0][1] = fields[0][1]; this->data[1][1] = fields[1][1]; this->data[1][0] = fields[1][0];
this->data[0][1] = fields[0][1];
this->data[1][1] = fields[1][1];
} }
/** /**
* Construct Matrix from parameters. * Construct Matrix from parameters.
* *
* @param(n00) M[0][0] * @param(n00) M[0][0]
* @param(n10) M[1][0] * @param(n01) M[1][0]
* @param(n01) M[0][1] * @param(n10) M[0][1]
* @param(n11) M[1][1] * @param(n11) M[1][1]
* *
* @note nXY = n[Row][Col] * @note nXY = n[Col][Row]
*/ */
TMatrix2(T n00, T n01, T n10, T n11) TMatrix2(T n00, T n01, T n10, T n11)
{ {
this->data[0][0] = n00; this->data[1][0] = n01; this->data[0][0] = n00;
this->data[0][1] = n10; this->data[1][1] = n11; this->data[1][0] = n01;
this->data[0][1] = n10;
this->data[1][1] = n11;
} }
/** /**
@@ -94,21 +97,19 @@ namespace Phanes::Core::Math {
} }
public: public:
T& operator()(int n, int m)
T& operator() (int n, int m)
{ {
return this->data[m][n]; return this->data[m][n];
} }
T operator() (int n, int m) const T operator()(int n, int m) const
{ {
return this->data[m][n]; return this->data[m][n];
} }
TVector2<T, false>& operator[] (int m) TVector2<T, false>& operator[](int m)
{ {
switch (m) switch(m)
{ {
case 0: case 0:
return this->c0; return this->c0;
@@ -119,9 +120,9 @@ namespace Phanes::Core::Math {
throw std::invalid_argument("m is outside valid range."); throw std::invalid_argument("m is outside valid range.");
} }
TVector2<T, false> operator[] (int m) const TVector2<T, false> operator[](int m) const
{ {
switch (m) switch(m)
{ {
case 0: case 0:
return this->c0; return this->c0;
@@ -131,15 +132,14 @@ namespace Phanes::Core::Math {
throw std::invalid_argument("m is outside valid range."); throw std::invalid_argument("m is outside valid range.");
} }
}; };
// ====================== // // ====================== //
// TMatrix2 operator // // TMatrix2 operator //
// ====================== // // ====================== //
template<RealType T> template <RealType T>
TMatrix2<T>& operator+= (TMatrix2<T>& m1, T s) TMatrix2<T>& operator+=(TMatrix2<T>& m1, T s)
{ {
m1(0, 0) += s; m1(0, 0) += s;
m1(0, 1) += s; m1(0, 1) += s;
@@ -149,8 +149,8 @@ namespace Phanes::Core::Math {
return m1; return m1;
} }
template<RealType T> template <RealType T>
TMatrix2<T>& operator+= (TMatrix2<T>& m1, const TMatrix2<T>& m2) TMatrix2<T>& operator+=(TMatrix2<T>& m1, const TMatrix2<T>& m2)
{ {
m1(0, 0) += m2(0, 0); m1(0, 0) += m2(0, 0);
m1(0, 1) += m2(0, 1); m1(0, 1) += m2(0, 1);
@@ -160,8 +160,8 @@ namespace Phanes::Core::Math {
return m1; return m1;
} }
template<RealType T> template <RealType T>
TMatrix2<T>& operator-= (TMatrix2<T>& m1, T s) TMatrix2<T>& operator-=(TMatrix2<T>& m1, T s)
{ {
m1(0, 0) -= s; m1(0, 0) -= s;
m1(0, 1) -= s; m1(0, 1) -= s;
@@ -171,8 +171,8 @@ namespace Phanes::Core::Math {
return m1; return m1;
} }
template<RealType T> template <RealType T>
TMatrix2<T>& operator-= (TMatrix2<T>& m1, const TMatrix2<T>& m2) TMatrix2<T>& operator-=(TMatrix2<T>& m1, const TMatrix2<T>& m2)
{ {
m1(0, 0) -= m2(0, 0); m1(0, 0) -= m2(0, 0);
m1(0, 1) -= m2(0, 1); m1(0, 1) -= m2(0, 1);
@@ -182,8 +182,8 @@ namespace Phanes::Core::Math {
return m1; return m1;
} }
template<RealType T> template <RealType T>
TMatrix2<T>& operator*= (TMatrix2<T>& m1, T s) TMatrix2<T>& operator*=(TMatrix2<T>& m1, T s)
{ {
m1.data[0][0] *= s; m1.data[0][0] *= s;
m1.data[0][1] *= s; m1.data[0][1] *= s;
@@ -193,8 +193,8 @@ namespace Phanes::Core::Math {
return m1; return m1;
} }
template<RealType T> template <RealType T>
TMatrix2<T>& operator*= (TMatrix2<T>& m1, const TMatrix2<T>& m2) TMatrix2<T>& operator*=(TMatrix2<T>& m1, const TMatrix2<T>& m2)
{ {
TMatrix2<T> c = m1; TMatrix2<T> c = m1;
@@ -207,8 +207,8 @@ namespace Phanes::Core::Math {
return m1; return m1;
} }
template<RealType T> template <RealType T>
TMatrix2<T>& operator/= (TMatrix2<T>& m1, T s) TMatrix2<T>& operator/=(TMatrix2<T>& m1, T s)
{ {
s = (T)1.0 / s; s = (T)1.0 / s;
m1.data[0][0] *= s; m1.data[0][0] *= s;
@@ -219,87 +219,83 @@ namespace Phanes::Core::Math {
return m1; return m1;
} }
template<RealType T> template <RealType T>
TMatrix2<T> operator+ (const TMatrix2<T>& m1, T s) TMatrix2<T> operator+(const TMatrix2<T>& m1, T s)
{ {
return TMatrix2<T>(m1(0, 0) + s, m1(0, 1) + s, return TMatrix2<T>(m1(0, 0) + s, m1(0, 1) + s, m1(1, 0) + s, m1(1, 1) + s);
m1(1, 0) + s, m1(1, 1) + s);
} }
template<RealType T> template <RealType T>
TMatrix2<T> operator+ (const TMatrix2<T>& m1, const TMatrix2<T>& m2) TMatrix2<T> operator+(const TMatrix2<T>& m1, const TMatrix2<T>& m2)
{ {
return TMatrix2<T>(m1(0, 0) + m2(0, 0), m1(0, 1) + m2(0, 1), return TMatrix2<T>(
m1(1, 0) + m2(1, 0), m1(1, 1) + m2(1, 1)); m1(0, 0) + m2(0, 0), m1(0, 1) + m2(0, 1), m1(1, 0) + m2(1, 0), m1(1, 1) + m2(1, 1));
} }
template<RealType T> template <RealType T>
TMatrix2<T> operator- (const TMatrix2<T>& m1, T s) TMatrix2<T> operator-(const TMatrix2<T>& m1, T s)
{ {
return TMatrix2<T>(m1(0, 0) - s, m1(0, 1) - s, return TMatrix2<T>(m1(0, 0) - s, m1(0, 1) - s, m1(1, 0) - s, m1(1, 1) - s);
m1(1, 0) - s, m1(1, 1) - s);
} }
template<RealType T> template <RealType T>
TMatrix2<T> operator- (const TMatrix2<T>& m1, const TMatrix2<T>& m2) TMatrix2<T> operator-(const TMatrix2<T>& m1, const TMatrix2<T>& m2)
{ {
return TMatrix2<T>(m1(0, 0) - m2(0, 0), m1(0, 1) - m2(0, 1), return TMatrix2<T>(
m1(1, 0) - m2(1, 0), m1(1, 1) - m2(1, 1)); m1(0, 0) - m2(0, 0), m1(0, 1) - m2(0, 1), m1(1, 0) - m2(1, 0), m1(1, 1) - m2(1, 1));
} }
template<RealType T> template <RealType T>
TMatrix2<T> operator* (const TMatrix2<T>& m1, T s) TMatrix2<T> operator*(const TMatrix2<T>& m1, T s)
{ {
return TMatrix2<T>(m1(0, 0) * s, m1(0, 1) * s, return TMatrix2<T>(m1(0, 0) * s, m1(0, 1) * s, m1(1, 0) * s, m1(1, 1) * s);
m1(1, 0) * s, m1(1, 1) * s);
} }
template<RealType T> template <RealType T>
TMatrix2<T> operator/ (const TMatrix2<T>& m1, T s) TMatrix2<T> operator/(const TMatrix2<T>& m1, T s)
{ {
s = (T)1.0 / s; s = (T)1.0 / s;
return TMatrix2<T>(m1(0, 0) * s, m1(0, 1) * s, return TMatrix2<T>(m1(0, 0) * s, m1(0, 1) * s, m1(1, 0) * s, m1(1, 1) * s);
m1(1, 0) * s, m1(1, 1) * s);
} }
template<RealType T> template <RealType T>
TMatrix2<T> operator* (const TMatrix2<T>& m1, const TMatrix2<T>& m2) TMatrix2<T> operator*(const TMatrix2<T>& m1, const TMatrix2<T>& m2)
{ {
return TMatrix2<T>(m1(0, 0) * m2(0, 0) + m1(0, 1) * m2(1, 0), m1(0, 0) * m2(0, 1) + m1(0, 1) * m2(1, 1), return TMatrix2<T>(m1(0, 0) * m2(0, 0) + m1(0, 1) * m2(1, 0),
m1(1, 0) * m2(0, 0) + m1(1, 1) * m2(1, 0), m1(1, 0) * m2(0, 1) + m1(1, 1) * m2(1, 1)); m1(0, 0) * m2(0, 1) + m1(0, 1) * m2(1, 1),
m1(1, 0) * m2(0, 0) + m1(1, 1) * m2(1, 0),
m1(1, 0) * m2(0, 1) + m1(1, 1) * m2(1, 1));
} }
template<RealType T> template <RealType T>
TVector2<T, false> operator* (const TMatrix2<T>& m1, const TVector2<T, false>& v) TVector2<T, false> operator*(const TMatrix2<T>& m1, const TVector2<T, false>& v)
{ {
return TVector2<T, false>(m1(0, 0) * v.x + m1(0, 1) * v.y, return TVector2<T, false>(m1(0, 0) * v.x + m1(0, 1) * v.y, m1(1, 0) * v.x + m1(1, 1) * v.y);
m1(1, 0) * v.x + m1(1, 1) * v.y);
} }
template<RealType T> template <RealType T>
bool operator== (const TMatrix2<T>& m1, const TMatrix2<T>& m2) bool operator==(const TMatrix2<T>& m1, const TMatrix2<T>& m2)
{ {
return m1[0] == m2[0] && m1[1] == m2[1]; return m1[0] == m2[0] && m1[1] == m2[1];
} }
template<RealType T> template <RealType T>
bool operator!= (const TMatrix2<T>& m1, const TMatrix2<T>& m2) bool operator!=(const TMatrix2<T>& m1, const TMatrix2<T>& m2)
{ {
return m1[0] != m2[0] || m1[1] != m2[1]; return m1[0] != m2[0] || m1[1] != m2[1];
} }
// ============================== // // ============================== //
// Matrix function definition // // Matrix function definition //
// ============================== // // ============================== //
template<RealType T> template <RealType T>
T Determinant(const TMatrix2<T>& m1) T Determinant(const TMatrix2<T>& m1)
{ {
return m1(0, 0) * m1(1, 1) - m1(0, 1) * m1(1, 0); return m1(0, 0) * m1(1, 1) - m1(0, 1) * m1(1, 0);
} }
template<RealType T> template <RealType T>
TMatrix2<T>& InverseV(TMatrix2<T>& m1) TMatrix2<T>& InverseV(TMatrix2<T>& m1)
{ {
float _1_det = 1.0f / Determinant(m1); float _1_det = 1.0f / Determinant(m1);
@@ -314,7 +310,7 @@ namespace Phanes::Core::Math {
return m1; return m1;
} }
template<RealType T> template <RealType T>
TMatrix2<T>& TransposeV(TMatrix2<T>& m1) TMatrix2<T>& TransposeV(TMatrix2<T>& m1)
{ {
Swap(m1(0, 1), m1(1, 0)); Swap(m1(0, 1), m1(1, 0));
@@ -326,33 +322,30 @@ namespace Phanes::Core::Math {
// WITH RETURN // // WITH RETURN //
// =============== // // =============== //
template<RealType T> template <RealType T>
TMatrix2<T> Inverse(TMatrix2<T>& m1) TMatrix2<T> Inverse(TMatrix2<T>& m1)
{ {
float _1_det = 1.0f / Determinant(m1); float _1_det = 1.0f / Determinant(m1);
return TMatrix2<T>( m1(1, 1) * _1_det, -m1(0, 1) * _1_det, return TMatrix2<T>(
-m1(1, 0) * _1_det, m1(0, 0) * _1_det); m1(1, 1) * _1_det, -m1(0, 1) * _1_det, -m1(1, 0) * _1_det, m1(0, 0) * _1_det);
} }
template<RealType T> template <RealType T>
TMatrix2<T> Transpose(const TMatrix2<T>& m1) TMatrix2<T> Transpose(const TMatrix2<T>& m1)
{ {
return TMatrix2<T>(m1(0, 0), m1(1, 0), return TMatrix2<T>(m1(0, 0), m1(1, 0), m1(0, 1), m1(1, 1));
m1(0, 1), m1(1, 1));
} }
template<RealType T> template <RealType T>
bool IsIdentityMatrix(const TMatrix2<T>& m1, T threshold = P_FLT_INAC) bool IsIdentityMatrix(const TMatrix2<T>& m1, T threshold = P_FLT_INAC)
{ {
return (abs(m1(0, 0) - (T)1.0) < P_FLT_INAC && abs(m1(0, 1)) < P_FLT_INAC && return (abs(m1(0, 0) - (T)1.0) < P_FLT_INAC && abs(m1(0, 1)) < P_FLT_INAC &&
abs(m1(1, 0)) < P_FLT_INAC && abs(m1(1, 1) - (T)1.0) < P_FLT_INAC); abs(m1(1, 0)) < P_FLT_INAC && abs(m1(1, 1) - (T)1.0) < P_FLT_INAC);
} }
} // Phanes::Core::Math } // namespace Phanes::Core::Math
#endif // !MATRIX2_H #endif // !MATRIX2_H
#include "Core/Math/SIMD/SIMDIntrinsics.h" #include "Core/Math/SIMD/SIMDIntrinsics.h"

View File

@@ -83,7 +83,7 @@ namespace Phanes::Core::Math {
/// Construct matrix from field of values. /// Construct matrix from field of values.
/// </summary> /// </summary>
/// <param name="field"></param> /// <param name="field"></param>
TMatrix4(T field[4][4]) explicit TMatrix4(T field[4][4])
{ {
this->c0 = TVector4(field[0]); this->c0 = TVector4(field[0]);
this->c1 = TVector4(field[1]); this->c1 = TVector4(field[1]);

View File

@@ -0,0 +1,85 @@
#pragma once
#include "Core/Math/Boilerplate.h"
#include "Core/Math/MathFwd.h"
#include "Core/Math/SIMD/PhanesSIMDTypes.h"
#include "Core/Math/SIMD/Storage.h"
#include "Core/Math/Vector3.hpp"
#include "Core/Math/Vector4.hpp"
#ifndef QUATERNION_H
# define QUATERNION_H
namespace Phanes::Core::Math
{
// Quaternion
template <RealType T, bool S>
struct TQuaternion
{
using Real = T;
public:
union
{
struct
{
float x;
float y;
float z;
float w;
};
union
{
typename SIMD::Storage<4, Real, SIMD::use_simd<Real, 4, S>::value>::type comp;
typename SIMD::Storage<4, Real, SIMD::use_simd<Real, 4, S>::value>::type data;
};
};
public:
/// Default constructor
TQuaternion() = default;
/**
* Construct quaternion from vector4.
* v.w is the scalar part of the quaternion (q.w).
*/
explicit TQuaternion(const TVector4<T, S>& v);
/**
* Construct quaternion from vector (x,y,z) and scalar part (w).
*
* @param x X
* @param y Y
* @param z Z
* @param w W
*/
TQuaternion(Real x, Real y, Real z, Real w);
/**
* Construct vector from vector part and scalar part.
*/
TQuaternion(const TVector3<Real, S>& v, Real w);
/**
* Construct quaternion from array of length >= four.
*
* @note If used with SIMD the array will is assumed to be aligned.
*/
explicit TQuaternion(const Real* comp);
/**
* Construct from euler angles (yaw, pitch, roll)
*/
explicit TQuaternion(const TVector3<Real, S>& euler_angels);
/**
* Construct from Transformation
*/
explicit TQuaternion(const TTransform<Real>& t);
explicit TQuaternion(const TMatrix4<Real, S>& t);
};
} // namespace Phanes::Core::Math
#endif // QUATERNION_H

View File

@@ -1,21 +0,0 @@
#include <iostream>
#include "Core/Math/Include.h"
namespace PMath = Phanes::Core::Math;
int main()
{
PMath::Matrix4 m0 = PMath::Matrix4(1.0f, 5.0f, 3.0f, 4.0f,
2.0f, 6.0f, 4.0f, 1.0f,
2.0f, -3.0f, 5.0f, 3.0f,
8.0f, -4.0f, 6.0f, -2.0f);
PMath::Matrix4 m2;
std::cout << std::to_string(PMath::InverseV<float, false>(m0)) << std::endl;
std::cout << PMath::ToString(m0) << std::endl;
return 0;
}

File diff suppressed because it is too large Load Diff

View File

@@ -1,2 +1,45 @@
# PhanesEngine # PhanesEngine
3D / 2D Game Engine.
Yet another Game Engine written in C++.
## Build
For building the engine premake5 is required. Execute `premake5 gmake` to generate the Makefile.
### PhanesCore
The Core Runtime library is build with:
make PhanesCore
## Status
Phanes is and will be developed, though progress will be slow.
### Currenty under development
- PhanesCore
- <span style="color:green; font-weight:800">Math</span>
## Testing
Testing PhanesEngine happens via the gtest framework. To run the tests for PhanesEngine one needs to
build the test applications (currently only MathTestFPU) as well as gtet.
make MathTestFPU
They depend on the gtest library so it should not be required to build it manually. If for some reason this doesn't
work gtest can be build via:
make gtest
## Sample Project
The repository contains a sample game project using PhanesEngine. It can be build by executing:
make DevPlayground
## Copyright
PhanesEngine was developed by Thorben Höhne and is licensed under the Apache License Version 2.0. See
[LICENSE](LICENSE) for more information.

View File

@@ -63,6 +63,8 @@ function boilerplate()
buildoptions({ "-Wno-unused-parameter", "-fms-extensions" }) buildoptions({ "-Wno-unused-parameter", "-fms-extensions" })
end end
buildoptions({"-fno-fast-math"})
filter("configurations:Debug") filter("configurations:Debug")
defines({ "DEBUG", "TRACE", "P_DEBUG" }) defines({ "DEBUG", "TRACE", "P_DEBUG" })
symbols("On") symbols("On")