normalize axis in rotate function, little style fixes

This commit is contained in:
BlackMATov
2020-12-06 04:49:18 +07:00
parent b246cad6af
commit 422d251df1
2 changed files with 221 additions and 221 deletions

View File

@@ -213,26 +213,27 @@ namespace vmath_hpp
template < typename T > template < typename T >
[[nodiscard]] mat<T, 4> rotate(T angle, const vec<T, 3>& axis) { [[nodiscard]] mat<T, 4> rotate(T angle, const vec<T, 3>& axis) {
const T x = axis.x; const auto [s, c] = sincos(angle);
const T y = axis.y; const auto [x, y, z] = normalize(axis);
const T z = axis.z;
const T px = x * x; const T xx = x * x;
const T py = y * y; const T yy = y * y;
const T pz = z * z; const T zz = z * z;
const T cs = cos(angle);
const T sn = sin(angle); const T xs = x * s;
const T ics = T(1) - cs; const T ys = y * s;
const T xym = x * y * ics; const T zs = z * s;
const T xzm = x * z * ics;
const T yzm = y * z * ics; const T ic = T(1) - c;
const T xsn = x * sn; const T xym = x * y * ic;
const T ysn = y * sn; const T xzm = x * z * ic;
const T zsn = z * sn; const T yzm = y * z * ic;
return { return {
px * ics + cs, xym + zsn, xzm - ysn, 0, xx * ic + c, xym + zs, xzm - ys, 0,
xym - zsn, py * ics + cs, yzm + xsn, 0, xym - zs, yy * ic + c, yzm + xs, 0,
xzm + ysn, yzm - xsn, pz * ics + cs, 0, xzm + ys, yzm - xs, zz * ic + c, 0,
0, 0, 0, 1}; 0, 0, 0, 1};
} }
template < typename T > template < typename T >
@@ -242,13 +243,12 @@ namespace vmath_hpp
template < typename T > template < typename T >
[[nodiscard]] mat<T, 4> rotate_x(T angle) { [[nodiscard]] mat<T, 4> rotate_x(T angle) {
const T cs = cos(angle); const auto [s, c] = sincos(angle);
const T sn = sin(angle);
return { return {
1, 0, 0, 0, 1, 0, 0, 0,
0, cs, sn, 0, 0, c, s, 0,
0, -sn, cs, 0, 0, -s, c, 0,
0, 0, 0, 1}; 0, 0, 0, 1};
} }
template < typename T > template < typename T >
@@ -258,13 +258,12 @@ namespace vmath_hpp
template < typename T > template < typename T >
[[nodiscard]] mat<T, 4> rotate_y(T angle) { [[nodiscard]] mat<T, 4> rotate_y(T angle) {
const T cs = cos(angle); const auto [s, c] = sincos(angle);
const T sn = sin(angle);
return { return {
cs, 0, -sn, 0, c, 0, -s, 0,
0, 1, 0, 0, 0, 1, 0, 0,
sn, 0, cs, 0, s, 0, c, 0,
0, 0, 0, 1}; 0, 0, 0, 1};
} }
template < typename T > template < typename T >
@@ -274,13 +273,12 @@ namespace vmath_hpp
template < typename T > template < typename T >
[[nodiscard]] mat<T, 4> rotate_z(T angle) { [[nodiscard]] mat<T, 4> rotate_z(T angle) {
const T cs = cos(angle); const auto [s, c] = sincos(angle);
const T sn = sin(angle);
return { return {
cs, sn, 0, 0, c, s, 0, 0,
-sn, cs, 0, 0, -s, c, 0, 0,
0, 0, 1, 0, 0, 0, 1, 0,
0, 0, 0, 1}; 0, 0, 0, 1};
} }
template < typename T > template < typename T >
@@ -321,9 +319,11 @@ namespace vmath_hpp
const vec<T, 3> az = normalize(at - eye); const vec<T, 3> az = normalize(at - eye);
const vec<T, 3> ax = normalize(cross(up, az)); const vec<T, 3> ax = normalize(cross(up, az));
const vec<T, 3> ay = cross(az, ax); const vec<T, 3> ay = cross(az, ax);
const T dx = dot(ax, eye); const T dx = dot(ax, eye);
const T dy = dot(ay, eye); const T dy = dot(ay, eye);
const T dz = dot(az, eye); const T dz = dot(az, eye);
return { return {
ax.x, ay.x, az.x, 0, ax.x, ay.x, az.x, 0,
ax.y, ay.y, az.y, 0, ax.y, ay.y, az.y, 0,
@@ -336,9 +336,11 @@ namespace vmath_hpp
const vec<T, 3> az = normalize(eye - at); const vec<T, 3> az = normalize(eye - at);
const vec<T, 3> ax = normalize(cross(up, az)); const vec<T, 3> ax = normalize(cross(up, az));
const vec<T, 3> ay = cross(az, ax); const vec<T, 3> ay = cross(az, ax);
const T dx = dot(ax, eye); const T dx = dot(ax, eye);
const T dy = dot(ay, eye); const T dy = dot(ay, eye);
const T dz = dot(az, eye); const T dz = dot(az, eye);
return { return {
ax.x, ay.x, az.x, 0, ax.x, ay.x, az.x, 0,
ax.y, ay.y, az.y, 0, ax.y, ay.y, az.y, 0,
@@ -382,12 +384,11 @@ namespace vmath_hpp
template < typename T > template < typename T >
[[nodiscard]] mat<T, 3> rotate(T angle) { [[nodiscard]] mat<T, 3> rotate(T angle) {
const T cs = cos(angle); const auto [s, c] = sincos(angle);
const T sn = sin(angle);
return { return {
cs, sn, 0, c, s, 0,
-sn, cs, 0, -s, c, 0,
0, 0, 1}; 0, 0, 1};
} }
template < typename T > template < typename T >
@@ -482,9 +483,9 @@ namespace vmath_hpp
template < typename T > template < typename T >
[[nodiscard]] mat<T, 4> orthographic_lh_zo(T left, T right, T bottom, T top, T znear, T zfar) { [[nodiscard]] mat<T, 4> orthographic_lh_zo(T left, T right, T bottom, T top, T znear, T zfar) {
const T sx = T(2) / (right - left); const T sx = T(2) * reciprocal(right - left);
const T sy = T(2) / (top - bottom); const T sy = T(2) * reciprocal(top - bottom);
const T sz = T(1) / (zfar - znear); const T sz = T(1) * reciprocal(zfar - znear);
const T tx = - (right + left) / (right - left); const T tx = - (right + left) / (right - left);
const T ty = - (top + bottom) / (top - bottom); const T ty = - (top + bottom) / (top - bottom);
@@ -499,9 +500,9 @@ namespace vmath_hpp
template < typename T > template < typename T >
[[nodiscard]] mat<T, 4> orthographic_lh_no(T left, T right, T bottom, T top, T znear, T zfar) { [[nodiscard]] mat<T, 4> orthographic_lh_no(T left, T right, T bottom, T top, T znear, T zfar) {
const T sx = T(2) / (right - left); const T sx = T(2) * reciprocal(right - left);
const T sy = T(2) / (top - bottom); const T sy = T(2) * reciprocal(top - bottom);
const T sz = T(2) / (zfar - znear); const T sz = T(2) * reciprocal(zfar - znear);
const T tx = - (right + left) / (right - left); const T tx = - (right + left) / (right - left);
const T ty = - (top + bottom) / (top - bottom); const T ty = - (top + bottom) / (top - bottom);
@@ -516,9 +517,9 @@ namespace vmath_hpp
template < typename T > template < typename T >
[[nodiscard]] mat<T, 4> orthographic_rh_zo(T left, T right, T bottom, T top, T znear, T zfar) { [[nodiscard]] mat<T, 4> orthographic_rh_zo(T left, T right, T bottom, T top, T znear, T zfar) {
const T sx = T(2) / (right - left); const T sx = T(2) * reciprocal(right - left);
const T sy = T(2) / (top - bottom); const T sy = T(2) * reciprocal(top - bottom);
const T sz = -T(1) / (zfar - znear); const T sz = -T(1) * reciprocal(zfar - znear);
const T tx = - (right + left) / (right - left); const T tx = - (right + left) / (right - left);
const T ty = - (top + bottom) / (top - bottom); const T ty = - (top + bottom) / (top - bottom);
@@ -533,9 +534,9 @@ namespace vmath_hpp
template < typename T > template < typename T >
[[nodiscard]] mat<T, 4> orthographic_rh_no(T left, T right, T bottom, T top, T znear, T zfar) { [[nodiscard]] mat<T, 4> orthographic_rh_no(T left, T right, T bottom, T top, T znear, T zfar) {
const T sx = T(2) / (right - left); const T sx = T(2) * reciprocal(right - left);
const T sy = T(2) / (top - bottom); const T sy = T(2) * reciprocal(top - bottom);
const T sz = -T(2) / (zfar - znear); const T sz = -T(2) * reciprocal(zfar - znear);
const T tx = - (right + left) / (right - left); const T tx = - (right + left) / (right - left);
const T ty = - (top + bottom) / (top - bottom); const T ty = - (top + bottom) / (top - bottom);
@@ -552,7 +553,7 @@ namespace vmath_hpp
template < typename T > template < typename T >
[[nodiscard]] mat<T, 4> perspective_lh_zo(T fov, T aspect, T znear, T zfar) { [[nodiscard]] mat<T, 4> perspective_lh_zo(T fov, T aspect, T znear, T zfar) {
const T sy = T(1) / tan(fov * T(0.5)); const T sy = reciprocal(tan(fov * T(0.5)));
const T sx = sy / aspect; const T sx = sy / aspect;
const T sz = zfar / (zfar - znear); const T sz = zfar / (zfar - znear);
const T tz = (znear * zfar) / (znear - zfar); const T tz = (znear * zfar) / (znear - zfar);
@@ -565,7 +566,7 @@ namespace vmath_hpp
template < typename T > template < typename T >
[[nodiscard]] mat<T, 4> perspective_lh_no(T fov, T aspect, T znear, T zfar) { [[nodiscard]] mat<T, 4> perspective_lh_no(T fov, T aspect, T znear, T zfar) {
const T sy = T(1) / tan(fov * T(0.5)); const T sy = reciprocal(tan(fov * T(0.5)));
const T sx = sy / aspect; const T sx = sy / aspect;
const T sz = (zfar + znear) / (zfar - znear); const T sz = (zfar + znear) / (zfar - znear);
const T tz = (T(2) * znear * zfar) / (znear - zfar); const T tz = (T(2) * znear * zfar) / (znear - zfar);
@@ -578,28 +579,28 @@ namespace vmath_hpp
template < typename T > template < typename T >
[[nodiscard]] mat<T, 4> perspective_rh_zo(T fov, T aspect, T znear, T zfar) { [[nodiscard]] mat<T, 4> perspective_rh_zo(T fov, T aspect, T znear, T zfar) {
const T sy = T(1) / tan(fov * T(0.5)); const T sy = reciprocal(tan(fov * T(0.5)));
const T sx = sy / aspect; const T sx = sy / aspect;
const T sz = zfar / (znear - zfar); const T sz = zfar / (znear - zfar);
const T tz = (znear * zfar) / (znear - zfar); const T tz = (znear * zfar) / (znear - zfar);
return { return {
sx, 0, 0, 0, sx, 0, 0, 0,
0, sy, 0, 0, 0, sy, 0, 0,
0, 0, sz, -1, 0, 0, sz, -1,
0, 0, tz, 0}; 0, 0, tz, 0};
} }
template < typename T > template < typename T >
[[nodiscard]] mat<T, 4> perspective_rh_no(T fov, T aspect, T znear, T zfar) { [[nodiscard]] mat<T, 4> perspective_rh_no(T fov, T aspect, T znear, T zfar) {
const T sy = T(1) / tan(fov * T(0.5)); const T sy = reciprocal(tan(fov * T(0.5)));
const T sx = sy / aspect; const T sx = sy / aspect;
const T sz = (zfar + znear) / (znear - zfar); const T sz = (zfar + znear) / (znear - zfar);
const T tz = (T(2) * znear * zfar) / (znear - zfar); const T tz = (T(2) * znear * zfar) / (znear - zfar);
return { return {
sx, 0, 0, 0, sx, 0, 0, 0,
0, sy, 0, 0, 0, sy, 0, 0,
0, 0, sz, -1, 0, 0, sz, -1,
0, 0, tz, 0}; 0, 0, tz, 0};
} }
} }
@@ -620,11 +621,10 @@ namespace vmath_hpp
template < typename T > template < typename T >
[[nodiscard]] vec<T, 2> rotate(const vec<T, 2>& v, T angle) { [[nodiscard]] vec<T, 2> rotate(const vec<T, 2>& v, T angle) {
const T cs = cos(angle); const auto [s, c] = sincos(angle);
const T sn = sin(angle);
return { return {
v.x * cs - v.y * sn, v.x * c - v.y * s,
v.x * sn + v.y * cs}; v.x * s + v.y * c};
} }
template < typename T > template < typename T >

View File

@@ -8,6 +8,158 @@
#include "vmath_fwd.hpp" #include "vmath_fwd.hpp"
//
// Common Functions
//
namespace vmath_hpp
{
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_unsigned_v<T>, T>
constexpr abs(T x) noexcept {
return x;
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_signed_v<T>, T>
constexpr abs(T x) noexcept {
return x >= T(0) ? x : -x;
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_arithmetic_v<T>, T>
constexpr sign(T x) noexcept {
return static_cast<T>((T(0) < x) - (x < T(0)));
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
constexpr reciprocal(T x) noexcept {
return T(1) / x;
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
floor(T x) noexcept {
return std::floor(x);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
trunc(T x) noexcept {
return std::trunc(x);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
round(T x) noexcept {
return std::round(x);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
ceil(T x) noexcept {
return std::ceil(x);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
fract(T x) noexcept {
return x - floor(x);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
fmod(T x, T y) noexcept {
return std::fmod(x, y);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
modf(T x, T* y) noexcept {
return std::modf(x, y);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_arithmetic_v<T>, T>
constexpr min(T x, T y) noexcept {
return x < y ? x : y;
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_arithmetic_v<T>, T>
constexpr max(T x, T y) noexcept {
return x < y ? y : x;
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_arithmetic_v<T>, T>
constexpr clamp(T x, T min_x, T max_x) noexcept {
return min(max(x, min_x), max_x);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_arithmetic_v<T>, T>
constexpr saturate(T x) noexcept {
return clamp(x, T(0), T(1));
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
constexpr lerp(T x, T y, T a) noexcept {
return x * (T(1) - a) + y * a;
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
constexpr step(T edge, T x) noexcept {
return x < edge ? T(0) : T(1);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
constexpr smoothstep(T edge0, T edge1, T x) noexcept {
const T t = clamp((x - edge0) / (edge1 - edge0), T(0), T(1));
return t * t * (T(3) - T(2) * t);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_arithmetic_v<T>, bool>
isnan(T x) noexcept {
return std::isnan(x);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_arithmetic_v<T>, bool>
isinf(T x) noexcept {
return std::isinf(x);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_arithmetic_v<T>, bool>
isfinite(T x) noexcept {
return std::isfinite(x);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
fma(T x, T y, T z) noexcept {
return std::fma(x, y, z);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
frexp(T x, int* exp) noexcept {
return std::frexp(x, exp);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
ldexp(T x, int exp) noexcept {
return std::ldexp(x, exp);
}
}
// //
// Angle and Trigonometry Functions // Angle and Trigonometry Functions
// //
@@ -163,159 +315,7 @@ namespace vmath_hpp
template < typename T > template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T> [[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
rsqrt(T x) noexcept { rsqrt(T x) noexcept {
return T(1) / sqrt(x); return reciprocal(sqrt(x));
}
}
//
// Common Functions
//
namespace vmath_hpp
{
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_unsigned_v<T>, T>
constexpr abs(T x) noexcept {
return x;
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_signed_v<T>, T>
constexpr abs(T x) noexcept {
return x >= T(0) ? x : -x;
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_arithmetic_v<T>, T>
constexpr sign(T x) noexcept {
return static_cast<T>((T(0) < x) - (x < T(0)));
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
constexpr reciprocal(T x) noexcept {
return T(1) / x;
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
floor(T x) noexcept {
return std::floor(x);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
trunc(T x) noexcept {
return std::trunc(x);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
round(T x) noexcept {
return std::round(x);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
ceil(T x) noexcept {
return std::ceil(x);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
fract(T x) noexcept {
return x - floor(x);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
fmod(T x, T y) noexcept {
return std::fmod(x, y);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
modf(T x, T* y) noexcept {
return std::modf(x, y);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_arithmetic_v<T>, T>
constexpr min(T x, T y) noexcept {
return x < y ? x : y;
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_arithmetic_v<T>, T>
constexpr max(T x, T y) noexcept {
return x < y ? y : x;
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_arithmetic_v<T>, T>
constexpr clamp(T x, T min_x, T max_x) noexcept {
return min(max(x, min_x), max_x);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_arithmetic_v<T>, T>
constexpr saturate(T x) noexcept {
return clamp(x, T(0), T(1));
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
constexpr lerp(T x, T y, T a) noexcept {
return x * (T(1) - a) + y * a;
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
constexpr step(T edge, T x) noexcept {
return x < edge ? T(0) : T(1);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
constexpr smoothstep(T edge0, T edge1, T x) noexcept {
const T t = clamp((x - edge0) / (edge1 - edge0), T(0), T(1));
return t * t * (T(3) - T(2) * t);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_arithmetic_v<T>, bool>
isnan(T x) noexcept {
return std::isnan(x);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_arithmetic_v<T>, bool>
isinf(T x) noexcept {
return std::isinf(x);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_arithmetic_v<T>, bool>
isfinite(T x) noexcept {
return std::isfinite(x);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
fma(T x, T y, T z) noexcept {
return std::fma(x, y, z);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
frexp(T x, int* exp) noexcept {
return std::frexp(x, exp);
}
template < typename T >
[[nodiscard]] std::enable_if_t<std::is_floating_point_v<T>, T>
ldexp(T x, int exp) noexcept {
return std::ldexp(x, exp);
} }
} }