1use ::serde::{Deserialize, Serialize};
2
3use crate::fill_styles;
4use crate::helpers::{buffer_to_hex, hex_to_buffer};
5use crate::join_styles;
6
7#[derive(Copy, Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
8#[serde(rename_all = "kebab-case")]
9pub enum CapStyle {
10 None,
11 Round,
12 Square,
13}
14
15#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
16#[serde(rename_all = "snake_case")]
17pub struct ClipAction {
18 pub events: ClipEventFlags,
19 #[serde(skip_serializing_if = "Option::is_none")]
20 pub key_code: Option<u8>,
21 #[serde(serialize_with = "buffer_to_hex", deserialize_with = "hex_to_buffer")]
22 pub actions: Vec<u8>,
23}
24
25#[derive(Copy, Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
26#[serde(rename_all = "snake_case")]
27pub struct ClipEventFlags {
28 pub key_up: bool,
29 pub key_down: bool,
30 pub mouse_up: bool,
31 pub mouse_down: bool,
32 pub mouse_move: bool,
33 pub unload: bool,
34 pub enter_frame: bool,
35 pub load: bool,
36 pub drag_over: bool,
37 pub roll_out: bool,
38 pub roll_over: bool,
39 pub release_outside: bool,
40 pub release: bool,
41 pub press: bool,
42 pub initialize: bool,
43 pub data: bool,
44 pub construct: bool,
45 pub key_press: bool,
46 pub drag_out: bool,
47}
48
49#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
50#[serde(tag = "type", rename_all = "kebab-case")]
51pub enum FillStyle {
52 Bitmap(fill_styles::Bitmap),
53 FocalGradient(fill_styles::FocalGradient),
54 LinearGradient(fill_styles::LinearGradient),
55 RadialGradient(fill_styles::RadialGradient),
56 Solid(fill_styles::Solid),
57}
58
59#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
60#[serde(tag = "type", rename_all = "kebab-case")]
61pub enum MorphFillStyle {
62 Bitmap(fill_styles::MorphBitmap),
63 FocalGradient(fill_styles::MorphFocalGradient),
64 LinearGradient(fill_styles::MorphLinearGradient),
65 RadialGradient(fill_styles::MorphRadialGradient),
66 Solid(fill_styles::MorphSolid),
67}
68
69#[derive(Copy, Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
70#[serde(tag = "type", rename_all = "kebab-case")]
71pub enum JoinStyle {
72 Bevel,
73 Miter(join_styles::Miter),
74 Round,
75}
76
77#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
78#[serde(rename_all = "snake_case")]
79pub struct LineStyle {
80 pub width: u16,
81 pub start_cap: CapStyle,
82 pub end_cap: CapStyle,
83 pub join: JoinStyle,
84 pub no_h_scale: bool,
85 pub no_v_scale: bool,
86 pub no_close: bool,
87 pub pixel_hinting: bool,
88 pub fill: FillStyle,
89}
90
91#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
92#[serde(rename_all = "snake_case")]
93pub struct MorphLineStyle {
94 pub width: u16,
95 pub morph_width: u16,
96 pub start_cap: CapStyle,
97 pub end_cap: CapStyle,
98 pub join: JoinStyle,
99 pub no_h_scale: bool,
100 pub no_v_scale: bool,
101 pub no_close: bool,
102 pub pixel_hinting: bool,
103 pub fill: MorphFillStyle,
104}
105
106#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
107#[serde(rename_all = "snake_case")]
108pub struct Glyph {
109 pub records: Vec<ShapeRecord>,
110}
111
112#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
113#[serde(rename_all = "snake_case")]
114pub struct Shape {
115 pub initial_styles: ShapeStyles,
116 pub records: Vec<ShapeRecord>,
117}
118
119#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
120#[serde(rename_all = "snake_case")]
121pub struct MorphShape {
122 pub initial_styles: MorphShapeStyles,
123 pub records: Vec<MorphShapeRecord>,
124}
125
126#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
127#[serde(tag = "type", rename_all = "kebab-case")]
128pub enum ShapeRecord {
129 Edge(shape_records::Edge),
130 StyleChange(shape_records::StyleChange),
131}
132
133#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
134#[serde(tag = "type", rename_all = "kebab-case")]
135pub enum MorphShapeRecord {
136 Edge(shape_records::MorphEdge),
137 StyleChange(shape_records::MorphStyleChange),
138}
139
140#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
141#[serde(rename_all = "snake_case")]
142pub struct ShapeStyles {
143 pub fill: Vec<FillStyle>,
144 pub line: Vec<LineStyle>,
145}
146
147#[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
148#[serde(rename_all = "snake_case")]
149pub struct MorphShapeStyles {
150 pub fill: Vec<MorphFillStyle>,
151 pub line: Vec<MorphLineStyle>,
152}
153
154pub mod shape_records {
155 use ::serde::{Deserialize, Serialize};
156
157 use crate::Vector2D;
158
159 use super::{MorphShapeStyles, ShapeStyles};
160
161 #[derive(Copy, Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
162 pub struct Edge {
163 pub delta: Vector2D,
165
166 #[serde(skip_serializing_if = "Option::is_none")]
169 pub control_delta: Option<Vector2D>,
170 }
171
172 #[derive(Copy, Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
173 pub struct MorphEdge {
174 pub delta: Vector2D,
177
178 pub morph_delta: Vector2D,
181
182 #[serde(skip_serializing_if = "Option::is_none")]
185 pub control_delta: Option<Vector2D>,
186
187 #[serde(skip_serializing_if = "Option::is_none")]
190 pub morph_control_delta: Option<Vector2D>,
191 }
192
193 #[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
194 pub struct StyleChange {
195 #[serde(skip_serializing_if = "Option::is_none")]
196 pub move_to: Option<Vector2D>,
197 #[serde(skip_serializing_if = "Option::is_none")]
198 pub left_fill: Option<usize>,
199 #[serde(skip_serializing_if = "Option::is_none")]
200 pub right_fill: Option<usize>,
201 #[serde(skip_serializing_if = "Option::is_none")]
202 pub line_style: Option<usize>,
203 #[serde(skip_serializing_if = "Option::is_none")]
204 pub new_styles: Option<ShapeStyles>,
205 }
206
207 #[derive(Clone, Debug, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize)]
208 pub struct MorphStyleChange {
209 #[serde(skip_serializing_if = "Option::is_none")]
210 pub move_to: Option<Vector2D>,
211 #[serde(skip_serializing_if = "Option::is_none")]
212 pub morph_move_to: Option<Vector2D>,
213 #[serde(skip_serializing_if = "Option::is_none")]
214 pub left_fill: Option<usize>,
215 #[serde(skip_serializing_if = "Option::is_none")]
216 pub right_fill: Option<usize>,
217 #[serde(skip_serializing_if = "Option::is_none")]
218 pub line_style: Option<usize>,
219 #[serde(skip_serializing_if = "Option::is_none")]
220 pub new_styles: Option<MorphShapeStyles>,
221 }
222}