1use crate::{Angle, Color, OnLinePos, OnPlanePos, Point, RelativeDir};
2
3#[derive(Copy, Clone, Debug, Default, PartialEq)]
5pub struct GradientStop {
6 pub pos: Option<OnLinePos>,
7 pub color: Color,
8}
9
10impl GradientStop {
11 pub fn new(pos: Option<OnLinePos>, color: Color) -> GradientStop {
13 GradientStop { pos, color }
14 }
15}
16
17impl From<(OnLinePos, Color)> for GradientStop {
18 fn from(d: (OnLinePos, Color)) -> Self {
19 Self {
20 pos: Some(d.0),
21 color: d.1,
22 }
23 }
24}
25
26impl From<(f64, Color)> for GradientStop {
27 fn from(d: (f64, Color)) -> Self {
28 Self {
29 pos: Some(OnLinePos::from_unit_percent(d.0)),
30 color: d.1,
31 }
32 }
33}
34
35impl From<Color> for GradientStop {
36 fn from(color: Color) -> Self {
37 Self { pos: None, color }
38 }
39}
40
41#[derive(Copy, Clone, PartialEq, Debug)]
43pub enum LinearGradientCoords {
44 Ends { start: Point, end: Point },
46 Angle {
48 angle: Angle,
49 displacement: OnPlanePos,
51 },
52 Direction {
54 direction: RelativeDir,
55 displacement: OnPlanePos,
56 },
57}
58
59impl LinearGradientCoords {
60 pub fn from_ends(start: impl Into<Point>, end: impl Into<Point>) -> LinearGradientCoords {
62 LinearGradientCoords::Ends {
63 start: start.into(),
64 end: end.into(),
65 }
66 }
67
68 pub fn from_angle(angle: Angle) -> LinearGradientCoords {
70 LinearGradientCoords::Angle {
71 angle,
72 displacement: OnPlanePos::default(),
73 }
74 }
75
76 pub fn with_displacement(&mut self, displacement: impl Into<OnPlanePos>) -> Self {
78 if let LinearGradientCoords::Angle {
79 angle: _,
80 displacement: disp,
81 } = self
82 {
83 *disp = displacement.into();
84 }
85 *self
86 }
87}
88
89impl Default for LinearGradientCoords {
90 fn default() -> LinearGradientCoords {
91 LinearGradientCoords::Direction {
92 direction: RelativeDir::Top,
93 displacement: OnPlanePos::default(),
94 }
95 }
96}
97
98#[derive(Clone, PartialEq, Debug)]
100pub struct Gradient {
101 pub kind: GradientKind,
102 pub stops: Vec<GradientStop>,
103 pub repeat: bool,
104}
105
106impl Default for Gradient {
107 fn default() -> Self {
108 Self {
109 kind: GradientKind::Linear(LinearGradientCoords::default()),
110 stops: vec![
111 GradientStop {
112 pos: None,
113 color: Color::rgb(0, 0, 0),
114 },
115 GradientStop {
116 pos: None,
117 color: Color::rgb(255, 255, 255),
118 },
119 ],
120 repeat: false,
121 }
122 }
123}
124
125#[derive(Copy, Clone, PartialEq, Debug)]
127pub enum GradientKind {
128 Linear(LinearGradientCoords),
129 }
131
132impl Default for GradientKind {
133 fn default() -> GradientKind {
134 GradientKind::Linear(LinearGradientCoords::default())
135 }
136}