From b6b28dcb0ca741fd455be2cb302e6ac7a36aa8eb Mon Sep 17 00:00:00 2001 From: "C. J. Howard" Date: Sun, 23 Oct 2022 02:51:04 +0800 Subject: [PATCH] Minor fixes and improvements to the linear algebra structs --- src/ai/steering/behavior/flee.cpp | 6 +- src/ai/steering/behavior/seek.cpp | 6 +- src/game/load.cpp | 10 +-- src/game/system/collision.cpp | 8 +- src/game/system/steering.cpp | 2 +- src/geom/intersection.cpp | 8 +- src/geom/primitive/hypersphere.hpp | 6 +- src/geom/primitive/intersection.hpp | 2 +- src/math/noise/simplex.hpp | 2 +- src/math/noise/voronoi.hpp | 6 +- src/math/quaternion.hpp | 106 ++++++++++++++------------ src/math/se3.hpp | 2 +- src/math/transform-functions.hpp | 2 +- src/math/vector.hpp | 112 ++++++++++++++++------------ src/render/passes/sky-pass.cpp | 2 +- 15 files changed, 152 insertions(+), 128 deletions(-) diff --git a/src/ai/steering/behavior/flee.cpp b/src/ai/steering/behavior/flee.cpp index f5db702..adf4377 100644 --- a/src/ai/steering/behavior/flee.cpp +++ b/src/ai/steering/behavior/flee.cpp @@ -27,11 +27,11 @@ float3 flee(const agent& agent, const float3& target) { float3 force = {0, 0, 0}; const float3 difference = target - agent.position; - const float distance_squared = math::dot(difference, difference); + const float sqr_distance = math::dot(difference, difference); - if (distance_squared) + if (sqr_distance) { - const float inverse_distance = 1.0f / std::sqrt(distance_squared); + const float inverse_distance = 1.0f / std::sqrt(sqr_distance); force = difference * inverse_distance * agent.max_force; force = agent.velocity - force; } diff --git a/src/ai/steering/behavior/seek.cpp b/src/ai/steering/behavior/seek.cpp index 41e8478..c5064ed 100644 --- a/src/ai/steering/behavior/seek.cpp +++ b/src/ai/steering/behavior/seek.cpp @@ -27,11 +27,11 @@ float3 seek(const agent& agent, const float3& target) { float3 force = {0, 0, 0}; const float3 difference = target - agent.position; - const float distance_squared = math::dot(difference, difference); + const float sqr_distance = math::dot(difference, difference); - if (distance_squared) + if (sqr_distance) { - const float inverse_distance = 1.0f / std::sqrt(distance_squared); + const float inverse_distance = 1.0f / std::sqrt(sqr_distance); force = difference * inverse_distance * agent.max_force; force -= agent.velocity; } diff --git a/src/game/load.cpp b/src/game/load.cpp index 164babe..15d7eba 100644 --- a/src/game/load.cpp +++ b/src/game/load.cpp @@ -113,12 +113,12 @@ void biome(game::context& ctx, const std::filesystem::path& path) // f2_sqr_distance, // f2_displacement, // f2_id - edge_sqr_distance + edge_sqr_distance( ] = math::noise::voronoi::f1_edge(position); - float f1_distance = std::sqrt(f1_sqr_distance); - //float f2_distance = std::sqrt(f2_sqr_distance); - float edge_distance = std::sqrt(edge_sqr_distance); + float f1_distance = std::sqrt(f1_sqr_distance(); + //float f2_distance = std::sqrt(f2_sqr_distance(); + float edge_distance = std::sqrt(edge_sqr_distance(); pixel = static_cast(std::min(255.0f, f1_distance * 255.0f)); //pixel = static_cast(id % 255); @@ -217,7 +217,7 @@ void biome(game::context& ctx, const std::filesystem::path& path) f1_displacement, f1_id ] = math::noise::voronoi::f1(position); - float f1_distance = std::sqrt(f1_sqr_distance); + float f1_distance = std::sqrt(f1_sqr_distance(); float y = f1_distance * 5.0f + fbm * 0.5f; */ diff --git a/src/game/system/collision.cpp b/src/game/system/collision.cpp index a66344d..ad82a27 100644 --- a/src/game/system/collision.cpp +++ b/src/game/system/collision.cpp @@ -86,7 +86,7 @@ entity::id collision::pick_nearest(const geom::primitive::ray& ray, st entity::id collision::pick_nearest(const float3& origin, const float3& normal, std::uint32_t flags) const { entity::id nearest_eid = entt::null; - float nearest_distance_squared = std::numeric_limits::infinity(); + float nearest_sqr_distance = std::numeric_limits::infinity(); // Construct picking plane const geom::primitive::plane picking_plane = geom::primitive::plane(origin, normal); @@ -108,13 +108,13 @@ entity::id collision::pick_nearest(const float3& origin, const float3& normal, s return; // Measure distance from picking plane origin to picking sphere center - const float distance_squared = math::distance_squared(picking_sphere_center, origin); + const float sqr_distance = math::sqr_distance(picking_sphere_center, origin); // Check if entity is nearer than the current nearest entity - if (distance_squared < nearest_distance_squared) + if (sqr_distance < nearest_sqr_distance) { nearest_eid = entity_id; - nearest_distance_squared = distance_squared; + nearest_sqr_distance = sqr_distance; } } ); diff --git a/src/game/system/steering.cpp b/src/game/system/steering.cpp index 071cc87..569fa73 100644 --- a/src/game/system/steering.cpp +++ b/src/game/system/steering.cpp @@ -65,7 +65,7 @@ void steering::update(double t, double dt) agent.velocity += agent.acceleration * static_cast(dt); // Limit speed - const float speed_squared = math::length_squared(agent.velocity); + const float speed_squared = math::sqr_length(agent.velocity); if (speed_squared > agent.max_speed_squared) { const float speed = std::sqrt(speed_squared); diff --git a/src/geom/intersection.cpp b/src/geom/intersection.cpp index 067b5b7..cf22bf9 100644 --- a/src/geom/intersection.cpp +++ b/src/geom/intersection.cpp @@ -171,17 +171,17 @@ bool aabb_aabb_intersection(const aabb& a, const aabb& b) bool aabb_sphere_intersection(const aabb& aabb, const float3& center, float radius) { - float distance_squared = 0.0f; + float sqr_distance = 0.0f; for (int i = 0; i < 3; ++i) { float v = center[i]; if (v < aabb.min_point[i]) - distance_squared += (aabb.min_point[i] - v) * (aabb.min_point[i] - v); + sqr_distance += (aabb.min_point[i] - v) * (aabb.min_point[i] - v); if (v > aabb.max_point[i]) - distance_squared += (v - aabb.max_point[i]) * (v - aabb.max_point[i]); + sqr_distance += (v - aabb.max_point[i]) * (v - aabb.max_point[i]); } - return (distance_squared <= (radius * radius)); + return (sqr_distance <= (radius * radius)); } } // namespace geom diff --git a/src/geom/primitive/hypersphere.hpp b/src/geom/primitive/hypersphere.hpp index d991e31..19056bd 100644 --- a/src/geom/primitive/hypersphere.hpp +++ b/src/geom/primitive/hypersphere.hpp @@ -52,7 +52,7 @@ struct hypersphere */ constexpr bool contains(const vector_type& point) const noexcept { - return math::distance_squared(center, point) <= radius * radius; + return math::sqr_distance(center, point) <= radius * radius; } /** @@ -68,7 +68,7 @@ struct hypersphere if (containment_radius < T{0}) return false; - return math::distance_squared(center, other.center) <= containment_radius * containment_radius; + return math::sqr_distance(center, other.center) <= containment_radius * containment_radius; } /** @@ -93,7 +93,7 @@ struct hypersphere constexpr bool intersects(const hypersphere& other) const noexcept { const T intersection_radius = radius + other.radius; - return math::distance_squared(center, other.center) <= intersection_radius * intersection_radius; + return math::sqr_distance(center, other.center) <= intersection_radius * intersection_radius; } /** diff --git a/src/geom/primitive/intersection.hpp b/src/geom/primitive/intersection.hpp index 438b1af..a34dc5c 100644 --- a/src/geom/primitive/intersection.hpp +++ b/src/geom/primitive/intersection.hpp @@ -117,7 +117,7 @@ std::optional> intersection(const ray& ray, const hypersp { const math::vector displacement = ray.origin - hypersphere.center; const T b = math::dot(displacement, ray.direction); - const T c = math::length_squared(displacement) - hypersphere.radius * hypersphere.radius; + const T c = math::sqr_length(displacement) - hypersphere.radius * hypersphere.radius; T h = b * b - c; if (h < T{0}) diff --git a/src/math/noise/simplex.hpp b/src/math/noise/simplex.hpp index 3bb2001..5d79dd4 100644 --- a/src/math/noise/simplex.hpp +++ b/src/math/noise/simplex.hpp @@ -202,7 +202,7 @@ T simplex const vector d = dx - (current_vertex - origin_vertex) + g * static_cast(i); // Calculate falloff - T t = falloff(length_squared(d)); + T t = falloff(sqr_length(d)); if (t > T{0}) { const hash::make_uint_t gradient_index = hash(current_vertex)[0] % simplex_edges.size(); diff --git a/src/math/noise/voronoi.hpp b/src/math/noise/voronoi.hpp index 0d64edc..bc79de4 100644 --- a/src/math/noise/voronoi.hpp +++ b/src/math/noise/voronoi.hpp @@ -160,7 +160,7 @@ f1 vector displacement = (offset_i + offset_f) - position_f; // Calculate square distance to the current cell center - T sqr_distance = length_squared(displacement); + T sqr_distance = sqr_length(displacement); // Update F1 cell if (sqr_distance < f1_sqr_distance) @@ -250,7 +250,7 @@ f1_edge displacement_cache[i] = (offset_i + offset_f) - position_f; // Calculate square distance to the current cell center - T sqr_distance = length_squared(displacement_cache[i]); + T sqr_distance = sqr_length(displacement_cache[i]); // Update F1 cell if (sqr_distance < f1_sqr_distance_center) @@ -377,7 +377,7 @@ f1_f2 vector displacement = (offset_i + offset_f) - position_f; // Calculate square distance to the current cell center - T sqr_distance = length_squared(displacement); + T sqr_distance = sqr_length(displacement); // Update F1 and F2 cells if (sqr_distance < f1_sqr_distance_center) diff --git a/src/math/quaternion.hpp b/src/math/quaternion.hpp index bcefa78..fdfc58a 100644 --- a/src/math/quaternion.hpp +++ b/src/math/quaternion.hpp @@ -30,7 +30,7 @@ namespace math { /** - * A quaternion type is a tuple made of a scalar (real) part and vector (imaginary) part. + * Quaternion composed of a real scalar part and imaginary vector part. * * @tparam T Scalar type. */ @@ -148,6 +148,31 @@ struct quaternion return {static_cast(r), vector(i)}; } + /** + * Constructs a matrix representing the rotation described the quaternion. + * + * @return Rotation matrix. + */ + constexpr explicit operator matrix_type() const noexcept + { + const T xx = x() * x(); + const T xy = x() * y(); + const T xz = x() * z(); + const T xw = x() * w(); + const T yy = y() * y(); + const T yz = y() * z(); + const T yw = y() * w(); + const T zz = z() * z(); + const T zw = z() * w(); + + return + { + T(1) - (yy + zz) * T(2), (xy + zw) * T(2), (xz - yw) * T(2), + (xy - zw) * T(2), T(1) - (xx + zz) * T(2), (yz + xw) * T(2), + (xz + yw) * T(2), (yz - xw) * T(2), T(1) - (xx + yy) * T(2) + }; + } + /** * Casts the quaternion to a 4-element vector, with the real part as the first element and the imaginary part as the following three elements. * @@ -248,24 +273,24 @@ template constexpr quaternion div(T a, const quaternion& b) noexcept; /** - * Calculates the length of a quaternion. + * Calculates the inverse length of a quaternion. * - * @param q Quaternion to calculate the length of. + * @param q Quaternion to calculate the inverse length of. * - * @return Length of the quaternion. + * @return Inverse length of the quaternion. */ template -T length(const quaternion& q); +T inv_length(const quaternion& q); /** - * Calculates the squared length of a quaternion. The squared length can be calculated faster than the length because a call to `std::sqrt` is saved. + * Calculates the length of a quaternion. * - * @param q Quaternion to calculate the squared length of. + * @param q Quaternion to calculate the length of. * - * @return Squared length of the quaternion. + * @return Length of the quaternion. */ template -constexpr T length_squared(const quaternion& q) noexcept; +T length(const quaternion& q); /** * Performs linear interpolation between two quaternions. @@ -290,16 +315,6 @@ constexpr quaternion lerp(const quaternion& a, const quaternion& b, T t template quaternion look_rotation(const vector& forward, vector up); -/** - * Converts a quaternion to a rotation matrix. - * - * @param q Unit quaternion. - * - * @return Matrix representing the rotation described by `q`. - */ -template -constexpr matrix matrix_cast(const quaternion& q) noexcept; - /** * Multiplies two quaternions. * @@ -403,6 +418,16 @@ quaternion rotation(const vector& source, const vector& destinati template quaternion slerp(const quaternion& a, const quaternion& b, T t, T error = T{1e-6}); +/** + * Calculates the square length of a quaternion. The square length can be calculated faster than the length because a call to `std::sqrt` is saved. + * + * @param q Quaternion to calculate the square length of. + * + * @return Square length of the quaternion. + */ +template +constexpr T sqr_length(const quaternion& q) noexcept; + /** * Subtracts a quaternion from another quaternion. * @@ -496,15 +521,15 @@ constexpr inline quaternion div(T a, const quaternion& b) noexcept } template -inline T length(const quaternion& q) +inline T inv_length(const quaternion& q) { - return std::sqrt(length_squared(q)); + return T{1} / length(q); } template -constexpr inline T length_squared(const quaternion& q) noexcept +inline T length(const quaternion& q) { - return q.r * q.r + length_squared(q.i); + return std::sqrt(sqr_length(q)); } template @@ -534,27 +559,6 @@ quaternion look_rotation(const vector& forward, vector up) return normalize(quaternion_cast(m)); } -template -constexpr matrix matrix_cast(const quaternion& q) noexcept -{ - const T xx = q.x() * q.x(); - const T xy = q.x() * q.y(); - const T xz = q.x() * q.z(); - const T xw = q.x() * q.w(); - const T yy = q.y() * q.y(); - const T yz = q.y() * q.z(); - const T yw = q.y() * q.w(); - const T zz = q.z() * q.z(); - const T zw = q.z() * q.w(); - - return - { - T(1) - (yy + zz) * T(2), (xy + zw) * T(2), (xz - yw) * T(2), - (xy - zw) * T(2), T(1) - (xx + zz) * T(2), (yz + xw) * T(2), - (xz + yw) * T(2), (yz - xw) * T(2), T(1) - (xx + yy) * T(2) - }; -} - template constexpr quaternion mul(const quaternion& a, const quaternion& b) noexcept { @@ -576,7 +580,7 @@ constexpr inline quaternion mul(const quaternion& a, T b) noexcept template constexpr vector mul(const quaternion& a, const vector& b) noexcept { - return a.i * dot(a.i, b) * T(2) + b * (a.r * a.r - length_squared(a.i)) + cross(a.i, b) * a.r * T(2); + return a.i * dot(a.i, b) * T(2) + b * (a.r * a.r - sqr_length(a.i)) + cross(a.i, b) * a.r * T(2); } template @@ -600,7 +604,7 @@ quaternion nlerp(const quaternion& a, const quaternion& b, T t) template inline quaternion normalize(const quaternion& q) { - return mul(q, T(1) / length(q)); + return mul(q, inv_length(q)); } template @@ -634,6 +638,12 @@ quaternion slerp(const quaternion& a, const quaternion& b, T t, T error return add(mul(a, std::cos(theta)), mul(c, std::sin(theta))); } +template +constexpr inline T sqr_length(const quaternion& q) noexcept +{ + return q.r * q.r + sqr_length(q.i); +} + template constexpr inline quaternion sub(const quaternion& a, const quaternion& b) noexcept { @@ -655,7 +665,7 @@ constexpr inline quaternion sub(T a, const quaternion& b) noexcept template void swing_twist(const quaternion& q, const vector& a, quaternion& qs, quaternion& qt, T error) { - if (length_squared(q.i) > error) + if (sqr_length(q.i) > error) { qt = normalize(quaternion{q.w(), a * dot(a, q.i)}); qs = mul(q, conjugate(qt)); @@ -666,7 +676,7 @@ void swing_twist(const quaternion& q, const vector& a, quaternion& q const vector qa = mul(q, a); const vector sa = cross(a, qa); - if (length_squared(sa) > error) + if (sqr_length(sa) > error) qs = angle_axis(std::acos(dot(a, qa)), sa); else qs = quaternion::identity(); diff --git a/src/math/se3.hpp b/src/math/se3.hpp index c5ed2a6..e573d48 100644 --- a/src/math/se3.hpp +++ b/src/math/se3.hpp @@ -93,7 +93,7 @@ se3 se3::inverse() const template typename se3::matrix_type se3::matrix() const { - matrix_type m = math::matrix(math::matrix_cast(r)); + matrix_type m = math::matrix(math::matrix(r)); m[3].x() = t.x(); m[3].y() = t.y(); diff --git a/src/math/transform-functions.hpp b/src/math/transform-functions.hpp index 4546e66..9eec8ce 100644 --- a/src/math/transform-functions.hpp +++ b/src/math/transform-functions.hpp @@ -75,7 +75,7 @@ transform inverse(const transform& t) template matrix matrix_cast(const transform& t) { - matrix transformation = matrix(matrix_cast(t.rotation)); + matrix transformation = matrix(matrix(t.rotation)); transformation[3] = {t.translation[0], t.translation[1], t.translation[2], T(1)}; return scale(transformation, t.scale); } diff --git a/src/math/vector.hpp b/src/math/vector.hpp index 3774a5a..5b1056e 100644 --- a/src/math/vector.hpp +++ b/src/math/vector.hpp @@ -394,17 +394,6 @@ constexpr vector cross(const vector& x, const vector& y) noexc template T distance(const vector& p0, const vector& p1); -/** - * Calculates the squared distance between two points. The squared distance can be calculated faster than the distance because a call to `std::sqrt` is saved. - * - * @param p0 First of two points. - * @param p1 Second of two points. - * - * @return Squared distance between the two points. - */ -template -constexpr T distance_squared(const vector& p0, const vector& p1) noexcept; - /** * Divides a vector by a value. * @@ -503,24 +492,24 @@ template constexpr vector greater_than_equal(const vector& x, const vector& y) noexcept; /** - * Calculates the length of a vector. + * Calculates the inverse length of a vector. * - * @param x Vector of which to calculate the length. + * @param x Vector of which to calculate the inverse length. * - * @return Length of the vector. + * @return Inverse length of the vector. */ template -T length(const vector& x); +T inv_length(const vector& x); /** - * Calculates the squared length of a vector. The squared length can be calculated faster than the length because a call to `std::sqrt` is saved. + * Calculates the length of a vector. * - * @param x Vector of which to calculate the squared length. + * @param x Vector of which to calculate the length. * - * @return Squared length of the vector. + * @return Length of the vector. */ template -constexpr T length_squared(const vector& x) noexcept; +T length(const vector& x); /** * Performs a element-wise less-than comparison of two vectors. @@ -691,6 +680,27 @@ constexpr vector round(const vector& x); template constexpr vector sign(const vector& x); +/** + * Calculates the square distance between two points. The square distance can be calculated faster than the distance because a call to `std::sqrt` is saved. + * + * @param p0 First of two points. + * @param p1 Second of two points. + * + * @return Square distance between the two points. + */ +template +constexpr T sqr_distance(const vector& p0, const vector& p1) noexcept; + +/** + * Calculates the square length of a vector. The square length can be calculated faster than the length because a call to `std::sqrt` is saved. + * + * @param x Vector of which to calculate the square length. + * + * @return Square length of the vector. + */ +template +constexpr T sqr_length(const vector& x) noexcept; + /** * Takes the square root of each element. * @@ -819,13 +829,13 @@ constexpr inline bool any(const vector& x) noexcept template constexpr inline vector ceil(const vector& x, std::index_sequence) { + static_assert(std::is_floating_point::value); return {std::ceil(x[I])...}; } template constexpr inline vector ceil(const vector& x) { - static_assert(std::is_floating_point::value); return ceil(x, std::make_index_sequence{}); } @@ -859,8 +869,8 @@ template vector clamp_length(const vector& x, T max_length) { static_assert(std::is_floating_point::value); - T length2 = length_squared(x); - return (length2 > max_length * max_length) ? (x * max_length / std::sqrt(length2)) : x; + T length2 = sqr_length(x); + return (length2 > max_length * max_length) ? (x * (max_length / std::sqrt(length2))) : x; } template @@ -877,16 +887,9 @@ constexpr inline vector cross(const vector& x, const vector& y template inline T distance(const vector& p0, const vector& p1) { - static_assert(std::is_floating_point::value); return length(sub(p0, p1)); } -template -constexpr inline T distance_squared(const vector& p0, const vector& p1) noexcept -{ - return length_squared(sub(p0, p1)); -} - /// @private template constexpr inline vector div(const vector& x, const vector& y, std::index_sequence) noexcept @@ -956,13 +959,13 @@ constexpr inline vector equal(const vector& x, const vector template constexpr inline vector floor(const vector& x, std::index_sequence) { + static_assert(std::is_floating_point::value); return {std::floor(x[I])...}; } template constexpr inline vector floor(const vector& x) { - static_assert(std::is_floating_point::value); return floor(x, std::make_index_sequence{}); } @@ -970,13 +973,13 @@ constexpr inline vector floor(const vector& x) template constexpr inline vector fma(const vector& x, const vector& y, const vector& z, std::index_sequence) { + static_assert(std::is_floating_point::value); return {std::fma(x[I], y[I], z[I])...}; } template constexpr inline vector fma(const vector& x, const vector& y, const vector& z) { - static_assert(std::is_floating_point::value); return fma(x, y, z, std::make_index_sequence{}); } @@ -984,13 +987,13 @@ constexpr inline vector fma(const vector& x, const vector& y, template constexpr inline vector fma(const vector& x, T y, T z, std::index_sequence) { + static_assert(std::is_floating_point::value); return {std::fma(x[I], y, z)...}; } template constexpr inline vector fma(const vector& x, T y, T z) { - static_assert(std::is_floating_point::value); return fma(x, y, z, std::make_index_sequence{}); } @@ -998,13 +1001,13 @@ constexpr inline vector fma(const vector& x, T y, T z) template constexpr inline vector fract(const vector& x, std::index_sequence) { + static_assert(std::is_floating_point::value); return {x[I] - std::floor(x[I])...}; } template constexpr inline vector fract(const vector& x) { - static_assert(std::is_floating_point::value); return fract(x, std::make_index_sequence{}); } @@ -1035,16 +1038,16 @@ constexpr inline vector greater_than_equal(const vector& x, const } template -inline T length(const vector& x) +inline T inv_length(const vector& x) { - static_assert(std::is_floating_point::value); - return std::sqrt(dot(x, x)); + return T{1} / length(x); } template -constexpr inline T length_squared(const vector& x) noexcept +inline T length(const vector& x) { - return dot(x, x); + static_assert(std::is_floating_point::value); + return std::sqrt(sqr_length(x)); } /// @private @@ -1115,13 +1118,13 @@ constexpr inline T min(const vector& x) template constexpr inline vector mod(const vector& x, const vector& y, std::index_sequence) { + static_assert(std::is_floating_point::value); return {std::fmod(x[I], y[I])...}; } template constexpr inline vector mod(const vector& x, const vector& y) { - static_assert(std::is_floating_point::value); return mod(x, y, std::make_index_sequence{}); } @@ -1129,13 +1132,13 @@ constexpr inline vector mod(const vector& x, const vector& y) template constexpr inline vector mod(const vector& x, T y, std::index_sequence) { + static_assert(std::is_floating_point::value); return {std::fmod(x[I], y)...}; } template constexpr inline vector mod(const vector& x, T y) { - static_assert(std::is_floating_point::value); return mod(x, y, std::make_index_sequence{}); } @@ -1181,8 +1184,7 @@ constexpr inline vector negate(const vector& x) noexcept template inline vector normalize(const vector& x) { - static_assert(std::is_floating_point::value); - return mul(x, T{1} / length(x)); + return mul(x, inv_length(x)); } /// @private @@ -1215,13 +1217,13 @@ constexpr inline vector not_equal(const vector& x, const vector inline vector pow(const vector& x, const vector& y, std::index_sequence) { + static_assert(std::is_floating_point::value); return {std::pow(x[I], y[I])...}; } template inline vector pow(const vector& x, const vector& y) { - static_assert(std::is_floating_point::value); return pow(x, y, std::make_index_sequence{}); } @@ -1229,13 +1231,13 @@ inline vector pow(const vector& x, const vector& y) template inline vector pow(const vector& x, T y, std::index_sequence) { + static_assert(std::is_floating_point::value); return {std::pow(x[I], y)...}; } template inline vector pow(const vector& x, T y) { - static_assert(std::is_floating_point::value); return pow(x, y, std::make_index_sequence{}); } @@ -1243,13 +1245,13 @@ inline vector pow(const vector& x, T y) template constexpr inline vector round(const vector& x, std::index_sequence) { + static_assert(std::is_floating_point::value); return {std::round(x[I])...}; } template constexpr inline vector round(const vector& x) { - static_assert(std::is_floating_point::value); return round(x, std::make_index_sequence{}); } @@ -1257,28 +1259,40 @@ constexpr inline vector round(const vector& x) template constexpr inline vector sign(const vector& x, std::index_sequence) { + static_assert(std::is_floating_point::value); return {std::copysign(T{1}, x[I])...}; } template constexpr inline vector sign(const vector& x) { - static_assert(std::is_floating_point::value); return sign(x, std::make_index_sequence{}); } +template +constexpr inline T sqr_distance(const vector& p0, const vector& p1) noexcept +{ + return sqr_length(sub(p0, p1)); +} + +template +constexpr inline T sqr_length(const vector& x) noexcept +{ + return dot(x, x); +} + /// @private template inline vector sqrt(const vector& x, std::index_sequence) { + static_assert(std::is_floating_point::value); return {std::sqrt(x[I])...}; } template inline vector sqrt(const vector& x, const vector& y) { - static_assert(std::is_floating_point::value); - return pow(x, std::make_index_sequence{}); + return sqrt(x, std::make_index_sequence{}); } /// @private @@ -1343,13 +1357,13 @@ constexpr inline vector swizzle(const vector& x) no template constexpr inline vector trunc(const vector& x, std::index_sequence) { + static_assert(std::is_floating_point::value); return {std::trunc(x[I])...}; } template constexpr inline vector trunc(const vector& x) { - static_assert(std::is_floating_point::value); return trunc(x, std::make_index_sequence{}); } diff --git a/src/render/passes/sky-pass.cpp b/src/render/passes/sky-pass.cpp index 03b6573..2c4f1a2 100644 --- a/src/render/passes/sky-pass.cpp +++ b/src/render/passes/sky-pass.cpp @@ -300,7 +300,7 @@ void sky_pass::render(const render::context& ctx, render::queue& queue) const { float star_distance = (clip_near + clip_far) * 0.5f; - model = float4x4(math::matrix_cast(icrf_to_eus.r)); + model = float4x4(float3x3(icrf_to_eus.r)); model = math::scale(model, {star_distance, star_distance, star_distance}); model_view = view * model;