Skip to main content

ear_algae/
rigid.rs

1#[cfg(feature = "serde")]
2use serde::{Deserialize, Serialize};
3
4use crate::{
5    Mat, Vect,
6    ops::{Apl, BefAft},
7    rotor::*,
8    traits::*,
9};
10
11#[derive(Copy, Clone, Default)]
12#[cfg_attr(
13    feature = "serde",
14    derive(Serialize, Deserialize),
15    serde(bound(
16        serialize = "
17            [S; N]: Serialize,
18            Bivector<N, S>: Serialize,
19        ",
20        deserialize = " 
21            [S; N]: Deserialize<'de>,
22            Bivector<N, S>: Deserialize<'de>,
23        ",
24    ))
25)]
26pub struct Rig<const N: usize, S: Field>
27where
28    (): RotDim<N>,
29{
30    pub trans: Vect<N, S>,
31    pub rot: Rot<N, S>,
32}
33
34impl<const N: usize, S: Field> Rig<N, S>
35where
36    (): RotDim<N>,
37{
38    pub const IDENT: Self = Self {
39        trans: Vect::ZERO,
40        rot: Rot::IDENT,
41    };
42
43    pub fn new(trans: Vect<N, S>, rot: Rot<N, S>) -> Self {
44        Self { trans, rot }
45    }
46
47    pub fn rot(rot: Rot<N, S>) -> Self {
48        Self { rot, ..Self::IDENT }
49    }
50
51    pub fn trans(trans: Vect<N, S>) -> Self {
52        Self {
53            trans,
54            ..Self::IDENT
55        }
56    }
57
58    pub fn inv(self) -> Self {
59        let rot = self.rot.inv();
60        Self {
61            rot,
62            trans: rot.apl(-self.trans),
63        }
64    }
65}
66
67impl<const N: usize, S: Field> From<Rot<N, S>> for Rig<N, S>
68where
69    (): RotDim<N>,
70{
71    fn from(value: Rot<N, S>) -> Self {
72        Self::rot(value)
73    }
74}
75
76impl<const N: usize, S: Field> Apl<Vect<N, S>> for Rig<N, S>
77where
78    (): RotDim<N>,
79{
80    type Output = Vect<N, S>;
81
82    fn apl(self, other: Vect<N, S>) -> Vect<N, S> {
83        self.rot.apl(other) + self.trans
84    }
85}
86
87impl<const N: usize, S: Field> BefAft for Rig<N, S>
88where
89    (): RotDim<N>,
90{
91    fn aft(self, other: Self) -> Self {
92        Self {
93            rot: self.rot.aft(other.rot),
94            trans: self.rot.apl(other.trans) + self.trans,
95        }
96    }
97}
98
99impl<S: Field> Rig<3, S> {
100    pub fn to_hmat(self) -> Mat<4, 4, S> {
101        Mat::affine(self.rot.mat(), self.trans)
102    }
103}