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
pub trait IsColor { type Channel: IsColorChannel; } pub trait IsColorChannel: Sized + Copy + PartialOrd { const MIN: Self; const MAX: Self; #[inline] fn clamp_channel(self) -> Self { if self < Self::MIN { Self::MIN } else if self > Self::MAX { Self::MAX } else { self } } fn unwind_channel(self) -> Self; } pub trait HasAlpha: IsColor + Sized { type Alphaless: HasntAlpha + Sized; fn split_alpha(self) -> (Self::Alphaless, Self::Channel); fn without_alpha(self) -> Self::Alphaless { self.split_alpha().0 } fn only_alpha(self) -> Self::Channel { self.split_alpha().1 } } pub trait HasntAlpha: IsColor { type Alphaful: HasAlpha; fn with_alpha(self, alpha: Self::Channel) -> Self::Alphaful; } impl IsColorChannel for u8 { const MIN: Self = 0; const MAX: Self = 255; #[inline] fn unwind_channel(self) -> Self { self } } impl IsColorChannel for f32 { const MIN: Self = 0.0; const MAX: Self = 1.0; #[inline] fn unwind_channel(self) -> Self { if self >= 0.0 && self <= 1.0 { self } else { ((self % 1.0) + 1.0) % 1.0 } } }