Merge branch 'master' into blender2.8
[blender.git] / source / blender / blenlib / BLI_math_matrix.h
1 /*
2  * ***** BEGIN GPL LICENSE BLOCK *****
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License
6  * as published by the Free Software Foundation; either version 2
7  * of the License, or (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software Foundation,
16  * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
17  *
18  * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV.
19  * All rights reserved.
20
21  * The Original Code is: some of this file.
22  *
23  * ***** END GPL LICENSE BLOCK *****
24  * */
25
26 #ifndef __BLI_MATH_MATRIX_H__
27 #define __BLI_MATH_MATRIX_H__
28
29 /** \file BLI_math_matrix.h
30  *  \ingroup bli
31  */
32
33 #ifdef __cplusplus
34 extern "C" {
35 #endif
36
37 #include "BLI_compiler_attrs.h"
38
39 /********************************* Init **************************************/
40
41 void zero_m2(float R[2][2]);
42 void zero_m3(float R[3][3]);
43 void zero_m4(float R[4][4]);
44
45 void unit_m2(float R[2][2]);
46 void unit_m3(float R[3][3]);
47 void unit_m4(float R[4][4]);
48
49 void copy_m2_m2(float R[2][2], const float A[2][2]);
50 void copy_m3_m3(float R[3][3], const float A[3][3]);
51 void copy_m4_m4(float R[4][4], const float A[4][4]);
52 void copy_m3_m4(float R[3][3], const float A[4][4]);
53 void copy_m4_m3(float R[4][4], const float A[3][3]);
54
55 /* double->float */
56 void copy_m3_m3d(float R[3][3], const double A[3][3]);
57
58 void swap_m3m3(float A[3][3], float B[3][3]);
59 void swap_m4m4(float A[4][4], float B[4][4]);
60
61 /******************************** Arithmetic *********************************/
62
63 void add_m3_m3m3(float R[3][3], const float A[3][3], const float B[3][3]);
64 void add_m4_m4m4(float R[4][4], const float A[4][4], const float B[4][4]);
65
66 void sub_m3_m3m3(float R[3][3], const float A[3][3], const float B[3][3]);
67 void sub_m4_m4m4(float R[4][4], const float A[4][4], const float B[4][4]);
68
69 void mul_m3_m3m3(float R[3][3], const float A[3][3], const float B[3][3]);
70 void mul_m4_m3m4(float R[4][4], const float A[3][3], const float B[4][4]);
71 void mul_m4_m4m3(float R[4][4], const float A[4][4], const float B[3][3]);
72 void mul_m4_m4m4(float R[4][4], const float A[4][4], const float B[4][4]);
73 void mul_m3_m3m4(float R[3][3], const float A[4][4], const float B[3][3]);
74
75 /* special matrix multiplies
76  * uniq: R <-- AB, R is neither A nor B
77  * pre:  R <-- AR
78  * post: R <-- RB
79  */
80 void mul_m3_m3m3_uniq(float R[3][3], const float A[3][3], const float B[3][3]);
81 void mul_m3_m3_pre(float R[3][3], const float A[3][3]);
82 void mul_m3_m3_post(float R[3][3], const float B[3][3]);
83 void mul_m4_m4m4_uniq(float R[4][4], const float A[4][4], const float B[4][4]);
84 void mul_m4_m4_pre(float R[4][4], const float A[4][4]);
85 void mul_m4_m4_post(float R[4][4], const float B[4][4]);
86
87 /* mul_m3_series */
88 void _va_mul_m3_series_3(
89         float R[3][3], const float M1[3][3], const float M2[3][3]) ATTR_NONNULL();
90 void _va_mul_m3_series_4(
91         float R[3][3], const float M1[3][3], const float M2[3][3], const float M3[3][3]) ATTR_NONNULL();
92 void _va_mul_m3_series_5(
93         float R[3][3], const float M1[3][3], const float M2[3][3], const float M3[3][3],
94         const float M4[3][3]) ATTR_NONNULL();
95 void _va_mul_m3_series_6(
96         float R[3][3], const float M1[3][3], const float M2[3][3], const float M3[3][3],
97         const float M4[3][3], const float M5[3][3]) ATTR_NONNULL();
98 void _va_mul_m3_series_7(
99         float R[3][3], const float M1[3][3], const float M2[3][3], const float M3[3][3],
100         const float M4[3][3], const float M5[3][3], const float M6[3][3]) ATTR_NONNULL();
101 void _va_mul_m3_series_8(
102         float R[3][3], const float M1[3][3], const float M2[3][3], const float M3[3][3],
103         const float M4[3][3], const float M5[3][3], const float M6[3][3], const float M7[3][3]) ATTR_NONNULL();
104 void _va_mul_m3_series_9(
105         float R[3][3], const float M1[3][3], const float M2[3][3], const float M3[3][3],
106         const float M4[3][3], const float M5[3][3], const float M6[3][3], const float M7[3][3],
107         const float M8[3][3]) ATTR_NONNULL();
108 /* mul_m4_series */
109 void _va_mul_m4_series_3(
110         float R[4][4], const float M1[4][4], const float M2[4][4]) ATTR_NONNULL();
111 void _va_mul_m4_series_4(
112         float R[4][4], const float M1[4][4], const float M2[4][4], const float M3[4][4]) ATTR_NONNULL();
113 void _va_mul_m4_series_5(
114         float R[4][4], const float M1[4][4], const float M2[4][4], const float M3[4][4],
115         const float M4[4][4]) ATTR_NONNULL();
116 void _va_mul_m4_series_6(
117         float R[4][4], const float M1[4][4], const float M2[4][4], const float M3[4][4],
118         const float M4[4][4], const float M5[4][4]) ATTR_NONNULL();
119 void _va_mul_m4_series_7(
120         float R[4][4], const float M1[4][4], const float M2[4][4], const float M3[4][4],
121         const float M4[4][4], const float M5[4][4], const float M6[4][4]) ATTR_NONNULL();
122 void _va_mul_m4_series_8(
123         float R[4][4], const float M1[4][4], const float M2[4][4], const float M3[4][4],
124         const float M4[4][4], const float M5[4][4], const float M6[4][4], const float M7[4][4]) ATTR_NONNULL();
125 void _va_mul_m4_series_9(
126         float R[4][4], const float M1[4][4], const float M2[4][4], const float M3[4][4],
127         const float M4[4][4], const float M5[4][4], const float M6[4][4], const float M7[4][4],
128         const float M8[4][4]) ATTR_NONNULL();
129
130 #define mul_m3_series(...) VA_NARGS_CALL_OVERLOAD(_va_mul_m3_series_, __VA_ARGS__)
131 #define mul_m4_series(...) VA_NARGS_CALL_OVERLOAD(_va_mul_m4_series_, __VA_ARGS__)
132
133 void mul_m4_v3(const float M[4][4], float r[3]);
134 void mul_v3_m4v3(float r[3], const float M[4][4], const float v[3]);
135 void mul_v2_m4v3(float r[2], const float M[4][4], const float v[3]);
136 void mul_v2_m2v2(float r[2], const float M[2][2], const float v[2]);
137 void mul_m2v2(const float M[2][2], float v[2]);
138 void mul_mat3_m4_v3(const float M[4][4], float r[3]);
139 void mul_v3_mat3_m4v3(float r[3], const float M[4][4], const float v[3]);
140 void mul_m4_v4(const float M[4][4], float r[4]);
141 void mul_v4_m4v4(float r[4], const float M[4][4], const float v[4]);
142 void mul_v4_m4v3(float r[4], const float M[4][4], const float v[3]); /* v has implicit w = 1.0f */
143 void mul_project_m4_v3(const float M[4][4], float vec[3]);
144 void mul_v3_project_m4_v3(float r[3], const float mat[4][4], const float vec[3]);
145 void mul_v2_project_m4_v3(float r[2], const float M[4][4], const float vec[3]);
146
147 void mul_m3_v2(const float m[3][3], float r[2]);
148 void mul_v2_m3v2(float r[2], const float m[3][3], const float v[2]);
149 void mul_m3_v3(const float M[3][3], float r[3]);
150 void mul_v3_m3v3(float r[3], const float M[3][3], const float a[3]);
151 void mul_v2_m3v3(float r[2], const float M[3][3], const float a[3]);
152 void mul_transposed_m3_v3(const float M[3][3], float r[3]);
153 void mul_transposed_mat3_m4_v3(const float M[4][4], float r[3]);
154 void mul_m3_v3_double(const float M[3][3], double r[3]);
155
156 void mul_m3_fl(float R[3][3], float f);
157 void mul_m4_fl(float R[4][4], float f);
158 void mul_mat3_m4_fl(float R[4][4], float f);
159
160 void negate_m3(float R[3][3]);
161 void negate_mat3_m4(float R[4][4]);
162 void negate_m4(float R[4][4]);
163
164 bool invert_m3_ex(float m[3][3], const float epsilon);
165 bool invert_m3_m3_ex(float m1[3][3], const float m2[3][3], const float epsilon);
166
167 bool invert_m3(float R[3][3]);
168 bool invert_m3_m3(float R[3][3], const float A[3][3]);
169 bool invert_m4(float R[4][4]);
170 bool invert_m4_m4(float R[4][4], const float A[4][4]);
171
172 /* double arithmetic (mixed float/double) */
173 void mul_m4_v4d(const float M[4][4], double r[4]);
174 void mul_v4d_m4v4d(double r[4], const float M[4][4], const double v[4]);
175
176 /* double matrix functions (no mixing types) */
177 void mul_v3_m3v3_db(double r[3], const double M[3][3], const double a[3]);
178 void mul_m3_v3_db(const double M[3][3], double r[3]);
179
180
181 /****************************** Linear Algebra *******************************/
182
183 void transpose_m3(float R[3][3]);
184 void transpose_m3_m3(float R[3][3], const float A[3][3]);
185 void transpose_m3_m4(float R[3][3], const float A[4][4]);
186 void transpose_m4(float R[4][4]);
187 void transpose_m4_m4(float R[4][4], const float A[4][4]);
188
189 int compare_m4m4(const float mat1[4][4], const float mat2[4][4], float limit);
190
191 void normalize_m3_ex(float R[3][3], float r_scale[3]) ATTR_NONNULL();
192 void normalize_m3(float R[3][3]) ATTR_NONNULL();
193 void normalize_m3_m3_ex(float R[3][3], const float A[3][3], float r_scale[3]) ATTR_NONNULL();
194 void normalize_m3_m3(float R[3][3], const float A[3][3]) ATTR_NONNULL();
195 void normalize_m4_ex(float R[4][4], float r_scale[3]) ATTR_NONNULL();
196 void normalize_m4(float R[4][4]) ATTR_NONNULL();
197 void normalize_m4_m4_ex(float R[4][4], const float A[4][4], float r_scale[3]) ATTR_NONNULL();
198 void normalize_m4_m4(float R[4][4], const float A[4][4]) ATTR_NONNULL();
199
200 void orthogonalize_m3(float R[3][3], int axis);
201 void orthogonalize_m4(float R[4][4], int axis);
202
203 bool is_orthogonal_m3(const float mat[3][3]);
204 bool is_orthogonal_m4(const float mat[4][4]);
205 bool is_orthonormal_m3(const float mat[3][3]);
206 bool is_orthonormal_m4(const float mat[4][4]);
207
208 bool is_uniform_scaled_m3(const float mat[3][3]);
209 bool is_uniform_scaled_m4(const float m[4][4]);
210
211 /* Note: 'adjoint' here means the adjugate (adjunct, "classical adjoint") matrix!
212  * Nowadays 'adjoint' usually refers to the conjugate transpose,
213  * which for real-valued matrices is simply the transpose.
214  */
215 void adjoint_m2_m2(float R[2][2], const float A[2][2]);
216 void adjoint_m3_m3(float R[3][3], const float A[3][3]);
217 void adjoint_m4_m4(float R[4][4], const float A[4][4]);
218
219 float determinant_m2(float a, float b,
220                      float c, float d);
221 float determinant_m3(float a, float b, float c,
222                      float d, float e, float f,
223                      float g, float h, float i);
224 float determinant_m3_array(const float m[3][3]);
225 float determinant_m4(const float A[4][4]);
226
227 #define PSEUDOINVERSE_EPSILON 1e-8f
228
229 void svd_m4(float U[4][4], float s[4], float V[4][4], float A[4][4]);
230 void pseudoinverse_m4_m4(float Ainv[4][4], const float A[4][4], float epsilon);
231 void pseudoinverse_m3_m3(float Ainv[3][3], const float A[3][3], float epsilon);
232
233 bool has_zero_axis_m4(const float matrix[4][4]);
234
235 void invert_m4_m4_safe(float Ainv[4][4], const float A[4][4]);
236
237 /****************************** Transformations ******************************/
238
239 void scale_m3_fl(float R[3][3], float scale);
240 void scale_m4_fl(float R[4][4], float scale);
241
242 float mat3_to_scale(const float M[3][3]);
243 float mat4_to_scale(const float M[4][4]);
244 float mat4_to_xy_scale(const float M[4][4]);
245
246 void size_to_mat3(float R[3][3], const float size[3]);
247 void size_to_mat4(float R[4][4], const float size[3]);
248
249 void mat3_to_size(float r[3], const float M[3][3]);
250 void mat4_to_size(float r[3], const float M[4][4]);
251
252 void translate_m4(float mat[4][4], float tx, float ty, float tz);
253 void rotate_m4(float mat[4][4], const char axis, const float angle);
254 void transform_pivot_set_m4(float mat[4][4], const float pivot[3]);
255
256 void mat3_to_rot_size(float rot[3][3], float size[3], const float mat3[3][3]);
257 void mat4_to_loc_rot_size(float loc[3], float rot[3][3], float size[3], const float wmat[4][4]);
258 void mat4_to_loc_quat(float loc[3], float quat[4], const float wmat[4][4]);
259 void mat4_decompose(float loc[3], float quat[4], float size[3], const float wmat[4][4]);
260
261 void mat3_polar_decompose(const float mat3[3][3], float r_U[3][3], float r_P[3][3]);
262
263 void loc_eul_size_to_mat4(float R[4][4],
264                           const float loc[3], const float eul[3], const float size[3]);
265 void loc_eulO_size_to_mat4(float R[4][4],
266                            const float loc[3], const float eul[3], const float size[3], const short order);
267 void loc_quat_size_to_mat4(float R[4][4],
268                            const float loc[3], const float quat[4], const float size[3]);
269 void loc_axisangle_size_to_mat4(float R[4][4],
270                                 const float loc[3], const float axis[4], const float angle, const float size[3]);
271
272 void blend_m3_m3m3(float R[3][3], const float A[3][3], const float B[3][3], const float t);
273 void blend_m4_m4m4(float R[4][4], const float A[4][4], const float B[4][4], const float t);
274
275 void interp_m3_m3m3(float R[3][3], const float A[3][3], const float B[3][3], const float t);
276 void interp_m4_m4m4(float R[4][4], const float A[4][4], const float B[4][4], const float t);
277
278 bool is_negative_m3(const float mat[3][3]);
279 bool is_negative_m4(const float mat[4][4]);
280
281 bool is_zero_m3(const float mat[3][3]);
282 bool is_zero_m4(const float mat[4][4]);
283
284 bool equals_m3m3(const float mat1[3][3], const float mat2[3][3]);
285 bool equals_m4m4(const float mat1[4][4], const float mat2[4][4]);
286
287 /* SpaceTransform helper */
288 typedef struct SpaceTransform {
289         float local2target[4][4];
290         float target2local[4][4];
291
292 } SpaceTransform;
293
294 void BLI_space_transform_from_matrices(struct SpaceTransform *data, const float local[4][4], const float target[4][4]);
295 void BLI_space_transform_global_from_matrices(struct SpaceTransform *data, const float local[4][4], const float target[4][4]);
296 void BLI_space_transform_apply(const struct SpaceTransform *data, float co[3]);
297 void BLI_space_transform_invert(const struct SpaceTransform *data, float co[3]);
298 void BLI_space_transform_apply_normal(const struct SpaceTransform *data, float no[3]);
299 void BLI_space_transform_invert_normal(const struct SpaceTransform *data, float no[3]);
300
301 #define BLI_SPACE_TRANSFORM_SETUP(data, local, target) \
302         BLI_space_transform_from_matrices((data), (local)->obmat, (target)->obmat)
303
304 /*********************************** Other ***********************************/
305
306 void print_m3(const char *str, const float M[3][3]);
307 void print_m4(const char *str, const float M[4][4]);
308
309 #define print_m3_id(M) print_m3(STRINGIFY(M), M)
310 #define print_m4_id(M) print_m4(STRINGIFY(M), M)
311
312 #ifdef __cplusplus
313 }
314 #endif
315
316 #endif /* __BLI_MATH_MATRIX_H__ */
317