1#[macro_export]
3macro_rules! assert_near {
4 ($val: expr, $exp: expr, $tol: expr) => {
5 assert!(
6 ($val - $exp).abs() < $tol,
7 "Approximation failed\nvalue: {}\nexpected: {}\n tolerance: {}",
8 $val, $exp, $tol
9 )
10 }
11}
12
13#[macro_export]
15macro_rules! impl_vector {
16 ($VectorN:ident { $($field:ident),+ }, $n: expr, $label: ident) => {
17 impl From<f64> for $VectorN {
18 fn from(s: f64) -> Self {
19 $VectorN { $($field: s),+ }
20 }
21 }
22
23 impl $VectorN {
24 #[inline]
25 pub const fn new($($field: f64),+) -> Self {
26 $VectorN { $($field: $field),+ }
27 }
28 }
29
30 impl Initializer for $VectorN {
31 #[inline]
32 fn zeros() -> Self {
33 $VectorN { $($field: 0.),+ }
34 }
35
36 #[inline]
37 fn ones() -> Self {
38 $VectorN { $($field: 1.),+ }
39 }
40 }
41
42 impl Reset<$VectorN> for $VectorN {
43 #[inline]
44 fn reset0(&mut self) -> &mut Self {
45 $(self.$field = 0.;)+
46 self
47 }
48
49 #[inline]
50 fn reset1(&mut self) -> &mut Self {
51 $(self.$field = 1.;)+
52 self
53 }
54
55 #[inline]
56 fn reset(&mut self, val: &$VectorN) -> &mut Self {
57 $(self.$field = val.$field;)+
58 self
59 }
60 }
61
62 impl Metric for $VectorN {
63
64 #[inline]
65 fn dot(&self, rhs: &Self) -> f64 {
66 let mut ret = 0.;
67 $(ret += self.$field * rhs.$field;)+
68 ret
69 }
70
71 #[inline]
72 fn magnitude2(&self) -> f64 {
73 let mut ret = 0.;
74 $(ret += self.$field * self.$field;)+
75 ret
76 }
77
78 #[inline]
79 fn magnitude(&self) -> f64 {
80 self.magnitude2().sqrt()
81 }
82
83 #[inline]
84 fn distance2(&self, rhs: &Self) -> f64 {
85 let mut ret = 0.;
86 let mut distance;
87 $(
88 distance = self.$field - rhs.$field;
89 ret += distance * distance;
90 )+
91 ret
92 }
93
94 #[inline]
95 fn distance(&self, rhs: &Self) -> f64 {
96 self.distance2(rhs).sqrt()
97 }
98
99 #[inline]
100 fn set_normalized(&mut self) -> &mut Self {
101 let magnitude = self.magnitude();
102 $(self.$field /= magnitude;)+
103 self
104 }
105 }
106
107 impl BitOr<$VectorN> for $VectorN {
108 type Output = f64;
109
110 #[inline]
111 fn bitor(self, rhs: $VectorN) -> Self::Output {
112 self.dot(&rhs)
113 }
114 }
115
116 impl Not for $VectorN {
117 type Output = f64;
118
119 #[inline]
120 fn not(self) -> Self::Output {
121 self.magnitude()
122 }
123 }
124
125 impl Rem<$VectorN> for $VectorN {
126 type Output = f64;
127
128 #[inline]
129 fn rem(self, rhs: Self) -> Self::Output {
130 self.distance(&rhs)
131 }
132 }
133
134 impl PartialEq for $VectorN {
135
136 #[inline]
137 fn eq(&self, other: &Self) -> bool {
138 self.distance2(other) < std::f64::MIN_POSITIVE
139 }
140
141 #[inline]
142 fn ne(&self, other: &Self) -> bool {
143 self.distance2(other) >= std::f64::MIN_POSITIVE
144 }
145 }
146
147 impl Add<$VectorN> for $VectorN {
148 type Output = Self;
149
150 #[inline]
151 fn add(self, rhs: Self) -> Self::Output {
152 $VectorN { $($field: self.$field + rhs.$field),+ }
153 }
154 }
155
156 impl AddAssign<$VectorN> for $VectorN {
157
158 #[inline]
159 fn add_assign(&mut self, rhs: $VectorN) {
160 $(self.$field += rhs.$field;)+
161 }
162 }
163
164 impl Sub<$VectorN> for $VectorN {
165 type Output = Self;
166
167 #[inline]
168 fn sub(self, rhs: Self) -> Self::Output {
169 $VectorN { $($field: self.$field - rhs.$field),+ }
170 }
171 }
172
173 impl SubAssign<$VectorN> for $VectorN {
174
175 #[inline]
176 fn sub_assign(&mut self, rhs: $VectorN) {
177 $(self.$field -= rhs.$field;)+
178 }
179 }
180
181 impl Neg for $VectorN {
182 type Output = Self;
183
184 #[inline]
185 fn neg(self) -> Self::Output {
186 $VectorN { $($field: -self.$field),+ }
187 }
188 }
189
190 impl Mul<f64> for $VectorN {
191 type Output = Self;
192
193 #[inline]
194 fn mul(self, rhs: f64) -> Self::Output {
195 $VectorN { $($field: self.$field * rhs),+ }
196 }
197 }
198
199 impl MulAssign<f64> for $VectorN {
200
201 #[inline]
202 fn mul_assign(&mut self, rhs: f64) {
203 $(self.$field *= rhs;)+
204 }
205 }
206
207 impl Div<f64> for $VectorN {
208 type Output = Self;
209
210 #[inline]
211 fn div(self, rhs: f64) -> Self::Output {
212 $VectorN { $($field: self.$field / rhs),+ }
213 }
214 }
215
216 impl DivAssign<f64> for $VectorN {
217
218 #[inline]
219 fn div_assign(&mut self, rhs: f64) {
220 $(self.$field /= rhs;)+
221 }
222 }
223
224 impl Interpolation for $VectorN {
225 fn set_lerp(&mut self, other: &Self, s: f64) -> &mut Self {
226 $(self.$field += (other.$field - self.$field) * s;)+
227 self
228 }
229
230 fn set_herp(&mut self, other: &Self, other1: &Self, other2: &Self, s: f64) -> &mut Self {
231 let s2 = s * s;
232 let t0 = s2 * (2. * s - 3.) + 1.;
233 let t1 = s2 * (s - 2.) + s;
234 let t2 = s2 * (s - 1.);
235 let t3 = s2 * (3. - 2. * s);
236 $(self.$field = self.$field * t0 + other1.$field * t1 + other2.$field * t2 + other.$field * t3;)+
237 self
238 }
239
240 fn set_berp(&mut self, other: &Self, other1: &Self, other2: &Self, s: f64) -> &mut Self {
241 let s2 = s * s;
242 let inv = 1. - s;
243 let inv2 = inv * inv;
244 let t0 = inv2 * inv;
245 let t1 = 3. * s * inv2;
246 let t2 = 3. * s2 * inv;
247 let t3 = s2 * s;
248 $(self.$field = self.$field * t0 + other1.$field * t1 + other2.$field * t2 + other.$field * t3;)+
249 self
250 }
251 }
252
253 #[inline]
254 pub const fn $label($($field: f64),+) -> $VectorN {
255 $VectorN::new($($field),+)
256 }
257 }
258}
259
260#[macro_export]
262macro_rules! impl_debug_vector {
263($VectorN:ident { $($field:ident),+ }) => {
264 impl Debug for $VectorN {
265 fn fmt(&self, f: &mut Formatter<'_>) -> Result<(), Error> {
266 let mut buffer = String::from("(");
267 if self.magnitude() > 1000. {
268 $(buffer += format!(" {:.3e} ", self.$field).as_str();)+
269 } else {
270 $(buffer += format!(" {:.3} ", self.$field).as_str();)+
271 }
272 buffer += ")";
273 write!(f, "{}", buffer)
274 }
275 }
276 }
277}
278
279#[macro_export]
281macro_rules! impl_debug_matrix {
282($MatrixN:ident) => {
283 impl Debug for $MatrixN {
284 fn fmt(&self, f: &mut Formatter<'_>) -> Result<(), Error> {
285 let rows = self.rows();
286 let mut buffer = String::from("");
287 for row in rows.iter() {
288 buffer += &format!("\n{:?}", row);
289 }
290 write!(f, "{}", buffer)
291 }
292 }
293 }
294}