geomath/
matrix.rs

1//!
2//! A matrix is represented as a struct containing a `f64` field for each component.
3//!
4
5use std::fmt::{Debug, Error, Formatter};
6use std::ops::*;
7use crate::prelude::*;
8use crate::vector::*;
9use crate::prelude::transforms;
10use crate::{impl_vector, impl_debug_matrix};
11
12/// constant matrices
13pub mod consts {
14    use super::*;
15
16    /// 2x2 zero matrix
17    pub const ZEROS_2: Matrix2 = Matrix2 { xx: 0., xy: 0., yx: 0., yy: 0. };
18    /// 2x2 one matrix
19    pub const ONES_2: Matrix2 = Matrix2 { xx: 1., xy: 1., yx: 1., yy: 1. };
20    /// 2x2 identity matrix
21    pub const EYE_2: Matrix2 = Matrix2 { xx: 1., xy: 0., yx: 0., yy: 1. };
22
23    /// 3x3 zero matrix
24    pub const ZEROS_3: Matrix3 = Matrix3 { xx: 0., xy: 0., xz: 0., yx: 0., yy: 0., yz: 0., zx: 0., zy: 0., zz: 0. };
25    /// 3x3 one matrix
26    pub const ONES_3: Matrix3 = Matrix3 { xx: 1., xy: 1., xz: 1., yx: 1., yy: 1., yz: 0., zx: 1., zy: 1., zz: 1. };
27    /// 3x3 identity matrix
28    pub const EYE_3: Matrix3 = Matrix3 { xx: 1., xy: 0., xz: 0., yx: 0., yy: 1., yz: 0., zx: 0., zy: 0., zz: 1. };
29
30    /// 4x4 zero matrix
31    pub const ZEROS_4: Matrix4 = Matrix4 { xx: 0., xy: 0., xz: 0., xw: 0., yx: 0., yy: 0., yz: 0., yw: 0., zx: 0., zy: 0., zz: 0., zw: 0., wx: 0., wy: 0., wz: 0., ww: 0. };
32    /// 4x4 one matrix
33    pub const ONES_4: Matrix4 = Matrix4 { xx: 1., xy: 1., xz: 1., xw: 1., yx: 1., yy: 1., yz: 1., yw: 1., zx: 1., zy: 1., zz: 1., zw: 1., wx: 1., wy: 1., wz: 1., ww: 1. };
34    /// 4x4 identity matrix
35    pub const EYE_4: Matrix4 = Matrix4 { xx: 1., xy: 0., xz: 0., xw: 0., yx: 0., yy: 1., yz: 0., yw: 0., zx: 0., zy: 0., zz: 1., zw: 0., wx: 0., wy: 0., wz: 0., ww: 1. };
36}
37
38/// 2x2 matrix
39#[derive(Copy, Clone)]
40pub struct Matrix2 {
41    pub xx: f64,
42    pub xy: f64,
43    pub yx: f64,
44    pub yy: f64,
45}
46
47/// 3x3 matrix
48#[derive(Copy, Clone)]
49pub struct Matrix3 {
50    pub xx: f64,
51    pub xy: f64,
52    pub xz: f64,
53    pub yx: f64,
54    pub yy: f64,
55    pub yz: f64,
56    pub zx: f64,
57    pub zy: f64,
58    pub zz: f64,
59}
60
61/// 4x4 matrix
62#[derive(Copy, Clone)]
63pub struct Matrix4 {
64    pub xx: f64,
65    pub xy: f64,
66    pub xz: f64,
67    pub xw: f64,
68    pub yx: f64,
69    pub yy: f64,
70    pub yz: f64,
71    pub yw: f64,
72    pub zx: f64,
73    pub zy: f64,
74    pub zz: f64,
75    pub zw: f64,
76    pub wx: f64,
77    pub wy: f64,
78    pub wz: f64,
79    pub ww: f64,
80}
81
82impl_vector!(Matrix2 {xx, xy, yx, yy}, 4, mat2);
83impl_vector!(Matrix3 {xx, xy, xz, yx, yy, yz, zx, zy, zz}, 9, mat3);
84impl_vector!(Matrix4 {xx, xy, xz, xw, yx, yy, yz, yw, zx, zy, zz, zw, wx, wy, wz, ww}, 16, mat4);
85
86impl_debug_matrix!(Matrix2);
87impl_debug_matrix!(Matrix3);
88impl_debug_matrix!(Matrix4);
89
90impl Rows<[Vector2; 2]> for Matrix2 {
91    fn rows(&self) -> [Vector2; 2] {
92        [
93            vec2(self.xx, self.xy),
94            vec2(self.yx, self.yy)
95        ]
96    }
97
98    fn set_rows(&mut self, rows: &[Vector2; 2]) -> &mut Self {
99        self.xx = rows[0].x;
100        self.xy = rows[0].y;
101
102        self.yx = rows[1].x;
103        self.yy = rows[1].y;
104        self
105    }
106}
107
108impl Rows<[Vector3; 3]> for Matrix3 {
109    fn rows(&self) -> [Vector3; 3] {
110        [
111            vec3(self.xx, self.xy, self.xz),
112            vec3(self.yx, self.yy, self.yz),
113            vec3(self.zx, self.zy, self.zz),
114        ]
115    }
116
117    fn set_rows(&mut self, rows: &[Vector3; 3]) -> &mut Self {
118        self.xx = rows[0].x;
119        self.xy = rows[0].y;
120        self.xz = rows[0].z;
121
122        self.yx = rows[1].x;
123        self.yy = rows[1].y;
124        self.yz = rows[1].z;
125
126        self.zx = rows[2].x;
127        self.zy = rows[2].y;
128        self.zz = rows[2].z;
129        self
130    }
131}
132
133impl Rows<[Vector4; 4]> for Matrix4 {
134    fn rows(&self) -> [Vector4; 4] {
135        [
136            vec4(self.xx, self.xy, self.xz, self.xw),
137            vec4(self.yx, self.yy, self.yz, self.yw),
138            vec4(self.zx, self.zy, self.zz, self.zw),
139            vec4(self.wx, self.wy, self.wz, self.ww),
140        ]
141    }
142
143    fn set_rows(&mut self, rows: &[Vector4; 4]) -> &mut Self {
144        self.xx = rows[0].x;
145        self.xy = rows[0].y;
146        self.xz = rows[0].z;
147        self.xw = rows[0].w;
148
149        self.yx = rows[1].x;
150        self.yy = rows[1].y;
151        self.yz = rows[1].z;
152        self.yw = rows[1].w;
153
154        self.zx = rows[2].x;
155        self.zy = rows[2].y;
156        self.zz = rows[2].z;
157        self.zw = rows[2].w;
158
159        self.wx = rows[3].x;
160        self.wy = rows[3].y;
161        self.wz = rows[3].z;
162        self.ww = rows[3].w;
163        self
164    }
165}
166
167impl Mul<Matrix2> for Matrix2 {
168    type Output = Matrix2;
169
170    fn mul(self, rhs: Matrix2) -> Self::Output {
171        let mut ret = self;
172        ret *= rhs;
173        ret
174    }
175}
176
177impl Mul<Vector2> for Matrix2 {
178    type Output = Vector2;
179
180    fn mul(self, rhs: Vector2) -> Self::Output {
181        let mut ret = rhs;
182        ret *= self;
183        ret
184    }
185}
186
187impl MulAssign<Matrix2> for Matrix2 {
188    fn mul_assign(&mut self, rhs: Matrix2) {
189        let xx = self.xx;
190        let yx = self.yx;
191        let xy = self.xy;
192        let yy = self.yy;
193
194        self.xx = rhs.xx * xx + rhs.yx * xy;
195        self.yx = rhs.xx * yx + rhs.yx * yy;
196        self.xy = rhs.xy * xx + rhs.yy * xy;
197        self.yy = rhs.xy * yx + rhs.yy * yy;
198    }
199}
200
201impl Mul<Matrix3> for Matrix3 {
202    type Output = Matrix3;
203
204    fn mul(self, rhs: Matrix3) -> Self::Output {
205        let mut ret = self;
206        ret *= rhs;
207        ret
208    }
209}
210
211impl Mul<Vector3> for Matrix3 {
212    type Output = Vector3;
213
214    fn mul(self, rhs: Vector3) -> Self::Output {
215        let mut ret = rhs;
216        ret *= self;
217        ret
218    }
219}
220
221impl Mul<Vector2> for Matrix3 {
222    type Output = Vector2;
223
224    fn mul(self, rhs: Vector2) -> Self::Output {
225        let mut ret = rhs;
226        ret *= self;
227        ret
228    }
229}
230
231impl MulAssign<Matrix3> for Matrix3 {
232    fn mul_assign(&mut self, rhs: Matrix3) {
233        let xx = self.xx;
234        let yx = self.yx;
235        let zx = self.zx;
236        let xy = self.xy;
237        let yy = self.yy;
238        let zy = self.zy;
239        let xz = self.xz;
240        let yz = self.yz;
241        let zz = self.zz;
242
243        self.xx = rhs.xx * xx + rhs.yx * xy + rhs.zx * xz;
244        self.yx = rhs.xx * yx + rhs.yx * yy + rhs.zx * yz;
245        self.zx = rhs.xx * zx + rhs.yx * zy + rhs.zx * zz;
246
247        self.xy = rhs.xy * xx + rhs.yy * xy + rhs.zy * xz;
248        self.yy = rhs.xy * yx + rhs.yy * yy + rhs.zy * yz;
249        self.zy = rhs.xy * zx + rhs.yy * zy + rhs.zy * zz;
250
251        self.xz = rhs.xz * xx + rhs.yz * xy + rhs.zz * xz;
252        self.yz = rhs.xz * yx + rhs.yz * yy + rhs.zz * yz;
253        self.zz = rhs.xz * zx + rhs.yz * zy + rhs.zz * zz;
254    }
255}
256
257impl Mul<Matrix4> for Matrix4 {
258    type Output = Matrix4;
259
260    fn mul(self, rhs: Matrix4) -> Self::Output {
261        let mut ret = self;
262        ret *= rhs;
263        ret
264    }
265}
266
267impl Mul<Vector4> for Matrix4 {
268    type Output = Vector4;
269
270    fn mul(self, rhs: Vector4) -> Self::Output {
271        let mut ret = rhs;
272        ret *= self;
273        ret
274    }
275}
276
277impl Mul<Vector3> for Matrix4 {
278    type Output = Vector3;
279
280    fn mul(self, rhs: Vector3) -> Self::Output {
281        let mut ret = rhs;
282        ret *= self;
283        ret
284    }
285}
286
287impl MulAssign<Matrix4> for Matrix4 {
288    fn mul_assign(&mut self, rhs: Matrix4) {
289        let xx = self.xx;
290        let yx = self.yx;
291        let zx = self.zx;
292        let wx = self.wx;
293        let xy = self.xy;
294        let yy = self.yy;
295        let zy = self.zy;
296        let wy = self.wy;
297        let xz = self.xz;
298        let yz = self.yz;
299        let zz = self.zz;
300        let wz = self.wz;
301        let xw = self.xw;
302        let yw = self.yw;
303        let zw = self.zw;
304        let ww = self.ww;
305
306        self.xx = rhs.xx * xx + rhs.yx * xy + rhs.zx * xz + rhs.wx * xw;
307        self.yx = rhs.xx * yx + rhs.yx * yy + rhs.zx * yz + rhs.wx * yw;
308        self.zx = rhs.xx * zx + rhs.yx * zy + rhs.zx * zz + rhs.wx * zw;
309        self.wx = rhs.xx * wx + rhs.yx * wy + rhs.zx * wz + rhs.wx * ww;
310
311        self.xy = rhs.xy * xx + rhs.yy * xy + rhs.zy * xz + rhs.wy * xw;
312        self.yy = rhs.xy * yx + rhs.yy * yy + rhs.zy * yz + rhs.wy * yw;
313        self.zy = rhs.xy * zx + rhs.yy * zy + rhs.zy * zz + rhs.wy * zw;
314        self.wy = rhs.xy * wx + rhs.yy * wy + rhs.zy * wz + rhs.wy * ww;
315
316        self.xz = rhs.xz * xx + rhs.yz * xy + rhs.zz * xz + rhs.wz * xw;
317        self.yz = rhs.xz * yx + rhs.yz * yy + rhs.zz * yz + rhs.wz * yw;
318        self.zz = rhs.xz * zx + rhs.yz * zy + rhs.zz * zz + rhs.wz * zw;
319        self.wz = rhs.xz * wx + rhs.yz * wy + rhs.zz * wz + rhs.wz * ww;
320
321        self.xw = rhs.xw * xx + rhs.yw * xy + rhs.zw * xz + rhs.ww * xw;
322        self.yw = rhs.xw * yx + rhs.yw * yy + rhs.zw * yz + rhs.ww * yw;
323        self.zw = rhs.xw * zx + rhs.yw * zy + rhs.zw * zz + rhs.ww * zw;
324        self.ww = rhs.xw * wx + rhs.yw * wy + rhs.zw * wz + rhs.ww * ww;
325    }
326}
327
328impl Algebra<Matrix2> for Matrix2 {
329    fn determinant(&self) -> f64 {
330        let xx = self.xx;
331        let yx = self.yx;
332        let xy = self.xy;
333        let yy = self.yy;
334
335        xx * yy - xy * yx
336    }
337
338    fn set_inverse(&mut self) -> &mut Self {
339        let xx = self.xx;
340        let yx = self.yx;
341        let xy = self.xy;
342        let yy = self.yy;
343
344        let mut det = xx * yy - xy * yx;
345
346        if det == 0. {
347            return self;
348        }
349
350        det = 1. / det;
351
352        self.xx = yy * det;
353        self.xy = -xy * det;
354        self.yx = -yx * det;
355        self.yy = xx * det;
356
357        self
358    }
359
360    fn set_transposed(&mut self) -> &mut Self {
361        let yx = self.yx;
362
363        self.yx = self.xy;
364        self.xy = yx;
365
366        self
367    }
368
369    fn set_adjugate(&mut self) -> &mut Self {
370        let xx = self.xx;
371
372        self.xx = self.yy;
373        self.yx = -self.yx;
374        self.xy = -self.xy;
375        self.yy = xx;
376
377        self
378    }
379}
380
381impl Algebra<Matrix3> for Matrix3 {
382    fn determinant(&self) -> f64 {
383        let xx = self.xx;
384        let yx = self.yx;
385        let zx = self.zx;
386        let xy = self.xy;
387        let yy = self.yy;
388        let zy = self.zy;
389        let xz = self.xz;
390        let yz = self.yz;
391        let zz = self.zz;
392
393        let dyx = zz * yy - zy * yz;
394        let dyy = -zz * xy + zy * xz;
395        let dyz = yz * xy - yy * xz;
396
397        xx * dyx + yx * dyy + zx * dyz
398    }
399
400    fn set_inverse(&mut self) -> &mut Self {
401        let xx = self.xx;
402        let yx = self.yx;
403        let zx = self.zx;
404        let xy = self.xy;
405        let yy = self.yy;
406        let zy = self.zy;
407        let xz = self.xz;
408        let yz = self.yz;
409        let zz = self.zz;
410
411        let dyx = zz * yy - zy * yz;
412        let dyy = -zz * xy + zy * xz;
413        let dyz = yz * xy - yy * xz;
414        let mut det = xx * dyx + yx * dyy + zx * dyz;
415
416        if det == 0. {
417            return self;
418        }
419
420        det = 1. / det;
421        self.xx = dyx * det;
422        self.yx = (-zz * yx + zx * yz) * det;
423        self.zx = (zy * yx - zx * yy) * det;
424        self.xy = dyy * det;
425        self.yy = (zz * xx - zx * xz) * det;
426        self.zy = (-zy * xx + zx * xy) * det;
427        self.xz = dyz * det;
428        self.yz = (-yz * xx + yx * xz) * det;
429        self.zz = (yy * xx - yx * xy) * det;
430
431        self
432    }
433
434    fn set_transposed(&mut self) -> &mut Self {
435        let yx = self.yx;
436        let zx = self.zx;
437        let yz = self.yz;
438
439        self.yx = self.xy;
440        self.xy = yx;
441        self.zx = self.xz;
442        self.xz = zx;
443        self.yz = self.zy;
444        self.zy = yz;
445
446        self
447    }
448
449    fn set_adjugate(&mut self) -> &mut Self {
450        let xx = self.xx;
451        let yx = self.yx;
452        let zx = self.zx;
453        let xy = self.xy;
454        let yy = self.yy;
455        let zy = self.zy;
456        let xz = self.xz;
457        let yz = self.yz;
458        let zz = self.zz;
459
460        self.xx = yy * zz - zy * yz;
461        self.yx = zx * yz - yx * zz;
462        self.zx = yx * zy - zx * yy;
463        self.xy = zy * xz - xy * zz;
464        self.yy = xx * zz - zx * xz;
465        self.zy = zx * xy - xx * zy;
466        self.xz = xy * yz - yy * xz;
467        self.yz = yx * xz - xx * yz;
468        self.zz = xx * yy - yx * xy;
469
470        self
471    }
472}
473
474impl Algebra<Matrix4> for Matrix4 {
475    fn determinant(&self) -> f64 {
476        let xx = self.xx;
477        let yx = self.yx;
478        let zx = self.zx;
479        let wx = self.wx;
480        let xy = self.xy;
481        let yy = self.yy;
482        let zy = self.zy;
483        let wy = self.wy;
484        let xz = self.xz;
485        let yz = self.yz;
486        let zz = self.zz;
487        let wz = self.wz;
488        let xw = self.xw;
489        let yw = self.yw;
490        let zw = self.zw;
491        let ww = self.ww;
492
493        let d00 = xx * yy - yx * xy;
494        let d01 = xx * zy - zx * xy;
495        let d02 = xx * wy - wx * xy;
496        let d03 = yx * zy - zx * yy;
497        let d04 = yx * wy - wx * yy;
498        let d05 = zx * wy - wx * zy;
499        let d06 = xz * yw - yz * xw;
500        let d07 = xz * zw - zz * xw;
501        let d08 = xz * ww - wz * xw;
502        let d09 = yz * zw - zz * yw;
503        let d10 = yz * ww - wz * yw;
504        let d11 = zz * ww - wz * zw;
505
506        d00 * d11 - d01 * d10 + d02 * d09 + d03 * d08 - d04 * d07 + d05 * d06
507    }
508
509    fn set_inverse(&mut self) -> &mut Self {
510        let xx = self.xx;
511        let yx = self.yx;
512        let zx = self.zx;
513        let wx = self.wx;
514        let xy = self.xy;
515        let yy = self.yy;
516        let zy = self.zy;
517        let wy = self.wy;
518        let xz = self.xz;
519        let yz = self.yz;
520        let zz = self.zz;
521        let wz = self.wz;
522        let xw = self.xw;
523        let yw = self.yw;
524        let zw = self.zw;
525        let ww = self.ww;
526
527        let d00 = xx * yy - yx * xy;
528        let d01 = xx * zy - zx * xy;
529        let d02 = xx * wy - wx * xy;
530        let d03 = yx * zy - zx * yy;
531        let d04 = yx * wy - wx * yy;
532        let d05 = zx * wy - wx * zy;
533        let d06 = xz * yw - yz * xw;
534        let d07 = xz * zw - zz * xw;
535        let d08 = xz * ww - wz * xw;
536        let d09 = yz * zw - zz * yw;
537        let d10 = yz * ww - wz * yw;
538        let d11 = zz * ww - wz * zw;
539
540        let mut det = d00 * d11 - d01 * d10 + d02 * d09 + d03 * d08 - d04 * d07 + d05 * d06;
541
542        if det == 0. {
543            return self;
544        }
545
546        det = 1.0 / det;
547
548        self.xx = (yy * d11 - zy * d10 + wy * d09) * det;
549        self.yx = (zx * d10 - yx * d11 - wx * d09) * det;
550        self.zx = (yw * d05 - zw * d04 + ww * d03) * det;
551        self.wx = (zz * d04 - yz * d05 - wz * d03) * det;
552        self.xy = (zy * d08 - xy * d11 - wy * d07) * det;
553        self.yy = (xx * d11 - zx * d08 + wx * d07) * det;
554        self.zy = (zw * d02 - xw * d05 - ww * d01) * det;
555        self.wy = (xz * d05 - zz * d02 + wz * d01) * det;
556        self.xz = (xy * d10 - yy * d08 + wy * d06) * det;
557        self.yz = (yx * d08 - xx * d10 - wx * d06) * det;
558        self.zz = (xw * d04 - yw * d02 + ww * d00) * det;
559        self.wz = (yz * d02 - xz * d04 - wz * d00) * det;
560        self.xw = (yy * d07 - xy * d09 - zy * d06) * det;
561        self.yw = (xx * d09 - yx * d07 + zx * d06) * det;
562        self.zw = (yw * d01 - xw * d03 - zw * d00) * det;
563        self.ww = (xz * d03 - yz * d01 + zz * d00) * det;
564
565        self
566    }
567
568    fn set_transposed(&mut self) -> &mut Self {
569        let yx = self.yx;
570        let zx = self.zx;
571        let wx = self.wx;
572        let zy = self.zy;
573        let wy = self.wy;
574        let wz = self.wz;
575
576        self.yx = self.xy;
577        self.zx = self.xz;
578        self.wx = self.xw;
579        self.xy = yx;
580        self.zy = self.yz;
581        self.wy = self.yw;
582        self.xz = zx;
583        self.yz = zy;
584        self.wz = self.zw;
585        self.xw = wx;
586        self.yw = wy;
587        self.zw = wz;
588
589        self
590    }
591
592    fn set_adjugate(&mut self) -> &mut Self {
593        let xx = self.xx;
594        let yx = self.yx;
595        let zx = self.zx;
596        let wx = self.wx;
597        let xy = self.xy;
598        let yy = self.yy;
599        let zy = self.zy;
600        let wy = self.wy;
601        let xz = self.xz;
602        let yz = self.yz;
603        let zz = self.zz;
604        let wz = self.wz;
605        let xw = self.xw;
606        let yw = self.yw;
607        let zw = self.zw;
608        let ww = self.ww;
609
610        self.xx = yy * (zz * ww - wz * zw) - yz * (zy * ww - wy * zw) + yw * (zy * wz - wy * zz);
611        self.yx = -(yx * (zz * ww - wz * zw) - yz * (zx * ww - wx * zw) + yw * (zx * wz - wx * zz));
612        self.zx = yx * (zy * ww - wy * zw) - yy * (zx * ww - wx * zw) + yw * (zx * wy - wx * zy);
613        self.wx = -(yx * (zy * wz - wy * zz) - yy * (zx * wz - wx * zz) + yz * (zx * wy - wx * zy));
614        self.xy = -(xy * (zz * ww - wz * zw) - xz * (zy * ww - wy * zw) + xw * (zy * wz - wy * zz));
615        self.yy = xx * (zz * ww - wz * zw) - xz * (zx * ww - wx * zw) + xw * (zx * wz - wx * zz);
616        self.zy = -(xx * (zy * ww - wy * zw) - xy * (zx * ww - wx * zw) + xw * (zx * wy - wx * zy));
617        self.wy = xx * (zy * wz - wy * zz) - xy * (zx * wz - wx * zz) + xz * (zx * wy - wx * zy);
618        self.xz = xy * (yz * ww - wz * yw) - xz * (yy * ww - wy * yw) + xw * (yy * wz - wy * yz);
619        self.yz = -(xx * (yz * ww - wz * yw) - xz * (yx * ww - wx * yw) + xw * (yx * wz - wx * yz));
620        self.zz = xx * (yy * ww - wy * yw) - xy * (yx * ww - wx * yw) + xw * (yx * wy - wx * yy);
621        self.wz = -(xx * (yy * wz - wy * yz) - xy * (yx * wz - wx * yz) + xz * (yx * wy - wx * yy));
622        self.xw = -(xy * (yz * zw - zz * yw) - xz * (yy * zw - zy * yw) + xw * (yy * zz - zy * yz));
623        self.yw = xx * (yz * zw - zz * yw) - xz * (yx * zw - zx * yw) + xw * (yx * zz - zx * yz);
624        self.zw = -(xx * (yy * zw - zy * yw) - xy * (yx * zw - zx * yw) + xw * (yx * zy - zx * yy));
625        self.ww = xx * (yy * zz - zy * yz) - xy * (yx * zz - zx * yz) + xz * (yx * zy - zx * yy);
626
627        self
628    }
629}
630
631impl transforms::Translation<Vector2> for Matrix3 {
632    fn set_translation(&mut self, vector: &Vector2) -> &mut Self {
633        self.xx = 1.;
634        self.xy = 0.;
635        self.xz = vector.x;
636        self.yx = 0.;
637        self.yy = 1.;
638        self.yz = vector.y;
639        self.zx = 0.;
640        self.zy = 0.;
641        self.zz = 1.;
642
643        self
644    }
645}
646
647impl transforms::Translation<Vector3> for Matrix4 {
648    fn set_translation(&mut self, vector: &Vector3) -> &mut Self {
649        self.xx = 1.;
650        self.xy = 0.;
651        self.xz = 0.;
652        self.xw = vector.x;
653        self.yx = 0.;
654        self.yy = 1.;
655        self.yz = 0.;
656        self.yw = vector.y;
657        self.zx = 0.;
658        self.zy = 0.;
659        self.zz = 1.;
660        self.zw = vector.z;
661        self.wx = 0.;
662        self.wy = 0.;
663        self.wz = 0.;
664        self.ww = 1.;
665
666        self
667    }
668}
669
670impl transforms::Rigid<Matrix2, Vector2> for Matrix3 {
671    fn set_rigid(&mut self, rotation: &Matrix2, vector: &Vector2) -> &mut Self {
672        self.xx = rotation.xx;
673        self.xy = rotation.xy;
674        self.xz = vector.x;
675        self.yx = rotation.yx;
676        self.yy = rotation.yy;
677        self.yz = vector.y;
678        self.zx = 0.;
679        self.zy = 0.;
680        self.zz = 1.;
681
682        self
683    }
684}
685
686impl transforms::Rigid<Matrix3, Vector3> for Matrix4 {
687    fn set_rigid(&mut self, rotation: &Matrix3, vector: &Vector3) -> &mut Self {
688        self.xx = rotation.xx;
689        self.xy = rotation.xy;
690        self.xz = rotation.xz;
691        self.xw = vector.x;
692        self.yx = rotation.yx;
693        self.yy = rotation.yy;
694        self.yz = rotation.yz;
695        self.yw = vector.y;
696        self.zx = rotation.zx;
697        self.zy = rotation.zy;
698        self.zz = rotation.zz;
699        self.zw = vector.z;
700        self.wx = 0.;
701        self.wy = 0.;
702        self.wz = 0.;
703        self.ww = 1.;
704
705        self
706    }
707}
708
709impl transforms::Similarity<Matrix2, Vector2> for Matrix3 {
710    fn set_similarity(&mut self, scale: f64, rotation: &Matrix2, vector: &Vector2) -> &mut Self {
711        self.xx = scale * rotation.xx;
712        self.xy = scale * rotation.xy;
713        self.xz = vector.x;
714        self.yx = scale * rotation.yx;
715        self.yy = scale * rotation.yy;
716        self.yz = vector.y;
717        self.zx = 0.;
718        self.zy = 0.;
719        self.zz = 1.;
720
721        self
722    }
723}
724
725impl transforms::Similarity<Matrix3, Vector3> for Matrix4 {
726    fn set_similarity(&mut self, scale: f64, rotation: &Matrix3, vector: &Vector3) -> &mut Self {
727        self.xx = scale * rotation.xx;
728        self.xy = scale * rotation.xy;
729        self.xz = scale * rotation.xz;
730        self.xw = vector.x;
731        self.yx = scale * rotation.yx;
732        self.yy = scale * rotation.yy;
733        self.yz = scale * rotation.yz;
734        self.yw = vector.y;
735        self.zx = scale * rotation.zx;
736        self.zy = scale * rotation.zy;
737        self.zz = scale * rotation.zz;
738        self.zw = vector.z;
739        self.wx = 0.;
740        self.wy = 0.;
741        self.wz = 0.;
742        self.ww = 1.;
743
744        self
745    }
746}
747
748impl transforms::Rotation2 for Matrix2 {
749    fn set_rotation(&mut self, angle: f64) -> &mut Self {
750        let c = angle.cos();
751        let s = angle.sin();
752
753        self.xx = c;
754        self.xy = -s;
755        self.yx = s;
756        self.yy = c;
757
758        self
759    }
760}
761
762impl transforms::Rotation3 for Matrix3 {
763    fn set_rotation(&mut self, angle: f64, axis: &Vector3) -> &mut Self {
764        let c = angle.cos();
765        let s = angle.sin();
766        let k = 1. - c;
767
768        let ux = axis.x;
769        let uy = axis.y;
770        let uz = axis.z;
771
772        let k_uxy = k * ux * uy;
773        let k_uxz = k * ux * uz;
774        let k_uyz = k * uy * uz;
775
776        self.xx = k * ux * ux + c;
777        self.xy = k_uxy - uz * s;
778        self.xz = k_uxz + uy * s;
779        self.yx = k_uxy + uz * s;
780        self.yy = k * uy * uy + c;
781        self.yz = k_uyz - ux * s;
782        self.zx = k_uxz - uy * s;
783        self.zy = k_uyz + ux * s;
784        self.zz = k * uz * uz + c;
785
786        self
787    }
788
789    fn set_rotation_x(&mut self, angle: f64) -> &mut Self {
790        let c = angle.cos();
791        let s = angle.sin();
792
793        self.xx = 1.;
794        self.xy = 0.;
795        self.xz = 0.;
796        self.yx = 0.;
797        self.yy = c;
798        self.yz = -s;
799        self.zx = 0.;
800        self.zy = s;
801        self.zz = c;
802
803        self
804    }
805
806    fn set_rotation_y(&mut self, angle: f64) -> &mut Self {
807        let c = angle.cos();
808        let s = angle.sin();
809
810        self.xx = c;
811        self.xy = 0.;
812        self.xz = s;
813        self.yx = 0.;
814        self.yy = 1.;
815        self.yz = 0.;
816        self.zx = -s;
817        self.zy = 0.;
818        self.zz = c;
819
820        self
821    }
822
823    fn set_rotation_z(&mut self, angle: f64) -> &mut Self {
824        let c = angle.cos();
825        let s = angle.sin();
826
827        self.xx = c;
828        self.xy = -s;
829        self.xz = 0.;
830        self.yx = s;
831        self.yy = c;
832        self.yz = 0.;
833        self.zx = 0.;
834        self.zy = 0.;
835        self.zz = 1.;
836
837        self
838    }
839}
840
841#[cfg(test)]
842mod tests {
843    mod matrix3 {
844        use crate::prelude::transforms::Rotation3;
845        use crate::prelude::transforms::Translation;
846        use crate::vector::{self};
847        use crate::matrix::{self, *};
848
849        #[test]
850        fn arithmetic() {
851            let a = matrix::consts::EYE_3 * 2.;
852            let b = matrix::consts::ONES_3;
853            let c = a * b;
854            assert_eq!(c, b * 2.);
855        }
856
857        #[test]
858        fn determinant() {
859            let a = matrix::consts::EYE_3 * 2.;
860            assert_eq!(a.determinant(), 8.);
861        }
862
863        #[test]
864        fn transposed() {
865            let a = mat3(1., 2., 3., 4., 5., 6., 7., 8., 9.);
866            assert_eq!(a.transposed(), mat3(1., 4., 7., 2., 5., 8., 3., 6., 9.));
867        }
868
869        #[test]
870        fn inverse() {
871            let a = matrix::Matrix3::from_translation(&vector::vec2(1.0, 2.0));
872            assert_eq!(a.inverse(), matrix::Matrix3::from_translation(&vector::vec2(-1.0, -2.0)));
873        }
874
875        #[test]
876        fn adjugate() {
877            let a = matrix::consts::EYE_3 * 2.;
878            assert_eq!(a.adjugate(), a.inverse() * a.determinant());
879        }
880
881        #[test]
882        fn rotations() {
883            let angle = std::f64::consts::FRAC_PI_8;
884            let rot_x = Matrix3::from_rotation_x(angle);
885            let rot_y = Matrix3::from_rotation_y(angle);
886            let rot_z = Matrix3::from_rotation_z(angle);
887
888            let mut axis = vector::consts::EX_3;
889            let mut rot = Matrix3::from_rotation(angle, &axis);
890            assert_eq!(rot, rot_x);
891
892            axis = vector::consts::EY_3;
893            rot = Matrix3::from_rotation(angle, &axis);
894            assert_eq!(rot, rot_y);
895
896            axis = vector::consts::EZ_3;
897            rot = Matrix3::from_rotation(angle, &axis);
898            assert_eq!(rot, rot_z);
899        }
900    }
901
902    mod matrix4 {
903        use crate::assert_near;
904        use crate::prelude::*;
905        use crate::prelude::coordinates::Homogeneous;
906        use crate::prelude::transforms::{Rigid, Rotation3, Similarity, Translation};
907        use crate::matrix::{self, *};
908        use crate::vector::{self, Vector3};
909
910        #[test]
911        fn arithmetic() {
912            let a = matrix::consts::EYE_4 * 2.;
913            let b = matrix::consts::ONES_4;
914            let c = a * b;
915            assert_eq!(c, b * 2.);
916        }
917
918        #[test]
919        fn determinant() {
920            let a = matrix::consts::EYE_4 * 2.;
921            assert_eq!(a.determinant(), 16.);
922        }
923
924        #[test]
925        fn transposed() {
926            let a = mat4(1., 2., 3., 4., 5., 6., 7., 8., 9., 10., 11., 12., 13., 14., 15., 16.);
927            assert_eq!(a.transposed(), mat4(1., 5., 9., 13., 2., 6., 10., 14., 3., 7., 11., 15., 4., 8., 12., 16.));
928        }
929
930        #[test]
931        fn inverse() {
932            let a = matrix::consts::EYE_4 * 2.;
933            assert_eq!(a.inverse(), matrix::consts::EYE_4 * 0.5);
934        }
935
936        #[test]
937        fn adjugate() {
938            let a = matrix::consts::EYE_4 * 2.;
939            assert_eq!(a.adjugate(), a.inverse() * a.determinant());
940        }
941
942        #[test]
943        fn translations() {
944            let unit_x = vector::consts::EX_3;
945            let a = Matrix4::from_translation(&unit_x);
946            let u = unit_x.to_homogeneous();
947            let translated = a * u;
948            assert_eq!(Vector3::from_homogeneous(&translated), (unit_x * 2.));
949        }
950
951        #[test]
952        fn rigid() {
953            let angle = std::f64::consts::FRAC_PI_2;
954            let unit_x = vector::consts::EX_3;
955            let rotation_z = Matrix3::from_rotation_z(angle);
956            let a = Matrix4::from_rigid(&rotation_z, &unit_x);
957            let u = unit_x.to_homogeneous();
958            let moved = a * u;
959            assert_eq!(Vector3::from_homogeneous(&moved), vec3(1., 1., 0.));
960        }
961
962        #[test]
963        fn similarity() {
964            let angle = std::f64::consts::FRAC_PI_2;
965            let scale = 2.;
966            let unit_x = vector::consts::EX_3;
967            let rotation_z = Matrix3::from_rotation_z(angle);
968            let a = Matrix4::from_similarity(scale, &rotation_z, &unit_x);
969            let u = unit_x.to_homogeneous();
970            let moved = a * u;
971            assert_near!(Vector3::from_homogeneous(&moved).distance2(&vec3(1., 2., 0.)), 0.,  std::f64::EPSILON);
972        }
973    }
974}