API Documentation
Loading...
Searching...
No Matches
AngleFunctions.h
Go to the documentation of this file.
1/*--------------------------------------------------------------------------------------------
2Copyright (c) 2019, NDEVR LLC
3tyler.parke@ndevr.org
4 __ __ ____ _____ __ __ _______
5 | \ | | | __ \ | ___|\ \ / / | __ \
6 | \ | | | | \ \ | |___ \ \ / / | |__) |
7 | . \| | | |__/ / | |___ \ V / | _ /
8 | |\ |_|_____/__|_____|___\_/____| | \ \
9 |__| \__________________________________| \__\
10
11Subject to the terms of the Enterprise+ Agreement, NDEVR hereby grants
12Licensee a limited, non-exclusive, non-transferable, royalty-free license
13(without the right to sublicense) to use the API solely for the purpose of
14Licensee's internal development efforts to develop applications for which
15the API was provided.
16
17The above copyright notice and this permission notice shall be included in all
18copies or substantial portions of the Software.
19
20THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
21INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
22PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE
23FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
24OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
25DEALINGS IN THE SOFTWARE.
26
27Library: Base
28File: AngleFunctions
29Included in API: True
30Author(s): Tyler Parke
31 *-----------------------------------------------------------------------------------------**/
32#pragma once
33#include "DLLInfo.h"
34#include <NDEVR/Angle.h>
35#include <NDEVR/Vector.h>
36namespace NDEVR
37{
38 extern NDEVR_BASE_API const fltp08* const s_index_sin;
39 /**\brief Greater-than comparison operator.
40 \param[in] angle_a The first instance to compare.
41 \param[in] angle_b The second instance to compare.
42 \return True if the first parameter is greater than to the second.**/
43 template<class t_type_a, class t_type_b>
44 constexpr static bool operator>(const Angle<t_type_a>& angle_a, const Angle<t_type_b>& angle_b)
45 {
46 return angle_a.template internal<false>() > cast<t_type_a>(angle_b.template internal<false>());
47 }
48 /**\brief Less-than comparison operator.
49 \param[in] angle_a The first instance to compare.
50 \param[in] angle_b The second instance to compare.
51 \return True if the first parameter is less than to the second.**/
52 template<class t_type_a, class t_type_b>
53 constexpr static bool operator<(const Angle<t_type_a>& angle_a, const Angle<t_type_b>& angle_b)
54 {
55 return angle_a.template internal<false>() < cast<t_type_a>(angle_b.template internal<false>());
56 }
57 /** \brief Greater-than-or-equal comparison operator.
58 \param[in] angle_a The first instance to compare.
59 \param[in] angle_b The second instance to compare.
60 \return True if the first parameter is greater than or equal to the second.**/
61 template<class t_type_a, class t_type_b>
62 constexpr static bool operator>=(const Angle<t_type_a>& angle_a, const Angle<t_type_b>& angle_b)
63 {
64 return angle_a.template internal<false>() >= cast<t_type_a>(angle_b.template internal<false>());
65 }
66 /**\brief Less-than-or-equal comparison operator.
67 \param[in] angle_a The first instance to compare.
68 \param[in] angle_b The second instance to compare.
69 \return True if the first parameter is less than or equal to the second.**/
70 template<class t_type_a, class t_type_b>
71 constexpr static bool operator<=(const Angle<t_type_a>& angle_a, const Angle<t_type_b>& angle_b)
72 {
73 return angle_a.template internal<false>() <= cast<t_type_a>(angle_b.template internal<false>());
74 }
75 /** \brief Performs optimized sine operation on the given angle using pre-computed lookup table for optimal speed.
76 \param[in] angle The angle to perform sin on.
77 \return The sine of the given angle**/
78 template<class t_type>
79 typename std::enable_if<!ObjectInfo<t_type>::Float, fltp08>::type sin(const Angle<t_type>& angle)
80 {
81
82 const uint02 internal_angle = cast<uint02>(angle.template internal<true>());
83 if (internal_angle <= Angle<t_type>::INDEX_PI)
84 {
85 if (internal_angle > (Angle<t_type>::INDEX_PI / 2))
86 return s_index_sin[Angle<t_type>::INDEX_PI - internal_angle];
87 else
88 return s_index_sin[internal_angle];
89 }
90 else
91 {
92 if (internal_angle >= Angle<t_type>::INDEX_PI + (Angle<t_type>::INDEX_PI / 2))
93 return -s_index_sin[2 * Angle<t_type>::INDEX_PI - internal_angle];
94 else
95 return -s_index_sin[internal_angle - Angle<t_type>::INDEX_PI];
96 }
97 }
98 /**
99 \brief Performs sine operation on the given angle.
100 \param[in] angle The angle to perform sin on.
101 \return The sine of the given angle
102 **/
103 template<class t_type>
104 typename std::enable_if<ObjectInfo<t_type>::Float, fltp08>::type sin(const Angle<t_type>& angle)
105 {
106 return ::sin(angle.template as<RADIANS>());
107 }
108 /**
109 \brief Performs sine operation on the given number assumed to be in radians.
110 \param[in] angle The number, in radians to perform sin on.
111 \return The sine of the given angle
112 **/
113 template<class t_type>
114 t_type sin(const t_type& angle)
115 {
116 return ::sin(angle);
117 }
118 /**
119 \brief Performs optimized cosine operation on the given angle using pre-computed lookup table for optimal speed.
120 \param[in] angle The angle to perform cosin on.
121 \return The cosine of the given angle
122 **/
123 template<class t_type>
124 typename std::enable_if<!ObjectInfo<t_type>::Float, fltp08>::type cos(const Angle<t_type>& angle)
125 {
126 const Angle<t_type> internal_angle = Angle<t_type>(cast<uint02>((angle.template internal<true>() + (Angle<t_type>::INDEX_PI / 2)) % (2 * Angle<t_type>::INDEX_PI)));
127 return sin(internal_angle);
128 }
129 /**
130 \brief Performs cosine operation on the given angle.
131 \param[in] angle The angle to perform cosine on.
132 \return The cosine of the given angle
133 **/
134 template<class t_type>
135 typename std::enable_if<ObjectInfo<t_type>::Float, fltp08>::type cos(const Angle<t_type>& angle)
136 {
137 return ::cos(angle.template as<RADIANS>());
138 }
139 /**
140 \brief Performs cosine operation on the given angle assumed to be in radians.
141 \param[in] angle The number, in radians, to perform cosine on.
142 \return The cosine of the given angle
143 **/
144 template<class t_type>
145 t_type cos(const t_type& angle)
146 {
147 return ::cos(angle);
148 }
149
150 /**
151 \brief Performs optimized tangent operation on the given angle using pre-computed lookup table for optimal speed.
152 \param[in] angle The angle to perform tangent on.
153 \return The tangent of the given angle
154 **/
155 template<class t_type>
156 typename std::enable_if<!ObjectInfo<t_type>::Float, fltp08>::type tan(const Angle<t_type>& angle)
157 {
158 return sin(angle) / cos(angle);
159 }
160 /**
161 \brief Performs tan operation on the given angle.
162 \param[in] angle The angle to perform tan on.
163 \return The tangent of the given angle
164 **/
165 template<class t_type>
166 typename std::enable_if<ObjectInfo<t_type>::Float, fltp08>::type tan(const Angle<t_type>& angle)
167 {
168 return ::tan(angle.template as<RADIANS>());
169 }
170
171 /**
172 \brief Performs tan operation on the given angle assumed to be in radians.
173 \param[in] angle The angle, in radians, to perform tan on.
174 \return The tangent of the given angle
175 **/
176 template<class t_type>
177 t_type tan(const t_type& angle)
178 {
179 return ::tan(angle);
180 }
181
182 /**
183 \brief Subtraction operator.
184 \param[in] angle_a The first value.
185 \param[in] angle_b A value to subtract from it.
186 \return The result of the subtraction operation.
187 **/
188 template<class t_type>
189 constexpr static Angle<t_type> operator-(const Angle<t_type>& angle_a, const Angle<t_type>& angle_b)
190 {
191 return Angle<t_type>(cast<t_type>(angle_a.template internal<false>() - angle_b.template internal<false>()));
192 }
193 /**
194 \brief Addition operator.
195 \param[in] angle_a The first value.
196 \param[in] angle_b A value to add to it.
197 \return The result of the addition operation.
198 **/
199 template<class t_type>
200 constexpr static Angle<t_type> operator+(const Angle<t_type>& angle_a, const Angle<t_type>& angle_b)
201 {
202 return Angle<t_type>(cast<t_type>(angle_a.template internal<false>() + angle_b.template internal<false>()));
203 }
204
205 /**
206 \brief Calculates minimal absolute signed angle between two angles
207 \param[in] angle_a The first angle.
208 \param[in] angle_b The second angle
209 \return The absolute minimal angle (-180 to 180 degrees) between the two angles
210 **/
211 template<class t_type>
212 constexpr static Angle<t_type> difference(const Angle<t_type>& angle_a, const Angle<t_type>& angle_b)
213 {
214 Angle<t_type> angle = (angle_a - angle_b).normalized();
215 if (angle <= Angle<t_type>(DEGREES, 180.0f))
216 return angle;
217 else
218 return Angle<t_type>(DEGREES, -360.0f) + angle;
219 }
220 /**
221 \brief Calculates the minimal absolute signed angle between two angles
222 \param[in] angle_a A vector of the first angle.
223 \param[in] angle_b A vector of the second angle
224 \return The A vector that for each axis returns the absolute minimal angle (-180 to 180 degrees)
225 between the two input angles
226 **/
227 template<uint01 t_dims, class t_type>
228 constexpr static Vector<t_dims, Angle<t_type>> difference(const Vector<t_dims, Angle<t_type>>& angle_a, const Vector<t_dims, Angle<t_type>>& angle_b)
229 {
230 Vector<t_dims, Angle<t_type>> angle;
231 for (uint01 dim = 0; dim < t_dims; ++dim)
232 {
233 angle[dim] = difference(angle_a[dim], angle_b[dim]);
234 }
235 return angle;
236 }
237
238 /**
239 \brief Calculates the average of two normalized angles. For example 359.1 and 720.1 would average to
240 be 0.0 and 0.0 and 180.0 would average to be 90.0
241 \param[in] angle_a the first angle.
242 \param[in] angle_b the second angle
243 \return The averaged normalized angle
244 **/
245 template<class t_type>
246 constexpr static Angle<t_type> Average(const Angle<t_type>& angle_a, const Angle<t_type>& angle_b)
247 {
248 Angle<t_type> angle = difference(angle_a, angle_b) / 2.0;
249 angle += angle_b;
250 return angle;
251 }
252
253 /**
254 \brief Calculates the average of two normalized angles. For example 359.1 and 720.1 would average to
255 be 0.0 and 0.0 and 180.0 would average to be 90.0
256 \param[in] angle_a the first angle.
257 \param[in] angle_b the second angle
258 \return The averaged normalized angle
259 **/
260 template<uint01 t_dims, class t_type>
261 constexpr static Vector<t_dims, Angle<t_type>> Average(const Vector<t_dims, Angle<t_type>>& angle_a, const Vector<t_dims, Angle<t_type>>& angle_b)
262 {
263 Vector<t_dims, Angle<t_type>> angle;
264 for (uint01 dim = 0; dim < t_dims; ++dim)
265 {
266 angle[dim] = Average(angle_a[dim], angle_b[dim]);
267 }
268 return angle;
269 }
270
271 /**
272 \brief Multiplication operator.
273 \param[in] angle_a The first value.
274 \param[in] angle_b A value to add to it.
275 \return The result of the multiplication operation.
276 **/
277 template<class t_type>
278 constexpr static Angle<t_type> operator*(const Angle<t_type>& angle_a, const Angle<t_type>& angle_b)
279 {
280 return Angle<t_type>(cast<t_type>(angle_a.template internal<false>() * angle_b.template internal<false>()));
281 }
282
283 /**
284 \brief Division operator.
285 \param[in] angle_a The first value.
286 \param[in] angle_b A value to add to it.
287 \return The result of the division operation.
288 **/
289 template<class t_type>
290 constexpr static fltp08 operator/(const Angle<t_type>& angle_a, const Angle<t_type>& angle_b)
291 {
292 return cast<fltp08>(angle_a.template internal<false>()) / cast<fltp08>(angle_b.template internal<false>());
293 }
294
295 /**
296 \brief Multiplication operator.
297 \param[in] angle An angle to multiply
298 \param[in] mult A scaler value to multiply the angle by.
299 \return The result of the multiplication operation.
300 **/
301 template<class t_type, class t_angle_type>
302 constexpr static Angle<t_angle_type> operator*(const Angle<t_angle_type>& angle, t_type mult)
303 {
304 return Angle<t_angle_type>(cast<t_angle_type>(cast<t_type>(angle.template internal<false>()) * mult));
305 }
306
307 /**
308 \brief Multiplication operator.
309 \param[in] mult A scaler value to multiply the angle by.
310 \param[in] angle The angle to multiply.
311 \return The result of the multiplication operation.
312 **/
313 template<class t_type, class t_angle_type>
314 constexpr static Angle<t_angle_type> operator*(t_type mult, const Angle<t_angle_type>& angle)
315 {
316 return Angle<t_angle_type>(cast<t_angle_type>(cast<t_type>(angle.template internal<false>()) * mult));
317 }
318 /**
319 \brief Multiplication operator for a Vector of Angles.
320 \param[in] mult A scaler value to multiply the angle by.
321 \param[in] angle The vector of Angles to multiply.
322 \return The result of the multiplication operation.
323 **/
324 template<class t_type, class t_vector_type>
325 constexpr typename std::enable_if<IsVecType<t_vector_type, Angle<fltp08>>::value, t_vector_type>::type
326 operator*(const t_vector_type& angle, const t_type& mult)
327 {
328 t_vector_type product;
329 for (uint01 dim = 0; dim < t_vector_type::NumberOfDimensions(); ++dim)
330 product[dim] = angle[dim] * mult;
331 return product;
332 }
333
334 /**
335 \brief Multiplication operator for a Vector of Angles.
336 \param[in] mult A scaler value to multiply the angle by.
337 \param[in] angle The vector of Angles to multiply.
338 \return The result of the multiplication operation.
339 **/
340 template<class t_type, class t_vector_type>
341 constexpr typename std::enable_if<IsVecType<t_vector_type, Angle<sint04>>::value, t_vector_type>::type
342 operator*(const t_vector_type& angle, const t_type& mult)
343 {
344 t_vector_type product;
345 for (uint01 dim = 0; dim < t_vector_type::NumberOfDimensions(); ++dim)
346 product[dim] = angle[dim] * mult;
347 return product;
348 }
349
350 /**
351 \brief Multiplication operator for a Vector of Angles.
352 \param[in] mult A Vector scaler value to multiply the angle by.
353 \param[in] angle The vector of Angles to multiply.
354 \return The result of the multiplication operation.
355 **/
356 template<uint01 t_dims, class t_type, class t_vector_type>
357 constexpr typename std::enable_if<std::is_base_of<Vector<t_dims, Angle<fltp08>>, t_vector_type>::value, t_vector_type>::type
358 operator*(const t_vector_type& angle, const Vector<t_dims, t_type>& mult)
359 {
360 t_vector_type product;
361 for (uint01 dim = 0; dim < t_dims; ++dim)
362 product[dim] = angle[dim] * mult[dim];
363 return product;
364 }
365
366 /**
367 \brief Multiplication operator for a Vector of Angles.
368 \param[in] angle The vector of Angles to multiply.
369 \param[in] mult A Vector scaler value to multiply the angle by.
370 \return The result of the multiplication operation.
371 **/
372 template<uint01 t_dims, class t_type, class t_vector_type>
373 constexpr typename std::enable_if<std::is_base_of<Vector<t_dims, Angle<sint04>>, t_vector_type>::value, t_vector_type>::type
374 operator*(const t_vector_type& angle, const Vector<t_dims, t_type>& mult)
375 {
376 t_vector_type product;
377 for (uint01 dim = 0; dim < t_dims; ++dim)
378 product[dim] = angle[dim] * mult[dim];
379 return product;
380 }
381
382 template<class t_type, class t_vector_type>
383 constexpr typename std::enable_if<IsVecType<t_vector_type, Angle<fltp08>>::value, t_vector_type>::type
384 operator*(const t_type& mult, const t_vector_type& angle)
385 {
386 t_vector_type product;
387 for (uint01 dim = 0; dim < t_vector_type::NumberOfDimensions(); ++dim)
388 product[dim] = mult * angle[dim];
389 return product;
390 }
391 template<class t_type, class t_vector_type>
392 constexpr typename std::enable_if<IsVecType<t_vector_type, Angle<sint04>>::value, t_vector_type>::type
393 operator*(const t_type& mult, const t_vector_type& angle)
394 {
395 t_vector_type product;
396 for (uint01 dim = 0; dim < t_vector_type::NumberOfDimensions(); ++dim)
397 product[dim] = mult * angle[dim];
398 return product;
399 }
400 template<uint01 t_dims, class t_type, class t_vector_type>
401 constexpr typename std::enable_if<std::is_base_of<Vector<t_dims, Angle<fltp08>>, t_vector_type>::value, t_vector_type>::type
402 operator*(const Vector<t_dims, t_type>& mult, const t_vector_type& angle)
403 {
404 t_vector_type product;
405 for (uint01 dim = 0; dim < t_vector_type::NumberOfDimensions(); ++dim)
406 product[dim] = mult[dim] * angle[dim];
407 return product;
408 }
409 template<uint01 t_dims, class t_type, class t_vector_type>
410 constexpr typename std::enable_if<std::is_base_of<Vector<t_dims, Angle<sint04>>, t_vector_type>::value, t_vector_type>::type
411 operator*(const Vector<t_dims, t_type>& mult, const t_vector_type& angle)
412 {
413 t_vector_type product;
414 for (uint01 dim = 0; dim < t_vector_type::NumberOfDimensions(); ++dim)
415 product[dim] = mult[dim] * angle[dim];
416 return product;
417 }
418 template<class t_type, class t_vector_type>
419 constexpr typename std::enable_if<IsVecType<t_vector_type, Angle<fltp08>>::value, t_vector_type>::type
420 operator*(const t_vector_type& mult, const t_vector_type& angle)
421 {
422 t_vector_type product;
423 for (uint01 dim = 0; dim < t_vector_type::NumberOfDimensions(); ++dim)
424 product[dim] = mult[dim] * angle[dim];
425 return product;
426 }
427 template<class t_type, class t_vector_type>
428 constexpr typename std::enable_if<IsVecType<t_vector_type, Angle<sint04>>::value, t_vector_type>::type
429 operator*(const t_vector_type& mult, const t_vector_type& angle)
430 {
431 t_vector_type product;
432 for (uint01 dim = 0; dim < t_vector_type::NumberOfDimensions(); ++dim)
433 product[dim] = mult[dim] * angle[dim];
434 return product;
435 }
436 /**
437 \brief Division operator for a Vector of Angles.
438 \param[in] angle The Angles to divide.
439 \param[in] den A scaler value to divide the angle by.
440 \return The result of the multiplication operation.
441 **/
442 template<class t_type, class t_angle_type>
443 constexpr static Angle<t_angle_type> operator/(const Angle<t_angle_type>& num, t_type den)
444 {
445 return Angle<t_angle_type>(cast<t_angle_type>(cast<t_type>(num.template internal<false>()) / den));
446 }
447
448 /**
449 \brief Division operator for a Vector of Angles.
450 \param[in] den A scaler value to divide the angle by.
451 \param[in] angle The Vector of Angles to divide.
452 \return The result of the multiplication operation.
453 **/
454 template<class t_type, class t_vector_type, class t_angle_type>
455 constexpr typename std::enable_if<IsVecType<t_vector_type, Angle<t_angle_type>>::value, t_vector_type>::type
456 operator/(const t_vector_type& angle, const t_type& den)
457 {
458 t_vector_type div;
459 for (uint01 dim = 0; dim < t_vector_type::NumberOfDimensions(); ++dim)
460 div[dim] = angle[dim] / den;
461 return div;
462 }
463
464 /**
465 \brief Division operator for a Vector of Angles.
466 \param[in] den A scaler value to divide the angle by.
467 \param[in] angle The Vector of Angles to divide.
468 \return The result of the multiplication operation.
469 **/
470 template<class t_type, class t_vector_type>
471 constexpr typename std::enable_if<IsVecType<t_vector_type, Angle<fltp08>>::value, t_vector_type>::type
472 operator/(const t_vector_type& angle, const t_type& den)
473 {
474 t_vector_type div;
475 for (uint01 dim = 0; dim < t_vector_type::NumberOfDimensions(); ++dim)
476 div[dim] = angle[dim] / den;
477 return div;
478 }
479
480 /**
481 \brief Division operator for a Vector of Angles.
482 \param[in] den A scaler value to divide the angle by.
483 \param[in] angle The Vector of Angles to divide.
484 \return The result of the multiplication operation.
485 **/
486 template<class t_type, class t_vector_type>
487 constexpr typename std::enable_if<IsVecType<t_vector_type, Angle<sint04>>::value, t_vector_type>::type
488 operator/(const t_vector_type& angle, const t_type& den)
489 {
490 t_vector_type div;
491 for (uint01 dim = 0; dim < t_vector_type::NumberOfDimensions(); ++dim)
492 div[dim] = angle[dim] / den;
493 return div;
494 }
495
496 /**
497 \brief Division operator for a Vector of Angles.
498 \param[in] den A scaler value the angle will divide by.
499 \param[in] angle The Vector of Angles to divide the den by.
500 \return The result of the multiplication operation.
501 **/
502 template<uint01 t_dims, class t_type, class t_vector_type, class t_angle_type>
503 constexpr typename std::enable_if<std::is_base_of<Vector<t_dims, Angle<t_angle_type>>, t_vector_type>::value, t_vector_type>::type
504 operator/(const t_vector_type& angle, const Vector<t_dims, t_type>& den)
505 {
506 t_vector_type div;
507 for (uint01 dim = 0; dim < t_dims; ++dim)
508 div[dim] = angle[dim] / den[dim];
509 return div;
510 }
511
512 /**
513 \brief Division operator for a Vector of Angles.
514 \param[in] den A scaler value the angle will divide by.
515 \param[in] angle The Vector of Angles to divide the den by.
516 \return The result of the multiplication operation.
517 **/
518 template<uint01 t_dims, class t_vector_type, class t_angle_type>
519 constexpr typename std::enable_if<std::is_base_of<Vector<t_dims, Angle<t_angle_type>>, t_vector_type>::value, Vector<t_dims, fltp08>>::type
520 operator/(const t_vector_type& angle, const Vector<t_dims, Angle<t_angle_type>>& den)
521 {
523 for (uint01 dim = 0; dim < t_dims; ++dim)
524 div[dim] = angle[dim] / den[dim];
525 return div;
526 }
527 /**
528 \brief Division operator for a Vector of Angles.
529 \param[in] den A scaler value the angle will divide by.
530 \param[in] angle The Vector of Angles to divide the den by.
531 \return The result of the multiplication operation.
532 **/
533 template<uint01 t_dims, class t_angle_type>
534 constexpr Vector<t_dims, fltp08> operator/(const Vector<t_dims, Angle<t_angle_type>>& angle, const Vector<t_dims, Angle<t_angle_type>>& den)
535 {
537 for (uint01 dim = 0; dim < t_dims; ++dim)
538 div[dim] = angle[dim] / den[dim];
539 return div;
540 }
541
542 template<class t_type, class t_angle_type>
543 constexpr static Angle<t_angle_type> operator/(t_type num, const Angle<t_angle_type>& den)
544 {
545 return Angle(cast<t_angle_type>(num / cast<t_type>(den.template internal<false>())));
546 }
547 template<class t_type, class t_vector_type, class t_angle_type>
548 constexpr typename std::enable_if<IsVecType<t_vector_type, Angle<t_angle_type>>::value, t_vector_type>::type
549 operator/(t_type num, const t_vector_type& angle)
550 {
551 t_vector_type div;
552 for (uint01 dim = 0; dim < t_vector_type::NumberOfDimensions(); ++dim)
553 div[dim] = num / angle[dim];
554 return div;
555 }
556 template<class t_angle_type>
557 constexpr static Angle<t_angle_type>& operator+=(Angle<t_angle_type>& angle, const Angle<t_angle_type>& add)
558 {
559 angle = angle + add;
560 return angle;
561 }
562 template<class t_angle_type>
563 constexpr static Angle<t_angle_type>& operator-=(Angle<t_angle_type>& angle, const Angle<t_angle_type>& sub)
564 {
565 angle = angle - sub;
566 return angle;
567 }
568 template<class t_type, class t_angle_type>
569 constexpr static Angle<t_angle_type>& operator*=(Angle<t_angle_type>& angle, const t_type& mult)
570 {
571 angle = angle * mult;
572 return angle;
573 }
574 template<uint01 t_dims, class t_type, class t_angle_type>
575 constexpr static Vector<t_dims, Angle<t_angle_type>>& operator*=(Vector<t_dims, Angle<t_angle_type>>& angle, const t_type& mult)
576 {
577 for (uint01 dim = 0; dim < t_dims; ++dim)
578 angle[dim] = angle[dim] * mult;
579 return angle;
580 }
581 template<uint01 t_dims, class t_type, class t_angle_type>
582 constexpr static Vector<t_dims, Angle<t_angle_type>>& operator*=(Vector<t_dims, Angle<t_angle_type>>& angle, const Vector<t_dims, t_type>& mult)
583 {
584 for (uint01 dim = 0; dim < t_dims; ++dim)
585 angle[dim] = angle[dim] * mult[dim];
586 return angle;
587 }
588 template<class t_angle_type>
589 constexpr static Angle<t_angle_type>& operator*=(Angle<t_angle_type>& angle, const Angle<t_angle_type>& mult)
590 {
591 angle = angle * mult;
592 return angle;
593 }
594
595 template<class t_type, class t_angle_type>
596 constexpr static Angle<t_angle_type>& operator/=(Angle<t_angle_type>& angle, const t_type& mult)
597 {
598 angle = angle / mult;
599 return angle;
600 }
601 template<uint01 t_dims, class t_type, class t_angle_type>
602 constexpr static Vector<t_dims, Angle<t_angle_type>>& operator/=(Vector<t_dims, Angle<t_angle_type>>& angle, const t_type& den)
603 {
604 for (uint01 dim = 0; dim < t_dims; ++dim)
605 angle[dim] = angle[dim] / den;
606 return angle;
607 }
608 template<uint01 t_dims, class t_type, class t_angle_type>
609 constexpr static Vector<t_dims, Angle<t_angle_type>>& operator/=(Vector<t_dims, Angle<t_angle_type>>& angle, const Vector<t_dims, t_type>& den)
610 {
611 for (uint01 dim = 0; dim < t_dims; ++dim)
612 angle[dim] = angle[dim] / den[dim];
613 return angle;
614 }
615
616 template<uint01 t_dims, class t_angle_type>
618 {
620 for (uint01 dim = 0; dim < t_dims; ++dim)
621 mod[dim] = Angle<t_angle_type>(cast<t_angle_type>(vec_a[dim].template internal<false>() % vec_b[dim].template internal<false>()));
622 return mod;
623 }
624 /**
625 \brief Computes the remainder of an Angle given an angle and a modulo divisor.
626 \param[in] vec_a The Vector to compute the remainder.
627 \param[in] value_b The Vector to use as the modulo
628 \return The result of the modulo operation.
629 **/
630 template<uint01 t_dims, class t_angle_type>
632 {
634 for (uint01 dim = 0; dim < t_dims; ++dim)
635 mod[dim] = Angle<t_angle_type>(cast<t_angle_type>(vec_a[dim].template internal<false>() % value_b.template internal<false>()));
636 return mod;
637 }
638
639 /**
640 \brief Changes an input with a negative sign, to a positive sign.
641 \param[in] value The signed angle
642 \return The absolute value of the input angle
643 **/
644 template<class t_angle_type>
646 {
647 return value >= Angle<t_angle_type>(0) ? value : -value;
648 }
649
650
651 /**
652 \brief Converts a Vector of one angle to a different container type
653 \param[in] old The value to change into a different angle container
654 \return The same angle with a new container type
655 **/
656 template<class t_new_type, uint01 t_dims, class t_angle_type>
658 {
660 for(uint01 dim = 0; dim < t_dims; ++dim)
661 angle[dim] = old[dim].template toTypeAngle<t_new_type>();
662 return angle;
663 }
664
665 /**
666 \brief Logic for converting between Euler angles and basic rotations or normals
667 **/
669 {
670 public:
671 /**
672 \brief Converts a quaternion to Euler angles (Roll, Pitch and Yaw)
673 \param[in] quaternion The quaternion to compute
674 \return The Euler angles of that quaternion.
675 **/
677
678 /**
679
680 Gets a rotation.
681
682 Author: Tyler Parke
683
684 Date: 2017-11-13
685
686 Parameters:
687 left - The left.
688 middle - The middle.
689 right - The right.
690
691 \returns The rotation.
692 **/
693 template<class t_angle_type, uint01 t_dims, class t_type>
695 {
696 const Vector<t_dims, t_type> v_left(left - middle);
697 const Vector<t_dims, t_type> v_right(right - middle);
698 return Angle<t_angle_type>(RADIANS, acos(dot(v_left, v_right) / cast<fltp08>(sqrt(v_left.magnitudeSquared() * v_right.magnitudeSquared()))));
699 }
700 /**
701 Gets the Inclination of .
702
703 Author: Tyler Parke
704
705 Date: 2018-08-15
706
707 Parameters:
708 roll - The rotation about the X axis.
709 pitch - The rotation about the Y axis.
710
711 \returns The rotation.
712 **/
713 template<class t_angle_type>
715 {
716 return Angle<t_angle_type>::atan(cast<fltp08>(sqrt(tan(roll) * tan(roll) + tan(pitch) * tan(pitch))));
717 }
718
719 template<class t_angle_type, uint01 t_dims, class t_type>
721 {
722 const Vector<2, t_type> xy_diff = ray.template as<2, t_type>();
723 return Angle<t_angle_type>::atan2(ray[Z], xy_diff.template magnitude<t_type>());
724 }
725
726 template<class t_angle_type, uint01 t_dims, class t_type>
728 {
729 return Angle<t_angle_type>::atan2(ray[Y], ray[X]);
730 }
731
732 template<class t_angle_type, uint01 t_dims, class t_type>
734 {
736 for (uint01 i = 0; i < t_dims; i++)
737 orient_vector[i] = Angle<t_angle_type>(angle_type, ray[i]);
738 return orient_vector;
739 }
740 template<bool t_normalized, uint01 t_dims, class t_angle_type>
741 static constexpr Vector<t_dims, fltp08> Orientation(AngleType angle_type, const Vector<t_dims, Angle<t_angle_type>>& ray)
742 {
743 Vector<t_dims, fltp08> orient_vector;
744 for (uint01 i = 0; i < t_dims; i++)
745 orient_vector[i] = ray[i].as(angle_type);
746 return orient_vector;
747 }
748 /**
749
750 Normal to orientation.
751
752 Author: Tyler Parke
753
754 Date: 2017-11-13
755
756 Parameters:
757 normal - The normal.
758 yaw - (Optional) The yaw.
759
760 \returns A Vector&lt;3,Angle&gt;
761 **/
762 template<class t_angle_type, class t_type>
764 {
765 Angle<t_angle_type> pitch(RADIANS, (cast<fltp08>(asin((normal[Y] * sin(yaw) + normal[X] * cos(yaw))))));
767 if (::fabs(cos(pitch)) < 0.001)
768 roll = Angle<t_angle_type>(DEGREES, 0.0);
769 else if (::fabs(cos(yaw)) < 0.01)
770 roll = Angle<t_angle_type>(RADIANS, cast<fltp08>(-asin((cos(yaw) * sin(pitch) - normal[X]) / cos(pitch) * -sin(yaw))));
771 else
772 roll = Angle<t_angle_type>(RADIANS, cast<fltp08>(-asin((-normal[Y] + sin(yaw) * sin(pitch)) / (cos(pitch) * cos(yaw)))));
773 if (normal[Z] < 0)
774 roll = Angle<t_angle_type>(DEGREES, 180.0) - roll;
775 return Vector<3, Angle<t_angle_type>>(roll, pitch, yaw);
776 }
777
778 template<class t_angle_type>
780 {
781 fltp08 suggested_pitch_value = angle[PITCH].template as<DEGREES>();
782 fltp08 our_pitch_value = reference[PITCH].template as<DEGREES>();
783
784 fltp08 suggested_yaw_value = angle[YAW].template as<DEGREES>();
785 fltp08 our_yaw_value = reference[YAW].template as<DEGREES>();
786
787 fltp08 suggested_roll_value = angle[ROLL].template as<DEGREES>();
788 fltp08 our_roll_value = reference[ROLL].template as<DEGREES>();
789
790 if (suggested_pitch_value - our_pitch_value > 180)
791 our_pitch_value += 360;
792 else if (our_pitch_value - suggested_pitch_value > 180)
793 suggested_pitch_value += 360;
794
795 if (suggested_yaw_value - our_yaw_value > 180)
796 our_yaw_value += 360;
797 else if (our_yaw_value - suggested_yaw_value > 180)
798 suggested_yaw_value += 360;
799
800 if (suggested_roll_value - our_roll_value > 180)
801 our_roll_value += 360;
802 else if (our_roll_value - suggested_roll_value > 180)
803 suggested_roll_value += 360;
804
805 bool flip = ::abs(suggested_roll_value - our_roll_value) >= 90.0f && ::abs(suggested_yaw_value - our_yaw_value) >= 90.0f;
806 if (flip)
807 {
808 angle[ROLL] = Angle<fltp08>(DEGREES, angle[ROLL].template as<DEGREES>() - 180);
809 angle[YAW] = Angle<fltp08>(DEGREES, angle[YAW].template as<DEGREES>() - 180);
810 }
811 return angle;
812 }
813
814 public:
815 /**
816 Calculates the index sine.
817
818 Author: Tyler Parke
819
820 Date: 2017-11-13
821
822 \returns Null if it fails, else the calculated index sine.
823 **/
824 static const fltp08* CalcIndexSin();
825 };
826
827 template<uint01 t_dims, class t_angle_type>
832
833 template<uint01 t_dims, class t_angle_type>
838};
839
#define NDEVR_BASE_API
Definition DLLInfo.h:57
Logic for converting between Euler angles and basic rotations or normals.
Definition AngleFunctions.h:669
static Vector< 3, Angle< t_angle_type > > NormalToOrientation(const Vector< 3, t_type > &normal, const Angle< t_angle_type > &yaw=Angle< t_angle_type >(0))
Definition AngleFunctions.h:763
static Vector< 3, Angle< t_angle_type > > NormalizeOrientation(Vector< 3, Angle< t_angle_type > > angle, const Vector< 3, Angle< t_angle_type > > &reference)
Definition AngleFunctions.h:779
static Vector< 3, Angle< fltp08 > > QuaternionToOrientation(const Vector< 4, fltp08 > &quaternion)
Converts a quaternion to Euler angles (Roll, Pitch and Yaw)
static constexpr Angle< t_angle_type > Heading(const Vector< t_dims, t_type > ray)
Definition AngleFunctions.h:727
static constexpr Vector< t_dims, fltp08 > Orientation(AngleType angle_type, const Vector< t_dims, Angle< t_angle_type > > &ray)
Definition AngleFunctions.h:741
static Angle< t_angle_type > Rotation(const Vector< t_dims, t_type > &left, const Vector< t_dims, t_type > &middle, const Vector< t_dims, t_type > &right)
Definition AngleFunctions.h:694
static Angle< t_angle_type > Inclination(const Angle< t_angle_type > &roll, const Angle< t_angle_type > &pitch)
Definition AngleFunctions.h:714
static const fltp08 * CalcIndexSin()
static constexpr Vector< t_dims, Angle< t_angle_type > > Orientation(AngleType angle_type, const Vector< t_dims, t_type > &ray)
Definition AngleFunctions.h:733
static constexpr Angle< t_angle_type > Inclination(const Vector< t_dims, t_type > ray)
Definition AngleFunctions.h:720
The primary angle storage class for this API. Stores an angle in an optimized format.
Definition StringStream.h:540
A fixed-size array with better performance compared to dynamic containers.
Definition Vector.hpp:60
constexpr t_type magnitudeSquared() const
Definition Vector.hpp:426
Definition ACIColor.h:37
std::enable_if<!ObjectInfo< t_type >::Float, fltp08 >::type tan(const Angle< t_type > &angle)
Performs optimized tangent operation on the given angle using pre-computed lookup table for optimal s...
Definition AngleFunctions.h:156
t_type dot(const Vector< t_dims, t_type > &v1, const Vector< t_dims, t_type > &v2)
Definition VectorFunctions.hpp:1030
@ ROLL
Definition Angle.h:45
@ YAW
Definition Angle.h:47
@ PITCH
Definition Angle.h:46
constexpr Vector< t_dims, Angle< t_angle_type > > quantize(const Vector< t_dims, Angle< t_angle_type > > &value, Angle< t_angle_type > d=Angle< t_angle_type >(DEGREES, 1.0))
Definition AngleFunctions.h:828
@ angle_b
Definition Triangle.hpp:56
@ angle_a
Definition Triangle.hpp:55
uint8_t uint01
-Defines an alias representing a 1 byte, unsigned integer -Can represent exact integer values 0 throu...
Definition BaseValues.hpp:80
AngleType
The possible units that can be used by the angle class. These are returned and used for real world an...
Definition Angle.h:56
@ RADIANS
Definition Angle.h:57
@ DEGREES
Definition Angle.h:58
@ INTERNAL_ANGLE
Definition Angle.h:59
std::enable_if<!ObjectInfo< t_type >::Float, fltp08 >::type cos(const Angle< t_type > &angle)
Performs optimized cosine operation on the given angle using pre-computed lookup table for optimal sp...
Definition AngleFunctions.h:124
constexpr Vector< t_dims, Angle< t_new_type > > ToTypeAngle(const Vector< t_dims, Angle< t_angle_type > > &old)
Converts a Vector of one angle to a different container type.
Definition AngleFunctions.h:657
t_type sqrt(const t_type &value)
Definition VectorFunctions.hpp:1225
constexpr t_to cast(const Angle< t_from > &value)
Definition Angle.h:375
uint16_t uint02
-Defines an alias representing a 2 byte, unsigned integer -Can represent exact integer values 0 throu...
Definition BaseValues.hpp:88
constexpr Angle< t_angle_type > abs(const Angle< t_angle_type > &value)
Changes an input with a negative sign, to a positive sign.
Definition AngleFunctions.h:645
std::enable_if<!ObjectInfo< t_type >::Float, fltp08 >::type sin(const Angle< t_type > &angle)
Performs optimized sine operation on the given angle using pre-computed lookup table for optimal spee...
Definition AngleFunctions.h:79
const fltp08 *const s_index_sin
constexpr Vector< t_dims, Angle< t_angle_type > > operator%(const Vector< t_dims, Angle< t_angle_type > > &vec_a, const Vector< t_dims, Angle< t_angle_type > > &vec_b)
Definition AngleFunctions.h:617
@ Y
Definition BaseValues.hpp:169
@ X
Definition BaseValues.hpp:167
@ Z
Definition BaseValues.hpp:171
double fltp08
Defines an alias representing an 8 byte floating-point number.
Definition BaseValues.hpp:149