Pioneer
Loading...
Searching...
No Matches
MathUtil.h
Go to the documentation of this file.
1// Copyright © 2008-2024 Pioneer Developers. See AUTHORS.txt for details
2// Licensed under the terms of the GPL v3. See licenses/GPL-3.txt
3
4#ifndef _MATHUTIL_H
5#define _MATHUTIL_H
6
7#include "matrix3x3.h"
8#include "matrix4x4.h"
9#include "vector3.h"
10#include "fixed.h"
11
12#include <cmath>
13
14template <class T>
15inline const T &Clamp(const T &x, const T &min, const T &max) { return x > max ? max : (x < min ? min : x); }
16
17inline constexpr double DEG2RAD(double x) { return x * (M_PI / 180.); }
18inline constexpr float DEG2RAD(float x) { return x * (float(M_PI) / 180.f); }
19inline constexpr double RAD2DEG(double x) { return x * (180. / M_PI); }
20inline constexpr float RAD2DEG(float x) { return x * (180.f / float(M_PI)); }
21
22static inline Sint64 isqrt(Sint64 a)
23{
24 // replace with cast from sqrt below which is between x7.3 (win32, Debug) & x15 (x64, Release) times faster
25 return static_cast<int64_t>(sqrt(static_cast<double>(a)));
26}
27
28static inline Sint64 isqrt(fixed v)
29{
30 Sint64 ret = 0;
31 Sint64 s;
32 Sint64 ret_sq = -v.v - 1;
33 for (s = 62; s >= 0; s -= 2) {
34 Sint64 b;
35 ret += ret;
36 b = ret_sq + ((2 * ret + 1) << s);
37 if (b < 0) {
38 ret_sq = b;
39 ret++;
40 }
41 }
42 return ret;
43}
44
45// add a few things that MSVC is missing
46#if defined(_MSC_VER) && (_MSC_VER < 1800)
47
48// round & roundf. taken from http://cgit.freedesktop.org/mesa/mesa/tree/src/gallium/auxiliary/util/u_math.h
49static inline double round(double x)
50{
51 return x >= 0.0 ? floor(x + 0.5) : ceil(x - 0.5);
52}
53
54static inline float roundf(float x)
55{
56 return x >= 0.0f ? floorf(x + 0.5f) : ceilf(x - 0.5f);
57}
58#endif /* _MSC_VER < 1800 */
59
60static inline Uint32 ceil_pow2(Uint32 v)
61{
62 v--;
63 v |= v >> 1;
64 v |= v >> 2;
65 v |= v >> 4;
66 v |= v >> 8;
67 v |= v >> 16;
68 v++;
69 return v;
70}
71
72namespace MathUtil {
73
74 // random point on a sphere, distributed uniformly by area
75 vector3d RandomPointOnSphere(double minRadius, double maxRadius);
76 inline vector3d RandomPointOnSphere(double radius) { return RandomPointOnSphere(radius, radius); }
77
78 vector3d RandomPointInCircle(double minRadius, double maxRadius);
79 inline vector3d RandomPointInCircle(double radius) { return RandomPointInCircle(0.0, radius); }
80 inline vector3d RandomPointOnCircle(double radius) { return RandomPointInCircle(radius, radius); }
81
82 // interpolation, glsl style naming "mix"
83 template <class T, class F>
84 inline T mix(const T &v1, const T &v2, const F t)
85 {
86 return t * v2 + (F(1.0) - t) * v1;
87 }
88 template <class T, class F>
89 inline T Lerp(const T &v1, const T &v2, const F t)
90 {
91 return mix(v1, v2, t);
92 }
93
94 inline float Dot(const vector3f &a, const vector3f &b) { return a.x * b.x + a.y * b.y + a.z * b.z; }
95
96 // unit vector orthogonal to given vector
97 template <typename T>
99 {
100 vector3<T> b;
101 if (std::abs(a.x) > std::abs(a.y)) {
102 if (std::abs(a.y) > std::abs(a.z))
103 b = vector3<T>(-a.y, a.x, 0);
104 else
105 b = vector3<T>(a.z, 0, -a.x);
106 } else {
107 if (std::abs(a.x) > std::abs(a.z))
108 b = vector3<T>(-a.y, a.x, 0);
109 else
110 b = vector3<T>(0, -a.z, a.y);
111 }
112 return b.Normalized();
113 }
114
115 // matrix4x4f utility functions
119
120 // matrix3x3f utility functions
123
124 // distance from a line segment:
125 float DistanceFromLineSegment(const vector3f &start, const vector3f &end, const vector3f &pos, bool &isWithinLineSegment);
126 float DistanceFromLine(const vector3f &start, const vector3f &end, const vector3f &pos);
127
128 inline static matrix3x3d LookAt(const vector3d eye, const vector3d target, const vector3d up)
129 {
130 const vector3d z = (eye - target).NormalizedSafe();
131 const vector3d x = (up.Cross(z)).NormalizedSafe();
132 const vector3d y = (z.Cross(x)).NormalizedSafe();
133
134 return matrix3x3d::FromVectors(x, y, z);
135 }
136
137//#define TEST_MATHUTIL
138#ifdef TEST_MATHUTIL
139 bool TestDistanceFromLine();
140#endif
141} // namespace MathUtil
142
143#endif
constexpr double DEG2RAD(double x)
Definition: MathUtil.h:17
const T & Clamp(const T &x, const T &min, const T &max)
Definition: MathUtil.h:15
constexpr double RAD2DEG(double x)
Definition: MathUtil.h:19
Sint64 v
Definition: fixed.h:239
static matrix3x3 FromVectors(const vector3< double > &rx, const vector3< double > &ry, const vector3< double > &rz)
Definition: matrix3x3.h:68
T y
Definition: vector3.h:20
T x
Definition: vector3.h:20
T z
Definition: vector3.h:20
vector3 Normalized() const
Definition: vector3.h:136
vector3 Cross(const vector3 &b) const
Definition: vector3.h:128
Definition: MathUtil.cpp:7
vector3d RandomPointOnSphere(double minRadius, double maxRadius)
Definition: MathUtil.cpp:9
matrix4x4f Inverse(const matrix4x4f &cell)
Definition: MathUtil.cpp:33
vector3< T > OrthogonalDirection(const vector3< T > &a)
Definition: MathUtil.h:98
T mix(const T &v1, const T &v2, const F t)
Definition: MathUtil.h:84
T Lerp(const T &v1, const T &v2, const F t)
Definition: MathUtil.h:89
float Dot(const vector3f &a, const vector3f &b)
Definition: MathUtil.h:94
float DistanceFromLineSegment(const vector3f &start, const vector3f &end, const vector3f &pos, bool &isWithinLineSegment)
Definition: MathUtil.cpp:246
vector3d RandomPointInCircle(double minRadius, double maxRadius)
Definition: MathUtil.cpp:20
matrix4x4f InverseSlow(const matrix4x4f &cell)
Definition: MathUtil.cpp:54
vector3d RandomPointOnCircle(double radius)
Definition: MathUtil.h:80
float DistanceFromLine(const vector3f &start, const vector3f &end, const vector3f &pos)
Definition: MathUtil.cpp:265
matrix4x4f Transpose(const matrix4x4f &cell)
Definition: MathUtil.cpp:183
vector3< T > max(const vector3< T > &lhs, const vector3< T > &rhs)
Definition: vector3.h:312
vector3< T > min(const vector3< T > &lhs, const vector3< T > &rhs)
Definition: vector3.h:320