Hypatia
/home/dagostinelli/projects/hypatia/hypatia.h
Go to the documentation of this file.
1 /* SPDX-License-Identifier: MIT */
2 
3 #ifndef _INC_HYPATIA
4 #define _INC_HYPATIA
5 
6 #define HYPATIA_VERSION "2.0.0"
7 
8 #ifndef HYPAPI
9 # ifdef HYP_STATIC
10 # define HYPAPI static
11 # else
12 # define HYPAPI extern
13 # endif
14 #endif
15 
16 #ifndef HYP_DEF
17 # define HYPDEF HYPAPI
18 #endif
19 
20 #ifndef HYP_INLINE
21 # ifdef _MSC_VER
22 # define HYP_INLINE __inline
23 # else
24 # define HYP_INLINE __inline__
25 # endif
26 #endif
27 
28 #ifndef HYP_FLOAT
29 # ifdef HYPATIA_SINGLE_PRECISION_FLOATS
30 # define HYP_FLOAT float
31 # else
32 # define HYP_FLOAT double
33 # endif
34 #endif
35 
36 #ifndef HYP_NO_C_MATH
37 # include <math.h> /* sin, cos, acos, fmod */
38 #endif
39 
40 #ifndef HYP_NO_STDIO
41 # include <stdio.h> /* printf */
42 #endif
43 
50 #ifndef HYP_PI
51 # define HYP_PI 3.1415926535897932384626433832795028841971693993751058209749445923078164062862089986280348253421170679f
52 #endif
54 #ifndef HYP_TAU
55 # define HYP_TAU 6.2831853071795864769252867665590057683943387987502116419498891846156328125724179972560696506842341359f
56 #endif
58 #ifndef HYP_PI_HALF
59 # define HYP_PI_HALF 1.5707963267948966f
60 #endif
62 #ifndef HYP_PI_SQUARED
63 # define HYP_PI_SQUARED 9.8696044010893586f
64 #endif
66 #ifndef HYP_E
67 # define HYP_E 2.71828182845904523536028747135266249775724709369995f
68 #endif
70 #ifndef HYP_RAD_PER_DEG
71 # define HYP_RAD_PER_DEG 0.0174532925199432957692369076848861f
72 #endif
74 #ifndef HYP_DEG_PER_RAD
75 # define HYP_DEG_PER_RAD 57.2957795130823208767981548141052f
76 #endif
78 #ifndef HYP_PIOVER180
79 # define HYP_PIOVER180 HYP_RAD_PER_DEG
80 #endif
82 #ifndef HYP_PIUNDER180
83 # define HYP_PIUNDER180 HYP_DEG_PER_RAD
84 #endif
88 #ifndef HYP_EPSILON
89 # ifdef HYPATIA_SINGLE_PRECISION_FLOATS
90 # define HYP_EPSILON 1E-5f
91 # else
92 # define HYP_EPSILON 1E-5
93 # endif
94 #endif
98 #ifndef HYP_MEMSET
99 # include <memory.h> /* memset */
100 # define HYP_MEMSET(a, b, c) memset(a, b, c)
101 #endif
102 
105 {
106  return (a < b) ? a : b;
107 }
108 
111 {
112  return (a > b) ? b : a;
113 }
114 
117 {
118  HYP_FLOAT f = *a; *a = *b; *b = f;
119 }
120 
122 #ifndef HYP_RANDOM_FLOAT
123 # include <stdlib.h> /* RAND_MAX, rand */
124 # define HYP_RANDOM_FLOAT (((HYP_FLOAT)rand() - (HYP_FLOAT)rand()) / (HYP_FLOAT)RAND_MAX)
125 #endif
126 
128 #ifndef HYP_DEG_TO_RAD
129 # define HYP_DEG_TO_RAD(angle) ((angle) * HYP_RAD_PER_DEG)
130 #endif
131 
133 #ifndef HYP_RAD_TO_DEG
134 # define HYP_RAD_TO_DEG(radians) ((radians) * HYP_DEG_PER_RAD)
135 #endif
136 
139 {
140  return number * number;
141 }
142 
144 #ifndef HYP_SQRT
145 # define HYP_SQRT(number) ((HYP_FLOAT)sqrt(number))
146 #endif
147 
150 {
151  return (value < 0.0f) ? -value : value;
152 }
153 
156 {
157  return (HYP_FLOAT)fmod(start + (value - start), (limit - start));
158 }
159 
162 {
163  return ((value < start) ? start : (value > limit) ? limit : value);
164 }
165 
166 #ifndef DOXYGEN_SHOULD_SKIP_THIS
167 
168 /* forward declarations */
169 struct vector2;
170 struct vector3;
171 struct vector4;
172 struct matrix2;
173 struct matrix3;
174 struct matrix4;
175 struct quaternion;
176 
177 #define HYP_REF_VECTOR2_ZERO 0
178 #define HYP_REF_VECTOR2_UNIT_X 1
179 #define HYP_REF_VECTOR2_UNIT_Y 2
180 #define HYP_REF_VECTOR2_UNIT_X_NEGATIVE 3
181 #define HYP_REF_VECTOR2_UNIT_Y_NEGATIVE 4
182 #define HYP_REF_VECTOR2_ONE 5
183 
184 HYPAPI const struct vector2 *vector2_get_reference_vector2(int id);
185 
186 #define HYP_REF_VECTOR3_ZERO 0
187 #define HYP_REF_VECTOR3_UNIT_X 1
188 #define HYP_REF_VECTOR3_UNIT_Y 2
189 #define HYP_REF_VECTOR3_UNIT_Z 3
190 #define HYP_REF_VECTOR3_UNIT_X_NEGATIVE 4
191 #define HYP_REF_VECTOR3_UNIT_Y_NEGATIVE 5
192 #define HYP_REF_VECTOR3_UNIT_Z_NEGATIVE 6
193 #define HYP_REF_VECTOR3_ONE 7
194 
195 HYPAPI const struct vector3 *vector3_get_reference_vector3(int id);
196 
197 #define HYP_REF_VECTOR4_ZERO 0
198 #define HYP_REF_VECTOR4_UNIT_X 1
199 #define HYP_REF_VECTOR4_UNIT_Y 2
200 #define HYP_REF_VECTOR4_UNIT_Z 3
201 #define HYP_REF_VECTOR4_UNIT_X_NEGATIVE 4
202 #define HYP_REF_VECTOR4_UNIT_Y_NEGATIVE 5
203 #define HYP_REF_VECTOR4_UNIT_Z_NEGATIVE 6
204 #define HYP_REF_VECTOR4_ONE 7
205 
206 HYPAPI const struct vector4 *vector4_get_reference_vector4(int id);
207 
208 #endif /* DOXYGEN_SHOULD_SKIP_THIS */
209 
212 #define HYP_VECTOR3_ZERO vector3_get_reference_vector3(HYP_REF_VECTOR3_ZERO)
215 #define HYP_VECTOR3_UNIT_X vector3_get_reference_vector3(HYP_REF_VECTOR3_UNIT_X)
218 #define HYP_VECTOR3_UNIT_Y vector3_get_reference_vector3(HYP_REF_VECTOR3_UNIT_Y)
221 #define HYP_VECTOR3_UNIT_Z vector3_get_reference_vector3(HYP_REF_VECTOR3_UNIT_Z)
224 #define HYP_VECTOR3_UNIT_X_NEGATIVE vector3_get_reference_vector3(HYP_REF_VECTOR3_UNIT_X_NEGATIVE)
227 #define HYP_VECTOR3_UNIT_Y_NEGATIVE vector3_get_reference_vector3(HYP_REF_VECTOR3_UNIT_Y_NEGATIVE)
230 #define HYP_VECTOR3_UNIT_Z_NEGATIVE vector3_get_reference_vector3(HYP_REF_VECTOR3_UNIT_Z_NEGATIVE)
233 #define HYP_VECTOR3_ONE vector3_get_reference_vector3(HYP_REF_VECTOR3_ONE)
234 /* @} */
235 
236 
239 #define HYP_VECTOR2_ZERO vector2_get_reference_vector2(HYP_REF_VECTOR2_ZERO)
242 #define HYP_VECTOR2_UNIT_X vector2_get_reference_vector2(HYP_REF_VECTOR2_UNIT_X)
245 #define HYP_VECTOR2_UNIT_Y vector2_get_reference_vector2(HYP_REF_VECTOR2_UNIT_Y)
248 #define HYP_VECTOR2_UNIT_X_NEGATIVE vector2_get_reference_vector2(HYP_REF_VECTOR2_UNIT_X_NEGATIVE)
251 #define HYP_VECTOR2_UNIT_Y_NEGATIVE vector2_get_reference_vector2(HYP_REF_VECTOR2_UNIT_Y_NEGATIVE)
254 #define HYP_VECTOR2_ONE vector2_get_reference_vector2(HYP_REF_VECTOR2_ONE)
255 /* @} */
256 
257 
258 HYPAPI short scalar_equalsf(const HYP_FLOAT f1, const HYP_FLOAT f2);
259 HYPAPI short scalar_equals_epsilonf(const HYP_FLOAT f1, const HYP_FLOAT f2, const HYP_FLOAT epsilon);
260 
261 #define scalar_equals scalar_equalsf
262 
263 
269 #define HYP_SIN(x) ((HYP_FLOAT)sin(x))
270 #define HYP_COS(x) ((HYP_FLOAT)cos(x))
271 #define HYP_TAN(x) ((HYP_FLOAT)tan(x))
272 #define HYP_ASIN(x) ((HYP_FLOAT)asin(x))
273 #define HYP_ACOS(x) ((HYP_FLOAT)acos(x))
274 #define HYP_ATAN2(y, x) ((HYP_FLOAT)atan2(y, x))
275 #define HYP_COT(a) (1.0f / HYP_TAN(a))
276 
277 /* @} */
278 
279 
287 HYPAPI struct matrix2 *_matrix2_set_random(struct matrix2 *self);
288 
291 HYPAPI struct matrix3 *_matrix3_set_random(struct matrix3 *self);
292 
293 HYPAPI void _matrix4_print_with_columnrow_indexer(struct matrix4 *self);
294 HYPAPI void _matrix4_print_with_rowcolumn_indexer(struct matrix4 *self);
295 HYPAPI struct matrix4 *_matrix4_set_random(struct matrix4 *self);
296 
297 HYPAPI void _quaternion_print(const struct quaternion *self);
298 HYPAPI struct quaternion *_quaternion_set_random(struct quaternion *self);
299 
300 HYPAPI void _vector3_print(const struct vector3 *self);
301 HYPAPI struct vector3 *_vector3_set_random(struct vector3 *self);
302 
303 HYPAPI void _vector2_print(const struct vector2 *self);
304 HYPAPI struct vector2 *_vector2_set_random(struct vector2 *self);
305 
306 HYPAPI void _vector4_print(const struct vector4 *self);
307 HYPAPI struct vector4 *_vector4_set_random(struct vector4 *self);
308 
309 /* @} */
310 
311 struct vector2 {
312  union {
314  struct {
316  };
317  };
318 };
319 
320 
321 HYPAPI int vector2_equals(const struct vector2 *self, const struct vector2 *vT);
322 
323 HYPAPI struct vector2 *vector2_zero(struct vector2 *self);
324 HYPAPI struct vector2 *vector2_set(struct vector2 *self, const struct vector2 *vT);
325 HYPAPI struct vector2 *vector2_setf2(struct vector2 *self, HYP_FLOAT xT, HYP_FLOAT yT);
326 HYPAPI struct vector2 *vector2_negate(struct vector2 *self);
327 HYPAPI struct vector2 *vector2_add(struct vector2 *self, const struct vector2 *vT);
328 HYPAPI struct vector2 *vector2_addf(struct vector2 *self, HYP_FLOAT fT);
329 HYPAPI struct vector2 *vector2_subtract(struct vector2 *self, const struct vector2 *vT);
330 HYPAPI struct vector2 *vector2_subtractf(struct vector2 *self, HYP_FLOAT fT);
331 HYPAPI struct vector2 *vector2_multiply(struct vector2 *self, const struct vector2 *vT);
332 HYPAPI struct vector2 *vector2_multiplyf(struct vector2 *self, HYP_FLOAT fT);
333 HYPAPI struct vector2 *vector2_multiplym2(struct vector2 *self, const struct matrix2 *mT);
334 HYPAPI struct vector2 *vector2_multiplym3(struct vector2 *self, const struct matrix3 *mT);
335 HYPAPI struct vector2 *vector2_divide(struct vector2 *self, const struct vector2 *vT);
336 HYPAPI struct vector2 *vector2_dividef(struct vector2 *self, HYP_FLOAT fT);
337 
338 HYPAPI struct vector2 *vector2_normalize(struct vector2 *self);
339 HYPAPI HYP_FLOAT vector2_magnitude(const struct vector2 *self);
340 HYPAPI HYP_FLOAT vector2_distance(const struct vector2 *v1, const struct vector2 *v2);
341 
342 HYPAPI HYP_FLOAT vector2_dot_product(const struct vector2 *self, const struct vector2 *vT);
343 HYPAPI struct vector2 *vector2_cross_product(struct vector2 *vR, const struct vector2 *vT1, const struct vector2 *vT2);
344 
345 HYPAPI HYP_FLOAT vector2_angle_between(const struct vector2 *self, const struct vector2 *vT);
346 HYPAPI struct vector2 *vector2_find_normal_axis_between(struct vector2 *vR, const struct vector2 *vT1, const struct vector2 *vT2);
347 
348 /* the length is the same as "magnitude" */
349 #define vector2_length(v) vector2_magnitude(v)
350 
351 #ifndef DOXYGEN_SHOULD_SKIP_THIS
352 
353 /* BETA aliases */
354 #define vec2 struct vector2
355 
356 #endif /* DOXYGEN_SHOULD_SKIP_THIS */
357 
358 
359 struct vector3 {
360  union {
362  struct {
364  };
365  struct {
367  };
368  };
369 };
370 
371 
372 HYPAPI int vector3_equals(const struct vector3 *self, const struct vector3 *vT);
373 
374 HYPAPI struct vector3 *vector3_zero(struct vector3 *self);
375 HYPAPI struct vector3 *vector3_set(struct vector3 *self, const struct vector3 *vT);
376 HYPAPI struct vector3 *vector3_setf3(struct vector3 *self, HYP_FLOAT xT, HYP_FLOAT yT, HYP_FLOAT zT);
377 HYPAPI struct vector3 *vector3_negate(struct vector3 *self);
378 HYPAPI struct vector3 *vector3_add(struct vector3 *self, const struct vector3 *vT);
379 HYPAPI struct vector3 *vector3_addf(struct vector3 *self, HYP_FLOAT fT);
380 HYPAPI struct vector3 *vector3_subtract(struct vector3 *self, const struct vector3 *vT);
381 HYPAPI struct vector3 *vector3_subtractf(struct vector3 *self, HYP_FLOAT fT);
382 HYPAPI struct vector3 *vector3_multiply(struct vector3 *self, const struct vector3 *vT);
383 HYPAPI struct vector3 *vector3_multiplyf(struct vector3 *self, HYP_FLOAT fT);
384 HYPAPI struct vector3 *vector3_multiplym4(struct vector3 *self, const struct matrix4 *mT);
385 HYPAPI struct vector3 *vector3_divide(struct vector3 *self, const struct vector3 *vT);
386 HYPAPI struct vector3 *vector3_dividef(struct vector3 *self, HYP_FLOAT fT);
387 
388 HYPAPI struct vector3 *vector3_normalize(struct vector3 *self);
389 HYPAPI HYP_FLOAT vector3_magnitude(const struct vector3 *self);
390 HYPAPI HYP_FLOAT vector3_distance(const struct vector3 *v1, const struct vector3 *v2);
391 
392 HYPAPI HYP_FLOAT vector3_dot_product(const struct vector3 *self, const struct vector3 *vT);
393 HYPAPI struct vector3 *vector3_cross_product(struct vector3 *vR, const struct vector3 *vT1, const struct vector3 *vT2);
394 
395 HYPAPI HYP_FLOAT vector3_angle_between(const struct vector3 *self, const struct vector3 *vT);
396 HYPAPI struct vector3 *vector3_find_normal_axis_between(struct vector3 *vR, const struct vector3 *vT1, const struct vector3 *vT2);
397 
398 HYPAPI struct vector3 *vector3_rotate_by_quaternion(struct vector3 *self, const struct quaternion *qT);
399 HYPAPI struct vector3 *vector3_reflect_by_quaternion(struct vector3 *self, const struct quaternion *qT);
400 
401 /*the length is the same as "magnitude" */
402 #define vector3_length(v) vector3_magnitude(v)
403 
404 #ifndef DOXYGEN_SHOULD_SKIP_THIS
405 
406 /*BETA aliases */
407 #define vec3 struct vector3
408 
409 #endif /*DOXYGEN_SHOULD_SKIP_THIS */
410 
411 
412 struct vector4 {
413  union {
415  struct {
417  };
418  };
419 };
420 
421 
422 HYPAPI int vector4_equals(const struct vector4 *self, const struct vector4 *vT);
423 
424 HYPAPI struct vector4 *vector4_zero(struct vector4 *self);
425 HYPAPI struct vector4 *vector4_set(struct vector4 *self, const struct vector4 *vT);
426 HYPAPI struct vector4 *vector4_setf4(struct vector4 *self, HYP_FLOAT xT, HYP_FLOAT yT, HYP_FLOAT zT, HYP_FLOAT wT);
427 HYPAPI struct vector4 *vector4_negate(struct vector4 *self);
428 HYPAPI struct vector4 *vector4_add(struct vector4 *self, const struct vector4 *vT);
429 HYPAPI struct vector4 *vector4_addf(struct vector4 *self, HYP_FLOAT fT);
430 HYPAPI struct vector4 *vector4_subtract(struct vector4 *self, const struct vector4 *vT);
431 HYPAPI struct vector4 *vector4_subtractf(struct vector4 *self, HYP_FLOAT fT);
432 HYPAPI struct vector4 *vector4_multiply(struct vector4 *self, const struct vector4 *vT);
433 HYPAPI struct vector4 *vector4_multiplyf(struct vector4 *self, HYP_FLOAT fT);
434 HYPAPI struct vector4 *vector4_divide(struct vector4 *self, const struct vector4 *vT);
435 HYPAPI struct vector4 *vector4_dividef(struct vector4 *self, HYP_FLOAT fT);
436 
437 HYPAPI struct vector4 *vector4_normalize(struct vector4 *self);
438 HYPAPI HYP_FLOAT vector4_magnitude(const struct vector4 *self);
439 HYPAPI HYP_FLOAT vector4_distance(const struct vector4 *v1, const struct vector4 *v2);
440 
441 HYPAPI HYP_FLOAT vector4_dot_product(const struct vector4 *self, const struct vector4 *vT);
442 HYPAPI struct vector4 *vector4_cross_product(struct vector4 *vR, const struct vector4 *vT1, const struct vector4 *vT2);
443 
444 /* the length is the same as "magnitude" */
445 #define vector4_length(v) vector4_magnitude(v)
446 
447 #ifndef DOXYGEN_SHOULD_SKIP_THIS
448 
449 /* BETA aliases */
450 #define vec4 struct vector4
451 
452 #endif /* DOXYGEN_SHOULD_SKIP_THIS */
453 
454 
455 struct matrix2 {
456  union {
457  HYP_FLOAT m[4]; /* row-major numbering */
458  struct {
459  /* reference the matrix [row][column] */
460  HYP_FLOAT m22[2][2];
461  };
462  struct {
463  /* indexed (column-major numbering) */
466  };
467  struct {
468  /* col-row */
471  };
472  struct {
473  /* row-col */
476  };
477  };
478 };
479 
480 
481 HYPAPI int matrix2_equals(const struct matrix2 *self, const struct matrix2 *mT);
482 
483 HYPAPI struct matrix2 *matrix2_zero(struct matrix2 *self);
484 HYPAPI struct matrix2 *matrix2_identity(struct matrix2 *self);
485 HYPAPI struct matrix2 *matrix2_set(struct matrix2 *self, const struct matrix2 *mT);
486 HYPAPI struct matrix2 *matrix2_add(struct matrix2 *self, const struct matrix2 *mT);
487 HYPAPI struct matrix2 *matrix2_subtract(struct matrix2 *self, const struct matrix2 *mT);
488 
489 HYPAPI struct matrix2 *matrix2_multiply(struct matrix2 *self, const struct matrix2 *mT);
490 HYPAPI struct matrix2 *matrix2_multiplyf(struct matrix2 *self, HYP_FLOAT scalar);
491 HYPAPI struct vector2 *matrix2_multiplyv2(const struct matrix2 *self, const struct vector2 *vT, struct vector2 *vR);
492 
493 HYPAPI struct matrix2 *matrix2_transpose(struct matrix2 *self);
494 HYPAPI HYP_FLOAT matrix2_determinant(const struct matrix2 *self);
495 HYPAPI struct matrix2 *matrix2_invert(struct matrix2 *self);
496 HYPAPI struct matrix2 *matrix2_inverse(const struct matrix2 *self, struct matrix2 *mR);
497 
498 HYPAPI struct matrix2 *matrix2_make_transformation_scalingv2(struct matrix2 *self, const struct vector2 *scale);
500 
501 HYPAPI struct matrix2 *matrix2_rotate(struct matrix2 *self, HYP_FLOAT angle);
502 HYPAPI struct matrix2 *matrix2_scalev2(struct matrix2 *self, const struct vector2 *scale);
503 
504 HYPAPI struct matrix2 *_matrix2_transpose_rowcolumn(struct matrix2 *self);
505 HYPAPI struct matrix2 *_matrix2_transpose_columnrow(struct matrix2 *self);
506 
507 
508 #ifndef DOXYGEN_SHOULD_SKIP_THIS
509 
510 /* BETA aliases */
511 #define mat2 struct matrix2
512 
513 #define mat2_equals matrix2_equals
514 #define mat2_zero matrix2_zero
515 #define mat2_identity matrix2_identity
516 #define mat2_set matrix2_setm2
517 #define mat2_add matrix2_add
518 #define mat2_sub matrix2_subtract
519 #define mat2_mul matrix2_multiply
520 #define mat2_transpose matrix2_transpose
521 
522 #define mat2_rotate matrix2_rotate
523 #define mat2_scalev2 matrix2_scalev2
524 
525 
526 /*#define m2 struct matrix2*/
527 
528 #define m2_equals matrix2_equals
529 #define m2_zero matrix2_zero
530 #define m2_identity matrix2_identity
531 #define m2_set matrix2_set
532 #define m2_add matrix2_add
533 #define m2_sub matrix2_subtract
534 #define m2_mul matrix2_multiply
535 #define m2_transpose matrix2_transpose
536 
537 #define m2_rotate matrix2_rotate
538 #define m2_scalev2 matrix2_scalev2
539 
540 #endif /* DOXYGEN_SHOULD_SKIP_THIS */
541 
542 
543 struct matrix3 {
544  union {
545  HYP_FLOAT m[9]; /* row-major numbering */
546  struct {
547  /* reference the matrix [row][column] */
548  HYP_FLOAT m33[3][3];
549  };
550  struct {
551  /* indexed (column-major numbering) */
555  };
556  struct {
557  /* col-row */
561  };
562  struct {
563  /* row-col */
567  };
568  };
569 };
570 
571 
572 HYPAPI int matrix3_equals(const struct matrix3 *self, const struct matrix3 *mT);
573 
574 HYPAPI struct matrix3 *matrix3_zero(struct matrix3 *self);
575 HYPAPI struct matrix3 *matrix3_identity(struct matrix3 *self);
576 HYPAPI struct matrix3 *matrix3_set(struct matrix3 *self, const struct matrix3 *mT);
577 HYPAPI struct matrix3 *matrix3_add(struct matrix3 *self, const struct matrix3 *mT);
578 HYPAPI struct matrix3 *matrix3_subtract(struct matrix3 *self, const struct matrix3 *mT);
579 
580 HYPAPI struct matrix3 *matrix3_multiply(struct matrix3 *self, const struct matrix3 *mT);
581 HYPAPI struct matrix3 *matrix3_multiplyf(struct matrix3 *self, HYP_FLOAT scalar);
582 HYPAPI struct vector2 *matrix3_multiplyv2(const struct matrix3 *self, const struct vector2 *vT, struct vector2 *vR);
583 
584 HYPAPI struct matrix3 *matrix3_transpose(struct matrix3 *self);
585 HYPAPI HYP_FLOAT matrix3_determinant(const struct matrix3 *self);
586 HYPAPI struct matrix3 *matrix3_invert(struct matrix3 *self);
587 HYPAPI struct matrix3 *matrix3_inverse(const struct matrix3 *self, struct matrix3 *mR);
588 
589 HYPAPI struct matrix3 *matrix3_make_transformation_translationv2(struct matrix3 *self, const struct vector2 *translation);
590 HYPAPI struct matrix3 *matrix3_make_transformation_scalingv2(struct matrix3 *self, const struct vector2 *scale);
592 
593 HYPAPI struct matrix3 *matrix3_translatev2(struct matrix3 *self, const struct vector2 *translation);
594 HYPAPI struct matrix3 *matrix3_rotate(struct matrix3 *self, HYP_FLOAT angle);
595 HYPAPI struct matrix3 *matrix3_scalev2(struct matrix3 *self, const struct vector2 *scale);
596 
597 HYPAPI struct matrix3 *_matrix3_transpose_rowcolumn(struct matrix3 *self);
598 HYPAPI struct matrix3 *_matrix3_transpose_columnrow(struct matrix3 *self);
599 
600 
601 #ifndef DOXYGEN_SHOULD_SKIP_THIS
602 
603 /* BETA aliases */
604 #define mat3 struct matrix3
605 
606 #define mat3_equals matrix3_equals
607 #define mat3_zero matrix3_zero
608 #define mat3_identity matrix3_identity
609 #define mat3_set matrix3_setm3
610 #define mat3_add matrix3_add
611 #define mat3_sub matrix3_subtract
612 #define mat3_mul matrix3_multiply
613 #define mat3_transpose matrix3_transpose
614 
615 #define mat3_translatev2 matrix3_translatev2
616 #define mat3_rotate matrix3_rotate
617 #define mat3_scalev2 matrix3_scalev2
618 
619 
620 #define m3 struct matrix3
621 
622 #define m3_equals matrix3_equals
623 #define m3_zero matrix3_zero
624 #define m3_identity matrix3_identity
625 #define m3_set matrix3_set
626 #define m3_add matrix3_add
627 #define m3_sub matrix3_subtract
628 #define m3_mul matrix3_multiply
629 #define m3_transpose matrix3_transpose
630 
631 #define m3_translatev2 matrix3_translatev2
632 #define m3_rotate matrix3_rotate
633 #define m3_scalev2 matrix3_scalev2
634 
635 #endif /* DOXYGEN_SHOULD_SKIP_THIS */
636 
637 
638 struct matrix4 {
639  union {
640  HYP_FLOAT m[16]; /* row-major numbering */
641  struct {
642  /* reference the matrix [row][column] */
643  HYP_FLOAT m44[4][4];
644  };
645  struct {
646  /* indexed (column-major numbering) */
651  };
652  struct {
653  /* col-row */
658  };
659  struct {
660  /* row-col */
665  };
666  };
667 };
668 
669 HYPAPI int matrix4_equals(const struct matrix4 *self, const struct matrix4 *mT);
670 
671 HYPAPI struct matrix4 *matrix4_zero(struct matrix4 *self);
672 HYPAPI struct matrix4 *matrix4_identity(struct matrix4 *self);
673 HYPAPI struct matrix4 *matrix4_set(struct matrix4 *self, const struct matrix4 *mT);
674 HYPAPI struct matrix4 *matrix4_add(struct matrix4 *self, const struct matrix4 *mT);
675 HYPAPI struct matrix4 *matrix4_subtract(struct matrix4 *self, const struct matrix4 *mT);
676 
677 HYPAPI struct matrix4 *matrix4_multiply(struct matrix4 *self, const struct matrix4 *mT);
678 HYPAPI struct matrix4 *matrix4_multiplyf(struct matrix4 *self, HYP_FLOAT scalar);
679 HYPAPI struct vector4 *matrix4_multiplyv4(const struct matrix4 *self, const struct vector4 *vT, struct vector4 *vR);
680 HYPAPI struct vector3 *matrix4_multiplyv3(const struct matrix4 *self, const struct vector3 *vT, struct vector3 *vR);
681 HYPAPI struct vector2 *matrix4_multiplyv2(const struct matrix4 *self, const struct vector2 *vT, struct vector2 *vR);
682 
683 HYPAPI struct matrix4 *matrix4_transpose(struct matrix4 *self);
684 HYPAPI HYP_FLOAT matrix4_determinant(const struct matrix4 *self);
685 HYPAPI struct matrix4 *matrix4_invert(struct matrix4 *self);
686 HYPAPI struct matrix4 *matrix4_inverse(const struct matrix4 *self, struct matrix4 *mR);
687 
688 HYPAPI struct matrix4 *matrix4_make_transformation_translationv3(struct matrix4 *self, const struct vector3 *translation);
689 HYPAPI struct matrix4 *matrix4_make_transformation_scalingv3(struct matrix4 *self, const struct vector3 *scale);
690 HYPAPI struct matrix4 *matrix4_make_transformation_rotationq(struct matrix4 *self, const struct quaternion *qT);
694 
695 HYPAPI struct matrix4 *matrix4_translatev3(struct matrix4 *self, const struct vector3 *translation);
696 HYPAPI struct matrix4 *matrix4_rotatev3(struct matrix4 *self, const struct vector3 *axis, HYP_FLOAT angle);
697 HYPAPI struct matrix4 *matrix4_scalev3(struct matrix4 *self, const struct vector3 *scale);
698 
699 HYPAPI struct matrix4 *_matrix4_transpose_rowcolumn(struct matrix4 *self);
700 HYPAPI struct matrix4 *_matrix4_transpose_columnrow(struct matrix4 *self);
701 
702 
703 #ifndef DOXYGEN_SHOULD_SKIP_THIS
704 
705 /* BETA aliases */
706 #define mat4 struct matrix4
707 
708 #define mat4_equals matrix4_equals
709 #define mat4_zero matrix4_zero
710 #define mat4_identity matrix4_identity
711 #define mat4_set matrix4_setm4
712 #define mat4_add matrix4_add
713 #define mat4_sub matrix4_subtract
714 #define mat4_mul matrix4_multiply
715 #define mat4_transpose matrix4_transpose
716 
717 #define mat4_translatev3 matrix3_translatev3
718 #define mat4_rotatev3 matrix3_rotatev3
719 #define mat4_scalev3 matrix3_scalev3
720 
721 
722 #define m4 struct matrix4
723 
724 #define m4_equals matrix4_equals
725 #define m4_zero matrix4_zero
726 #define m4_identity matrix4_identity
727 #define m4_set matrix4_set
728 #define m4_add matrix4_add
729 #define m4_sub matrix4_subtract
730 #define m4_mul matrix4_multiply
731 #define m4_transpose matrix4_transpose
732 
733 #define m4_translatev3 matrix3_translatev3
734 #define m4_rotatev3 matrix3_rotatev3
735 #define m4_scalev3 matrix3_scalev3
736 
737 #endif /* DOXYGEN_SHOULD_SKIP_THIS */
738 
739 
740 struct quaternion {
741  union {
743  struct {
745  };
746  struct {
748  };
749  };
750 };
751 
752 
753 HYPAPI int quaternion_equals(const struct quaternion *self, const struct quaternion *vT);
754 
755 HYPAPI struct quaternion *quaternion_identity(struct quaternion *self);
757 HYPAPI struct quaternion *quaternion_set(struct quaternion *self, const struct quaternion *qT);
758 HYPAPI struct quaternion *quaternion_add(struct quaternion *self, const struct quaternion *qT);
759 HYPAPI struct quaternion *quaternion_multiply(struct quaternion *self, const struct quaternion *qT);
760 HYPAPI struct quaternion *quaternion_multiplyv3(struct quaternion *self, const struct vector3 *vT);
761 HYPAPI struct quaternion *quaternion_multiplyf(struct quaternion *self, HYP_FLOAT f);
762 HYPAPI struct quaternion *quaternion_subtract(struct quaternion *self, const struct quaternion *qT);
763 HYPAPI struct quaternion *quaternion_negate(struct quaternion *self);
764 HYPAPI struct quaternion *quaternion_conjugate(struct quaternion *self);
765 HYPAPI struct quaternion *quaternion_inverse(struct quaternion *self);
766 
767 HYPAPI short quaternion_is_unit(struct quaternion *self);
768 HYPAPI short quaternion_is_pure(struct quaternion *self);
769 HYPAPI HYP_FLOAT quaternion_norm(const struct quaternion *self);
770 HYPAPI HYP_FLOAT quaternion_magnitude(const struct quaternion *self);
771 HYPAPI struct quaternion *quaternion_normalize(struct quaternion *self);
772 HYPAPI HYP_FLOAT quaternion_dot_product(const struct quaternion *self, const struct quaternion *qT);
773 
774 HYPAPI struct quaternion *quaternion_lerp(const struct quaternion *start, const struct quaternion *end, HYP_FLOAT percent, struct quaternion *qR);
775 HYPAPI struct quaternion *quaternion_nlerp(const struct quaternion *start, const struct quaternion *end, HYP_FLOAT percent, struct quaternion *qR);
776 HYPAPI struct quaternion *quaternion_slerp(const struct quaternion *start, const struct quaternion *end, HYP_FLOAT percent, struct quaternion *qR);
777 
778 HYPAPI void quaternion_get_axis_anglev3(const struct quaternion *self, struct vector3 *vR, HYP_FLOAT *angle);
779 
780 HYPAPI struct quaternion *quaternion_set_from_axis_anglev3(struct quaternion *self, const struct vector3 *axis, HYP_FLOAT angle);
782 
784 HYPAPI void quaternion_get_euler_anglesf3(const struct quaternion *self, HYP_FLOAT *ax, HYP_FLOAT *ay, HYP_FLOAT *az);
785 
786 HYPAPI struct quaternion *quaternion_get_rotation_tov3(const struct vector3 *from, const struct vector3 *to, struct quaternion *qR);
787 
788 #ifndef DOXYGEN_SHOULD_SKIP_THIS
789 
790 /* BETA aliases */
791 #define quat struct quaternion
792 
793 #define quat_equals quaternion_equals
794 #define quat_identity quaternion_identity
795 #define quat_lerp quaternion_lerp
796 #define quat_nlerp quaternion_nlerp
797 #define quat_slerp quaternion_slerp
798 
799 #endif /* DOXYGEN_SHOULD_SKIP_THIS */
800 
801 
802 #include <stdint.h>
803 
804 HYPAPI struct quaternion *quaternion_rotate_by_quaternion_EXP(struct quaternion *self, const struct quaternion *qT);
805 HYPAPI struct quaternion *quaternion_rotate_by_axis_angle_EXP(struct quaternion *self, const struct vector3 *axis, HYP_FLOAT angle);
807 HYPAPI HYP_FLOAT quaternion_difference_EXP(const struct quaternion *q1, const struct quaternion *q2);
808 HYPAPI HYP_FLOAT quaternion_angle_between_EXP(const struct quaternion *self, const struct quaternion *qT);
809 HYPAPI void quaternion_axis_between_EXP(const struct quaternion *self, const struct quaternion *qT, struct quaternion *qR);
810 HYPAPI struct matrix4 *matrix4_projection_perspective_fovy_rh_EXP(struct matrix4 *self, HYP_FLOAT fovy, HYP_FLOAT aspect, HYP_FLOAT zNear, HYP_FLOAT zFar);
811 HYPAPI struct matrix4 *matrix4_projection_ortho3d_rh_EXP(struct matrix4 *self, HYP_FLOAT xmin, HYP_FLOAT xmax, HYP_FLOAT ymin, HYP_FLOAT ymax, HYP_FLOAT zNear, HYP_FLOAT zFar);
812 HYPAPI struct matrix4 *matrix4_view_lookat_rh_EXP(struct matrix4 *self, const struct vector3 *eye, const struct vector3 *target, const struct vector3 *up);
813 HYPAPI struct vector3 *matrix4_multiplyv3_EXP(const struct matrix4 *m, const struct vector3 *vT, struct vector3 *vR);
814 HYPAPI struct quaternion quaternion_cross_product_EXP(const struct quaternion *self, const struct quaternion *vT);
815 HYPAPI struct matrix4 *matrix4_set_from_quaternion_EXP(struct matrix4 *self, const struct quaternion *qT);
816 HYPAPI struct matrix4 *matrix4_set_from_axisv3_angle_EXP(struct matrix4 *self, const struct vector3 *axis, HYP_FLOAT angle);
817 HYPAPI struct matrix4 *matrix4_set_from_axisf3_angle_EXP(struct matrix4 *self, HYP_FLOAT x, HYP_FLOAT y, HYP_FLOAT z, const HYP_FLOAT angle);
818 HYPAPI struct matrix4 *matrix4_set_from_euler_anglesf3_EXP(struct matrix4 *self, const HYP_FLOAT x, const HYP_FLOAT y, const HYP_FLOAT z);
819 HYPAPI struct vector3 *matrix4_get_translation_EXP(const struct matrix4 *self, struct vector3 *vT);
820 HYPAPI struct matrix4 *matrix4_make_transformation_rotationv3_EXP(struct matrix4 *self, const struct vector3 *vR);
821 HYPAPI struct matrix4 *matrix4_transformation_compose_EXP(struct matrix4 *self, const struct vector3 *scale, const struct quaternion *rotation, const struct vector3 *translation);
822 HYPAPI uint8_t matrix4_transformation_decompose_EXP(struct matrix4 *self, struct vector3 *scale, struct quaternion *rotation, struct vector3 *translation);
823 
824 
825 #ifdef HYPATIA_IMPLEMENTATION
826 
827 
832 HYPAPI short scalar_equalsf(const HYP_FLOAT f1, const HYP_FLOAT f2)
833 {
834  return scalar_equals_epsilonf(f1, f2, HYP_EPSILON);
835 }
836 
841 HYPAPI short scalar_equals_epsilonf(const HYP_FLOAT f1, const HYP_FLOAT f2, const HYP_FLOAT epsilon)
842 {
843  if ((HYP_ABS(f1 - f2) < epsilon) == 0) {
844  return 0;
845  }
846 
847  return 1;
848 }
849 
850 
851 static struct vector2 _vector2_zero = { { {0.0f, 0.0f} } };
852 static struct vector2 _vector2_one = { { {1.0f, 1.0f} } };
853 static struct vector2 _vector2_unit_x = { { {1.0f, 0.0f} } };
854 static struct vector2 _vector2_unit_y = { { {0.0f, 1.0f} } };
855 static struct vector2 _vector2_unit_x_negative = { { {-1.0f, 0.0f} } };
856 static struct vector2 _vector2_unit_y_negative = { { {0.0f, -1.0f} } };
857 
858 
859 HYPAPI const struct vector2 *vector2_get_reference_vector2(int id)
860 {
861  switch (id) {
862  case HYP_REF_VECTOR2_ZERO:
863  return &_vector2_zero;
864  case HYP_REF_VECTOR2_ONE:
865  return &_vector2_one;
866  case HYP_REF_VECTOR2_UNIT_X:
867  return &_vector2_unit_x;
868  case HYP_REF_VECTOR2_UNIT_Y:
869  return &_vector2_unit_y;
870  case HYP_REF_VECTOR2_UNIT_X_NEGATIVE:
871  return &_vector2_unit_x_negative;
872  case HYP_REF_VECTOR2_UNIT_Y_NEGATIVE:
873  return &_vector2_unit_y_negative;
874  default:
875  /* undefined case */
876  return &_vector2_zero;
877  }
878 }
879 
880 
881 HYPAPI struct vector2 *vector2_set(struct vector2 *self, const struct vector2 *vT)
882 {
883  self->x = vT->x;
884  self->y = vT->y;
885  return self;
886 }
887 
888 
889 HYPAPI struct vector2 *vector2_setf2(struct vector2 *self, HYP_FLOAT xT, HYP_FLOAT yT)
890 {
891  self->x = xT;
892  self->y = yT;
893  return self;
894 }
895 
896 
897 HYPAPI struct vector2 *vector2_zero(struct vector2 *self)
898 {
899  return vector2_setf2(self, 0.0f, 0.0f);
900 }
901 
902 
903 HYPAPI int vector2_equals(const struct vector2 *self, const struct vector2 *vT)
904 {
905  return scalar_equals(self->x, vT->x) && scalar_equals(self->y, vT->y);
906 }
907 
908 
909 HYPAPI struct vector2 *vector2_negate(struct vector2 *self)
910 {
911  self->v[0] = -self->v[0];
912  self->v[1] = -self->v[1];
913  return self;
914 }
915 
916 
917 HYPAPI struct vector2 *vector2_add(struct vector2 *self, const struct vector2 *vT)
918 {
919  self->v[0] += vT->v[0];
920  self->v[1] += vT->v[1];
921  return self;
922 }
923 
924 
925 HYPAPI struct vector2 *vector2_addf(struct vector2 *self, HYP_FLOAT fT)
926 {
927  self->v[0] += fT;
928  self->v[1] += fT;
929  return self;
930 }
931 
932 
933 HYPAPI struct vector2 *vector2_subtract(struct vector2 *self, const struct vector2 *vT)
934 {
935  self->v[0] -= vT->v[0];
936  self->v[1] -= vT->v[1];
937  return self;
938 }
939 
940 
941 HYPAPI struct vector2 *vector2_subtractf(struct vector2 *self, HYP_FLOAT fT)
942 {
943  self->v[0] -= fT;
944  self->v[1] -= fT;
945  return self;
946 }
947 
948 
949 HYPAPI struct vector2 *vector2_multiply(struct vector2 *self, const struct vector2 *vT)
950 {
951  self->v[0] *= vT->v[0];
952  self->v[1] *= vT->v[1];
953  return self;
954 }
955 
956 
957 HYPAPI struct vector2 *vector2_multiplyf(struct vector2 *self, HYP_FLOAT fT)
958 {
959  self->v[0] *= fT;
960  self->v[1] *= fT;
961  return self;
962 }
963 
964 
965 HYPAPI struct vector2 *vector2_divide(struct vector2 *self, const struct vector2 *vT)
966 {
967  self->v[0] /= vT->v[0];
968  self->v[1] /= vT->v[1];
969  return self;
970 }
971 
972 
973 HYPAPI struct vector2 *vector2_dividef(struct vector2 *self, HYP_FLOAT fT)
974 {
975  self->v[0] /= fT;
976  self->v[1] /= fT;
977  return self;
978 }
979 
980 
981 HYPAPI HYP_FLOAT vector2_magnitude(const struct vector2 *self)
982 {
983  return HYP_SQRT((self->x * self->x) + (self->y * self->y));
984 }
985 
986 
987 HYPAPI struct vector2 *vector2_normalize(struct vector2 *self)
988 {
989  HYP_FLOAT mag = vector2_magnitude(self);
990 
991  self->x = self->x / mag;
992  self->y = self->y / mag;
993  return self;
994 }
995 
996 
997 HYPAPI HYP_FLOAT vector2_dot_product(const struct vector2 *self, const struct vector2 *vT)
998 {
999  return (self->x * vT->x) + (self->y * vT->y);
1000 }
1001 
1002 
1003 HYPAPI struct vector2 *vector2_cross_product(struct vector2 *vR, const struct vector2 *vT1, const struct vector2 *vT2)
1004 {
1005  vR->x = (vT1->x * vT2->y) - (vT1->y * vT2->x);
1006  vR->y = (vT1->y * vT2->x) - (vT1->x * vT2->y);
1007  return vR;
1008 }
1009 
1010 
1011 HYPAPI HYP_FLOAT vector2_angle_between(const struct vector2 *self, const struct vector2 *vT)
1012 {
1013  return vector2_dot_product(self, vT) / (vector2_magnitude(self) * vector2_magnitude(vT));
1014 }
1015 
1016 
1017 HYPAPI struct vector2 *vector2_find_normal_axis_between(struct vector2 *vR, const struct vector2 *vT1, const struct vector2 *vT2)
1018 {
1019  return vector2_normalize(vector2_cross_product(vR, vT1, vT2));
1020 }
1021 
1022 
1030 HYPAPI HYP_FLOAT vector2_distance(const struct vector2 *v1, const struct vector2 *v2)
1031 {
1032  return HYP_SQRT((v2->x - v1->x) * (v2->x - v1->x) + (v2->y - v1->y) * (v2->y - v1->y));
1033 }
1034 
1035 
1042 HYPAPI struct vector2 *vector2_multiplym2(struct vector2 *self, const struct matrix2 *mT)
1043 {
1044  struct vector2 vR;
1045 
1046  vector2_zero(&vR);
1047 
1048  matrix2_multiplyv2(mT, self, &vR);
1049 
1050  vector2_set(self, &vR);
1051 
1052  return self;
1053 }
1054 
1055 
1062 HYPAPI struct vector2 *vector2_multiplym3(struct vector2 *self, const struct matrix3 *mT)
1063 {
1064  struct vector2 vR;
1065 
1066  vector2_zero(&vR);
1067 
1068  matrix3_multiplyv2(mT, self, &vR);
1069 
1070  vector2_set(self, &vR);
1071 
1072  return self;
1073 }
1074 
1075 
1076 #ifndef HYP_NO_STDIO
1077 HYPAPI void _vector2_print(const struct vector2 *self)
1078 {
1079  printf("x:%10f, y:%10f\r\n", self->x, self->y);
1080 }
1081 #endif
1082 
1083 
1089 HYPAPI struct vector2 *_vector2_set_random(struct vector2 *self)
1090 {
1091  self->x = HYP_RANDOM_FLOAT;
1092  self->y = HYP_RANDOM_FLOAT;
1093  return self;
1094 }
1095 
1096 
1097 static struct vector3 _vector3_zero = { { {0.0f, 0.0f, 0.0f} } };
1098 static struct vector3 _vector3_one = { { {1.0f, 1.0f, 1.0f} } };
1099 static struct vector3 _vector3_unit_x = { { {1.0f, 0.0f, 0.0f} } };
1100 static struct vector3 _vector3_unit_y = { { {0.0f, 1.0f, 0.0f} } };
1101 static struct vector3 _vector3_unit_z = { { {0.0f, 0.0f, 1.0f} } };
1102 static struct vector3 _vector3_unit_x_negative = { { {-1.0f, 0.0f, 0.0f} } };
1103 static struct vector3 _vector3_unit_y_negative = { { {0.0f, -1.0f, 0.0f} } };
1104 static struct vector3 _vector3_unit_z_negative = { { {0.0f, 0.0f, -1.0f} } };
1105 
1106 
1107 HYPAPI const struct vector3 *vector3_get_reference_vector3(int id)
1108 {
1109  switch (id) {
1110  case HYP_REF_VECTOR3_ZERO:
1111  return &_vector3_zero;
1112  case HYP_REF_VECTOR3_ONE:
1113  return &_vector3_one;
1114  case HYP_REF_VECTOR3_UNIT_X:
1115  return &_vector3_unit_x;
1116  case HYP_REF_VECTOR3_UNIT_Y:
1117  return &_vector3_unit_y;
1118  case HYP_REF_VECTOR3_UNIT_Z:
1119  return &_vector3_unit_z;
1120  case HYP_REF_VECTOR3_UNIT_X_NEGATIVE:
1121  return &_vector3_unit_x_negative;
1122  case HYP_REF_VECTOR3_UNIT_Y_NEGATIVE:
1123  return &_vector3_unit_y_negative;
1124  case HYP_REF_VECTOR3_UNIT_Z_NEGATIVE:
1125  return &_vector3_unit_z_negative;
1126  default:
1127  /* undefined case */
1128  return &_vector3_zero;
1129  }
1130 }
1131 
1132 
1137 HYPAPI struct vector3 *vector3_setf3(struct vector3 *self, HYP_FLOAT xT, HYP_FLOAT yT, HYP_FLOAT zT)
1138 {
1139  self->x = xT;
1140  self->y = yT;
1141  self->z = zT;
1142  return self;
1143 }
1144 
1145 
1150 HYPAPI struct vector3 *vector3_set(struct vector3 *self, const struct vector3 *vT)
1151 {
1152  self->x = vT->x;
1153  self->y = vT->y;
1154  self->z = vT->z;
1155  return self;
1156 }
1157 
1158 
1163 HYPAPI struct vector3 *vector3_zero(struct vector3 *self)
1164 {
1165  return vector3_setf3(self, 0.0f, 0.0f, 0.0f);
1166 }
1167 
1168 
1173 HYPAPI int vector3_equals(const struct vector3 *self, const struct vector3 *vT)
1174 {
1175  return HYP_ABS(self->x - vT->x) < HYP_EPSILON &&
1176  HYP_ABS(self->y - vT->y) < HYP_EPSILON &&
1177  HYP_ABS(self->z - vT->z) < HYP_EPSILON;
1178 }
1179 
1180 
1185 HYPAPI struct vector3 *vector3_negate(struct vector3 *self)
1186 {
1187  self->v[0] = -self->v[0];
1188  self->v[1] = -self->v[1];
1189  self->v[2] = -self->v[2];
1190  return self;
1191 }
1192 
1193 
1198 HYPAPI struct vector3 *vector3_add(struct vector3 *self, const struct vector3 *vT)
1199 {
1200  self->v[0] += vT->v[0];
1201  self->v[1] += vT->v[1];
1202  self->v[2] += vT->v[2];
1203  return self;
1204 }
1205 
1206 
1211 HYPAPI struct vector3 *vector3_addf(struct vector3 *self, HYP_FLOAT f)
1212 {
1213  self->v[0] += f;
1214  self->v[1] += f;
1215  self->v[2] += f;
1216  return self;
1217 }
1218 
1219 
1224 HYPAPI struct vector3 *vector3_subtract(struct vector3 *self, const struct vector3 *vT)
1225 {
1226  self->v[0] -= vT->v[0];
1227  self->v[1] -= vT->v[1];
1228  self->v[2] -= vT->v[2];
1229  return self;
1230 }
1231 
1232 
1237 HYPAPI struct vector3 *vector3_subtractf(struct vector3 *self, HYP_FLOAT f)
1238 {
1239  self->v[0] -= f;
1240  self->v[1] -= f;
1241  self->v[2] -= f;
1242  return self;
1243 }
1244 
1245 
1250 HYPAPI struct vector3 *vector3_multiply(struct vector3 *self, const struct vector3 *vT)
1251 {
1252  self->v[0] *= vT->v[0];
1253  self->v[1] *= vT->v[1];
1254  self->v[2] *= vT->v[2];
1255  return self;
1256 }
1257 
1258 
1263 HYPAPI struct vector3 *vector3_multiplyf(struct vector3 *self, HYP_FLOAT f)
1264 {
1265  self->v[0] *= f;
1266  self->v[1] *= f;
1267  self->v[2] *= f;
1268  return self;
1269 }
1270 
1271 
1277 HYPAPI struct vector3 *vector3_divide(struct vector3 *self, const struct vector3 *vT)
1278 {
1279  self->v[0] /= vT->v[0];
1280  self->v[1] /= vT->v[1];
1281  self->v[2] /= vT->v[2];
1282  return self;
1283 }
1284 
1285 
1290 HYPAPI HYP_FLOAT vector3_magnitude(const struct vector3 *self)
1291 {
1292  return HYP_SQRT((self->x * self->x) + (self->y * self->y) + (self->z * self->z));
1293 }
1294 
1295 
1300 HYPAPI struct vector3 *vector3_normalize(struct vector3 *self)
1301 {
1302  HYP_FLOAT mag;
1303 
1304  mag = vector3_magnitude(self);
1305 
1306  if (scalar_equalsf(mag, 0.0f)) {
1307  /* can't normalize a zero
1308  * avoid divide by zero
1309  */
1310  return self;
1311  }
1312 
1313  self->x = self->x / mag;
1314  self->y = self->y / mag;
1315  self->z = self->z / mag;
1316 
1317  return self;
1318 }
1319 
1320 
1325 HYPAPI HYP_FLOAT vector3_dot_product(const struct vector3 *self, const struct vector3 *vT)
1326 {
1327  return (self->x * vT->x) + (self->y * vT->y) + (self->z * vT->z);
1328 }
1329 
1330 
1335 HYPAPI struct vector3 *vector3_cross_product(struct vector3 *vR, const struct vector3 *vT1, const struct vector3 *vT2)
1336 {
1337  vR->x = (vT1->y * vT2->z) - (vT1->z * vT2->y);
1338  vR->y = (vT1->z * vT2->x) - (vT1->x * vT2->z);
1339  vR->z = (vT1->x * vT2->y) - (vT1->y * vT2->x);
1340  return vR;
1341 }
1342 
1349 HYPAPI HYP_FLOAT vector3_angle_between(const struct vector3 *vT1, const struct vector3 *vT2)
1350 {
1351  HYP_FLOAT c; /* cosine */
1352 
1353  c = vector3_dot_product(vT1, vT2) / (vector3_magnitude(vT1) * vector3_magnitude(vT2));
1354 
1355  return 2.0f * HYP_ACOS(c);
1356 }
1357 
1358 
1364 HYPAPI struct vector3 *vector3_find_normal_axis_between(struct vector3 *vR, const struct vector3 *vT1, const struct vector3 *vT2)
1365 {
1366  vector3_cross_product(vR, vT1, vT2);
1367  vector3_normalize(vR);
1368  return vR;
1369 }
1370 
1371 
1379 HYPAPI HYP_FLOAT vector3_distance(const struct vector3 *v1, const struct vector3 *v2)
1380 {
1381  return HYP_SQRT((v2->x - v1->x) * (v2->x - v1->x) + (v2->y - v1->y) * (v2->y - v1->y) + (v2->z - v1->z) * (v2->z - v1->z));
1382 }
1383 
1384 
1391 HYPAPI struct vector3 *vector3_multiplym4(struct vector3 *self, const struct matrix4 *mT)
1392 {
1393  struct vector3 vR;
1394 
1395  vector3_zero(&vR);
1396 
1397  matrix4_multiplyv3(mT, self, &vR);
1398 
1399  vector3_set(self, &vR);
1400 
1401  return self;
1402 }
1403 
1404 
1405 #ifndef HYP_NO_STDIO
1406 HYPAPI void _vector3_print(const struct vector3 *self)
1407 {
1408  printf("x:%10f, y:%10f, z:%10f\r\n", self->x, self->y, self->z);
1409 }
1410 #endif
1411 
1412 
1423 HYPAPI struct vector3 *vector3_rotate_by_quaternion(struct vector3 *self, const struct quaternion *qT)
1424 {
1425  struct quaternion qconj;
1426  struct quaternion q;
1427 
1428  /* make the conjugate */
1429  quaternion_set(&qconj, qT);
1430  quaternion_conjugate(&qconj);
1431 
1432  quaternion_set(&q, qT);
1433  quaternion_multiplyv3(&q, self);
1434  quaternion_multiply(&q, &qconj);
1435 
1436  self->x = q.x;
1437  self->y = q.y;
1438  self->z = q.z;
1439 
1440  return self;
1441 }
1442 
1443 
1455 HYPAPI struct vector3 *vector3_reflect_by_quaternion(struct vector3 *self, const struct quaternion *qT)
1456 {
1457  struct quaternion q;
1458 
1459  quaternion_set(&q, qT);
1460  quaternion_multiplyv3(&q, self);
1461  quaternion_multiply(&q, qT);
1462 
1463  /* this seems to be necessary */
1465 
1466  self->x = q.x;
1467  self->y = q.y;
1468  self->z = q.z;
1469 
1470  return self;
1471 }
1472 
1473 
1479 HYPAPI struct vector3 *_vector3_set_random(struct vector3 *self)
1480 {
1481  self->x = HYP_RANDOM_FLOAT;
1482  self->y = HYP_RANDOM_FLOAT;
1483  self->z = HYP_RANDOM_FLOAT;
1484  return self;
1485 }
1486 
1487 
1488 static struct vector4 _vector4_zero = { { {0.0f, 0.0f, 0.0f, 0.0f} } };
1489 static struct vector4 _vector4_one = { { {1.0f, 1.0f, 1.0f, 1.0f} } };
1490 static struct vector4 _vector4_unit_x = { { {1.0f, 0.0f, 0.0f, 0.0f} } };
1491 static struct vector4 _vector4_unit_y = { { {0.0f, 1.0f, 0.0f, 0.0f} } };
1492 static struct vector4 _vector4_unit_z = { { {0.0f, 0.0f, 1.0f, 0.0f} } };
1493 static struct vector4 _vector4_unit_x_negative = { { {-1.0f, 0.0f, 0.0f, 0.0f} } };
1494 static struct vector4 _vector4_unit_y_negative = { { {0.0f, -1.0f, 0.0f, 0.0f} } };
1495 static struct vector4 _vector4_unit_z_negative = { { {0.0f, 0.0f, -1.0f, 0.0f} } };
1496 
1497 
1498 HYPAPI const struct vector4 *vector4_get_reference_vector4(int id)
1499 {
1500  switch (id) {
1501  case HYP_REF_VECTOR4_ZERO:
1502  return &_vector4_zero;
1503  case HYP_REF_VECTOR4_ONE:
1504  return &_vector4_one;
1505  case HYP_REF_VECTOR4_UNIT_X:
1506  return &_vector4_unit_x;
1507  case HYP_REF_VECTOR4_UNIT_Y:
1508  return &_vector4_unit_y;
1509  case HYP_REF_VECTOR4_UNIT_Z:
1510  return &_vector4_unit_z;
1511  case HYP_REF_VECTOR4_UNIT_X_NEGATIVE:
1512  return &_vector4_unit_x_negative;
1513  case HYP_REF_VECTOR4_UNIT_Y_NEGATIVE:
1514  return &_vector4_unit_y_negative;
1515  case HYP_REF_VECTOR4_UNIT_Z_NEGATIVE:
1516  return &_vector4_unit_z_negative;
1517  default:
1518  /* undefined case */
1519  return &_vector4_zero;
1520  }
1521 }
1522 
1523 
1528 HYPAPI struct vector4 *vector4_setf4(struct vector4 *self, HYP_FLOAT xT, HYP_FLOAT yT, HYP_FLOAT zT, HYP_FLOAT wT)
1529 {
1530  self->x = xT;
1531  self->y = yT;
1532  self->z = zT;
1533  self->w = wT;
1534  return self;
1535 }
1536 
1537 
1542 HYPAPI struct vector4 *vector4_set(struct vector4 *self, const struct vector4 *vT)
1543 {
1544  self->x = vT->x;
1545  self->y = vT->y;
1546  self->z = vT->z;
1547  return self;
1548 }
1549 
1550 
1555 HYPAPI struct vector4 *vector4_zero(struct vector4 *self)
1556 {
1557  return vector4_setf4(self, 0.0f, 0.0f, 0.0f, 0.0f);
1558 }
1559 
1560 
1565 HYPAPI int vector4_equals(const struct vector4 *self, const struct vector4 *vT)
1566 {
1567  return HYP_ABS(self->x - vT->x) < HYP_EPSILON &&
1568  HYP_ABS(self->y - vT->y) < HYP_EPSILON &&
1569  HYP_ABS(self->z - vT->z) < HYP_EPSILON &&
1570  HYP_ABS(self->w - vT->w) < HYP_EPSILON;
1571 }
1572 
1573 
1578 HYPAPI struct vector4 *vector4_negate(struct vector4 *self)
1579 {
1580  self->v[0] = -self->v[0];
1581  self->v[1] = -self->v[1];
1582  self->v[2] = -self->v[2];
1583  self->v[3] = -self->v[3];
1584  return self;
1585 }
1586 
1587 
1592 HYPAPI struct vector4 *vector4_add(struct vector4 *self, const struct vector4 *vT)
1593 {
1594  self->v[0] += vT->v[0];
1595  self->v[1] += vT->v[1];
1596  self->v[2] += vT->v[2];
1597  self->v[3] += vT->v[3];
1598  return self;
1599 }
1600 
1601 
1606 HYPAPI struct vector4 *vector4_addf(struct vector4 *self, HYP_FLOAT f)
1607 {
1608  self->v[0] += f;
1609  self->v[1] += f;
1610  self->v[2] += f;
1611  self->v[3] += f;
1612  return self;
1613 }
1614 
1615 
1620 HYPAPI struct vector4 *vector4_subtract(struct vector4 *self, const struct vector4 *vT)
1621 {
1622  self->v[0] -= vT->v[0];
1623  self->v[1] -= vT->v[1];
1624  self->v[2] -= vT->v[2];
1625  self->v[3] -= vT->v[3];
1626  return self;
1627 }
1628 
1629 
1634 HYPAPI struct vector4 *vector4_subtractf(struct vector4 *self, HYP_FLOAT f)
1635 {
1636  self->x -= f;
1637  self->y -= f;
1638  self->z -= f;
1639  self->w -= f;
1640  return self;
1641 }
1642 
1643 
1648 HYPAPI struct vector4 *vector4_multiply(struct vector4 *self, const struct vector4 *vT)
1649 {
1650  self->v[0] *= vT->v[0];
1651  self->v[1] *= vT->v[1];
1652  self->v[2] *= vT->v[2];
1653  self->v[3] *= vT->v[3];
1654  return self;
1655 }
1656 
1657 
1662 HYPAPI struct vector4 *vector4_multiplyf(struct vector4 *self, HYP_FLOAT f)
1663 {
1664  self->v[0] *= f;
1665  self->v[1] *= f;
1666  self->v[2] *= f;
1667  self->v[3] *= f;
1668  return self;
1669 }
1670 
1671 
1677 HYPAPI struct vector4 *vector4_divide(struct vector4 *self, const struct vector4 *vT)
1678 {
1679  self->v[0] /= vT->v[0];
1680  self->v[1] /= vT->v[1];
1681  self->v[2] /= vT->v[2];
1682  self->v[3] /= vT->v[3];
1683  return self;
1684 }
1685 
1686 
1691 HYPAPI HYP_FLOAT vector4_magnitude(const struct vector4 *self)
1692 {
1693  return HYP_SQRT((self->x * self->x) + (self->y * self->y) + (self->z * self->z) + (self->w * self->w));
1694 }
1695 
1696 
1701 HYPAPI struct vector4 *vector4_normalize(struct vector4 *self)
1702 {
1703  HYP_FLOAT mag;
1704 
1705  mag = vector4_magnitude(self);
1706 
1707  if (scalar_equalsf(mag, 0.0)) {
1708  /* can't normalize a zero
1709  * avoid divide by zero
1710  */
1711  return self;
1712  }
1713 
1714  self->x = self->x / mag;
1715  self->y = self->y / mag;
1716  self->z = self->z / mag;
1717  self->w = self->w / mag;
1718 
1719  return self;
1720 }
1721 
1722 
1727 HYPAPI HYP_FLOAT vector4_dot_product(const struct vector4 *self, const struct vector4 *vT)
1728 {
1729  return (self->x * vT->x) + (self->y * vT->y) + (self->z * vT->z) + (self->w * vT->w);
1730 }
1731 
1732 
1737 HYPAPI struct vector4 *vector4_cross_product(struct vector4 *vR, const struct vector4 *vT1, const struct vector4 *vT2)
1738 {
1739  vR->x = (vT1->y * vT2->z) - (vT1->z * vT2->y);
1740  vR->y = (vT1->z * vT2->x) - (vT1->x * vT2->z);
1741  vR->z = (vT1->x * vT2->y) - (vT1->y * vT2->x);
1742  vR->w = (vT1->w * vT2->w) - (vT1->w * vT2->w);
1743  return vR;
1744 }
1745 
1746 
1754 HYPAPI HYP_FLOAT vector4_distance(const struct vector4 *v1, const struct vector4 *v2)
1755 {
1756  return HYP_SQRT((v2->x - v1->x) * (v2->x - v1->x)
1757  + (v2->y - v1->y) * (v2->y - v1->y)
1758  + (v2->z - v1->z) * (v2->z - v1->z)
1759  + (v2->w - v1->w) * (v2->w - v1->w));
1760 }
1761 
1762 
1763 #ifndef HYP_NO_STDIO
1764 HYPAPI void _vector4_print(const struct vector4 *self)
1765 {
1766  printf("x:%10f, y:%10f, z:%10f, w:%10f\r\n", self->x, self->y, self->z, self->w);
1767 }
1768 #endif
1769 
1770 
1776 HYPAPI struct vector4 *_vector4_set_random(struct vector4 *self)
1777 {
1778  self->x = HYP_RANDOM_FLOAT;
1779  self->y = HYP_RANDOM_FLOAT;
1780  self->z = HYP_RANDOM_FLOAT;
1781  self->w = HYP_RANDOM_FLOAT;
1782  return self;
1783 }
1784 
1785 
1790 HYPAPI struct matrix2 *matrix2_zero(struct matrix2 *self)
1791 {
1792  HYP_MEMSET(self, 0, sizeof(struct matrix2));
1793  return self;
1794 }
1795 
1796 
1801 HYPAPI struct matrix2 *matrix2_identity(struct matrix2 *m)
1802 {
1803  m->c00 = 1.0f, m->c10 = 0.0f;
1804  m->c01 = 0.0f, m->c11 = 1.0f;
1805 
1806  return m;
1807 }
1808 
1809 
1817 HYPAPI struct matrix2 *matrix2_set(struct matrix2 *self, const struct matrix2 *mT)
1818 {
1819  uint8_t i;
1820 
1821  for (i = 0; i < 4; i++) {
1822  self->m[i] = mT->m[i];
1823  }
1824 
1825  return self;
1826 }
1827 
1828 
1834 HYPAPI int matrix2_equals(const struct matrix2 *self, const struct matrix2 *mT)
1835 {
1836  uint8_t i;
1837 
1838  for (i = 0; i < 4; i++) {
1839  if (scalar_equalsf(self->m[i], mT->m[i]) == 0) {
1840  return 0;
1841  }
1842  }
1843 
1844  return 1;
1845 }
1846 
1847 
1855 HYPAPI struct matrix2 *matrix2_add(struct matrix2 *self, const struct matrix2 *mT)
1856 {
1857  /* "add row and column to row and column" */
1858  uint8_t i;
1859 
1860  for (i = 0; i < 4; i++) {
1861  self->m[i] += mT->m[i];
1862  }
1863 
1864  return self;
1865 }
1866 
1867 
1875 HYPAPI struct matrix2 *matrix2_subtract(struct matrix2 *self, const struct matrix2 *mT)
1876 {
1877  /* "subtract row and column from row and column" */
1878  uint8_t i;
1879 
1880  for (i = 0; i < 4; i++) {
1881  self->m[i] -= mT->m[i];
1882  }
1883 
1884  return self;
1885 }
1886 
1887 
1895 HYPAPI struct matrix2 *matrix2_multiplyf(struct matrix2 *self, HYP_FLOAT scalar)
1896 {
1897  uint8_t i;
1898 
1899  for (i = 0; i < 4; i++) {
1900  self->m[i] *= scalar;
1901  }
1902 
1903  return self;
1904 }
1905 
1906 
1916 HYPAPI struct matrix2 *matrix2_multiply(struct matrix2 *self, const struct matrix2 *mT)
1917 {
1918  /* mT is the multiplicand */
1919 
1920  struct matrix2 r;
1921 
1922  matrix2_identity(&r);
1923 
1924  /* first row */
1925  r.r00 = self->c00 * mT->c00 + self->c01 * mT->c10;
1926  r.r01 = self->c10 * mT->c00 + self->c11 * mT->c10;
1927 
1928  /* second row */
1929  r.r10 = self->c00 * mT->c01 + self->c01 * mT->c11;
1930  r.r11 = self->c10 * mT->c01 + self->c11 * mT->c11;
1931 
1932  matrix2_set(self, &r); /* overwrite/save it */
1933 
1934  return self;
1935 }
1936 
1937 
1946 HYPAPI struct vector2 *matrix2_multiplyv2(const struct matrix2 *self, const struct vector2 *vT, struct vector2 *vR)
1947 {
1948  vR->x = vT->x * self->c00 + vT->y * self->c01;
1949  vR->y = vT->x * self->c10 + vT->y * self->c11;
1950 
1951  return vR;
1952 }
1953 
1954 
1961 HYPAPI struct matrix2 *matrix2_transpose(struct matrix2 *self)
1962 {
1963  return _matrix2_transpose_columnrow(self);
1964 }
1965 
1966 
1972 HYPAPI struct matrix2 *_matrix2_transpose_rowcolumn(struct matrix2 *self)
1973 {
1974  HYP_SWAP(&self->r01, &self->r10);
1975 
1976  return self;
1977 }
1978 
1979 
1985 HYPAPI struct matrix2 *_matrix2_transpose_columnrow(struct matrix2 *self)
1986 {
1987  HYP_SWAP(&self->c01, &self->c10);
1988 
1989  return self;
1990 }
1991 
1992 
1993 #ifndef HYP_NO_STDIO
1999 HYPAPI void _matrix2_print_with_columnrow_indexer(struct matrix2 *self)
2000 {
2001  printf("%10f, %10f\r\n", self->c00, self->c10);
2002  printf("%10f, %10f\r\n", self->c01, self->c11);
2003 }
2004 #endif
2005 
2006 
2007 #ifndef HYP_NO_STDIO
2013 HYPAPI void _matrix2_print_with_rowcolumn_indexer(struct matrix2 *self)
2014 {
2015  printf("%10f, %10f\r\n", self->r00, self->r01);
2016  printf("%10f, %10f\r\n", self->r10, self->r11);
2017 }
2018 #endif
2019 
2025 HYPAPI struct matrix2 *_matrix2_set_random(struct matrix2 *self)
2026 {
2027  uint8_t i;
2028 
2029  for (i = 0; i < 4; i++) {
2030  self->m[i] = HYP_RANDOM_FLOAT;
2031  }
2032 
2033  return self;
2034 }
2035 
2036 
2042 HYPAPI struct matrix2 *matrix2_make_transformation_scalingv2(struct matrix2 *self, const struct vector2 *scale)
2043 {
2044  matrix2_identity(self);
2045 
2046  self->r00 = scale->x;
2047  self->r11 = scale->y;
2048 
2049  return self;
2050 }
2051 
2052 
2060 HYPAPI struct matrix2 *matrix2_make_transformation_rotationf_z(struct matrix2 *m, HYP_FLOAT angle)
2061 {
2062  HYP_FLOAT c = HYP_COS(angle);
2063  HYP_FLOAT s = HYP_SIN(angle);
2064 
2066 
2067  m->r00 = c;
2068  m->r01 = s;
2069  m->r10 = -s;
2070  m->r11 = c;
2071 
2072  return m;
2073 }
2074 
2075 
2086 HYPAPI struct matrix2 *matrix2_rotate(struct matrix2 *self, HYP_FLOAT angle)
2087 {
2088  struct matrix2 rotationMatrix;
2089 
2090  return matrix2_multiply(self,
2091  matrix2_make_transformation_rotationf_z(&rotationMatrix, angle));
2092 }
2093 
2094 
2104 HYPAPI struct matrix2 *matrix2_scalev2(struct matrix2 *self, const struct vector2 *scale)
2105 {
2106  struct matrix2 scalingMatrix;
2107 
2108  return matrix2_multiply(self,
2109  matrix2_make_transformation_scalingv2(&scalingMatrix, scale));
2110 }
2111 
2112 
2120 HYPAPI HYP_FLOAT matrix2_determinant(const struct matrix2 *self)
2121 {
2122  HYP_FLOAT determinant;
2123 
2124  determinant =
2125  self->r00 * self->r11
2126  - self->r10 * self->r01
2127  ;
2128 
2129  return determinant;
2130 }
2131 
2132 
2140 HYPAPI struct matrix2 *matrix2_invert(struct matrix2 *self)
2141 {
2142  struct matrix2 inverse;
2143  uint8_t i;
2144 
2145  if (matrix2_inverse(self, &inverse)) {
2146  for (i = 0; i < 4; i++) {
2147  self->m[i] = inverse.m[i];
2148  }
2149  }
2150 
2151  return self;
2152 }
2153 
2154 
2163 HYPAPI struct matrix2 *matrix2_inverse(const struct matrix2 *self, struct matrix2 *mR)
2164 {
2165  struct matrix2 inverse;
2166  HYP_FLOAT determinant;
2167  uint8_t i;
2168 
2169  determinant = matrix2_determinant(self);
2170 
2171  /* calculated early for a quick exit if no determinant exists */
2172  if (scalar_equalsf(determinant, 0.0f)) {
2173  return NULL;
2174  }
2175 
2176  determinant = 1.0f / determinant;
2177 
2178  /* find the adjugate of self */
2179  inverse.c00 = self->c11;
2180  inverse.c01 = -self->c01;
2181  inverse.c10 = -self->c10;
2182  inverse.c11 = self->c00;
2183 
2184  /* divide the determinant */
2185  for (i = 0; i < 4; i++) {
2186  mR->m[i] = inverse.m[i] * determinant;
2187  }
2188 
2189  return mR;
2190 }
2191 
2192 
2197 HYPAPI struct matrix3 *matrix3_zero(struct matrix3 *self)
2198 {
2199  HYP_MEMSET(self, 0, sizeof(struct matrix3));
2200  return self;
2201 }
2202 
2203 
2208 HYPAPI struct matrix3 *matrix3_identity(struct matrix3 *m)
2209 {
2210  m->c00 = 1.0f, m->c10 = 0.0f, m->c20 = 0.0f;
2211  m->c01 = 0.0f, m->c11 = 1.0f, m->c21 = 0.0f;
2212  m->c02 = 0.0f, m->c12 = 0.0f, m->c22 = 1.0f;
2213 
2214  return m;
2215 }
2216 
2217 
2225 HYPAPI struct matrix3 *matrix3_set(struct matrix3 *self, const struct matrix3 *mT)
2226 {
2227  uint8_t i;
2228 
2229  for (i = 0; i < 9; i++) {
2230  self->m[i] = mT->m[i];
2231  }
2232 
2233  return self;
2234 }
2235 
2236 
2242 HYPAPI int matrix3_equals(const struct matrix3 *self, const struct matrix3 *mT)
2243 {
2244  uint8_t i;
2245 
2246  for (i = 0; i < 9; i++) {
2247  if (scalar_equalsf(self->m[i], mT->m[i]) == 0) {
2248  return 0;
2249  }
2250  }
2251 
2252  return 1;
2253 }
2254 
2255 
2263 HYPAPI struct matrix3 *matrix3_add(struct matrix3 *self, const struct matrix3 *mT)
2264 {
2265  /* "add row and column to row and column" */
2266  uint8_t i;
2267 
2268  for (i = 0; i < 9; i++) {
2269  self->m[i] += mT->m[i];
2270  }
2271 
2272  return self;
2273 }
2274 
2275 
2283 HYPAPI struct matrix3 *matrix3_subtract(struct matrix3 *self, const struct matrix3 *mT)
2284 {
2285  /* "subtract row and column from row and column" */
2286  uint8_t i;
2287 
2288  for (i = 0; i < 9; i++) {
2289  self->m[i] -= mT->m[i];
2290  }
2291 
2292  return self;
2293 }
2294 
2295 
2303 HYPAPI struct matrix3 *matrix3_multiplyf(struct matrix3 *self, HYP_FLOAT scalar)
2304 {
2305  uint8_t i;
2306 
2307  for (i = 0; i < 9; i++) {
2308  self->m[i] *= scalar;
2309  }
2310 
2311  return self;
2312 }
2313 
2314 
2324 HYPAPI struct matrix3 *matrix3_multiply(struct matrix3 *self, const struct matrix3 *mT)
2325 {
2326  /* mT is the multiplicand */
2327 
2328  struct matrix3 r;
2329 
2330  matrix3_identity(&r);
2331 
2332  /* first row */
2333  r.r00 = self->c00 * mT->c00 + self->c01 * mT->c10 + self->c02 * mT->c20;
2334  r.r01 = self->c10 * mT->c00 + self->c11 * mT->c10 + self->c12 * mT->c20;
2335  r.r02 = self->c20 * mT->c00 + self->c21 * mT->c10 + self->c22 * mT->c20;
2336 
2337  /* second row */
2338  r.r10 = self->c00 * mT->c01 + self->c01 * mT->c11 + self->c02 * mT->c21;
2339  r.r11 = self->c10 * mT->c01 + self->c11 * mT->c11 + self->c12 * mT->c21;
2340  r.r12 = self->c20 * mT->c01 + self->c21 * mT->c11 + self->c22 * mT->c21;
2341 
2342  /* third row */
2343  r.r20 = self->c00 * mT->c02 + self->c01 * mT->c12 + self->c02 * mT->c22;
2344  r.r21 = self->c10 * mT->c02 + self->c11 * mT->c12 + self->c12 * mT->c22;
2345  r.r22 = self->c20 * mT->c02 + self->c21 * mT->c12 + self->c22 * mT->c22;
2346 
2347  matrix3_set(self, &r); /* overwrite/save it */
2348 
2349  return self;
2350 }
2351 
2352 
2361 HYPAPI struct vector2 *matrix3_multiplyv2(const struct matrix3 *self, const struct vector2 *vT, struct vector2 *vR)
2362 {
2363  vR->x = vT->x * self->c00 + vT->y * self->c01 + self->c20;
2364  vR->y = vT->x * self->c10 + vT->y * self->c11 + self->c21;
2365 
2366  return vR;
2367 }
2368 
2369 
2376 HYPAPI struct matrix3 *matrix3_transpose(struct matrix3 *self)
2377 {
2378  return _matrix3_transpose_columnrow(self);
2379 }
2380 
2381 
2387 HYPAPI struct matrix3 *_matrix3_transpose_rowcolumn(struct matrix3 *self)
2388 {
2389  HYP_SWAP(&self->r01, &self->r10);
2390  HYP_SWAP(&self->r02, &self->r20);
2391  HYP_SWAP(&self->r12, &self->r21);
2392 
2393  return self;
2394 }
2395 
2396 
2402 HYPAPI struct matrix3 *_matrix3_transpose_columnrow(struct matrix3 *self)
2403 {
2404  HYP_SWAP(&self->c01, &self->c10);
2405  HYP_SWAP(&self->c02, &self->c20);
2406  HYP_SWAP(&self->c12, &self->c21);
2407 
2408  return self;
2409 }
2410 
2411 
2412 #ifndef HYP_NO_STDIO
2418 HYPAPI void _matrix3_print_with_columnrow_indexer(struct matrix3 *self)
2419 {
2420  printf("%10f, %10f, %10f\r\n", self->c00, self->c10, self->c20);
2421  printf("%10f, %10f, %10f\r\n", self->c01, self->c11, self->c21);
2422  printf("%10f, %10f, %10f\r\n", self->c02, self->c12, self->c22);
2423 }
2424 #endif
2425 
2426 
2427 #ifndef HYP_NO_STDIO
2433 HYPAPI void _matrix3_print_with_rowcolumn_indexer(struct matrix3 *self)
2434 {
2435  printf("%10f, %10f, %10f\r\n", self->r00, self->r01, self->r02);
2436  printf("%10f, %10f, %10f\r\n", self->r10, self->r11, self->r12);
2437  printf("%10f, %10f, %10f\r\n", self->r20, self->r21, self->r22);
2438 }
2439 #endif
2440 
2446 HYPAPI struct matrix3 *_matrix3_set_random(struct matrix3 *self)
2447 {
2448  uint8_t i;
2449 
2450  for (i = 0; i < 9; i++) {
2451  self->m[i] = HYP_RANDOM_FLOAT;
2452  }
2453 
2454  return self;
2455 }
2456 
2457 
2463 HYPAPI struct matrix3 *matrix3_make_transformation_translationv2(struct matrix3 *self, const struct vector2 *translation)
2464 {
2465  matrix3_identity(self);
2466 
2467  self->r02 = translation->x;
2468  self->r12 = translation->y;
2469 
2470  return self;
2471 }
2472 
2473 
2479 HYPAPI struct matrix3 *matrix3_make_transformation_scalingv2(struct matrix3 *self, const struct vector2 *scale)
2480 {
2481  matrix3_identity(self);
2482 
2483  self->r00 = scale->x;
2484  self->r11 = scale->y;
2485 
2486  return self;
2487 }
2488 
2489 
2497 HYPAPI struct matrix3 *matrix3_make_transformation_rotationf_z(struct matrix3 *m, HYP_FLOAT angle)
2498 {
2499  HYP_FLOAT c = HYP_COS(angle);
2500  HYP_FLOAT s = HYP_SIN(angle);
2501 
2503 
2504  m->r00 = c;
2505  m->r01 = s;
2506  m->r10 = -s;
2507  m->r12 = c;
2508 
2509  return m;
2510 }
2511 
2512 
2522 HYPAPI struct matrix3 *matrix3_translatev2(struct matrix3 *self, const struct vector2 *translation)
2523 {
2524  struct matrix3 translationMatrix;
2525 
2526  return matrix3_multiply(self,
2527  matrix3_make_transformation_translationv2(&translationMatrix, translation));
2528 }
2529 
2530 
2541 HYPAPI struct matrix3 *matrix3_rotate(struct matrix3 *self, HYP_FLOAT angle)
2542 {
2543  struct matrix3 rotationMatrix;
2544 
2545  return matrix3_multiply(self,
2546  matrix3_make_transformation_rotationf_z(&rotationMatrix, angle));
2547 }
2548 
2549 
2559 HYPAPI struct matrix3 *matrix3_scalev2(struct matrix3 *self, const struct vector2 *scale)
2560 {
2561  struct matrix3 scalingMatrix;
2562 
2563  return matrix3_multiply(self,
2564  matrix3_make_transformation_scalingv2(&scalingMatrix, scale));
2565 }
2566 
2567 
2568 #define _HYP_CAT(a, ...) _HYP_PRIMITIVE_CAT(a, __VA_ARGS__)
2569 #define _HYP_PRIMITIVE_CAT(a, ...) a ## __VA_ARGS__
2570 #define _HYP_DEC(x) _HYP_PRIMITIVE_CAT(DEC_, x)
2571 #define DEC_11 00
2572 #define DEC_12 01
2573 #define DEC_13 02
2574 #define DEC_14 03
2575 #define DEC_21 10
2576 #define DEC_22 11
2577 #define DEC_23 12
2578 #define DEC_24 13
2579 #define DEC_31 20
2580 #define DEC_32 21
2581 #define DEC_33 22
2582 #define DEC_34 23
2583 #define DEC_41 30
2584 #define DEC_42 31
2585 #define DEC_43 32
2586 #define DEC_44 33
2587 #define A(x) _HYP_CAT(self->r, _HYP_DEC(x))
2588 #define B(x) _HYP_CAT(inverse.r, _HYP_DEC(x))
2589 #define A4(x1, x2, x3, x4) (A(x1) * A(x2) * A(x3) * A(x4))
2590 #define A3(x1, x2, x3) (A(x1) * A(x2) * A(x3))
2591 #define A2(x1, x2) (A(x1) * A(x2))
2592 
2593 
2601 HYPAPI HYP_FLOAT matrix3_determinant(const struct matrix3 *self)
2602 {
2603  HYP_FLOAT determinant;
2604 
2605  determinant =
2606  (A(11) * (A2(22, 33) - A2(32, 23)))
2607  - (A(12) * (A2(21, 33) - A2(31, 23)))
2608  + (A(13) * (A2(21, 32) - A2(31, 22)))
2609  ;
2610 
2611  return determinant;
2612 }
2613 
2614 
2622 HYPAPI struct matrix3 *matrix3_invert(struct matrix3 *self)
2623 {
2624  struct matrix3 inverse;
2625  uint8_t i;
2626 
2627  if (matrix3_inverse(self, &inverse)) {
2628  for (i = 0; i < 9; i++) {
2629  self->m[i] = inverse.m[i];
2630  }
2631  }
2632 
2633  return self;
2634 }
2635 
2636 
2645 HYPAPI struct matrix3 *matrix3_inverse(const struct matrix3 *self, struct matrix3 *mR)
2646 {
2647  struct matrix3 inverse;
2648  HYP_FLOAT determinant;
2649  uint8_t i;
2650 
2651  determinant = matrix3_determinant(self);
2652 
2653  /* calculated early for a quick exit if no determinant exists */
2654  if (scalar_equalsf(determinant, 0.0f)) {
2655  return NULL;
2656  }
2657 
2658  determinant = 1.0f / determinant;
2659 
2660  matrix3_identity(&inverse);
2661 
2662  /* find the adjugate of self */
2663  B(11) = A2(22, 33) - A2(32, 23);
2664  B(12) = A2(32, 13) - A2(12, 33);
2665  B(13) = A2(12, 23) - A2(22, 13);
2666 
2667  B(21) = A2(23, 31) - A2(33, 21);
2668  B(22) = A2(33, 11) - A2(13, 31);
2669  B(23) = A2(13, 21) - A2(23, 11);
2670 
2671  B(31) = A2(21, 32) - A2(31, 22);
2672  B(32) = A2(31, 12) - A2(11, 32);
2673  B(33) = A2(11, 22) - A2(21, 12);
2674 
2675  /* divide the determinant */
2676  for (i = 0; i < 9; i++) {
2677  mR->m[i] = inverse.m[i] * determinant;
2678  }
2679 
2680  return mR;
2681 }
2682 
2683 
2688 HYPAPI struct matrix4 *matrix4_zero(struct matrix4 *self)
2689 {
2690  HYP_MEMSET(self, 0, sizeof(struct matrix4));
2691  return self;
2692 }
2693 
2694 
2699 HYPAPI struct matrix4 *matrix4_identity(struct matrix4 *m)
2700 {
2701  m->c00 = 1.0f, m->c10 = 0.0f, m->c20 = 0.0f, m->c30 = 0.0f;
2702  m->c01 = 0.0f, m->c11 = 1.0f, m->c21 = 0.0f, m->c31 = 0.0f;
2703  m->c02 = 0.0f, m->c12 = 0.0f, m->c22 = 1.0f, m->c32 = 0.0f;
2704  m->c03 = 0.0f, m->c13 = 0.0f, m->c23 = 0.0f, m->c33 = 1.0f;
2705 
2706  return m;
2707 }
2708 
2709 
2717 HYPAPI struct matrix4 *matrix4_set(struct matrix4 *self, const struct matrix4 *mT)
2718 {
2719  uint8_t i;
2720 
2721  for (i = 0; i < 16; i++) {
2722  self->m[i] = mT->m[i];
2723  }
2724 
2725  return self;
2726 }
2727 
2728 
2734 HYPAPI int matrix4_equals(const struct matrix4 *self, const struct matrix4 *mT)
2735 {
2736  uint8_t i;
2737 
2738  for (i = 0; i < 16; i++) {
2739  if (scalar_equalsf(self->m[i], mT->m[i]) == 0) {
2740  return 0;
2741  }
2742  }
2743 
2744  return 1;
2745 }
2746 
2747 
2755 HYPAPI struct matrix4 *matrix4_add(struct matrix4 *self, const struct matrix4 *mT)
2756 {
2757  /* "add row and column to row and column" */
2758  uint8_t i;
2759 
2760  for (i = 0; i < 16; i++) {
2761  self->m[i] += mT->m[i];
2762  }
2763 
2764  return self;
2765 }
2766 
2767 
2775 HYPAPI struct matrix4 *matrix4_subtract(struct matrix4 *self, const struct matrix4 *mT)
2776 {
2777  /* "subtract row and column from row and column" */
2778  uint8_t i;
2779 
2780  for (i = 0; i < 16; i++) {
2781  self->m[i] -= mT->m[i];
2782  }
2783 
2784  return self;
2785 }
2786 
2787 
2795 HYPAPI struct matrix4 *matrix4_multiplyf(struct matrix4 *self, HYP_FLOAT scalar)
2796 {
2797  uint8_t i;
2798 
2799  for (i = 0; i < 16; i++) {
2800  self->m[i] *= scalar;
2801  }
2802 
2803  return self;
2804 }
2805 
2806 
2816 HYPAPI struct matrix4 *matrix4_multiply(struct matrix4 *self, const struct matrix4 *mT)
2817 {
2818  /* mT is the multiplicand */
2819 
2820  struct matrix4 r;
2821 
2822  matrix4_identity(&r);
2823 
2824  /* first row */
2825  r.r00 = self->c00 * mT->c00 + self->c01 * mT->c10 + self->c02 * mT->c20 + self->c03 * mT->c30;
2826  r.r01 = self->c10 * mT->c00 + self->c11 * mT->c10 + self->c12 * mT->c20 + self->c13 * mT->c30;
2827  r.r02 = self->c20 * mT->c00 + self->c21 * mT->c10 + self->c22 * mT->c20 + self->c23 * mT->c30;
2828  r.r03 = self->c30 * mT->c00 + self->c31 * mT->c10 + self->c32 * mT->c20 + self->c33 * mT->c30;
2829 
2830  /* second row */
2831  r.r10 = self->c00 * mT->c01 + self->c01 * mT->c11 + self->c02 * mT->c21 + self->c03 * mT->c31;
2832  r.r11 = self->c10 * mT->c01 + self->c11 * mT->c11 + self->c12 * mT->c21 + self->c13 * mT->c31;
2833  r.r12 = self->c20 * mT->c01 + self->c21 * mT->c11 + self->c22 * mT->c21 + self->c23 * mT->c31;
2834  r.r13 = self->c30 * mT->c01 + self->c31 * mT->c11 + self->c32 * mT->c21 + self->c33 * mT->c31;
2835 
2836  /* third row */
2837  r.r20 = self->c00 * mT->c02 + self->c01 * mT->c12 + self->c02 * mT->c22 + self->c03 * mT->c32;
2838  r.r21 = self->c10 * mT->c02 + self->c11 * mT->c12 + self->c12 * mT->c22 + self->c13 * mT->c32;
2839  r.r22 = self->c20 * mT->c02 + self->c21 * mT->c12 + self->c22 * mT->c22 + self->c23 * mT->c32;
2840  r.r23 = self->c30 * mT->c02 + self->c31 * mT->c12 + self->c32 * mT->c22 + self->c33 * mT->c32;
2841 
2842  /* fourth row */
2843  r.r30 = self->c00 * mT->c03 + self->c01 * mT->c13 + self->c02 * mT->c23 + self->c03 * mT->c33;
2844  r.r31 = self->c10 * mT->c03 + self->c11 * mT->c13 + self->c12 * mT->c23 + self->c13 * mT->c33;
2845  r.r32 = self->c20 * mT->c03 + self->c21 * mT->c13 + self->c22 * mT->c23 + self->c23 * mT->c33;
2846  r.r33 = self->c30 * mT->c03 + self->c31 * mT->c13 + self->c32 * mT->c23 + self->c33 * mT->c33;
2847 
2848  matrix4_set(self, &r); /* overwrite/save it */
2849 
2850  return self;
2851 }
2852 
2853 
2864 HYPAPI struct vector4 *matrix4_multiplyv4(const struct matrix4 *self, const struct vector4 *vT, struct vector4 *vR)
2865 {
2866  vR->x = vT->x * self->r00 + vT->y * self->r01 + vT->z * self->r02 + vT->w * self->r03;
2867  vR->y = vT->x * self->r10 + vT->y * self->r11 + vT->z * self->r12 + vT->w * self->r13;
2868  vR->z = vT->x * self->r20 + vT->y * self->r21 + vT->z * self->r22 + vT->w * self->r23;
2869  vR->w = vT->x * self->r30 + vT->y * self->r31 + vT->z * self->r32 + vT->w * self->r33;
2870 
2871  return vR;
2872 }
2873 
2874 
2883 HYPAPI struct vector3 *matrix4_multiplyv3(const struct matrix4 *self, const struct vector3 *vT, struct vector3 *vR)
2884 {
2885  vR->x = vT->x * self->r00 + vT->y * self->r01 + vT->z * self->r02 + self->r03;
2886  vR->y = vT->x * self->r10 + vT->y * self->r11 + vT->z * self->r12 + self->r13;
2887  vR->z = vT->x * self->r20 + vT->y * self->r21 + vT->z * self->r22 + self->r23;
2888 
2889  return vR;
2890 }
2891 
2892 
2901 HYPAPI struct vector2 *matrix4_multiplyv2(const struct matrix4 *self, const struct vector2 *vT, struct vector2 *vR)
2902 {
2903  vR->x = vT->x * self->r00 + vT->y * self->r01 + self->r02 + self->r03;
2904  vR->y = vT->x * self->r10 + vT->y * self->r11 + self->r12 + self->r13;
2905 
2906  return vR;
2907 }
2908 
2909 
2916 HYPAPI struct matrix4 *matrix4_transpose(struct matrix4 *self)
2917 {
2918  return _matrix4_transpose_columnrow(self);
2919 }
2920 
2921 
2927 HYPAPI struct matrix4 *_matrix4_transpose_rowcolumn(struct matrix4 *self)
2928 {
2929  HYP_SWAP(&self->r01, &self->r10);
2930  HYP_SWAP(&self->r02, &self->r20);
2931  HYP_SWAP(&self->r03, &self->r30);
2932  HYP_SWAP(&self->r12, &self->r21);
2933  HYP_SWAP(&self->r13, &self->r31);
2934  HYP_SWAP(&self->r23, &self->r32);
2935 
2936  return self;
2937 }
2938 
2939 
2945 HYPAPI struct matrix4 *_matrix4_transpose_columnrow(struct matrix4 *self)
2946 {
2947  HYP_SWAP(&self->c01, &self->c10);
2948  HYP_SWAP(&self->c02, &self->c20);
2949  HYP_SWAP(&self->c03, &self->c30);
2950  HYP_SWAP(&self->c12, &self->c21);
2951  HYP_SWAP(&self->c13, &self->c31);
2952  HYP_SWAP(&self->c23, &self->c32);
2953 
2954  return self;
2955 }
2956 
2957 
2958 #ifndef HYP_NO_STDIO
2964 HYPAPI void _matrix4_print_with_columnrow_indexer(struct matrix4 *self)
2965 {
2966  printf("%10f, %10f, %10f, %10f\r\n", self->c00, self->c10, self->c20, self->c30);
2967  printf("%10f, %10f, %10f, %10f\r\n", self->c01, self->c11, self->c21, self->c31);
2968  printf("%10f, %10f, %10f, %10f\r\n", self->c02, self->c12, self->c22, self->c32);
2969  printf("%10f, %10f, %10f, %10f\r\n", self->c03, self->c13, self->c23, self->c33);
2970 }
2971 
2972 
2978 HYPAPI void _matrix4_print_with_rowcolumn_indexer(struct matrix4 *self)
2979 {
2980  printf("%10f, %10f, %10f, %10f\r\n", self->r00, self->r01, self->r02, self->r03);
2981  printf("%10f, %10f, %10f, %10f\r\n", self->r10, self->r11, self->r12, self->r13);
2982  printf("%10f, %10f, %10f, %10f\r\n", self->r20, self->r21, self->r22, self->r23);
2983  printf("%10f, %10f, %10f, %10f\r\n", self->r30, self->r31, self->r32, self->r33);
2984 }
2985 #endif
2986 
2987 
2993 HYPAPI struct matrix4 *_matrix4_set_random(struct matrix4 *self)
2994 {
2995  uint8_t i;
2996 
2997  for (i = 0; i < 16; i++) {
2998  self->m[i] = HYP_RANDOM_FLOAT;
2999  }
3000 
3001  return self;
3002 }
3003 
3004 
3011 HYPAPI struct matrix4 *matrix4_make_transformation_rotationq(struct matrix4 *self, const struct quaternion *qT)
3012 {
3013  struct matrix4 *m;
3014  const struct quaternion *q;
3015 
3016  q = qT;
3017  m = self;
3018 
3019  matrix4_identity(m);
3020 
3021  m->m[0] = 1.0f - 2.0f * (q->y * q->y + q->z * q->z);
3022  m->m[4] = 2.0f * (q->x * q->y - q->z * q->w);
3023  m->m[8] = 2.0f * (q->x * q->z + q->y * q->w);
3024  m->m[1] = 2.0f * (q->x * q->y + q->z * q->w);
3025  m->m[5] = 1.0f - 2.0f * (q->x * q->x + q->z * q->z);
3026  m->m[9] = 2.0f * (q->y * q->z - q->x * q->w);
3027  m->m[2] = 2.0f * (q->x * q->z - q->y * q->w);
3028  m->m[6] = 2.0f * (q->y * q->z + q->x * q->w);
3029  m->m[10] = 1.0f - 2.0f * (q->x * q->x + q->y * q->y);
3030 
3031  return self;
3032 }
3033 
3034 
3040 HYPAPI struct matrix4 *matrix4_make_transformation_translationv3(struct matrix4 *self, const struct vector3 *translation)
3041 {
3042  matrix4_identity(self);
3043 
3044  self->c30 = translation->x;
3045  self->c31 = translation->y;
3046  self->c32 = translation->z;
3047 
3048  return self;
3049 }
3050 
3051 
3057 HYPAPI struct matrix4 *matrix4_make_transformation_scalingv3(struct matrix4 *self, const struct vector3 *scale)
3058 {
3059  matrix4_identity(self);
3060 
3061  self->c00 = scale->x;
3062  self->c11 = scale->y;
3063  self->c22 = scale->z;
3064 
3065  return self;
3066 }
3067 
3068 
3076 HYPAPI struct matrix4 *matrix4_make_transformation_rotationf_x(struct matrix4 *m, HYP_FLOAT angle)
3077 {
3078  HYP_FLOAT c = HYP_COS(angle);
3079  HYP_FLOAT s = HYP_SIN(angle);
3080 
3082 
3083  m->r11 = c;
3084  m->r12 = s;
3085  m->r21 = -s;
3086  m->r22 = c;
3087 
3088  return m;
3089 }
3090 
3091 
3099 HYPAPI struct matrix4 *matrix4_make_transformation_rotationf_y(struct matrix4 *m, HYP_FLOAT angle)
3100 {
3101  HYP_FLOAT c = HYP_COS(angle);
3102  HYP_FLOAT s = HYP_SIN(angle);
3103 
3105 
3106  /* assuming col-major */
3107  m->r00 = c;
3108  m->r02 = -s;
3109  m->r20 = s;
3110  m->r22 = c;
3111 
3112  return m;
3113 }
3114 
3115 
3123 HYPAPI struct matrix4 *matrix4_make_transformation_rotationf_z(struct matrix4 *m, HYP_FLOAT angle)
3124 {
3125  HYP_FLOAT c = HYP_COS(angle);
3126  HYP_FLOAT s = HYP_SIN(angle);
3127 
3129 
3130  /* assuming col-major */
3131  m->r00 = c;
3132  m->r01 = s;
3133  m->r10 = -s;
3134  m->r11 = c;
3135 
3136  return m;
3137 }
3138 
3139 
3149 HYPAPI struct matrix4 *matrix4_translatev3(struct matrix4 *self, const struct vector3 *translation)
3150 {
3151  struct matrix4 translationMatrix;
3152 
3153  return matrix4_multiply(self,
3154  matrix4_make_transformation_translationv3(&translationMatrix, translation));
3155 }
3156 
3157 
3168 HYPAPI struct matrix4 *matrix4_rotatev3(struct matrix4 *self, const struct vector3 *axis, HYP_FLOAT angle)
3169 {
3170  struct matrix4 rotationMatrix;
3171  struct quaternion q;
3172 
3173  return matrix4_multiply(self,
3174  matrix4_make_transformation_rotationq(&rotationMatrix,
3175  quaternion_set_from_axis_anglev3(&q, axis, angle)));
3176 }
3177 
3178 
3188 HYPAPI struct matrix4 *matrix4_scalev3(struct matrix4 *self, const struct vector3 *scale)
3189 {
3190  struct matrix4 scalingMatrix;
3191 
3192  return matrix4_multiply(self,
3193  matrix4_make_transformation_scalingv3(&scalingMatrix, scale));
3194 }
3195 
3196 
3204 HYPAPI HYP_FLOAT matrix4_determinant(const struct matrix4 *self)
3205 {
3206  HYP_FLOAT determinant;
3207 
3208  /* using the Leibniz formula */
3209  /* avoids temporary structures */
3210 
3211  determinant =
3212  A4(11, 22, 33, 44) + A4(11, 23, 34, 42) + A4(11, 24, 32, 43)
3213  + A4(12, 21, 34, 43) + A4(12, 23, 31, 44) + A4(12, 24, 33, 41)
3214  + A4(13, 21, 32, 44) + A4(13, 22, 34, 41) + A4(13, 24, 31, 42)
3215  + A4(14, 21, 33, 42) + A4(14, 22, 31, 43) + A4(14, 23, 32, 41)
3216  - A4(11, 22, 34, 43) - A4(11, 23, 32, 44) - A4(11, 24, 33, 42)
3217  - A4(12, 21, 33, 44) - A4(12, 23, 34, 41) - A4(12, 24, 31, 43)
3218  - A4(13, 21, 34, 42) - A4(13, 22, 31, 44) - A4(13, 24, 32, 41)
3219  - A4(14, 21, 32, 43) - A4(14, 22, 33, 41) - A4(14, 23, 31, 42)
3220  ;
3221 
3222  return determinant;
3223 }
3224 
3225 
3233 HYPAPI struct matrix4 *matrix4_invert(struct matrix4 *self)
3234 {
3235  struct matrix4 inverse;
3236  uint8_t i;
3237 
3238  if (matrix4_inverse(self, &inverse)) {
3239  for (i = 0; i < 16; i++) {
3240  self->m[i] = inverse.m[i];
3241  }
3242  }
3243 
3244  return self;
3245 }
3246 
3247 
3256 HYPAPI struct matrix4 *matrix4_inverse(const struct matrix4 *self, struct matrix4 *mR)
3257 {
3258  struct matrix4 inverse;
3259  HYP_FLOAT determinant;
3260  uint8_t i;
3261 
3262  determinant = matrix4_determinant(self);
3263 
3264  /* calculated early for a quick exit if no determinant exists */
3265  if (scalar_equalsf(determinant, 0.0f)) {
3266  return NULL;
3267  }
3268 
3269  determinant = 1.0f / determinant;
3270 
3271  matrix4_identity(&inverse);
3272 
3273  B(11) = A3(22, 33, 44) + A3(23, 34, 42) + A3(24, 32, 43) - A3(22, 34, 43) - A3(23, 32, 44) - A3(24, 33, 42);
3274  B(12) = A3(12, 34, 43) + A3(13, 32, 44) + A3(14, 33, 42) - A3(12, 33, 44) - A3(13, 34, 42) - A3(14, 32, 43);
3275  B(13) = A3(12, 23, 44) + A3(13, 24, 42) + A3(14, 22, 43) - A3(12, 24, 43) - A3(13, 22, 44) - A3(14, 23, 42);
3276  B(14) = A3(12, 24, 33) + A3(13, 22, 34) + A3(14, 23, 32) - A3(12, 23, 34) - A3(13, 24, 32) - A3(14, 22, 33);
3277  B(21) = A3(21, 34, 43) + A3(23, 31, 44) + A3(24, 33, 41) - A3(21, 33, 44) - A3(23, 34, 41) - A3(24, 31, 43);
3278  B(22) = A3(11, 33, 44) + A3(13, 34, 41) + A3(14, 31, 43) - A3(11, 34, 43) - A3(13, 31, 44) - A3(14, 33, 41);
3279  B(23) = A3(11, 24, 43) + A3(13, 21, 44) + A3(14, 23, 41) - A3(11, 23, 44) - A3(13, 24, 41) - A3(14, 21, 43);
3280  B(24) = A3(11, 23, 34) + A3(13, 24, 31) + A3(14, 21, 33) - A3(11, 24, 33) - A3(13, 21, 34) - A3(14, 23, 31);
3281  B(31) = A3(21, 32, 44) + A3(22, 34, 41) + A3(24, 31, 42) - A3(21, 34, 42) - A3(22, 31, 44) - A3(24, 32, 41);
3282  B(32) = A3(11, 34, 42) + A3(12, 31, 44) + A3(14, 32, 41) - A3(11, 32, 44) - A3(12, 34, 41) - A3(14, 31, 42);
3283  B(33) = A3(11, 22, 44) + A3(12, 24, 41) + A3(14, 21, 42) - A3(11, 24, 42) - A3(12, 21, 44) - A3(14, 22, 41);
3284  B(34) = A3(11, 24, 32) + A3(12, 21, 34) + A3(14, 22, 31) - A3(11, 22, 34) - A3(12, 24, 31) - A3(14, 21, 32);
3285  B(41) = A3(21, 33, 42) + A3(22, 31, 43) + A3(23, 32, 41) - A3(21, 32, 43) - A3(22, 33, 41) - A3(23, 31, 42);
3286  B(42) = A3(11, 32, 43) + A3(12, 33, 41) + A3(13, 31, 42) - A3(11, 33, 42) - A3(12, 31, 43) - A3(13, 32, 41);
3287  B(43) = A3(11, 23, 42) + A3(12, 21, 43) + A3(13, 22, 41) - A3(11, 22, 43) - A3(12, 23, 41) - A3(13, 21, 42);
3288  B(44) = A3(11, 22, 33) + A3(12, 23, 31) + A3(13, 21, 32) - A3(11, 23, 32) - A3(12, 21, 33) - A3(13, 22, 31);
3289 
3290  /* divide the determinant */
3291  for (i = 0; i < 16; i++) {
3292  mR->m[i] = inverse.m[i] * determinant;
3293  }
3294 
3295  return mR;
3296 }
3297 
3298 
3312 HYPAPI struct quaternion *quaternion_identity(struct quaternion *self)
3313 {
3314  self->x = 0.0f;
3315  self->y = 0.0f;
3316  self->z = 0.0f;
3317  self->w = 1.0f;
3318 
3319  return self;
3320 }
3321 
3322 
3328 {
3329  self->x = x;
3330  self->y = y;
3331  self->z = z;
3332  self->w = w;
3333 
3334  return self;
3335 }
3336 
3337 
3343 HYPAPI struct quaternion *quaternion_set(struct quaternion *self, const struct quaternion *qT)
3344 {
3345  return quaternion_setf4(self, qT->x, qT->y, qT->z, qT->w);
3346 }
3347 
3348 
3365 {
3366  HYP_FLOAT s = HYP_SIN(angle / 2.0f);
3367  HYP_FLOAT c = HYP_COS(angle / 2.0f);
3368 
3369  self->x = x * s;
3370  self->y = y * s;
3371  self->z = z * s;
3372  self->w = c;
3373 
3374  /* reduce rounding errors caused by sin/cos */
3375  return quaternion_normalize(self);
3376 }
3377 
3378 
3390 HYPAPI struct quaternion *quaternion_set_from_axis_anglev3(struct quaternion *self, const struct vector3 *axis, HYP_FLOAT angle)
3391 {
3392  return quaternion_set_from_axis_anglef3(self, axis->x, axis->y, axis->z, angle);
3393 }
3394 
3395 
3409 {
3410  self->w = HYP_COS(az / 2.0f) * HYP_COS(ay / 2.0f) * HYP_COS(ax / 2.0f) + HYP_SIN(az / 2.0f) * HYP_SIN(ay / 2.0f) * HYP_SIN(ax / 2.0f);
3411  self->x = HYP_COS(az / 2.0f) * HYP_COS(ay / 2.0f) * HYP_SIN(ax / 2.0f) - HYP_SIN(az / 2.0f) * HYP_SIN(ay / 2.0f) * HYP_COS(ax / 2.0f);
3412  self->y = HYP_COS(az / 2.0f) * HYP_SIN(ay / 2.0f) * HYP_COS(ax / 2.0f) + HYP_SIN(az / 2.0f) * HYP_COS(ay / 2.0f) * HYP_SIN(ax / 2.0f);
3413  self->z = HYP_SIN(az / 2.0f) * HYP_COS(ay / 2.0f) * HYP_COS(ax / 2.0f) - HYP_COS(az / 2.0f) * HYP_SIN(ay / 2.0f) * HYP_SIN(ax / 2.0f);
3414 
3415  quaternion_normalize(self);
3416 
3417  return self;
3418 }
3419 
3420 
3433 HYPAPI void quaternion_get_euler_anglesf3(const struct quaternion *self, HYP_FLOAT *ax, HYP_FLOAT *ay, HYP_FLOAT *az)
3434 {
3435  HYP_FLOAT qx, qy, qz, qw;
3436 
3437  qw = self->w;
3438  qx = self->x;
3439  qy = self->y;
3440  qz = self->z;
3441 
3442  *ax = HYP_ATAN2(qy * qz + qw * qx, 0.5f - ((qx * qx) + (qy * qy)));
3443  *ay = HYP_ASIN(-2.0f * ((qx * qz) - (qw * qy)));
3444  *az = HYP_ATAN2(((qx * qy) + (qw * qz)), 0.5f - ((qy * qy) + (qz * qz)));
3445 }
3446 
3447 
3453 HYPAPI int quaternion_equals(const struct quaternion *self, const struct quaternion *qT)
3454 {
3455  return HYP_ABS(self->x - qT->x) < HYP_EPSILON &&
3456  HYP_ABS(self->y - qT->y) < HYP_EPSILON &&
3457  HYP_ABS(self->z - qT->z) < HYP_EPSILON &&
3458  HYP_ABS(self->w - qT->w) < HYP_EPSILON;
3459 }
3460 
3461 
3469 HYPAPI HYP_FLOAT quaternion_norm(const struct quaternion *self)
3470 {
3471  return (self->x * self->x) + (self->y * self->y) + (self->z * self->z) + (self->w * self->w);
3472 }
3473 
3474 
3483 HYPAPI HYP_FLOAT quaternion_magnitude(const struct quaternion *self)
3484 {
3485  return HYP_SQRT(quaternion_norm(self));
3486 }
3487 
3488 
3497 HYPAPI struct quaternion *quaternion_conjugate(struct quaternion *self)
3498 {
3499  self->x = -self->x;
3500  self->y = -self->y;
3501  self->z = -self->z;
3502  /* doesn't switch the sign of w (that would be negate) */
3503 
3504  return self;
3505 }
3506 
3507 
3513 HYPAPI struct quaternion *quaternion_negate(struct quaternion *self)
3514 {
3515  self->x = -self->x;
3516  self->y = -self->y;
3517  self->z = -self->z;
3518  self->w = -self->w;
3519 
3520  return self;
3521 }
3522 
3523 
3537 HYPAPI struct quaternion *quaternion_inverse(struct quaternion *self)
3538 {
3539  HYP_FLOAT norm;
3540 
3541  norm = quaternion_norm(self);
3542 
3543  if (scalar_equalsf(norm, 0.0f)) {
3544  /* avoid divide by zero */
3545  return self;
3546  }
3547 
3548  quaternion_conjugate(self);
3549 
3550  if (scalar_equalsf(norm, 1.0f)) {
3551  /* we're done */
3552  return self;
3553  }
3554 
3555  self->x /= norm;
3556  self->y /= norm;
3557  self->z /= norm;
3558  self->w /= norm;
3559 
3560  return self;
3561 }
3562 
3563 
3571 HYPAPI struct quaternion *quaternion_normalize(struct quaternion *self)
3572 {
3573  HYP_FLOAT mag;
3574 
3575  mag = quaternion_magnitude(self);
3576 
3577  if (scalar_equalsf(mag, 0.0f)) {
3578  /* can't normalize a zero
3579  * avoid divide by zero
3580  */
3581  return self;
3582  }
3583 
3584  self->x /= mag;
3585  self->y /= mag;
3586  self->z /= mag;
3587  self->w /= mag;
3588 
3589  return self;
3590 }
3591 
3592 
3598 HYPAPI short quaternion_is_unit(struct quaternion *self)
3599 {
3600  return scalar_equalsf(1.0f, quaternion_norm(self));
3601 }
3602 
3603 
3609 HYPAPI short quaternion_is_pure(struct quaternion *self)
3610 {
3611  return scalar_equalsf(self->w, 0.0f);
3612 }
3613 
3614 
3628 HYPAPI struct quaternion *quaternion_nlerp(const struct quaternion *start, const struct quaternion *end, HYP_FLOAT percent, struct quaternion *qR)
3629 {
3630  quaternion_lerp(start, end, percent, qR);
3632  return qR;
3633 }
3634 
3635 
3648 HYPAPI struct quaternion *quaternion_lerp(const struct quaternion *start, const struct quaternion *end, HYP_FLOAT percent, struct quaternion *qR)
3649 {
3650  HYP_FLOAT f1, f2;
3651 
3652  /* if percent is 0, return start */
3653  if (scalar_equalsf(percent, 0.0f)) {
3654  quaternion_set(qR, start);
3655  return qR;
3656  }
3657 
3658  /* if percent is 1 return end */
3659  if (scalar_equalsf(percent, 1.0f)) {
3660  quaternion_set(qR, end);
3661  return qR;
3662  }
3663 
3664  f1 = 1.0f - percent;
3665  f2 = percent;
3666 
3667  /* this expanded form avoids calling quaternion_multiply and
3668  * quaternion_add
3669  */
3670  qR->w = f1 * start->w + f2 * end->w;
3671  qR->x = f1 * start->x + f2 * end->x;
3672  qR->y = f1 * start->y + f2 * end->y;
3673  qR->z = f1 * start->z + f2 * end->z;
3674 
3675  return qR;
3676 }
3677 
3678 
3695 HYPAPI struct quaternion *quaternion_slerp(const struct quaternion *start, const struct quaternion *end, HYP_FLOAT percent, struct quaternion *qR)
3696 {
3697  HYP_FLOAT dot;
3698  HYP_FLOAT f1, f2;
3699  HYP_FLOAT theta;
3700  HYP_FLOAT s;
3701  struct quaternion qneg;
3702 
3703  /* if percent is 0, return start */
3704  if (scalar_equalsf(percent, 0.0f)) {
3705  quaternion_set(qR, start);
3706  return qR;
3707  }
3708 
3709  /* if percent is 1 return end */
3710  if (scalar_equalsf(percent, 1.0f)) {
3711  quaternion_set(qR, end);
3712  return qR;
3713  }
3714 
3715  /* how parallel are the quaternions (also the dot is the cosine) */
3716  dot = quaternion_dot_product(start, end);
3717 
3718  /* if they are close to parallel, use LERP
3719  * - This avoids div/0
3720  * - At small angles, the slerp and lerp are the same
3721  */
3722 
3723  if (scalar_equalsf(dot, 1.0f)) {
3724  quaternion_lerp(start, end, percent, qR);
3725  return qR;
3726  }
3727 
3728  /* if dot is negative, they are "pointing" away from one another,
3729  * use the shortest arc instead (reverse end and start)
3730  * This has the effect of changing the direction of travel around
3731  * the sphere beginning with "end" and going the other way around
3732  * the sphere
3733  */
3734  if (dot < 0.0f) {
3735  quaternion_set(&qneg, end);
3736  /*quaternion_conjugate(&qneg);*/
3737  quaternion_negate(&qneg);
3738  quaternion_slerp(start, &qneg, percent, qR);
3739  quaternion_negate(qR);
3740  /*quaternion_conjugate(qR);*/
3741  return qR;
3742  }
3743 
3744  /* keep the dot product in the range that acos can handle */
3745  /* (shouldn't get here) */
3746  HYP_CLAMP(dot, -1.0f, 1.0f);
3747 
3748  /* the angle between start and end in radians */
3749  theta = HYP_ACOS(dot);
3750  /* cache */
3751  s = HYP_SIN(theta);
3752  /* compute negative */
3753  f1 = HYP_SIN((1.0 - percent) * theta) / s;
3754  /* compute positive */
3755  f2 = HYP_SIN(percent * theta) / s;
3756 
3757  /* this expanded form avoids calling quaternion_multiply
3758  * and quaternion_add
3759  */
3760  qR->w = f1 * start->w + f2 * end->w;
3761  qR->x = f1 * start->x + f2 * end->x;
3762  qR->y = f1 * start->y + f2 * end->y;
3763  qR->z = f1 * start->z + f2 * end->z;
3764 
3765  return qR;
3766 }
3767 
3768 
3775 HYPAPI HYP_FLOAT quaternion_dot_product(const struct quaternion *self, const struct quaternion *qT)
3776 {
3777  return (self->x * qT->x) + (self->y * qT->y) + (self->z * qT->z) + (self->w * qT->w);
3778 }
3779 
3780 
3788 HYPAPI struct quaternion *quaternion_add(struct quaternion *self, const struct quaternion *qT)
3789 {
3790  self->x += qT->x;
3791  self->y += qT->y;
3792  self->z += qT->z;
3793  self->w += qT->w;
3794 
3795  return self;
3796 }
3797 
3798 
3806 HYPAPI struct quaternion *quaternion_subtract(struct quaternion *self, const struct quaternion *qT)
3807 {
3808  self->x -= qT->x;
3809  self->y -= qT->y;
3810  self->z -= qT->z;
3811  self->w -= qT->w;
3812 
3813  return self;
3814 }
3815 
3816 
3824 HYPAPI struct quaternion *quaternion_multiplyf(struct quaternion *self, HYP_FLOAT f)
3825 {
3826  self->x *= f;
3827  self->y *= f;
3828  self->z *= f;
3829  self->w *= f;
3830 
3831  return self;
3832 }
3833 
3834 
3839 HYPAPI struct quaternion *quaternion_multiply(struct quaternion *self, const struct quaternion *qT)
3840 {
3841  /* qT is the multiplicand */
3842 
3843  struct quaternion r;
3844 
3845  r.x = self->w * qT->x + self->x * qT->w + self->y * qT->z - self->z * qT->y;
3846  r.y = self->w * qT->y - self->x * qT->z + self->y * qT->w + self->z * qT->x;
3847  r.z = self->w * qT->z + self->x * qT->y - self->y * qT->x + self->z * qT->w;
3848  r.w = self->w * qT->w - self->x * qT->x - self->y * qT->y - self->z * qT->z;
3849 
3850  quaternion_set(self, &r); /* overwrite/save it */
3851 
3852  return self;
3853 }
3854 
3855 
3860 HYPAPI struct quaternion *quaternion_multiplyv3(struct quaternion *self, const struct vector3 *vT)
3861 {
3862  /* vT is the multiplicand */
3863 
3864  struct quaternion r;
3865 
3866  r.x = self->w * vT->x + self->y * vT->z - self->z * vT->y;
3867  r.y = self->w * vT->y - self->x * vT->z + self->z * vT->x;
3868  r.z = self->w * vT->z + self->x * vT->y - self->y * vT->x;
3869  r.w = self->x * vT->x - self->y * vT->y - self->z * vT->z;
3870 
3871  quaternion_set(self, &r); /* overwrite/save it */
3872 
3873  return self;
3874 }
3875 
3876 
3887 HYPAPI void quaternion_get_axis_anglev3(const struct quaternion *self, struct vector3 *vR, HYP_FLOAT *angle)
3888 {
3889  /* scale is not same as magnitude */
3890  HYP_FLOAT scale = HYP_SQRT(1.0f - self->w * self->w);
3891 
3892  /* avoid divide by zero */
3893  if (scalar_equalsf(scale, 0.0f)) {
3894  vR->x = self->x;
3895  vR->y = self->y;
3896  vR->z = self->z;
3897  } else {
3898  vR->x = self->x / scale;
3899  vR->y = self->y / scale;
3900  vR->z = self->z / scale;
3901  }
3902 
3903  *angle = 2.0f * HYP_ACOS(self->w);
3904 }
3905 
3906 
3911 HYPAPI struct quaternion *_quaternion_set_random(struct quaternion *self)
3912 {
3913  self->x = HYP_RANDOM_FLOAT;
3914  self->y = HYP_RANDOM_FLOAT;
3915  self->z = HYP_RANDOM_FLOAT;
3916  self->w = HYP_RANDOM_FLOAT;
3917 
3918  quaternion_normalize(self);
3919 
3920  return self;
3921 }
3922 
3923 
3924 #ifndef HYP_NO_STDIO
3929 HYPAPI void _quaternion_print(const struct quaternion *self)
3930 {
3931  printf("x:%10f, y:%10f, z:%10f, w:%10f\r\n", self->x, self->y, self->z, self->w);
3932 }
3933 #endif
3934 
3935 
3946 HYPAPI struct quaternion *quaternion_get_rotation_tov3(const struct vector3 *from, const struct vector3 *to, struct quaternion *qR)
3947 {
3948  /* this code avoids sqrt and cos and sin and would be nice to
3949  * avoid division
3950  */
3951  struct vector3 w;
3952  HYP_FLOAT dot;
3953  HYP_FLOAT norm;
3954 
3955  vector3_cross_product(&w, from, to);
3956  dot = vector3_dot_product(from, to);
3957 
3958  qR->x = w.x;
3959  qR->y = w.y;
3960  qR->z = w.z;
3961  qR->w = dot;
3962 
3963  norm = quaternion_norm(qR);
3964  qR->w += norm;
3965 
3966  /* normalization with avoidance of div/0 and reusing the norm */
3967  /* (already calculated above) */
3968  if (!scalar_equalsf(norm, 0.0f)) {
3969  qR->x /= norm;
3970  qR->y /= norm;
3971  qR->z /= norm;
3972  qR->w /= norm;
3973  }
3974 
3975  return qR;
3976 }
3977 
3978 
3979 
3989 HYPAPI struct quaternion *quaternion_rotate_by_quaternion_EXP(struct quaternion *self, const struct quaternion *qT)
3990 {
3991  /* self = self * qT */
3992  quaternion_multiply(self, qT);
3993  quaternion_normalize(self);
3994 
3995  return self;
3996 }
3997 
3998 
4010 HYPAPI struct quaternion *quaternion_rotate_by_axis_angle_EXP(struct quaternion *self, const struct vector3 *axis, HYP_FLOAT angle)
4011 {
4012  struct quaternion qT;
4013 
4014  quaternion_set_from_axis_anglev3(&qT, axis, angle);
4016 
4017  return self;
4018 }
4019 
4020 
4021 
4028 HYPAPI HYP_FLOAT quaternion_difference_EXP(const struct quaternion *q1, const struct quaternion *q2)
4029 {
4030  struct quaternion diff;
4031 
4032  diff.x = q2->x - q1->x;
4033  diff.y = q2->y - q1->y;
4034  diff.z = q2->z - q1->z;
4035  diff.w = q2->w - q1->w;
4036  return quaternion_norm(&diff);
4037 }
4038 
4039 
4054 {
4055  struct quaternion qT;
4056 
4057  /* make a quaternion from the eulers */
4058  quaternion_set_from_euler_anglesf3(&qT, ax, ay, az);
4059 
4060  /* rotate the quaternion by it */
4062 
4063  return self;
4064 }
4065 
4066 
4074 HYPAPI struct quaternion quaternion_cross_product_EXP(const struct quaternion *self, const struct quaternion *vT)
4075 {
4076  /*
4077  * The code is suspect (missing w element in this whole thing)
4078  * It is computing a cross-product on the vector portion and a
4079  * negative dot product on the real portion.
4080  */
4081  struct quaternion r;
4082 
4083  r.x = (self->y * vT->z) - (self->z * vT->y);
4084  r.y = (self->z * vT->x) - (self->x * vT->z);
4085  r.z = (self->x * vT->y) - (self->y * vT->x);
4086  r.w = -((self->x * vT->x) + (self->y * vT->y) + (self->z * vT->z));
4087 
4088  return r;
4089 }
4090 
4091 
4099 HYPAPI HYP_FLOAT quaternion_angle_between_EXP(const struct quaternion *self, const struct quaternion *qT)
4100 {
4101  HYP_FLOAT c; /* cosine */
4102 
4103  c = quaternion_dot_product(self, qT) / (quaternion_norm(self) * quaternion_norm(qT));
4104 
4105  return 2.0f * HYP_ACOS(c);
4106 }
4107 
4108 
4115 HYPAPI void quaternion_axis_between_EXP(const struct quaternion *self, const struct quaternion *qT, struct quaternion *qR)
4116 {
4117  struct quaternion axis;
4118 
4119  axis = quaternion_cross_product_EXP(self, qT);
4120  quaternion_set(qR, &axis);
4122 }
4123 
4124 
4130 HYPAPI struct matrix4 *matrix4_projection_perspective_fovy_rh_EXP(struct matrix4 *self, HYP_FLOAT fovy, HYP_FLOAT aspect, HYP_FLOAT zNear, HYP_FLOAT zFar)
4131 {
4132  HYP_FLOAT h;
4133  HYP_FLOAT w;
4134  HYP_FLOAT p;
4135  HYP_FLOAT q;
4136 
4137  h = HYP_COT(fovy) / 2.0f;
4138  w = h * aspect;
4139 
4140  p = zFar / (zNear - zFar);
4141  q = zNear * p;
4142 
4143  matrix4_zero(self);
4144 
4145  self->r00 = w;
4146  self->r11 = h;
4147  self->r22 = p;
4148  self->r23 = -1.0f; /* this is what makes this RH */
4149  self->r32 = q;
4150 
4151  return self;
4152 }
4153 
4154 
4159 HYPAPI struct matrix4 *matrix4_projection_ortho3d_rh_EXP(struct matrix4 *self,
4160  HYP_FLOAT xmin, HYP_FLOAT xmax,
4161  HYP_FLOAT ymin, HYP_FLOAT ymax,
4162  HYP_FLOAT zNear, HYP_FLOAT zFar)
4163 {
4164  HYP_FLOAT width;
4165  HYP_FLOAT height;
4166 
4167  matrix4_zero(self);
4168 
4169  width = xmax - xmin;
4170  height = ymax - ymin;
4171 
4172  self->c00 = 2.0f / width;
4173  self->c11 = 2.0f / height;
4174  self->c22 = 1.0f / (zFar - zNear);
4175  self->c23 = zNear / (zNear - zFar);
4176  self->c33 = 1.0f;
4177 
4178  return self;
4179 }
4180 
4181 
4190 HYPAPI struct vector3 *matrix4_multiplyv3_EXP(const struct matrix4 *m, const struct vector3 *vT, struct vector3 *vR)
4191 {
4192  vR->x = vT->x * m->c00 + vT->y * m->c01 + vT->z * m->c02 + m->c03;
4193  vR->y = vT->x * m->c10 + vT->y * m->c11 + vT->z * m->c12 + m->c13;
4194  vR->z = vT->x * m->c20 + vT->y * m->c21 + vT->z * m->c22 + m->c23;
4195 
4196  return vR;
4197 }
4198 
4199 
4212 HYPAPI struct matrix4 *matrix4_set_from_axisf3_angle_EXP(struct matrix4 *self, HYP_FLOAT x, HYP_FLOAT y, HYP_FLOAT z, const HYP_FLOAT angle)
4213 {
4214  HYP_FLOAT c = HYP_COS(angle);
4215  HYP_FLOAT s = HYP_SIN(angle);
4216 
4217  self->c00 = (x * x) * (1.0f - c) + c;
4218  self->c01 = (x * y) * (1.0f - c) + (z * s);
4219  self->c02 = (x * z) * (1.0f - c) - (y * s);
4220  self->c03 = 0.0f;
4221 
4222  self->c10 = (y * x) * (1.0f - c) - (z * s);
4223  self->c11 = (y * y) * (1.0f - c) + c;
4224  self->c12 = (y * z) * (1.0f - c) + (x * s);
4225  self->c13 = 0.0f;
4226 
4227  self->c20 = (z * x) * (1.0f - c) + (y * s);
4228  self->c21 = (z * y) * (1.0f - c) - (x * s);
4229  self->c22 = (z * z) * (1.0f - c) + c;
4230  self->c23 = 0.0f;
4231 
4232  self->c30 = 0.0f;
4233  self->c31 = 0.0f;
4234  self->c32 = 0.0f;
4235  self->c33 = 1.0f;
4236 
4237  return self;
4238 }
4239 
4240 
4251 HYPAPI struct matrix4 *matrix4_set_from_axisv3_angle_EXP(struct matrix4 *self, const struct vector3 *axis, HYP_FLOAT angle)
4252 {
4253  return matrix4_set_from_axisf3_angle_EXP(self, axis->x, axis->y, axis->z, angle);
4254 }
4255 
4256 
4257 HYPAPI struct matrix4 *matrix4_set_from_euler_anglesf3_EXP(struct matrix4 *self, const HYP_FLOAT x, const HYP_FLOAT y, const HYP_FLOAT z)
4258 {
4259  HYP_FLOAT A = HYP_COS(x);
4260  HYP_FLOAT B = HYP_SIN(x);
4261  HYP_FLOAT C = HYP_COS(y);
4262  HYP_FLOAT D = HYP_SIN(y);
4263  HYP_FLOAT E = HYP_COS(z);
4264  HYP_FLOAT F = HYP_SIN(z);
4265 
4266  HYP_FLOAT AD = A * D;
4267  HYP_FLOAT BD = B * D;
4268 
4269  self->c00 = C * E;
4270  self->c01 = -C * F;
4271  self->c02 = D;
4272  self->c03 = 0.0f;
4273 
4274  self->c10 = BD * E + A * F;
4275  self->c11 = -BD * F + A * E;
4276  self->c12 = -B * C;
4277  self->c13 = 0.0f;
4278 
4279  self->c20 = -AD * E + B * F;
4280  self->c21 = AD * F + B * E;
4281  self->c22 = A * C;
4282  self->c23 = 0.0f;
4283 
4284  self->c30 = 0.0f;
4285  self->c31 = 0.0f;
4286  self->c32 = 0.0f;
4287  self->c33 = 1.0f;
4288 
4289  return self;
4290 }
4291 
4292 
4293 HYPAPI struct vector3 *matrix4_get_translation_EXP(const struct matrix4 *self, struct vector3 *vT)
4294 {
4295  vT->x = self->c30;
4296  vT->y = self->c31;
4297  vT->z = self->c32;
4298 
4299  return vT;
4300 }
4301 
4302 
4307 HYPAPI struct matrix4 *matrix4_view_lookat_rh_EXP(struct matrix4 *self, const struct vector3 *eye, const struct vector3 *target, const struct vector3 *up)
4308 {
4309  struct vector3 yaxis;
4310  struct vector3 zaxis;
4311  struct vector3 xaxis;
4312 
4313  zaxis.x = target->x - eye->x;
4314  zaxis.y = target->y - eye->y;
4315  zaxis.z = target->z - eye->z;
4316  vector3_normalize(&zaxis);
4317 
4318  /* xaxis = zaxis x up */
4319  vector3_cross_product(&xaxis, &zaxis, up);
4320  vector3_normalize(&xaxis);
4321 
4322  /* yaxis = xaxis x zaxis */
4323  vector3_cross_product(&yaxis, &xaxis, &zaxis);
4324 
4325  matrix4_identity(self);
4326 
4327  self->c00 = xaxis.x;
4328  self->c10 = xaxis.y;
4329  self->c20 = xaxis.z;
4330 
4331  self->c01 = yaxis.x;
4332  self->c11 = yaxis.y;
4333  self->c21 = yaxis.z;
4334 
4335  self->c02 = -zaxis.x;
4336  self->c12 = -zaxis.y;
4337  self->c22 = -zaxis.z;
4338 
4339  self->c30 = -vector3_dot_product(&xaxis, eye);
4340  self->c31 = -vector3_dot_product(&yaxis, eye);
4341  self->c32 = -vector3_dot_product(&zaxis, eye);
4342 
4343  return self;
4344 }
4345 
4346 
4356 HYPAPI struct matrix4 *matrix4_make_transformation_rotationv3_EXP(struct matrix4 *self, const struct vector3 *vR)
4357 {
4358  struct matrix4 scratchMatrix;
4359 
4360  matrix4_identity(self);
4361 
4362  return matrix4_multiply(self,
4363  matrix4_set_from_euler_anglesf3_EXP(&scratchMatrix, vR->x, vR->y, vR->z));
4364 }
4365 
4366 
4367 HYPAPI struct matrix4 *matrix4_transformation_compose_EXP(struct matrix4 *self, const struct vector3 *scale, const struct quaternion *rotation, const struct vector3 *translation)
4368 {
4369  struct matrix4 scaleM, rotateM;
4370 
4371  matrix4_identity(self);
4372 
4373  /* scale */
4375 
4376  /* rotate */
4377  matrix4_multiply(self, matrix4_make_transformation_rotationq(&rotateM, rotation));
4378 
4379  /* translate */
4380  self->c30 = translation->x;
4381  self->c31 = translation->y;
4382  self->c32 = translation->z;
4383 
4384  return self;
4385 }
4386 
4387 HYPAPI uint8_t matrix4_transformation_decompose_EXP(struct matrix4 *self, struct vector3 *scale, struct quaternion *rotation, struct vector3 *translation)
4388 {
4389  HYP_FLOAT signx, signy, signz;
4390 
4391  /* translation */
4392  translation->x = self->c30;
4393  translation->y = self->c31;
4394  translation->z = self->c32;
4395 
4396  /*
4397  * self->c00 = scale->x;
4398  * self->c11 = scale->y;
4399  * self->c22 = scale->z;
4400  */
4401 
4402  /* sign */
4403  signx = ((self->c00 * self->c01 * self->c02 * self->c03) < 0) ? -1.0f : 1.0f;
4404  signy = ((self->c10 * self->c11 * self->c12 * self->c13) < 0) ? -1.0f : 1.0f;
4405  signz = ((self->c20 * self->c21 * self->c22 * self->c23) < 0) ? -1.0f : 1.0f;
4406 
4407  /* scale */
4408  scale->x = signx * HYP_SQRT(self->c00 * self->c00 + self->c01 * self->c01 + self->c02 * self->c02);
4409  scale->y = signy * HYP_SQRT(self->c10 * self->c10 + self->c11 * self->c11 + self->c12 * self->c12);
4410  scale->z = signz * HYP_SQRT(self->c20 * self->c20 + self->c21 * self->c21 + self->c22 * self->c22);
4411 
4412  /* todo */
4413  quaternion_identity(rotation);
4414 
4415  return 1;
4416 }
4417 
4418 #undef _HYP_CAT
4419 #undef _HYP_PRIMITIVE_CAT
4420 #undef _HYP_DEC
4421 #undef DEC_11
4422 #undef DEC_12
4423 #undef DEC_13
4424 #undef DEC_14
4425 #undef DEC_21
4426 #undef DEC_22
4427 #undef DEC_23
4428 #undef DEC_24
4429 #undef DEC_31
4430 #undef DEC_32
4431 #undef DEC_33
4432 #undef DEC_34
4433 #undef DEC_41
4434 #undef DEC_42
4435 #undef DEC_43
4436 #undef DEC_44
4437 #undef A
4438 #undef B
4439 #undef A4
4440 #undef A3
4441 #undef A2
4442 
4443 #endif /* HYPATIA_IMPLEMENTATION */
4444 
4445 #endif /* _INC_HYPATIA */
HYPAPI HYP_FLOAT matrix2_determinant(const struct matrix2 *self)
HYPAPI struct vector4 * _vector4_set_random(struct vector4 *self)
HYPAPI struct vector4 * matrix4_multiplyv4(const struct matrix4 *self, const struct vector4 *vT, struct vector4 *vR)
HYPAPI struct vector3 * vector3_add(struct vector3 *self, const struct vector3 *vT)
HYPAPI struct matrix2 * matrix2_zero(struct matrix2 *self)
#define HYP_RANDOM_FLOAT
A macro that returns a random float point number up to RAND_MAX.
Definition: hypatia.h:124
HYPAPI struct vector4 * vector4_multiplyf(struct vector4 *self, HYP_FLOAT fT)
#define HYP_MEMSET(a, b, c)
A macro that enabled you to override memset.
Definition: hypatia.h:100
HYPAPI struct vector3 * vector3_rotate_by_quaternion(struct vector3 *self, const struct quaternion *qT)
HYPAPI struct matrix4 * matrix4_invert(struct matrix4 *self)
HYPAPI struct matrix4 * matrix4_inverse(const struct matrix4 *self, struct matrix4 *mR)
HYPAPI int vector2_equals(const struct vector2 *self, const struct vector2 *vT)
HYPAPI struct matrix4 * matrix4_projection_perspective_fovy_rh_EXP(struct matrix4 *self, HYP_FLOAT fovy, HYP_FLOAT aspect, HYP_FLOAT zNear, HYP_FLOAT zFar)
HYPAPI struct matrix4 * matrix4_scalev3(struct matrix4 *self, const struct vector3 *scale)
HYPAPI struct matrix4 * matrix4_transpose(struct matrix4 *self)
HYPAPI struct matrix4 * matrix4_make_transformation_translationv3(struct matrix4 *self, const struct vector3 *translation)
HYPAPI struct vector3 * vector3_divide(struct vector3 *self, const struct vector3 *vT)
#define HYP_INLINE
Definition: hypatia.h:24
HYPAPI int matrix3_equals(const struct matrix3 *self, const struct matrix3 *mT)
HYPAPI struct matrix4 * matrix4_identity(struct matrix4 *self)
HYPAPI struct vector2 * vector2_multiplym3(struct vector2 *self, const struct matrix3 *mT)
HYPAPI struct quaternion * quaternion_multiply(struct quaternion *self, const struct quaternion *qT)
HYPAPI HYP_FLOAT matrix3_determinant(const struct matrix3 *self)
static HYP_INLINE HYP_FLOAT HYP_MAX(HYP_FLOAT a, HYP_FLOAT b)
A macro that returns the maximum of a and b.
Definition: hypatia.h:110
HYPAPI struct matrix4 * matrix4_set_from_quaternion_EXP(struct matrix4 *self, const struct quaternion *qT)
HYPAPI struct matrix3 * matrix3_invert(struct matrix3 *self)
HYPAPI struct vector2 * vector2_subtractf(struct vector2 *self, HYP_FLOAT fT)
#define HYP_COT(a)
Definition: hypatia.h:275
HYPAPI struct vector3 * vector3_multiply(struct vector3 *self, const struct vector3 *vT)
HYPAPI struct quaternion * quaternion_conjugate(struct quaternion *self)
HYPAPI struct vector2 * vector2_setf2(struct vector2 *self, HYP_FLOAT xT, HYP_FLOAT yT)
HYPAPI struct matrix4 * matrix4_transformation_compose_EXP(struct matrix4 *self, const struct vector3 *scale, const struct quaternion *rotation, const struct vector3 *translation)
HYPAPI struct vector2 * matrix3_multiplyv2(const struct matrix3 *self, const struct vector2 *vT, struct vector2 *vR)
HYPAPI struct matrix3 * matrix3_zero(struct matrix3 *self)
HYPAPI struct quaternion * quaternion_lerp(const struct quaternion *start, const struct quaternion *end, HYP_FLOAT percent, struct quaternion *qR)
#define HYP_ATAN2(y, x)
Definition: hypatia.h:274
HYPAPI struct vector4 * vector4_dividef(struct vector4 *self, HYP_FLOAT fT)
HYPAPI struct vector4 * vector4_set(struct vector4 *self, const struct vector4 *vT)
static HYP_INLINE HYP_FLOAT HYP_ABS(HYP_FLOAT value)
A macro that returns the absolute value.
Definition: hypatia.h:149
HYPAPI struct matrix3 * matrix3_transpose(struct matrix3 *self)
HYPAPI struct matrix2 * matrix2_identity(struct matrix2 *self)
HYPAPI void quaternion_get_euler_anglesf3(const struct quaternion *self, HYP_FLOAT *ax, HYP_FLOAT *ay, HYP_FLOAT *az)
HYPAPI void _matrix2_print_with_rowcolumn_indexer(struct matrix2 *self)
static HYP_INLINE void HYP_SWAP(HYP_FLOAT *a, HYP_FLOAT *b)
A macro that swaps a and b.
Definition: hypatia.h:116
HYPAPI struct matrix2 * _matrix2_transpose_columnrow(struct matrix2 *self)
HYPAPI short scalar_equalsf(const HYP_FLOAT f1, const HYP_FLOAT f2)
HYPAPI HYP_FLOAT quaternion_dot_product(const struct quaternion *self, const struct quaternion *qT)
HYPAPI struct quaternion * quaternion_identity(struct quaternion *self)
HYPAPI struct quaternion * quaternion_rotate_by_axis_angle_EXP(struct quaternion *self, const struct vector3 *axis, HYP_FLOAT angle)
HYPAPI HYP_FLOAT vector2_dot_product(const struct vector2 *self, const struct vector2 *vT)
HYPAPI struct matrix2 * matrix2_make_transformation_rotationf_z(struct matrix2 *self, HYP_FLOAT angle)
HYPAPI struct vector2 * vector2_negate(struct vector2 *self)
HYPAPI struct matrix4 * matrix4_multiplyf(struct matrix4 *self, HYP_FLOAT scalar)
HYPAPI struct matrix4 * matrix4_set_from_axisf3_angle_EXP(struct matrix4 *self, HYP_FLOAT x, HYP_FLOAT y, HYP_FLOAT z, const HYP_FLOAT angle)
HYPAPI struct vector3 * vector3_dividef(struct vector3 *self, HYP_FLOAT fT)
HYPAPI HYP_FLOAT quaternion_difference_EXP(const struct quaternion *q1, const struct quaternion *q2)
HYPAPI struct matrix3 * matrix3_subtract(struct matrix3 *self, const struct matrix3 *mT)
HYPAPI struct matrix4 * matrix4_add(struct matrix4 *self, const struct matrix4 *mT)
HYPAPI struct matrix2 * matrix2_set(struct matrix2 *self, const struct matrix2 *mT)
#define HYP_FLOAT
Definition: hypatia.h:32
static HYP_INLINE HYP_FLOAT HYP_MIN(HYP_FLOAT a, HYP_FLOAT b)
A function that returns the minimum of a and b.
Definition: hypatia.h:104
HYPAPI struct quaternion * quaternion_set_from_euler_anglesf3(struct quaternion *self, HYP_FLOAT ax, HYP_FLOAT ay, HYP_FLOAT az)
HYPAPI struct vector3 * vector3_find_normal_axis_between(struct vector3 *vR, const struct vector3 *vT1, const struct vector3 *vT2)
HYPAPI struct vector2 * vector2_multiplym2(struct vector2 *self, const struct matrix2 *mT)
HYPAPI HYP_FLOAT vector2_distance(const struct vector2 *v1, const struct vector2 *v2)
HYPAPI struct vector4 * vector4_add(struct vector4 *self, const struct vector4 *vT)
HYPAPI short quaternion_is_unit(struct quaternion *self)
HYPAPI struct matrix2 * matrix2_invert(struct matrix2 *self)
HYPAPI struct matrix3 * _matrix3_set_random(struct matrix3 *self)
#define HYP_SIN(x)
Definition: hypatia.h:269
HYPAPI struct vector4 * vector4_negate(struct vector4 *self)
HYPAPI struct vector2 * vector2_dividef(struct vector2 *self, HYP_FLOAT fT)
HYPAPI struct matrix3 * matrix3_make_transformation_scalingv2(struct matrix3 *self, const struct vector2 *scale)
HYPAPI struct matrix4 * matrix4_subtract(struct matrix4 *self, const struct matrix4 *mT)
HYPAPI void _matrix2_print_with_columnrow_indexer(struct matrix2 *self)
HYPAPI struct matrix2 * matrix2_rotate(struct matrix2 *self, HYP_FLOAT angle)
HYPAPI struct vector4 * vector4_addf(struct vector4 *self, HYP_FLOAT fT)
HYPAPI struct matrix2 * matrix2_scalev2(struct matrix2 *self, const struct vector2 *scale)
HYPAPI HYP_FLOAT vector2_magnitude(const struct vector2 *self)
HYPAPI struct matrix3 * _matrix3_transpose_columnrow(struct matrix3 *self)
HYPAPI struct vector2 * vector2_find_normal_axis_between(struct vector2 *vR, const struct vector2 *vT1, const struct vector2 *vT2)
HYPAPI struct matrix2 * matrix2_multiply(struct matrix2 *self, const struct matrix2 *mT)
HYPAPI struct vector2 * vector2_normalize(struct vector2 *self)
static HYP_INLINE HYP_FLOAT HYP_CLAMP(HYP_FLOAT value, HYP_FLOAT start, HYP_FLOAT limit)
A macro that constrains the value between two limits a and b.
Definition: hypatia.h:161
HYPAPI struct matrix4 * matrix4_view_lookat_rh_EXP(struct matrix4 *self, const struct vector3 *eye, const struct vector3 *target, const struct vector3 *up)
HYPAPI void quaternion_axis_between_EXP(const struct quaternion *self, const struct quaternion *qT, struct quaternion *qR)
#define HYP_ASIN(x)
Definition: hypatia.h:272
HYPAPI struct vector4 * vector4_normalize(struct vector4 *self)
HYPAPI struct matrix4 * matrix4_make_transformation_rotationf_z(struct matrix4 *self, HYP_FLOAT angle)
HYPAPI struct matrix4 * matrix4_make_transformation_rotationv3_EXP(struct matrix4 *self, const struct vector3 *vR)
HYPAPI struct vector3 * vector3_normalize(struct vector3 *self)
HYPAPI int matrix4_equals(const struct matrix4 *self, const struct matrix4 *mT)
static HYP_INLINE HYP_FLOAT HYP_SQUARE(HYP_FLOAT number)
A macro that squares a value squared.
Definition: hypatia.h:138
HYPAPI struct matrix4 * matrix4_set_from_euler_anglesf3_EXP(struct matrix4 *self, const HYP_FLOAT x, const HYP_FLOAT y, const HYP_FLOAT z)
HYPAPI struct matrix4 * matrix4_set(struct matrix4 *self, const struct matrix4 *mT)
HYPAPI HYP_FLOAT vector3_magnitude(const struct vector3 *self)
HYPAPI struct vector2 * matrix2_multiplyv2(const struct matrix2 *self, const struct vector2 *vT, struct vector2 *vR)
static HYP_INLINE HYP_FLOAT HYP_WRAP(HYP_FLOAT value, HYP_FLOAT start, HYP_FLOAT limit)
A macro that wraps a value around and around in a range.
Definition: hypatia.h:155
HYPAPI void quaternion_get_axis_anglev3(const struct quaternion *self, struct vector3 *vR, HYP_FLOAT *angle)
HYPAPI struct matrix3 * matrix3_add(struct matrix3 *self, const struct matrix3 *mT)
HYPAPI struct vector2 * matrix4_multiplyv2(const struct matrix4 *self, const struct vector2 *vT, struct vector2 *vR)
HYPAPI struct matrix3 * matrix3_identity(struct matrix3 *self)
HYPAPI struct vector3 * matrix4_multiplyv3_EXP(const struct matrix4 *m, const struct vector3 *vT, struct vector3 *vR)
HYPAPI int matrix2_equals(const struct matrix2 *self, const struct matrix2 *mT)
HYPAPI struct vector3 * vector3_multiplym4(struct vector3 *self, const struct matrix4 *mT)
HYPAPI HYP_FLOAT quaternion_magnitude(const struct quaternion *self)
HYPAPI struct vector4 * vector4_multiply(struct vector4 *self, const struct vector4 *vT)
HYPAPI struct matrix3 * matrix3_make_transformation_rotationf_z(struct matrix3 *self, HYP_FLOAT angle)
HYPAPI struct vector3 * vector3_setf3(struct vector3 *self, HYP_FLOAT xT, HYP_FLOAT yT, HYP_FLOAT zT)
#define HYP_COS(x)
Definition: hypatia.h:270
HYPAPI struct vector2 * vector2_addf(struct vector2 *self, HYP_FLOAT fT)
HYPAPI struct matrix2 * matrix2_subtract(struct matrix2 *self, const struct matrix2 *mT)
HYPAPI struct quaternion * quaternion_rotate_by_euler_angles_EXP(struct quaternion *self, HYP_FLOAT ax, HYP_FLOAT ay, HYP_FLOAT az)
HYPAPI struct matrix2 * matrix2_inverse(const struct matrix2 *self, struct matrix2 *mR)
HYPAPI int vector4_equals(const struct vector4 *self, const struct vector4 *vT)
#define scalar_equals
Definition: hypatia.h:261
HYPAPI struct vector2 * vector2_zero(struct vector2 *self)
HYPAPI struct vector2 * vector2_set(struct vector2 *self, const struct vector2 *vT)
HYPAPI struct matrix4 * matrix4_make_transformation_rotationf_y(struct matrix4 *self, HYP_FLOAT angle)
HYPAPI struct matrix3 * matrix3_multiplyf(struct matrix3 *self, HYP_FLOAT scalar)
HYPAPI struct matrix3 * matrix3_make_transformation_translationv2(struct matrix3 *self, const struct vector2 *translation)
HYPAPI void _matrix3_print_with_columnrow_indexer(struct matrix3 *self)
HYPAPI struct quaternion * quaternion_set(struct quaternion *self, const struct quaternion *qT)
HYPAPI struct vector3 * vector3_reflect_by_quaternion(struct vector3 *self, const struct quaternion *qT)
HYPAPI struct vector3 * vector3_subtract(struct vector3 *self, const struct vector3 *vT)
HYPAPI struct vector4 * vector4_zero(struct vector4 *self)
HYPAPI struct matrix4 * matrix4_make_transformation_scalingv3(struct matrix4 *self, const struct vector3 *scale)
HYPAPI struct quaternion * quaternion_set_from_axis_anglef3(struct quaternion *self, HYP_FLOAT x, HYP_FLOAT y, HYP_FLOAT z, HYP_FLOAT angle)
HYPAPI void _vector4_print(const struct vector4 *self)
HYPAPI struct quaternion * quaternion_negate(struct quaternion *self)
HYPAPI struct quaternion quaternion_cross_product_EXP(const struct quaternion *self, const struct quaternion *vT)
HYPAPI struct quaternion * quaternion_multiplyf(struct quaternion *self, HYP_FLOAT f)
HYPAPI struct quaternion * quaternion_slerp(const struct quaternion *start, const struct quaternion *end, HYP_FLOAT percent, struct quaternion *qR)
HYPAPI struct matrix2 * _matrix2_set_random(struct matrix2 *self)
HYPAPI struct vector2 * vector2_multiply(struct vector2 *self, const struct vector2 *vT)
#define HYP_SQRT(number)
A macro that finds the square root of a value.
Definition: hypatia.h:145
HYPAPI HYP_FLOAT vector3_dot_product(const struct vector3 *self, const struct vector3 *vT)
HYPAPI struct vector3 * vector3_multiplyf(struct vector3 *self, HYP_FLOAT fT)
HYPAPI uint8_t matrix4_transformation_decompose_EXP(struct matrix4 *self, struct vector3 *scale, struct quaternion *rotation, struct vector3 *translation)
HYPAPI HYP_FLOAT vector2_angle_between(const struct vector2 *self, const struct vector2 *vT)
HYPAPI struct quaternion * quaternion_nlerp(const struct quaternion *start, const struct quaternion *end, HYP_FLOAT percent, struct quaternion *qR)
HYPAPI int vector3_equals(const struct vector3 *self, const struct vector3 *vT)
HYPAPI struct quaternion * quaternion_rotate_by_quaternion_EXP(struct quaternion *self, const struct quaternion *qT)
HYPAPI struct matrix4 * matrix4_translatev3(struct matrix4 *self, const struct vector3 *translation)
HYPAPI struct matrix2 * matrix2_transpose(struct matrix2 *self)
HYPAPI struct vector2 * vector2_cross_product(struct vector2 *vR, const struct vector2 *vT1, const struct vector2 *vT2)
HYPAPI struct quaternion * quaternion_multiplyv3(struct quaternion *self, const struct vector3 *vT)
HYPAPI struct matrix4 * matrix4_make_transformation_rotationq(struct matrix4 *self, const struct quaternion *qT)
HYPAPI struct matrix2 * matrix2_add(struct matrix2 *self, const struct matrix2 *mT)
HYPAPI struct vector4 * vector4_subtract(struct vector4 *self, const struct vector4 *vT)
HYPAPI struct matrix3 * matrix3_inverse(const struct matrix3 *self, struct matrix3 *mR)
HYPAPI struct matrix2 * _matrix2_transpose_rowcolumn(struct matrix2 *self)
HYPAPI struct matrix3 * matrix3_rotate(struct matrix3 *self, HYP_FLOAT angle)
HYPAPI HYP_FLOAT vector3_distance(const struct vector3 *v1, const struct vector3 *v2)
HYPAPI struct quaternion * quaternion_setf4(struct quaternion *self, HYP_FLOAT x, HYP_FLOAT y, HYP_FLOAT z, HYP_FLOAT w)
HYPAPI struct matrix2 * matrix2_make_transformation_scalingv2(struct matrix2 *self, const struct vector2 *scale)
#define HYP_EPSILON
Epsilon. This is the value that is used to determine how much rounding error is tolerated.
Definition: hypatia.h:92
HYPAPI struct vector3 * vector3_cross_product(struct vector3 *vR, const struct vector3 *vT1, const struct vector3 *vT2)
HYPAPI struct vector2 * vector2_subtract(struct vector2 *self, const struct vector2 *vT)
HYPAPI short quaternion_is_pure(struct quaternion *self)
HYPAPI HYP_FLOAT vector3_angle_between(const struct vector3 *self, const struct vector3 *vT)
HYPAPI struct matrix4 * matrix4_multiply(struct matrix4 *self, const struct matrix4 *mT)
HYPAPI struct vector3 * vector3_negate(struct vector3 *self)
HYPAPI struct quaternion * quaternion_add(struct quaternion *self, const struct quaternion *qT)
HYPAPI struct vector4 * vector4_setf4(struct vector4 *self, HYP_FLOAT xT, HYP_FLOAT yT, HYP_FLOAT zT, HYP_FLOAT wT)
HYPAPI short scalar_equals_epsilonf(const HYP_FLOAT f1, const HYP_FLOAT f2, const HYP_FLOAT epsilon)
HYPAPI HYP_FLOAT quaternion_angle_between_EXP(const struct quaternion *self, const struct quaternion *qT)
HYPAPI struct matrix3 * matrix3_multiply(struct matrix3 *self, const struct matrix3 *mT)
HYPAPI struct quaternion * quaternion_normalize(struct quaternion *self)
HYPAPI struct matrix3 * matrix3_scalev2(struct matrix3 *self, const struct vector2 *scale)
HYPAPI struct matrix3 * matrix3_set(struct matrix3 *self, const struct matrix3 *mT)
HYPAPI struct vector3 * matrix4_get_translation_EXP(const struct matrix4 *self, struct vector3 *vT)
HYPAPI struct matrix3 * _matrix3_transpose_rowcolumn(struct matrix3 *self)
HYPAPI struct quaternion * quaternion_inverse(struct quaternion *self)
HYPAPI struct quaternion * quaternion_subtract(struct quaternion *self, const struct quaternion *qT)
HYPAPI struct matrix4 * matrix4_set_from_axisv3_angle_EXP(struct matrix4 *self, const struct vector3 *axis, HYP_FLOAT angle)
HYPAPI struct vector2 * vector2_divide(struct vector2 *self, const struct vector2 *vT)
HYPAPI struct matrix4 * matrix4_make_transformation_rotationf_x(struct matrix4 *self, HYP_FLOAT angle)
HYPAPI struct vector3 * vector3_addf(struct vector3 *self, HYP_FLOAT fT)
HYPAPI struct vector2 * vector2_multiplyf(struct vector2 *self, HYP_FLOAT fT)
HYPAPI struct matrix4 * matrix4_zero(struct matrix4 *self)
HYPAPI struct quaternion * quaternion_set_from_axis_anglev3(struct quaternion *self, const struct vector3 *axis, HYP_FLOAT angle)
HYPAPI struct vector3 * matrix4_multiplyv3(const struct matrix4 *self, const struct vector3 *vT, struct vector3 *vR)
HYPAPI HYP_FLOAT quaternion_norm(const struct quaternion *self)
HYPAPI struct vector3 * vector3_zero(struct vector3 *self)
HYPAPI struct matrix4 * matrix4_rotatev3(struct matrix4 *self, const struct vector3 *axis, HYP_FLOAT angle)
HYPAPI struct matrix2 * matrix2_multiplyf(struct matrix2 *self, HYP_FLOAT scalar)
#define HYP_ACOS(x)
Definition: hypatia.h:273
HYPAPI struct vector4 * vector4_divide(struct vector4 *self, const struct vector4 *vT)
HYPAPI HYP_FLOAT vector4_dot_product(const struct vector4 *self, const struct vector4 *vT)
HYPAPI struct vector3 * vector3_subtractf(struct vector3 *self, HYP_FLOAT fT)
HYPAPI struct vector4 * vector4_cross_product(struct vector4 *vR, const struct vector4 *vT1, const struct vector4 *vT2)
HYPAPI struct matrix3 * matrix3_translatev2(struct matrix3 *self, const struct vector2 *translation)
HYPAPI HYP_FLOAT matrix4_determinant(const struct matrix4 *self)
HYPAPI void _matrix3_print_with_rowcolumn_indexer(struct matrix3 *self)
HYPAPI struct matrix4 * matrix4_projection_ortho3d_rh_EXP(struct matrix4 *self, HYP_FLOAT xmin, HYP_FLOAT xmax, HYP_FLOAT ymin, HYP_FLOAT ymax, HYP_FLOAT zNear, HYP_FLOAT zFar)
HYPAPI struct vector3 * vector3_set(struct vector3 *self, const struct vector3 *vT)
HYPAPI struct vector4 * vector4_subtractf(struct vector4 *self, HYP_FLOAT fT)
HYPAPI struct vector2 * vector2_add(struct vector2 *self, const struct vector2 *vT)
HYPAPI int quaternion_equals(const struct quaternion *self, const struct quaternion *vT)
HYPAPI struct quaternion * quaternion_get_rotation_tov3(const struct vector3 *from, const struct vector3 *to, struct quaternion *qR)
HYPAPI HYP_FLOAT vector4_magnitude(const struct vector4 *self)
HYPAPI HYP_FLOAT vector4_distance(const struct vector4 *v1, const struct vector4 *v2)
Definition: hypatia.h:455
HYP_FLOAT r01
Definition: hypatia.h:474
HYP_FLOAT c00
Definition: hypatia.h:469
HYP_FLOAT m[4]
Definition: hypatia.h:457
HYP_FLOAT c01
Definition: hypatia.h:470
HYP_FLOAT i03
Definition: hypatia.h:465
HYP_FLOAT r00
Definition: hypatia.h:474
HYP_FLOAT c10
Definition: hypatia.h:469
HYP_FLOAT r10
Definition: hypatia.h:475
HYP_FLOAT r11
Definition: hypatia.h:475
HYP_FLOAT c11
Definition: hypatia.h:470
HYP_FLOAT m22[2][2]
Definition: hypatia.h:460
HYP_FLOAT i01
Definition: hypatia.h:465
HYP_FLOAT i00
Definition: hypatia.h:464
HYP_FLOAT i02
Definition: hypatia.h:464
Definition: hypatia.h:543
HYP_FLOAT r02
Definition: hypatia.h:564
HYP_FLOAT r11
Definition: hypatia.h:565
HYP_FLOAT c22
Definition: hypatia.h:560
HYP_FLOAT i02
Definition: hypatia.h:554
HYP_FLOAT r21
Definition: hypatia.h:566
HYP_FLOAT r10
Definition: hypatia.h:565
HYP_FLOAT c11
Definition: hypatia.h:559
HYP_FLOAT m[9]
Definition: hypatia.h:545
HYP_FLOAT c21
Definition: hypatia.h:559
HYP_FLOAT r22
Definition: hypatia.h:566
HYP_FLOAT i05
Definition: hypatia.h:554
HYP_FLOAT i00
Definition: hypatia.h:552
HYP_FLOAT i06
Definition: hypatia.h:552
HYP_FLOAT r01
Definition: hypatia.h:564
HYP_FLOAT i08
Definition: hypatia.h:554
HYP_FLOAT c10
Definition: hypatia.h:558
HYP_FLOAT i04
Definition: hypatia.h:553
HYP_FLOAT r20
Definition: hypatia.h:566
HYP_FLOAT c02
Definition: hypatia.h:560
HYP_FLOAT c20
Definition: hypatia.h:558
HYP_FLOAT i07
Definition: hypatia.h:553
HYP_FLOAT i01
Definition: hypatia.h:553
HYP_FLOAT c00
Definition: hypatia.h:558
HYP_FLOAT c12
Definition: hypatia.h:560
HYP_FLOAT m33[3][3]
Definition: hypatia.h:548
HYP_FLOAT r00
Definition: hypatia.h:564
HYP_FLOAT r12
Definition: hypatia.h:565
HYP_FLOAT i03
Definition: hypatia.h:552
HYP_FLOAT c01
Definition: hypatia.h:559
Definition: hypatia.h:638
HYP_FLOAT r01
Definition: hypatia.h:661
HYP_FLOAT r20
Definition: hypatia.h:663
HYP_FLOAT c12
Definition: hypatia.h:656
HYP_FLOAT r30
Definition: hypatia.h:664
HYP_FLOAT i15
Definition: hypatia.h:650
HYP_FLOAT r33
Definition: hypatia.h:664
HYP_FLOAT i05
Definition: hypatia.h:648
HYP_FLOAT i07
Definition: hypatia.h:650
HYP_FLOAT r22
Definition: hypatia.h:663
HYP_FLOAT r03
Definition: hypatia.h:661
HYP_FLOAT i14
Definition: hypatia.h:649
HYP_FLOAT c21
Definition: hypatia.h:655
HYP_FLOAT c01
Definition: hypatia.h:655
HYP_FLOAT i11
Definition: hypatia.h:650
HYP_FLOAT c23
Definition: hypatia.h:657
HYP_FLOAT i09
Definition: hypatia.h:648
HYP_FLOAT c00
Definition: hypatia.h:654
HYP_FLOAT c03
Definition: hypatia.h:657
HYP_FLOAT r21
Definition: hypatia.h:663
HYP_FLOAT r13
Definition: hypatia.h:662
HYP_FLOAT i03
Definition: hypatia.h:650
HYP_FLOAT r12
Definition: hypatia.h:662
HYP_FLOAT i01
Definition: hypatia.h:648
HYP_FLOAT i00
Definition: hypatia.h:647
HYP_FLOAT r32
Definition: hypatia.h:664
HYP_FLOAT r00
Definition: hypatia.h:661
HYP_FLOAT r23
Definition: hypatia.h:663
HYP_FLOAT c10
Definition: hypatia.h:654
HYP_FLOAT c30
Definition: hypatia.h:654
HYP_FLOAT i06
Definition: hypatia.h:649
HYP_FLOAT c11
Definition: hypatia.h:655
HYP_FLOAT c20
Definition: hypatia.h:654
HYP_FLOAT r11
Definition: hypatia.h:662
HYP_FLOAT i12
Definition: hypatia.h:647
HYP_FLOAT c02
Definition: hypatia.h:656
HYP_FLOAT c13
Definition: hypatia.h:657
HYP_FLOAT m[16]
Definition: hypatia.h:640
HYP_FLOAT r10
Definition: hypatia.h:662
HYP_FLOAT c31
Definition: hypatia.h:655
HYP_FLOAT r31
Definition: hypatia.h:664
HYP_FLOAT r02
Definition: hypatia.h:661
HYP_FLOAT i02
Definition: hypatia.h:649
HYP_FLOAT i13
Definition: hypatia.h:648
HYP_FLOAT i08
Definition: hypatia.h:647
HYP_FLOAT c33
Definition: hypatia.h:657
HYP_FLOAT i04
Definition: hypatia.h:647
HYP_FLOAT c22
Definition: hypatia.h:656
HYP_FLOAT m44[4][4]
Definition: hypatia.h:643
HYP_FLOAT c32
Definition: hypatia.h:656
HYP_FLOAT i10
Definition: hypatia.h:649
Definition: hypatia.h:740
HYP_FLOAT x
Definition: hypatia.h:744
HYP_FLOAT q[4]
Definition: hypatia.h:742
HYP_FLOAT a
Definition: hypatia.h:747
HYP_FLOAT y
Definition: hypatia.h:744
HYP_FLOAT w
Definition: hypatia.h:744
HYP_FLOAT j
Definition: hypatia.h:747
HYP_FLOAT z
Definition: hypatia.h:744
HYP_FLOAT i
Definition: hypatia.h:747
HYP_FLOAT k
Definition: hypatia.h:747
Definition: hypatia.h:311
HYP_FLOAT y
Definition: hypatia.h:315
HYP_FLOAT x
Definition: hypatia.h:315
HYP_FLOAT v[2]
Definition: hypatia.h:313
Definition: hypatia.h:359
HYP_FLOAT pitch
Definition: hypatia.h:366
HYP_FLOAT roll
Definition: hypatia.h:366
HYP_FLOAT x
Definition: hypatia.h:363
HYP_FLOAT y
Definition: hypatia.h:363
HYP_FLOAT v[3]
Definition: hypatia.h:361
HYP_FLOAT z
Definition: hypatia.h:363
HYP_FLOAT yaw
Definition: hypatia.h:366
Definition: hypatia.h:412
HYP_FLOAT x
Definition: hypatia.h:416
HYP_FLOAT w
Definition: hypatia.h:416
HYP_FLOAT z
Definition: hypatia.h:416
HYP_FLOAT v[4]
Definition: hypatia.h:414
HYP_FLOAT y
Definition: hypatia.h:416