11#ifndef LINMATH_H
22#define LINMATH_H
33
4+ #include <string.h>
45#include <math.h>
56#include <string.h>
67
@@ -58,6 +59,12 @@ LINMATH_H_FUNC void vec##n##_max(vec##n r, vec##n const a, vec##n const b) \
5859 int i; \
5960 for(i=0; i<n; ++i) \
6061 r[i] = a[i]>b[i] ? a[i] : b[i]; \
62+ } \
63+ LINMATH_H_FUNC void vec##n##_dup(vec##n r, vec##n const src) \
64+ { \
65+ int i; \
66+ for(i=0; i<n; ++i) \
67+ r[i] = src[i]; \
6168}
6269
6370LINMATH_H_DEFINE_VEC (2 )
@@ -79,15 +86,15 @@ LINMATH_H_FUNC void vec3_reflect(vec3 r, vec3 const v, vec3 const n)
7986 r [i ] = v [i ] - p * n [i ];
8087}
8188
82- LINMATH_H_FUNC void vec4_mul_cross (vec4 r , vec4 a , vec4 b )
89+ LINMATH_H_FUNC void vec4_mul_cross (vec4 r , vec4 const a , vec4 const b )
8390{
8491 r [0 ] = a [1 ]* b [2 ] - a [2 ]* b [1 ];
8592 r [1 ] = a [2 ]* b [0 ] - a [0 ]* b [2 ];
8693 r [2 ] = a [0 ]* b [1 ] - a [1 ]* b [0 ];
8794 r [3 ] = 1.f ;
8895}
8996
90- LINMATH_H_FUNC void vec4_reflect (vec4 r , vec4 v , vec4 n )
97+ LINMATH_H_FUNC void vec4_reflect (vec4 r , vec4 const v , vec4 const n )
9198{
9299 float p = 2.f * vec4_mul_inner (v , n );
93100 int i ;
@@ -103,61 +110,59 @@ LINMATH_H_FUNC void mat4x4_identity(mat4x4 M)
103110 for (j = 0 ; j < 4 ; ++ j )
104111 M [i ][j ] = i == j ? 1.f : 0.f ;
105112}
106- LINMATH_H_FUNC void mat4x4_dup (mat4x4 M , mat4x4 N )
113+ LINMATH_H_FUNC void mat4x4_dup (mat4x4 M , mat4x4 const N )
107114{
108- int i , j ;
115+ int i ;
109116 for (i = 0 ; i < 4 ; ++ i )
110- for (j = 0 ; j < 4 ; ++ j )
111- M [i ][j ] = N [i ][j ];
117+ vec4_dup (M [i ], N [i ]);
112118}
113- LINMATH_H_FUNC void mat4x4_row (vec4 r , mat4x4 M , int i )
119+ LINMATH_H_FUNC void mat4x4_row (vec4 r , mat4x4 const M , int i )
114120{
115121 int k ;
116122 for (k = 0 ; k < 4 ; ++ k )
117123 r [k ] = M [k ][i ];
118124}
119- LINMATH_H_FUNC void mat4x4_col (vec4 r , mat4x4 M , int i )
125+ LINMATH_H_FUNC void mat4x4_col (vec4 r , mat4x4 const M , int i )
120126{
121127 int k ;
122128 for (k = 0 ; k < 4 ; ++ k )
123129 r [k ] = M [i ][k ];
124130}
125- LINMATH_H_FUNC void mat4x4_transpose (mat4x4 M , mat4x4 N )
131+ LINMATH_H_FUNC void mat4x4_transpose (mat4x4 M , mat4x4 const N )
126132{
133+ // Note: if M and N are the same, the user has to
134+ // explicitly make a copy of M and set it to N.
127135 int i , j ;
128136 for (j = 0 ; j < 4 ; ++ j )
129137 for (i = 0 ; i < 4 ; ++ i )
130138 M [i ][j ] = N [j ][i ];
131139}
132- LINMATH_H_FUNC void mat4x4_add (mat4x4 M , mat4x4 a , mat4x4 b )
140+ LINMATH_H_FUNC void mat4x4_add (mat4x4 M , mat4x4 const a , mat4x4 const b )
133141{
134142 int i ;
135143 for (i = 0 ; i < 4 ; ++ i )
136144 vec4_add (M [i ], a [i ], b [i ]);
137145}
138- LINMATH_H_FUNC void mat4x4_sub (mat4x4 M , mat4x4 a , mat4x4 b )
146+ LINMATH_H_FUNC void mat4x4_sub (mat4x4 M , mat4x4 const a , mat4x4 const b )
139147{
140148 int i ;
141149 for (i = 0 ; i < 4 ; ++ i )
142150 vec4_sub (M [i ], a [i ], b [i ]);
143151}
144- LINMATH_H_FUNC void mat4x4_scale (mat4x4 M , mat4x4 a , float k )
152+ LINMATH_H_FUNC void mat4x4_scale (mat4x4 M , mat4x4 const a , float k )
145153{
146154 int i ;
147155 for (i = 0 ; i < 4 ; ++ i )
148156 vec4_scale (M [i ], a [i ], k );
149157}
150- LINMATH_H_FUNC void mat4x4_scale_aniso (mat4x4 M , mat4x4 a , float x , float y , float z )
158+ LINMATH_H_FUNC void mat4x4_scale_aniso (mat4x4 M , mat4x4 const a , float x , float y , float z )
151159{
152- int i ;
153160 vec4_scale (M [0 ], a [0 ], x );
154161 vec4_scale (M [1 ], a [1 ], y );
155162 vec4_scale (M [2 ], a [2 ], z );
156- for (i = 0 ; i < 4 ; ++ i ) {
157- M [3 ][i ] = a [3 ][i ];
158- }
163+ vec4_dup (M [3 ], a [3 ]);
159164}
160- LINMATH_H_FUNC void mat4x4_mul (mat4x4 M , mat4x4 a , mat4x4 b )
165+ LINMATH_H_FUNC void mat4x4_mul (mat4x4 M , mat4x4 const a , mat4x4 const b )
161166{
162167 mat4x4 temp ;
163168 int k , r , c ;
@@ -168,7 +173,7 @@ LINMATH_H_FUNC void mat4x4_mul(mat4x4 M, mat4x4 a, mat4x4 b)
168173 }
169174 mat4x4_dup (M , temp );
170175}
171- LINMATH_H_FUNC void mat4x4_mul_vec4 (vec4 r , mat4x4 M , vec4 v )
176+ LINMATH_H_FUNC void mat4x4_mul_vec4 (vec4 r , mat4x4 const M , vec4 const v )
172177{
173178 int i , j ;
174179 for (j = 0 ; j < 4 ; ++ j ) {
@@ -194,13 +199,13 @@ LINMATH_H_FUNC void mat4x4_translate_in_place(mat4x4 M, float x, float y, float
194199 M [3 ][i ] += vec4_mul_inner (r , t );
195200 }
196201}
197- LINMATH_H_FUNC void mat4x4_from_vec3_mul_outer (mat4x4 M , vec3 a , vec3 b )
202+ LINMATH_H_FUNC void mat4x4_from_vec3_mul_outer (mat4x4 M , vec3 const a , vec3 const b )
198203{
199204 int i , j ;
200205 for (i = 0 ; i < 4 ; ++ i ) for (j = 0 ; j < 4 ; ++ j )
201206 M [i ][j ] = i < 3 && j < 3 ? a [i ] * b [j ] : 0.f ;
202207}
203- LINMATH_H_FUNC void mat4x4_rotate (mat4x4 R , mat4x4 M , float x , float y , float z , float angle )
208+ LINMATH_H_FUNC void mat4x4_rotate (mat4x4 R , mat4x4 const M , float x , float y , float z , float angle )
204209{
205210 float s = sinf (angle );
206211 float c = cosf (angle );
@@ -228,13 +233,13 @@ LINMATH_H_FUNC void mat4x4_rotate(mat4x4 R, mat4x4 M, float x, float y, float z,
228233 mat4x4_add (T , T , C );
229234 mat4x4_add (T , T , S );
230235
231- T [3 ][3 ] = 1. ;
236+ T [3 ][3 ] = 1.f ;
232237 mat4x4_mul (R , M , T );
233238 } else {
234239 mat4x4_dup (R , M );
235240 }
236241}
237- LINMATH_H_FUNC void mat4x4_rotate_X (mat4x4 Q , mat4x4 M , float angle )
242+ LINMATH_H_FUNC void mat4x4_rotate_X (mat4x4 Q , mat4x4 const M , float angle )
238243{
239244 float s = sinf (angle );
240245 float c = cosf (angle );
@@ -246,7 +251,7 @@ LINMATH_H_FUNC void mat4x4_rotate_X(mat4x4 Q, mat4x4 M, float angle)
246251 };
247252 mat4x4_mul (Q , M , R );
248253}
249- LINMATH_H_FUNC void mat4x4_rotate_Y (mat4x4 Q , mat4x4 M , float angle )
254+ LINMATH_H_FUNC void mat4x4_rotate_Y (mat4x4 Q , mat4x4 const M , float angle )
250255{
251256 float s = sinf (angle );
252257 float c = cosf (angle );
@@ -258,7 +263,7 @@ LINMATH_H_FUNC void mat4x4_rotate_Y(mat4x4 Q, mat4x4 M, float angle)
258263 };
259264 mat4x4_mul (Q , M , R );
260265}
261- LINMATH_H_FUNC void mat4x4_rotate_Z (mat4x4 Q , mat4x4 M , float angle )
266+ LINMATH_H_FUNC void mat4x4_rotate_Z (mat4x4 Q , mat4x4 const M , float angle )
262267{
263268 float s = sinf (angle );
264269 float c = cosf (angle );
@@ -270,7 +275,7 @@ LINMATH_H_FUNC void mat4x4_rotate_Z(mat4x4 Q, mat4x4 M, float angle)
270275 };
271276 mat4x4_mul (Q , M , R );
272277}
273- LINMATH_H_FUNC void mat4x4_invert (mat4x4 T , mat4x4 M )
278+ LINMATH_H_FUNC void mat4x4_invert (mat4x4 T , mat4x4 const M )
274279{
275280 float s [6 ];
276281 float c [6 ];
@@ -311,10 +316,10 @@ LINMATH_H_FUNC void mat4x4_invert(mat4x4 T, mat4x4 M)
311316 T [3 ][2 ] = (- M [3 ][0 ] * s [3 ] + M [3 ][1 ] * s [1 ] - M [3 ][2 ] * s [0 ]) * idet ;
312317 T [3 ][3 ] = ( M [2 ][0 ] * s [3 ] - M [2 ][1 ] * s [1 ] + M [2 ][2 ] * s [0 ]) * idet ;
313318}
314- LINMATH_H_FUNC void mat4x4_orthonormalize (mat4x4 R , mat4x4 M )
319+ LINMATH_H_FUNC void mat4x4_orthonormalize (mat4x4 R , mat4x4 const M )
315320{
316321 mat4x4_dup (R , M );
317- float s = 1. ;
322+ float s = 1.f ;
318323 vec3 h ;
319324
320325 vec3_norm (R [2 ], R [2 ]);
@@ -370,7 +375,7 @@ LINMATH_H_FUNC void mat4x4_perspective(mat4x4 m, float y_fov, float aspect, floa
370375{
371376 /* NOTE: Degrees are an unhandy unit to work with.
372377 * linmath.h uses radians for everything! */
373- float const a = 1.f / tan (y_fov / 2.f );
378+ float const a = 1.f / tanf (y_fov / 2.f );
374379
375380 m [0 ][0 ] = a / aspect ;
376381 m [0 ][1 ] = 0.f ;
@@ -392,7 +397,7 @@ LINMATH_H_FUNC void mat4x4_perspective(mat4x4 m, float y_fov, float aspect, floa
392397 m [3 ][2 ] = - ((2.f * f * n ) / (f - n ));
393398 m [3 ][3 ] = 0.f ;
394399}
395- LINMATH_H_FUNC void mat4x4_look_at (mat4x4 m , vec3 eye , vec3 center , vec3 up )
400+ LINMATH_H_FUNC void mat4x4_look_at (mat4x4 m , vec3 const eye , vec3 const center , vec3 const up )
396401{
397402 /* Adapted from Android's OpenGL Matrix.java. */
398403 /* See the OpenGL GLUT documentation for gluLookAt for a description */
@@ -435,24 +440,18 @@ LINMATH_H_FUNC void mat4x4_look_at(mat4x4 m, vec3 eye, vec3 center, vec3 up)
435440}
436441
437442typedef float quat [4 ];
443+ #define quat_add vec4_add
444+ #define quat_sub vec4_sub
445+ #define quat_norm vec4_norm
446+ #define quat_scale vec4_scale
447+ #define quat_mul_inner vec4_mul_inner
448+
438449LINMATH_H_FUNC void quat_identity (quat q )
439450{
440451 q [0 ] = q [1 ] = q [2 ] = 0.f ;
441452 q [3 ] = 1.f ;
442453}
443- LINMATH_H_FUNC void quat_add (quat r , quat a , quat b )
444- {
445- int i ;
446- for (i = 0 ; i < 4 ; ++ i )
447- r [i ] = a [i ] + b [i ];
448- }
449- LINMATH_H_FUNC void quat_sub (quat r , quat a , quat b )
450- {
451- int i ;
452- for (i = 0 ; i < 4 ; ++ i )
453- r [i ] = a [i ] - b [i ];
454- }
455- LINMATH_H_FUNC void quat_mul (quat r , quat p , quat q )
454+ LINMATH_H_FUNC void quat_mul (quat r , quat const p , quat const q )
456455{
457456 vec3 w ;
458457 vec3_mul_cross (r , p , q );
@@ -462,37 +461,22 @@ LINMATH_H_FUNC void quat_mul(quat r, quat p, quat q)
462461 vec3_add (r , r , w );
463462 r [3 ] = p [3 ]* q [3 ] - vec3_mul_inner (p , q );
464463}
465- LINMATH_H_FUNC void quat_scale (quat r , quat v , float s )
466- {
467- int i ;
468- for (i = 0 ; i < 4 ; ++ i )
469- r [i ] = v [i ] * s ;
470- }
471- LINMATH_H_FUNC float quat_inner_product (quat a , quat b )
472- {
473- float p = 0.f ;
474- int i ;
475- for (i = 0 ; i < 4 ; ++ i )
476- p += b [i ]* a [i ];
477- return p ;
478- }
479- LINMATH_H_FUNC void quat_conj (quat r , quat q )
464+ LINMATH_H_FUNC void quat_conj (quat r , quat const q )
480465{
481466 int i ;
482467 for (i = 0 ; i < 3 ; ++ i )
483468 r [i ] = - q [i ];
484469 r [3 ] = q [3 ];
485470}
486- LINMATH_H_FUNC void quat_rotate (quat r , float angle , vec3 axis ) {
487- vec3 v ;
488- vec3_scale ( v , axis , sinf ( angle / 2 ) );
489- int i ;
490- for ( i = 0 ; i < 3 ; ++ i )
491- r [ i ] = v [ i ] ;
492- r [3 ] = cosf ( angle / 2 ) ;
471+ LINMATH_H_FUNC void quat_rotate (quat r , float angle , vec3 const axis ) {
472+ vec3 axis_norm ;
473+ vec3_norm ( axis_norm , axis );
474+ float s = sinf ( angle / 2 ) ;
475+ float c = cosf ( angle / 2 );
476+ vec3_scale ( r , axis_norm , s ) ;
477+ r [3 ] = c ;
493478}
494- #define quat_norm vec4_norm
495- LINMATH_H_FUNC void quat_mul_vec3 (vec3 r , quat q , vec3 v )
479+ LINMATH_H_FUNC void quat_mul_vec3 (vec3 r , quat const q , vec3 const v )
496480{
497481/*
498482 * Method by Fabian 'ryg' Giessen (of Farbrausch)
@@ -512,7 +496,7 @@ v' = v + q.w * t + cross(q.xyz, t)
512496 vec3_add (r , v , t );
513497 vec3_add (r , r , u );
514498}
515- LINMATH_H_FUNC void mat4x4_from_quat (mat4x4 M , quat q )
499+ LINMATH_H_FUNC void mat4x4_from_quat (mat4x4 M , quat const q )
516500{
517501 float a = q [3 ];
518502 float b = q [0 ];
@@ -542,18 +526,21 @@ LINMATH_H_FUNC void mat4x4_from_quat(mat4x4 M, quat q)
542526 M [3 ][3 ] = 1.f ;
543527}
544528
545- LINMATH_H_FUNC void mat4x4o_mul_quat (mat4x4 R , mat4x4 M , quat q )
529+ LINMATH_H_FUNC void mat4x4o_mul_quat (mat4x4 R , mat4x4 const M , quat const q )
546530{
547- /* XXX: The way this is written only works for othogonal matrices. */
531+ /* XXX: The way this is written only works for orthogonal matrices. */
548532/* TODO: Take care of non-orthogonal case. */
549533 quat_mul_vec3 (R [0 ], q , M [0 ]);
550534 quat_mul_vec3 (R [1 ], q , M [1 ]);
551535 quat_mul_vec3 (R [2 ], q , M [2 ]);
552536
553537 R [3 ][0 ] = R [3 ][1 ] = R [3 ][2 ] = 0.f ;
554- R [3 ][3 ] = 1.f ;
538+ R [0 ][3 ] = M [0 ][3 ];
539+ R [1 ][3 ] = M [1 ][3 ];
540+ R [2 ][3 ] = M [2 ][3 ];
541+ R [3 ][3 ] = M [3 ][3 ]; // typically 1.0, but here we make it general
555542}
556- LINMATH_H_FUNC void quat_from_mat4x4 (quat q , mat4x4 M )
543+ LINMATH_H_FUNC void quat_from_mat4x4 (quat q , mat4x4 const M )
557544{
558545 float r = 0.f ;
559546 int i ;
@@ -583,7 +570,7 @@ LINMATH_H_FUNC void quat_from_mat4x4(quat q, mat4x4 M)
583570 q [3 ] = (M [p [2 ]][p [1 ]] - M [p [1 ]][p [2 ]])/(2.f * r );
584571}
585572
586- LINMATH_H_FUNC void mat4x4_arcball (mat4x4 R , mat4x4 M , vec2 _a , vec2 _b , float s )
573+ LINMATH_H_FUNC void mat4x4_arcball (mat4x4 R , mat4x4 const M , vec2 const _a , vec2 const _b , float s )
587574{
588575 vec2 a ; memcpy (a , _a , sizeof (a ));
589576 vec2 b ; memcpy (b , _b , sizeof (b ));
0 commit comments