palette/macros/
mix.rs

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
macro_rules! impl_mix {
    ($ty: ident $(where $($where: tt)+)?) => {
        impl_mix!($ty<> $(where $($where)+)?);
    };
    ($ty: ident <$($ty_param: ident),*> $(where $($where: tt)+)?) => {
        impl<$($ty_param,)* T> crate::Mix for $ty<$($ty_param,)* T>
        where
            T: crate::num::Real
                + crate::num::Zero
                + crate::num::One
                + crate::num::Arithmetics
                + crate::num::Clamp
                + Clone,
            $($($where)+)?
        {
            type Scalar = T;

            #[inline]
            fn mix(self, other: Self, factor: T) -> Self {
                let factor = crate::clamp(factor, T::zero(), T::one());
                self.clone() + (other - self) * factor
            }
        }

        impl<$($ty_param,)* T> crate::MixAssign for $ty<$($ty_param,)* T>
        where
            T: crate::num::Real
                + crate::num::Zero
                + crate::num::One
                + core::ops::AddAssign
                + crate::num::Arithmetics
                + crate::num::Clamp
                + Clone,
            $($($where)+)?
        {
            type Scalar = T;

            #[inline]
            fn mix_assign(&mut self, other: Self, factor: T) {
                let factor = crate::clamp(factor, T::zero(), T::one());
                *self += (other - self.clone()) * factor;
            }
        }
    };
}

macro_rules! impl_mix_hue {
    ($ty: ident {$($other_field: ident),*} $(phantom: $phantom: ident)?) => {
        impl_mix_hue!($ty<> {$($other_field),*} $(phantom: $phantom)?);
    };
    ($ty: ident <$($ty_param: ident),*> {$($other_field: ident),*} $(phantom: $phantom: ident)?) => {
        impl<$($ty_param,)* T> crate::Mix for $ty<$($ty_param,)* T>
        where
            T: crate::angle::RealAngle
                + crate::angle::SignedAngle
                + crate::num::Zero
                + crate::num::One
                + crate::num::Clamp
                + crate::num::Arithmetics
                + Clone,
        {
            type Scalar = T;

            #[inline]
            fn mix(self, other: Self, factor: T) -> Self {
                let factor = crate::clamp(factor, T::zero(), T::one());
                let hue = (other.hue - self.hue.clone()).into_degrees();
                $(
                    let $other_field = other.$other_field - &self.$other_field;
                )*

                $ty {
                    $(
                        $other_field: self.$other_field + $other_field * &factor,
                    )*
                    hue: self.hue + hue * factor,
                    $($phantom: PhantomData)?
                }
            }
        }

        impl<$($ty_param,)* T> crate::MixAssign for $ty<$($ty_param,)* T>
        where
            T: crate::angle::RealAngle
                + crate::angle::SignedAngle
                + crate::num::Zero
                + crate::num::One
                + crate::num::Clamp
                + core::ops::AddAssign
                + crate::num::Arithmetics
                + Clone,
        {
            type Scalar = T;

            #[inline]
            fn mix_assign(&mut self, other: Self, factor: T) {
                let factor = crate::clamp(factor, T::zero(), T::one());
                let hue = (other.hue - self.hue.clone()).into_degrees();
                $(
                    let $other_field = other.$other_field - &self.$other_field;
                )*

                $(
                    self.$other_field += $other_field * &factor;
                )*
                self.hue += hue * factor;
            }
        }
    };
}