mirror of
https://github.com/orange-cpp/omath.git
synced 2026-02-13 07:03:25 +00:00
refactored camera
This commit is contained in:
@@ -16,7 +16,7 @@ namespace omath
|
||||
Clamped = 1,
|
||||
};
|
||||
|
||||
template<class Type, Type min = Type(0), Type max = Type(360), AngleFlags flags = AngleFlags::Normalized>
|
||||
template<class Type = float, Type min = Type(0), Type max = Type(360), AngleFlags flags = AngleFlags::Normalized>
|
||||
requires std::is_arithmetic_v<Type>
|
||||
class Angle
|
||||
{
|
||||
|
||||
@@ -320,23 +320,23 @@ namespace omath
|
||||
std::array<Type, Rows * Columns> m_data;
|
||||
};
|
||||
|
||||
template<class T = float, MatStoreType St = MatStoreType::ROW_MAJOR>
|
||||
template<class Type = float, MatStoreType St = MatStoreType::ROW_MAJOR>
|
||||
[[nodiscard]]
|
||||
constexpr static Mat<1, 4, T, St> MatRowFromVector(const Vector3& vector) noexcept
|
||||
constexpr static Mat<1, 4, Type, St> MatRowFromVector(const Vector3& vector) noexcept
|
||||
{
|
||||
return {{vector.x, vector.y, vector.z, 1}};
|
||||
}
|
||||
|
||||
template<class T = float, MatStoreType St = MatStoreType::ROW_MAJOR>
|
||||
template<class Type = float, MatStoreType St = MatStoreType::ROW_MAJOR>
|
||||
[[nodiscard]]
|
||||
constexpr static Mat<4, 1, T, St> MatColumnFromVector(const Vector3& vector) noexcept
|
||||
constexpr static Mat<4, 1, Type, St> MatColumnFromVector(const Vector3& vector) noexcept
|
||||
{
|
||||
return {{vector.x}, {vector.y}, {vector.z}, {1}};
|
||||
}
|
||||
|
||||
template<class T = float, MatStoreType St = MatStoreType::ROW_MAJOR>
|
||||
template<class Type = float, MatStoreType St = MatStoreType::ROW_MAJOR>
|
||||
[[nodiscard]]
|
||||
constexpr Mat<4, 4, T, St> MatTranslation(const Vector3& diff) noexcept
|
||||
constexpr Mat<4, 4, Type, St> MatTranslation(const Vector3& diff) noexcept
|
||||
{
|
||||
return
|
||||
{
|
||||
@@ -346,4 +346,42 @@ namespace omath
|
||||
{0, 0, 0, 1},
|
||||
};
|
||||
}
|
||||
|
||||
template<class Type = float, MatStoreType St = MatStoreType::ROW_MAJOR, class Angle>
|
||||
[[nodiscard]]
|
||||
constexpr Mat<3, 3, Type, St> RotationMatrixAxisX(const Angle& roll) noexcept
|
||||
{
|
||||
return
|
||||
{
|
||||
{1, 0, 0},
|
||||
{0, 0, roll.Cos(), -roll.Sin()},
|
||||
{0, 0, roll.Sin(), roll.Cos()},
|
||||
};
|
||||
}
|
||||
|
||||
template<class Type = float, MatStoreType St = MatStoreType::ROW_MAJOR, class Angle>
|
||||
[[nodiscard]]
|
||||
constexpr Mat<3, 3, Type, St> RotationMatrixAxisY(const Angle& pitch) noexcept
|
||||
{
|
||||
return
|
||||
{
|
||||
{pitch.Cos(), 0, pitch.Sin()},
|
||||
{0 , 1, 0},
|
||||
{-pitch.Sin(), 0, pitch.Cos()},
|
||||
};
|
||||
}
|
||||
|
||||
template<class Type = float, MatStoreType St = MatStoreType::ROW_MAJOR, class Angle>
|
||||
[[nodiscard]]
|
||||
constexpr Mat<3, 3, Type, St> RotationMatrixAxisZ(const Angle& Yaw) noexcept
|
||||
{
|
||||
return
|
||||
{
|
||||
{Yaw.Cos(), -Yaw.Sin(), 0},
|
||||
{Yaw.Sin(), Yaw.Cos(), 0},
|
||||
{0, 0, 1},
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
} // namespace omath
|
||||
|
||||
22
include/omath/engines/Source/Camera.hpp
Normal file
22
include/omath/engines/Source/Camera.hpp
Normal file
@@ -0,0 +1,22 @@
|
||||
//
|
||||
// Created by Orange on 12/4/2024.
|
||||
//
|
||||
#pragma once
|
||||
#include "Constants.h"
|
||||
#include "omath/projection/Camera.hpp"
|
||||
|
||||
namespace omath::source
|
||||
{
|
||||
class Camera final : public projection::Camera<Mat4x4, ViewAngles>
|
||||
{
|
||||
public:
|
||||
Camera(const Vector3& position, const ViewAngles& viewAngles,
|
||||
const projection::ViewPort& viewPort, const Angle<float, 0, 180, AngleFlags::Clamped>& fov, float near, const float far) :
|
||||
projection::Camera<Mat4x4, ViewAngles>(position, viewAngles, viewPort, fov, near, far)
|
||||
{
|
||||
}
|
||||
void LookAt(const Vector3& target) override;
|
||||
[[nodiscard]] Mat4x4 GetViewMatrix() const override;
|
||||
[[nodiscard]] Mat4x4 GetProjectionMatrix() const override;
|
||||
};
|
||||
}
|
||||
24
include/omath/engines/Source/Constants.h
Normal file
24
include/omath/engines/Source/Constants.h
Normal file
@@ -0,0 +1,24 @@
|
||||
//
|
||||
// Created by Orange on 12/4/2024.
|
||||
//
|
||||
#pragma once
|
||||
|
||||
#include <omath/Vector3.hpp>
|
||||
#include <omath/Mat.hpp>
|
||||
#include <omath/Angle.hpp>
|
||||
#include <omath/ViewAngles.hpp>
|
||||
namespace omath::source
|
||||
{
|
||||
constexpr Vector3 kAbsUp = {0, 0, 1};
|
||||
constexpr Vector3 kAbsRight = {0, -1, 0};
|
||||
constexpr Vector3 kAbsForward = {1, 0, 0};
|
||||
|
||||
using Mat4x4 = Mat<4, 4, float, MatStoreType::ROW_MAJOR>;
|
||||
using Mat3x3 = Mat<4, 4, float, MatStoreType::ROW_MAJOR>;
|
||||
|
||||
using PitchAngle = Angle<float, -89.f, 89.f, AngleFlags::Clamped>;
|
||||
using YawAngle = Angle<float, -180.f, 180.f, AngleFlags::Normalized>;
|
||||
using RollAngle = Angle<float, -180.f, 180.f, AngleFlags::Normalized>;
|
||||
|
||||
using ViewAngles = omath::ViewAngles<PitchAngle, YawAngle, RollAngle>;
|
||||
} // namespace omath::source
|
||||
98
include/omath/engines/Source/Formulas.hpp
Normal file
98
include/omath/engines/Source/Formulas.hpp
Normal file
@@ -0,0 +1,98 @@
|
||||
//
|
||||
// Created by Orange on 12/4/2024.
|
||||
//
|
||||
#pragma once
|
||||
#include "Constants.h"
|
||||
|
||||
|
||||
namespace omath::source
|
||||
{
|
||||
[[nodiscard]]
|
||||
inline Vector3 ForwardVector(const ViewAngles& angles)
|
||||
{
|
||||
const auto cosPitch = angles.pitch.Cos();
|
||||
const auto sinPitch = angles.pitch.Sin();
|
||||
|
||||
const auto cosYaw = angles.yaw.Cos();
|
||||
const auto sinYaw = angles.yaw.Sin();
|
||||
|
||||
|
||||
return {cosPitch * cosYaw, cosPitch * sinYaw, -sinPitch};
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
inline Vector3 RightVector(const ViewAngles& angles)
|
||||
{
|
||||
const auto cosPitch = angles.pitch.Cos();
|
||||
const auto sinPitch = angles.pitch.Sin();
|
||||
|
||||
const auto cosYaw = angles.yaw.Cos();
|
||||
const auto sinYaw = angles.yaw.Sin();
|
||||
|
||||
const auto cosRoll = angles.roll.Cos();
|
||||
const auto sinRoll = angles.roll.Sin();
|
||||
|
||||
|
||||
return
|
||||
{
|
||||
-1 * sinRoll * sinPitch * cosYaw + -1 * cosRoll * -sinYaw,
|
||||
-1 * sinRoll * sinPitch * sinYaw + -1 * cosRoll * cosYaw,
|
||||
-1 * sinRoll * cosPitch
|
||||
};
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
inline Vector3 UpVector(const ViewAngles& angles)
|
||||
{
|
||||
const auto cosPitch = angles.pitch.Cos();
|
||||
const auto sinPitch = angles.pitch.Sin();
|
||||
|
||||
const auto cosYaw = angles.yaw.Cos();
|
||||
const auto sinYaw = angles.yaw.Sin();
|
||||
|
||||
const auto cosRoll = angles.roll.Cos();
|
||||
const auto sinRoll = angles.roll.Sin();
|
||||
|
||||
|
||||
return
|
||||
{
|
||||
cosRoll * sinPitch * cosYaw + - sinRoll * -sinYaw,
|
||||
cosRoll * sinPitch * sinYaw + - sinRoll * cosYaw,
|
||||
cosRoll * cosPitch,
|
||||
};
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
constexpr Mat4x4 ViewMatrixFromVecs(const Vector3& forward, const Vector3& right, const Vector3& up,
|
||||
const Vector3& camera_pos)
|
||||
{
|
||||
return Mat4x4{
|
||||
{right.x, right.y, right.z, 0},
|
||||
{up.x, up.y, up.z, 0},
|
||||
{forward.x, forward.y, forward.z, 0},
|
||||
{0, 0, 0, 1},
|
||||
} *
|
||||
MatTranslation<float, MatStoreType::ROW_MAJOR>(-camera_pos);
|
||||
}
|
||||
|
||||
[[nodiscard]] inline Mat4x4 ViewMatrix(const ViewAngles& angles, const Vector3& cam_origin)
|
||||
{
|
||||
return ViewMatrixFromVecs(ForwardVector(angles), RightVector(angles), UpVector(angles), cam_origin);
|
||||
}
|
||||
|
||||
|
||||
[[nodiscard]]
|
||||
inline Mat4x4 PerspectiveProjectionMatrix(const float fieldOfView, const float aspectRatio, const float near, const float far)
|
||||
{
|
||||
constexpr auto kMultiplyFactor = 0.75f;
|
||||
|
||||
const float fovHalfTan = std::tan(angles::DegreesToRadians(fieldOfView) / 2.f) * kMultiplyFactor;
|
||||
|
||||
return {
|
||||
{-1.f / (aspectRatio * fovHalfTan), 0, 0, 0},
|
||||
{0, -1.f / (fovHalfTan), 0, 0},
|
||||
{0, 0, (far + near) / (far - near), -(2.f * far * near) / (far - near)},
|
||||
{0, 0, 1, 0},
|
||||
};
|
||||
}
|
||||
} // namespace omath::source
|
||||
@@ -2,9 +2,10 @@
|
||||
// Created by Orange on 11/23/2024.
|
||||
//
|
||||
#pragma once
|
||||
#include "omath/Vector3.hpp"
|
||||
#include "omath/Mat.hpp"
|
||||
|
||||
#include "omath/Angle.hpp"
|
||||
#include "omath/Mat.hpp"
|
||||
#include "omath/Vector3.hpp"
|
||||
|
||||
namespace omath::opengl
|
||||
{
|
||||
@@ -14,34 +15,31 @@ namespace omath::opengl
|
||||
|
||||
|
||||
template<class Type = float>
|
||||
requires std::is_floating_point_v<Type> || std::is_integral_v<Type>
|
||||
[[nodiscard]] Mat<4, 4, Type, MatStoreType::COLUMN_MAJOR> ViewMatrix(const Vector3& forward,
|
||||
const Vector3& right,
|
||||
const Vector3& up,
|
||||
const Vector3& cam_origin)
|
||||
requires std::is_arithmetic_v<Type>
|
||||
[[nodiscard]] Mat<4, 4, Type, MatStoreType::COLUMN_MAJOR> ViewMatrix(const Vector3& forward, const Vector3& right,
|
||||
const Vector3& up, const Vector3& cam_origin)
|
||||
{
|
||||
return
|
||||
return Mat<4, 4, Type, MatStoreType::COLUMN_MAJOR>
|
||||
{
|
||||
{right.x, up.x, -forward.x, 0},
|
||||
{right.y, up.y, -forward.y, 0},
|
||||
{right.z, up.z, -forward.z, 0},
|
||||
{-cam_origin.x, -cam_origin.y, -cam_origin.z, 1},
|
||||
};
|
||||
{right.x, right.y, right.z, 0},
|
||||
{up.x, up.y, up.z, 0},
|
||||
{-forward.x, -forward.y, -forward.z, 0},
|
||||
{0, 0, 0, 1},
|
||||
} * MatTranslation<Type, MatStoreType::COLUMN_MAJOR>(-cam_origin);
|
||||
}
|
||||
|
||||
template<class Type>
|
||||
requires std::is_floating_point_v<Type> || std::is_integral_v<Type>
|
||||
[[nodiscard]] Mat<4, 4, Type, MatStoreType::COLUMN_MAJOR> PerspectiveProjectionMatrix(
|
||||
const float fieldOfView, const Type& aspectRatio, const Type& near, const Type& far)
|
||||
requires std::is_arithmetic_v<Type>
|
||||
[[nodiscard]] Mat<4, 4, Type, MatStoreType::COLUMN_MAJOR>
|
||||
PerspectiveProjectionMatrix(const float fieldOfView, const Type& aspectRatio, const Type& near, const Type& far)
|
||||
{
|
||||
const float fovHalfTan = std::tan(angles::DegreesToRadians(fieldOfView) / 2);
|
||||
|
||||
return
|
||||
{
|
||||
{static_cast<Type>(1) / (aspectRatio * fovHalfTan), 0, 0, 0},
|
||||
{0, static_cast<Type>(1) / (fovHalfTan), 0, 0},
|
||||
{0, 0, -(far + near) / (far - near), -(static_cast<Type>(2) * far * near) / (far - near)},
|
||||
{0, 0, -1, 0},
|
||||
return {
|
||||
{static_cast<Type>(1) / (aspectRatio * fovHalfTan), 0, 0, 0},
|
||||
{0, static_cast<Type>(1) / (fovHalfTan), 0, 0},
|
||||
{0, 0, -(far + near) / (far - near), -(static_cast<Type>(2) * far * near) / (far - near)},
|
||||
{0, 0, -1, 0},
|
||||
};
|
||||
}
|
||||
}
|
||||
} // namespace omath::opengl
|
||||
|
||||
@@ -1,135 +0,0 @@
|
||||
//
|
||||
// Created by Orange on 11/24/2024.
|
||||
//
|
||||
#pragma once
|
||||
#include "omath/Mat.hpp"
|
||||
#include "omath/Vector3.hpp"
|
||||
|
||||
#include <omath/Angle.hpp>
|
||||
#include <omath/ViewAngles.hpp>
|
||||
#include <omath/projection/Camera.hpp>
|
||||
|
||||
namespace omath::source
|
||||
{
|
||||
constexpr Vector3 kAbsUp = {0, 0, 1};
|
||||
constexpr Vector3 kAbsRight = {0, -1, 0};
|
||||
constexpr Vector3 kAbsForward = {1, 0, 0};
|
||||
|
||||
using PitchAngle = Angle<float, -89.f, 89.f, AngleFlags::Clamped>;
|
||||
using YawAngle = Angle<float, -180.f, 180.f, AngleFlags::Normalized>;
|
||||
using RollAngle = Angle<float, -180.f, 180.f, AngleFlags::Normalized>;
|
||||
|
||||
using ViewAngles = omath::ViewAngles<PitchAngle, YawAngle, RollAngle>;
|
||||
|
||||
|
||||
inline Vector3 ForwardVector(const ViewAngles& angles);
|
||||
inline Vector3 RightVector(const ViewAngles& angles);
|
||||
inline Vector3 UpVector(const ViewAngles& angles);
|
||||
|
||||
|
||||
template<class Type = float>
|
||||
requires std::is_floating_point_v<Type> || std::is_integral_v<Type>
|
||||
[[nodiscard]] constexpr Mat<4, 4, Type, MatStoreType::ROW_MAJOR> ViewMatrixFromVecs(const Vector3& forward, const Vector3& right,
|
||||
const Vector3& up, const Vector3& camera_pos)
|
||||
{
|
||||
return Mat<4, 4, Type, MatStoreType::ROW_MAJOR>{
|
||||
{right.x, right.y, right.z, 0},
|
||||
{up.x, up.y, up.z, 0},
|
||||
{forward.x, forward.y, forward.z, 0},
|
||||
{0, 0, 0, 1},
|
||||
} * MatTranslation<float, MatStoreType::ROW_MAJOR>(-camera_pos) ;
|
||||
}
|
||||
|
||||
|
||||
template<class Type = float>
|
||||
requires std::is_floating_point_v<Type> || std::is_integral_v<Type>
|
||||
[[nodiscard]] Mat<4, 4, Type, MatStoreType::ROW_MAJOR> ViewMatrix(const ViewAngles& angles, const Vector3& cam_origin)
|
||||
{
|
||||
return ViewMatrixFromVecs(ForwardVector(angles), RightVector(angles), UpVector(angles), cam_origin);
|
||||
}
|
||||
|
||||
template<class Type>
|
||||
requires std::is_arithmetic_v<Type> && std::is_signed_v<Type>
|
||||
[[nodiscard]] Mat<4, 4, Type, MatStoreType::ROW_MAJOR>
|
||||
PerspectiveProjectionMatrix(const Type& fieldOfView, const Type& aspectRatio, const Type& near, const Type& far)
|
||||
{
|
||||
constexpr auto kMultiplyFactor = Type(0.75);
|
||||
|
||||
const Type fovHalfTan = std::tan(angles::DegreesToRadians(fieldOfView) / 2) * kMultiplyFactor;
|
||||
|
||||
return {
|
||||
{-static_cast<Type>(1) / (aspectRatio * fovHalfTan), 0, 0, 0},
|
||||
{0, -static_cast<Type>(1) / (fovHalfTan), 0, 0},
|
||||
{0, 0, (far + near) / (far - near), -(static_cast<Type>(2) * far * near) / (far - near)},
|
||||
{0, 0, 1, 0},
|
||||
};
|
||||
}
|
||||
// Copied from
|
||||
// https://github.com/ValveSoftware/source-sdk-2013/blob/0d8dceea4310fde5706b3ce1c70609d72a38efdf/mp/src/mathlib/mathlib_base.cpp#L919
|
||||
[[nodiscard]]
|
||||
inline Vector3 ForwardVector(const ViewAngles& angles)
|
||||
{
|
||||
const auto cosPitch = angles.pitch.Cos();
|
||||
const auto sinPitch = angles.pitch.Sin();
|
||||
|
||||
const auto cosYaw = angles.yaw.Cos();
|
||||
const auto sinYaw = angles.yaw.Sin();
|
||||
|
||||
|
||||
return {cosPitch * cosYaw, cosPitch * sinYaw, -sinPitch};
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
inline Vector3 RightVector(const ViewAngles& angles)
|
||||
{
|
||||
const auto cosPitch = angles.pitch.Cos();
|
||||
const auto sinPitch = angles.pitch.Sin();
|
||||
|
||||
const auto cosYaw = angles.yaw.Cos();
|
||||
const auto sinYaw = angles.yaw.Sin();
|
||||
|
||||
const auto cosRoll = angles.roll.Cos();
|
||||
const auto sinRoll = angles.roll.Sin();
|
||||
|
||||
|
||||
return
|
||||
{
|
||||
-1 * sinRoll * sinPitch * cosYaw + -1 * cosRoll * -sinYaw,
|
||||
-1 * sinRoll * sinPitch * sinYaw + -1 * cosRoll * cosYaw,
|
||||
-1 * sinRoll * cosPitch
|
||||
};
|
||||
}
|
||||
|
||||
[[nodiscard]]
|
||||
inline Vector3 UpVector(const ViewAngles& angles)
|
||||
{
|
||||
const auto cosPitch = angles.pitch.Cos();
|
||||
const auto sinPitch = angles.pitch.Sin();
|
||||
|
||||
const auto cosYaw = angles.yaw.Cos();
|
||||
const auto sinYaw = angles.yaw.Sin();
|
||||
|
||||
const auto cosRoll = angles.roll.Cos();
|
||||
const auto sinRoll = angles.roll.Sin();
|
||||
|
||||
|
||||
return
|
||||
{
|
||||
cosRoll * sinPitch * cosYaw + - sinRoll * -sinYaw,
|
||||
cosRoll * sinPitch * sinYaw + - sinRoll * cosYaw,
|
||||
cosRoll * cosPitch,
|
||||
};
|
||||
}
|
||||
using Camera = omath::projection::Camera<ViewAngles, decltype(ViewMatrix<float>), decltype(PerspectiveProjectionMatrix<float>)>;
|
||||
|
||||
|
||||
// Camera(const Vector3& position, const ViewAnglesType& viewAngles, const ViewPort& viewPort,
|
||||
// const Angle<float, 0.f, 180.f, AngleFlags::Clamped>& fov, const float near, const float far,
|
||||
// const std::function<ViewMatFunc>& viewMatFunc, const std::function<ProjectionFunc>& projFunc)
|
||||
|
||||
inline Camera CreateCamera(const Vector3& position, const auto& viewAngles, const projection::ViewPort& viewPort,
|
||||
const Angle<float, 0.f, 180.f, AngleFlags::Clamped>& fov, const float near, const float far)
|
||||
{
|
||||
return Camera(position, viewAngles, viewPort, fov, near, far, ViewMatrix<float>, PerspectiveProjectionMatrix<float>);
|
||||
}
|
||||
} // namespace omath::source
|
||||
@@ -26,42 +26,33 @@ namespace omath::projection
|
||||
}
|
||||
};
|
||||
|
||||
template<class ViewAnglesType, class ViewMatFunc, class ProjectionFunc>
|
||||
requires std::is_same_v<std::invoke_result_t<ViewMatFunc, const ViewAnglesType&, const Vector3&>,
|
||||
std::invoke_result_t<ProjectionFunc, const float&, const float&, const float&, const float&>>
|
||||
template<class Mat4x4Type, class ViewAnglesType>
|
||||
class Camera
|
||||
{
|
||||
|
||||
public:
|
||||
virtual ~Camera() = default;
|
||||
Camera(const Vector3& position, const ViewAnglesType& viewAngles, const ViewPort& viewPort,
|
||||
const Angle<float, 0.f, 180.f, AngleFlags::Clamped>& fov, const float near, const float far,
|
||||
const std::function<ViewMatFunc>& viewMatFunc, const std::function<ProjectionFunc>& projFunc) :
|
||||
const Angle<float, 0.f, 180.f, AngleFlags::Clamped>& fov, const float near, const float far) :
|
||||
m_viewPort(viewPort), m_fieldOfView(fov), m_farPlaneDistance(far), m_nearPlaneDistance(near),
|
||||
m_viewAngles(viewAngles), m_origin(position), CreateViewMatrix(viewMatFunc), CreateProjectionMatrix(projFunc)
|
||||
m_viewAngles(viewAngles), m_origin(position)
|
||||
{
|
||||
}
|
||||
|
||||
void LookAt(const Vector3& target);
|
||||
virtual void LookAt(const Vector3& target) = 0;
|
||||
|
||||
[[nodiscard]] auto GetViewMatrix() const
|
||||
{
|
||||
return CreateViewMatrix(m_viewAngles, m_origin);
|
||||
}
|
||||
[[nodiscard]] virtual Mat4x4Type GetViewMatrix() const = 0;
|
||||
|
||||
[[nodiscard]] auto GetProjectionMatrix() const
|
||||
{
|
||||
return CreateProjectionMatrix(m_fieldOfView.AsDegrees(), m_viewPort.AspectRatio(), m_nearPlaneDistance, m_farPlaneDistance);
|
||||
}
|
||||
[[nodiscard]] virtual Mat4x4Type GetProjectionMatrix() const = 0;
|
||||
|
||||
[[nodiscard]] auto GetViewProjectionMatrix() const
|
||||
[[nodiscard]] Mat4x4Type GetViewProjectionMatrix() const
|
||||
{
|
||||
return GetProjectionMatrix() * GetViewMatrix();
|
||||
}
|
||||
|
||||
[[nodiscard]] std::expected<Vector3, Error> WorldToScreen(const Vector3& worldPosition) const
|
||||
{
|
||||
using mat = std::invoke_result_t<ViewMatFunc, const ViewAnglesType&, const Vector3&>;
|
||||
auto projected = GetViewProjectionMatrix() * MatColumnFromVector<float, mat::GetStoreOrdering()>(worldPosition);
|
||||
auto projected = GetViewProjectionMatrix() * MatColumnFromVector<float, Mat4x4Type::GetStoreOrdering()>(worldPosition);
|
||||
|
||||
if (projected.At(3, 0) == 0.0f)
|
||||
return std::unexpected(Error::WORLD_POSITION_IS_OUT_OF_SCREEN_BOUNDS);
|
||||
@@ -74,20 +65,18 @@ namespace omath::projection
|
||||
return Vector3{++projected.At(0,0) / 2 * m_viewPort.m_width , ++projected.At(1,0) / 2 * m_viewPort.m_height, projected.At(2,0)};
|
||||
}
|
||||
|
||||
protected:
|
||||
ViewPort m_viewPort{};
|
||||
Angle<float, 0.f, 180.f, AngleFlags::Clamped> m_fieldOfView;
|
||||
|
||||
float m_farPlaneDistance;
|
||||
float m_nearPlaneDistance;
|
||||
|
||||
private:
|
||||
|
||||
ViewAnglesType m_viewAngles;
|
||||
Vector3 m_origin;
|
||||
|
||||
std::function<ViewMatFunc> CreateViewMatrix;
|
||||
std::function<ProjectionFunc> CreateProjectionMatrix;
|
||||
|
||||
private:
|
||||
|
||||
template<class Type>
|
||||
[[nodiscard]]
|
||||
|
||||
@@ -11,3 +11,4 @@ add_subdirectory(prediction)
|
||||
add_subdirectory(pathfinding)
|
||||
add_subdirectory(projection)
|
||||
add_subdirectory(collision)
|
||||
add_subdirectory(engines)
|
||||
1
source/engines/CMakeLists.txt
Normal file
1
source/engines/CMakeLists.txt
Normal file
@@ -0,0 +1 @@
|
||||
add_subdirectory(Source)
|
||||
1
source/engines/Source/CMakeLists.txt
Normal file
1
source/engines/Source/CMakeLists.txt
Normal file
@@ -0,0 +1 @@
|
||||
target_sources(omath PRIVATE Camera.cpp)
|
||||
31
source/engines/Source/Camera.cpp
Normal file
31
source/engines/Source/Camera.cpp
Normal file
@@ -0,0 +1,31 @@
|
||||
//
|
||||
// Created by Orange on 12/4/2024.
|
||||
//
|
||||
#include "omath/engines/Source/Camera.hpp"
|
||||
#include "omath/engines/Source/Formulas.hpp"
|
||||
|
||||
|
||||
namespace omath::source
|
||||
{
|
||||
|
||||
void Camera::LookAt(const Vector3& target)
|
||||
{
|
||||
const float distance = m_origin.DistTo(target);
|
||||
const auto delta = target - m_origin;
|
||||
|
||||
|
||||
m_viewAngles.pitch = PitchAngle::FromRadians(std::asin(delta.z / distance));
|
||||
m_viewAngles.yaw = YawAngle::FromRadians(std::atan2(delta.y, delta.x));
|
||||
m_viewAngles.roll = RollAngle::FromRadians(0.f);
|
||||
}
|
||||
|
||||
Mat4x4 Camera::GetViewMatrix() const
|
||||
{
|
||||
return ViewMatrix(m_viewAngles, m_origin);
|
||||
}
|
||||
|
||||
Mat4x4 Camera::GetProjectionMatrix() const
|
||||
{
|
||||
return PerspectiveProjectionMatrix(m_fieldOfView.AsDegrees(), m_viewPort.AspectRatio(), m_nearPlaneDistance, m_farPlaneDistance);
|
||||
}
|
||||
} // namespace omath::source
|
||||
@@ -4,13 +4,13 @@
|
||||
|
||||
#include "omath/prediction/Projectile.hpp"
|
||||
#include <cmath>
|
||||
#include <omath/engines/Source.hpp>
|
||||
#include <omath/engines/Source/Formulas.hpp>
|
||||
|
||||
namespace omath::prediction
|
||||
{
|
||||
Vector3 Projectile::PredictPosition(const float pitch, const float yaw, const float time, const float gravity) const
|
||||
{
|
||||
auto currentPos = m_origin + omath::source::ForwardVector({source::PitchAngle::FromDegrees(pitch), source::YawAngle::FromDegrees(yaw), source::RollAngle::FromDegrees(0)}) * m_launchSpeed * time;
|
||||
auto currentPos = m_origin + omath::source::ForwardVector({source::PitchAngle::FromDegrees(-pitch), source::YawAngle::FromDegrees(yaw), source::RollAngle::FromDegrees(0)}) * m_launchSpeed * time;
|
||||
currentPos.z -= (gravity * m_gravityScale) * std::pow(time, 2.f) * 0.5f;
|
||||
|
||||
return currentPos;
|
||||
|
||||
@@ -6,7 +6,6 @@
|
||||
#include <omath/Matrix.hpp>
|
||||
#include <print>
|
||||
#include <omath/engines/OpenGL.hpp>
|
||||
#include <omath/engines/Source.hpp>
|
||||
// #include <glm/glm.hpp>
|
||||
|
||||
// #include "glm/ext/matrix_clip_space.hpp"
|
||||
|
||||
@@ -2,7 +2,8 @@
|
||||
// Created by Orange on 11/23/2024.
|
||||
//
|
||||
#include <gtest/gtest.h>
|
||||
#include <omath/engines/Source.hpp>
|
||||
#include <omath/engines/Source/Constants.h>
|
||||
#include <omath/engines/Source/Formulas.hpp>
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -4,14 +4,14 @@
|
||||
#include <complex>
|
||||
#include <gtest/gtest.h>
|
||||
#include <omath/Matrix.hpp>
|
||||
#include <omath/engines/Source.hpp>
|
||||
#include <omath/engines/Source/Camera.hpp>
|
||||
#include <omath/projection/Camera.hpp>
|
||||
#include <print>
|
||||
|
||||
TEST(UnitTestProjection, Projection)
|
||||
{
|
||||
auto x = omath::Angle<float, 0.f, 180.f, omath::AngleFlags::Clamped>::FromDegrees(90.f);
|
||||
auto cam = omath::source::CreateCamera({-10, 0, 0}, omath::source::ViewAngles{}, {1920.f, 1080.f}, x, 0.1f, 1000.f);
|
||||
auto cam = omath::source::Camera({-10, 0, 0}, omath::source::ViewAngles{}, {1920.f, 1080.f}, x, 0.1f, 1000.f);
|
||||
|
||||
const auto projected = cam.WorldToScreen({10, 0, 0});
|
||||
std::print("{} {} {}", projected->x, projected->y, projected->z);
|
||||
|
||||
Reference in New Issue
Block a user