Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .github/workflows/cmake-multi-platform.yml
Original file line number Diff line number Diff line change
Expand Up @@ -107,7 +107,7 @@ jobs:
-DOMATH_BUILD_TESTS=ON \
-DOMATH_BUILD_BENCHMARK=OFF \
-DOMATH_ENABLE_COVERAGE=${{ matrix.coverage == true && 'ON' || 'OFF' }} \
-DVCPKG_MANIFEST_FEATURES="imgui;avx2;tests;lua"
-DVCPKG_MANIFEST_FEATURES="imgui;avx2;tests;lua;gcem"

- name: Build
shell: bash
Expand Down
10 changes: 10 additions & 0 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@ option(OMATH_ENABLE_FORCE_INLINE
option(OMATH_ENABLE_LUA
"omath bindings for lua" OFF)
option(OMATH_ENABLE_HOOKING "omath will HooksManager that can hook DirectX/OpenGL automatically" OFF)
option(OMATH_USE_GCEM "omath will use gcem library to make more functions/methods constexpr" OFF)

if(VCPKG_MANIFEST_FEATURES)
foreach(omath_feature IN LISTS VCPKG_MANIFEST_FEATURES)
Expand All @@ -50,6 +51,8 @@ if(VCPKG_MANIFEST_FEATURES)
set(OMATH_ENABLE_LUA ON)
elseif(omath_feature STREQUAL "hooking")
set(OMATH_ENABLE_HOOKING ON)
elseif (omath_feature STREQUAL "gcem")
set(OMATH_USE_GCEM ON)
endif()

endforeach()
Expand Down Expand Up @@ -80,6 +83,7 @@ if(${PROJECT_IS_TOP_LEVEL})
message(STATUS "[${PROJECT_NAME}]: Coverage feature status ${OMATH_ENABLE_COVERAGE}")
message(STATUS "[${PROJECT_NAME}]: Valgrind feature status ${OMATH_ENABLE_VALGRIND}")
message(STATUS "[${PROJECT_NAME}]: Lua feature status ${OMATH_ENABLE_LUA}")
message(STATUS "[${PROJECT_NAME}]: Gcem feature status ${OMATH_USE_GCEM}")
endif()

if(OMATH_STATIC_MSVC_RUNTIME_LIBRARY)
Expand Down Expand Up @@ -120,6 +124,12 @@ if (OMATH_ENABLE_HOOKING)
endif ()
endif ()


if (OMATH_USE_GCEM)
target_compile_definitions(${PROJECT_NAME} PUBLIC OMATH_USE_GCEM)
find_package(gcem CONFIG REQUIRED)
target_link_libraries(${PROJECT_NAME} PUBLIC gcem)
endif ()
add_library(${PROJECT_NAME}::${PROJECT_NAME} ALIAS ${PROJECT_NAME})

target_compile_definitions(${PROJECT_NAME} PUBLIC OMATH_VERSION="${PROJECT_VERSION}")
Expand Down
4 changes: 2 additions & 2 deletions CMakePresets.json
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,7 @@
"inherits": ["windows-base", "vcpkg-base"],
"cacheVariables": {
"VCPKG_TARGET_TRIPLET": "x64-windows-static",
"VCPKG_MANIFEST_FEATURES": "tests;imgui;avx2;examples;hooking",
"VCPKG_MANIFEST_FEATURES": "tests;imgui;avx2;examples;hooking;gcem",
"OMATH_STATIC_MSVC_RUNTIME_LIBRARY": "ON"
}
},
Expand Down Expand Up @@ -239,7 +239,7 @@
"hidden": true,
"inherits": ["darwin-base", "vcpkg-base"],
"cacheVariables": {
"VCPKG_MANIFEST_FEATURES": "tests;imgui;avx2;examples;lua"
"VCPKG_MANIFEST_FEATURES": "tests;imgui;avx2;examples;lua;gcem"
}
},
{
Expand Down
70 changes: 60 additions & 10 deletions include/omath/engines/cry_engine/formulas.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -8,31 +8,81 @@
namespace omath::cry_engine
{
[[nodiscard]]
Vector3<float> forward_vector(const ViewAngles& angles) noexcept;
inline OMATH_CONSTEXPR Mat4X4 rotation_matrix(const ViewAngles& angles) noexcept
{
return mat_rotation_axis_z<float, MatStoreType::ROW_MAJOR>(angles.yaw)
* mat_rotation_axis_y<float, MatStoreType::ROW_MAJOR>(angles.roll)
* mat_rotation_axis_x<float, MatStoreType::ROW_MAJOR>(angles.pitch);
}

[[nodiscard]]
Vector3<float> right_vector(const ViewAngles& angles) noexcept;
inline OMATH_CONSTEXPR Vector3<float> forward_vector(const ViewAngles& angles) noexcept
{
const auto vec = rotation_matrix(angles) * mat_column_from_vector(k_abs_forward);

return {vec.at(0, 0), vec.at(1, 0), vec.at(2, 0)};
}

[[nodiscard]]
Vector3<float> up_vector(const ViewAngles& angles) noexcept;
inline OMATH_CONSTEXPR Vector3<float> right_vector(const ViewAngles& angles) noexcept
{
const auto vec = rotation_matrix(angles) * mat_column_from_vector(k_abs_right);

[[nodiscard]] Mat4X4 calc_view_matrix(const ViewAngles& angles, const Vector3<float>& cam_origin) noexcept;
return {vec.at(0, 0), vec.at(1, 0), vec.at(2, 0)};
}

[[nodiscard]]
Mat4X4 rotation_matrix(const ViewAngles& angles) noexcept;
inline OMATH_CONSTEXPR Vector3<float> up_vector(const ViewAngles& angles) noexcept
{
const auto vec = rotation_matrix(angles) * mat_column_from_vector(k_abs_up);

return {vec.at(0, 0), vec.at(1, 0), vec.at(2, 0)};
}

[[nodiscard]]
Vector3<float> extract_origin(const Mat4X4& mat) noexcept;
inline OMATH_CONSTEXPR Mat4X4 calc_view_matrix(const ViewAngles& angles, const Vector3<float>& cam_origin) noexcept
{
return mat_camera_view<float, MatStoreType::ROW_MAJOR>(forward_vector(angles), right_vector(angles),
up_vector(angles), cam_origin);
}

[[nodiscard]]
Vector3<float> extract_scale(const Mat4X4& mat) noexcept;
inline OMATH_CONSTEXPR Vector3<float> extract_origin(const Mat4X4& mat) noexcept
{
return mat_extract_origin(mat);
}

[[nodiscard]]
ViewAngles extract_rotation_angles(const Mat4X4& mat) noexcept;
inline OMATH_CONSTEXPR Vector3<float> extract_scale(const Mat4X4& mat) noexcept
{
return mat_extract_scale(mat);
}

[[nodiscard]]
Mat4X4 calc_perspective_projection_matrix(float field_of_view, float aspect_ratio, float near, float far,
NDCDepthRange ndc_depth_range = NDCDepthRange::ZERO_TO_ONE) noexcept;
inline OMATH_CONSTEXPR ViewAngles extract_rotation_angles(const Mat4X4& mat) noexcept
{
const auto angles = mat_extract_rotation_zyx(mat);
return {
PitchAngle::from_degrees(angles.x),
YawAngle::from_degrees(angles.z),
RollAngle::from_degrees(angles.y),
};
}
[[nodiscard]]
inline OMATH_CONSTEXPR Mat4X4 calc_perspective_projection_matrix(
const float field_of_view, const float aspect_ratio, const float near, const float far,
const NDCDepthRange ndc_depth_range = NDCDepthRange::ZERO_TO_ONE) noexcept
{
if (ndc_depth_range == NDCDepthRange::ZERO_TO_ONE)
return mat_perspective_left_handed_vertical_fov<float, MatStoreType::ROW_MAJOR, NDCDepthRange::ZERO_TO_ONE>(
field_of_view, aspect_ratio, near, far);

if (ndc_depth_range == NDCDepthRange::NEGATIVE_ONE_TO_ONE)
return mat_perspective_left_handed_vertical_fov<float, MatStoreType::ROW_MAJOR,
NDCDepthRange::NEGATIVE_ONE_TO_ONE>(
field_of_view, aspect_ratio, near, far);
std::unreachable();
}

template<class FloatingType>
requires std::is_floating_point_v<FloatingType>
Expand Down
32 changes: 26 additions & 6 deletions include/omath/engines/cry_engine/traits/camera_trait.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -4,21 +4,41 @@

#pragma once
#include "omath/engines/cry_engine/formulas.hpp"
#include "omath/internal/optional_constexpr_math.hpp"
#include "omath/projection/camera.hpp"

namespace omath::cry_engine
{
class CameraTrait final
{
public:
[[nodiscard]]
static ViewAngles calc_look_at_angle(const Vector3<float>& cam_origin, const Vector3<float>& look_at) noexcept;
OMATH_CONSTEXPR static ViewAngles calc_look_at_angle(const Vector3<float>& cam_origin,
const Vector3<float>& look_at) noexcept
{
const auto direction = (look_at - cam_origin).normalized();
#ifdef OMATH_USE_GCEM
return {PitchAngle::from_radians(gcem::asin(direction.z)),
YawAngle::from_radians(-gcem::atan2(direction.x, direction.y)), RollAngle::from_radians(0.f)};
#else
return {PitchAngle::from_radians(std::asin(direction.z)),
YawAngle::from_radians(-std::atan2(direction.x, direction.y)), RollAngle::from_radians(0.f)};
#endif
}

[[nodiscard]]
static Mat4X4 calc_view_matrix(const ViewAngles& angles, const Vector3<float>& cam_origin) noexcept;
OMATH_CONSTEXPR static Mat4X4 calc_view_matrix(const ViewAngles& angles,
const Vector3<float>& cam_origin) noexcept
{
return cry_engine::calc_view_matrix(angles, cam_origin);
}
[[nodiscard]]
static Mat4X4 calc_projection_matrix(const projection::FieldOfView& fov, const projection::ViewPort& view_port,
float near, float far, NDCDepthRange ndc_depth_range) noexcept;
OMATH_CONSTEXPR static Mat4X4
calc_projection_matrix(const projection::FieldOfView& fov, const projection::ViewPort& view_port,
const float near, const float far, const NDCDepthRange ndc_depth_range) noexcept
{
return calc_perspective_projection_matrix(fov.as_degrees(), view_port.aspect_ratio(), near, far,
ndc_depth_range);
}
};

} // namespace omath::cry_engine
} // namespace omath::cry_engine
12 changes: 12 additions & 0 deletions include/omath/internal/optional_constexpr_math.hpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
//
// Created by orange on 6/11/2026.
//
#pragma once


#ifdef OMATH_USE_GCEM
#include <gcem.hpp>
#define OMATH_CONSTEXPR constexpr
#else
#define OMATH_CONSTEXPR
#endif
Loading
Loading