umya_spreadsheet/structs/drawing/
outline.rs

1// a:ln
2use super::Bevel;
3use super::GradientFill;
4use super::Miter;
5use super::NoFill;
6use super::PenAlignmentValues;
7use super::PresetDash;
8use super::Round;
9use super::SolidFill;
10use super::SystemColor;
11use super::TailEnd;
12use crate::reader::driver::*;
13use crate::structs::EnumValue;
14use crate::structs::UInt32Value;
15use crate::writer::driver::*;
16use crate::StringValue;
17use quick_xml::events::{BytesStart, Event};
18use quick_xml::Reader;
19use quick_xml::Writer;
20use std::io::Cursor;
21
22#[derive(Clone, Default, Debug)]
23pub struct Outline {
24    width: UInt32Value,
25    cap_type: StringValue,
26    compound_line_type: StringValue,
27    solid_fill: Option<Box<SolidFill>>,
28    gradient_fill: Option<Box<GradientFill>>,
29    tail_end: Option<Box<TailEnd>>,
30    no_fill: Option<NoFill>,
31    bevel: Option<Box<Bevel>>,
32    preset_dash: Option<PresetDash>,
33    miter: Option<Miter>,
34    round: Option<Round>,
35    alignment: EnumValue<PenAlignmentValues>,
36    system_color: Option<Box<SystemColor>>,
37}
38
39impl Outline {
40    #[inline]
41    pub fn get_width(&self) -> &u32 {
42        self.width.get_value()
43    }
44
45    #[inline]
46    pub fn set_width(&mut self, value: u32) -> &mut Self {
47        self.width.set_value(value);
48        self
49    }
50
51    #[inline]
52    pub fn get_cap_type(&self) -> Option<&str> {
53        self.cap_type.get_value()
54    }
55
56    #[inline]
57    pub fn set_cap_type<S: Into<String>>(&mut self, value: S) -> &mut Self {
58        self.cap_type.set_value(value);
59        self
60    }
61
62    #[inline]
63    pub fn get_compound_line_type(&self) -> Option<&str> {
64        self.compound_line_type.get_value()
65    }
66
67    #[inline]
68    pub fn set_compound_line_type<S: Into<String>>(&mut self, value: S) -> &mut Self {
69        self.compound_line_type.set_value(value);
70        self
71    }
72
73    #[inline]
74    pub fn get_solid_fill(&self) -> Option<&SolidFill> {
75        self.solid_fill.as_deref()
76    }
77
78    #[inline]
79    pub fn get_solid_fill_mut(&mut self) -> Option<&mut SolidFill> {
80        self.solid_fill.as_deref_mut()
81    }
82
83    #[inline]
84    pub fn set_solid_fill(&mut self, value: SolidFill) -> &mut Self {
85        self.solid_fill = Some(Box::new(value));
86        self
87    }
88
89    #[inline]
90    pub fn get_gradient_fill(&self) -> Option<&GradientFill> {
91        self.gradient_fill.as_deref()
92    }
93
94    #[inline]
95    pub fn get_gradient_fill_mut(&mut self) -> Option<&mut GradientFill> {
96        self.gradient_fill.as_deref_mut()
97    }
98
99    #[inline]
100    pub fn set_gradient_fill(&mut self, value: GradientFill) -> &mut Self {
101        self.gradient_fill = Some(Box::new(value));
102        self
103    }
104
105    #[inline]
106    pub fn get_tail_end(&self) -> Option<&TailEnd> {
107        self.tail_end.as_deref()
108    }
109
110    #[inline]
111    pub fn get_tail_end_mut(&mut self) -> Option<&mut TailEnd> {
112        self.tail_end.as_deref_mut()
113    }
114
115    #[inline]
116    pub fn set_tail_end(&mut self, value: TailEnd) -> &mut Self {
117        self.tail_end = Some(Box::new(value));
118        self
119    }
120
121    #[inline]
122    pub fn get_no_fill(&self) -> Option<&NoFill> {
123        self.no_fill.as_ref()
124    }
125
126    #[inline]
127    pub fn get_no_fill_mut(&mut self) -> Option<&mut NoFill> {
128        self.no_fill.as_mut()
129    }
130
131    #[inline]
132    pub fn set_no_fill(&mut self, value: NoFill) -> &mut Self {
133        self.no_fill = Some(value);
134        self
135    }
136
137    #[inline]
138    pub fn get_bevel(&self) -> Option<&Bevel> {
139        self.bevel.as_deref()
140    }
141
142    #[inline]
143    pub fn get_bevel_mut(&mut self) -> Option<&mut Bevel> {
144        self.bevel.as_deref_mut()
145    }
146
147    #[inline]
148    pub fn set_bevel(&mut self, value: Bevel) -> &mut Self {
149        self.bevel = Some(Box::new(value));
150        self
151    }
152
153    #[inline]
154    pub fn get_preset_dash(&self) -> Option<&PresetDash> {
155        self.preset_dash.as_ref()
156    }
157
158    #[inline]
159    pub fn get_preset_dash_mut(&mut self) -> Option<&mut PresetDash> {
160        self.preset_dash.as_mut()
161    }
162
163    #[inline]
164    pub fn set_preset_dash(&mut self, value: PresetDash) -> &mut Self {
165        self.preset_dash = Some(value);
166        self
167    }
168
169    #[inline]
170    pub fn get_miter(&self) -> Option<&Miter> {
171        self.miter.as_ref()
172    }
173
174    #[inline]
175    pub fn get_miter_mut(&mut self) -> Option<&mut Miter> {
176        self.miter.as_mut()
177    }
178
179    #[inline]
180    pub fn set_miter(&mut self, value: Miter) -> &mut Self {
181        self.miter = Some(value);
182        self
183    }
184
185    #[inline]
186    pub fn get_round(&self) -> Option<&Round> {
187        self.round.as_ref()
188    }
189
190    #[inline]
191    pub fn get_round_mut(&mut self) -> Option<&mut Round> {
192        self.round.as_mut()
193    }
194
195    #[inline]
196    pub fn set_round(&mut self, value: Round) -> &mut Self {
197        self.round = Some(value);
198        self
199    }
200
201    #[inline]
202    pub fn get_alignment(&self) -> &PenAlignmentValues {
203        self.alignment.get_value()
204    }
205
206    #[inline]
207    pub fn set_alignment(&mut self, value: PenAlignmentValues) {
208        self.alignment.set_value(value);
209    }
210
211    #[inline]
212    pub fn set_system_color(&mut self, value: SystemColor) {
213        self.system_color = Some(Box::new(value));
214    }
215
216    #[inline]
217    pub fn get_system_color(&self) -> Option<&SystemColor> {
218        self.system_color.as_deref()
219    }
220
221    #[inline]
222    pub fn get_system_color_mut(&mut self) -> Option<&mut SystemColor> {
223        self.system_color.as_deref_mut()
224    }
225
226    pub(crate) fn set_attributes<R: std::io::BufRead>(
227        &mut self,
228        reader: &mut Reader<R>,
229        e: &BytesStart,
230    ) {
231        if let Some(v) = get_attribute(e, b"w") {
232            self.set_width(v.parse::<u32>().unwrap());
233        }
234
235        if let Some(v) = get_attribute(e, b"cap") {
236            self.set_cap_type(v);
237        }
238
239        if let Some(v) = get_attribute(e, b"cmpd") {
240            self.set_compound_line_type(v);
241        }
242
243        set_string_from_xml!(self, e, alignment, "algn");
244
245        xml_read_loop!(
246            reader,
247            Event::Start(ref e) => {
248                match e.name().into_inner() {
249                    b"a:solidFill" => {
250                        let mut solid_fill = SolidFill::default();
251                        solid_fill.set_attributes(reader, e);
252                        self.set_solid_fill(solid_fill);
253                    }
254                    b"a:gradFill" => {
255                        let mut obj = GradientFill::default();
256                        obj.set_attributes(reader, e);
257                        self.set_gradient_fill(obj);
258                    }
259                    b"a:tailEnd" => {
260                        let mut obj = TailEnd::default();
261                        obj.set_attributes(reader, e, false);
262                        self.set_tail_end(obj);
263                    }
264                    b"a:noFill" => {
265                        let mut obj = NoFill::default();
266                        obj.set_attributes(reader, e, false);
267                        self.set_no_fill(obj);
268                    }
269                    b"a:bevel" => {
270                        let mut obj = Bevel::default();
271                        obj.set_attributes(reader, e, false);
272                        self.set_bevel(obj);
273                    }
274                    b"a:miter" => {
275                        let mut obj = Miter::default();
276                        obj.set_attributes(reader, e, false);
277                        self.set_miter(obj);
278                    }
279                    b"a:prstDash" => {
280                        let mut obj = PresetDash::default();
281                        obj.set_attributes(reader, e, false);
282                        self.set_preset_dash(obj);
283                    }
284                    b"a:round" => {
285                        let mut obj = Round::default();
286                        obj.set_attributes(reader, e, false);
287                        self.set_round(obj);
288                    }
289                    b"a:sysClr" => {
290                        let mut obj = SystemColor::default();
291                        obj.set_attributes(reader, e, false);
292                        self.set_system_color(obj);
293                    }
294                    _ => (),
295                }
296            },
297            Event::Empty(ref e) => {
298                match e.name().into_inner() {
299                    b"a:tailEnd" => {
300                        let mut obj = TailEnd::default();
301                        obj.set_attributes(reader, e, true);
302                        self.set_tail_end(obj);
303                    }
304                    b"a:noFill" => {
305                        let mut obj = NoFill::default();
306                        obj.set_attributes(reader, e, true);
307                        self.set_no_fill(obj);
308                    }
309                    b"a:bevel" => {
310                        let mut obj = Bevel::default();
311                        obj.set_attributes(reader, e, true);
312                        self.set_bevel(obj);
313                    }
314                    b"a:miter" => {
315                        let mut obj = Miter::default();
316                        obj.set_attributes(reader, e, true);
317                        self.set_miter(obj);
318                    }
319                    b"a:prstDash" => {
320                        let mut obj = PresetDash::default();
321                        obj.set_attributes(reader, e, true);
322                        self.set_preset_dash(obj);
323                    }
324                    b"a:round" => {
325                        let mut obj = Round::default();
326                        obj.set_attributes(reader, e, true);
327                        self.set_round(obj);
328                    }
329                    b"a:sysClr" => {
330                        let mut obj = SystemColor::default();
331                        obj.set_attributes(reader, e, true);
332                        self.set_system_color(obj);
333                    }
334                    _ => (),
335                }
336            },
337            Event::End(ref e) => {
338                if  e.name().into_inner() == b"a:ln" {
339                    return;
340                }
341            },
342            Event::Eof => panic!("Error: Could not find {} end element", "a:ln")
343        );
344    }
345
346    pub(crate) fn write_to(&self, writer: &mut Writer<Cursor<Vec<u8>>>) {
347        // a:ln
348        let mut attributes: Vec<(&str, &str)> = Vec::new();
349        let width = self.width.get_value_string();
350        if self.width.has_value() {
351            attributes.push(("w", &width));
352        }
353        if let Some(v) = self.cap_type.get_value() {
354            attributes.push(("cap", v));
355        }
356        if let Some(v) = self.compound_line_type.get_value() {
357            attributes.push(("cmpd", v));
358        }
359        if self.alignment.has_value() {
360            attributes.push(("algn", (self.alignment.get_value_string())));
361        }
362        write_start_tag(writer, "a:ln", attributes, false);
363
364        // a:solidFill
365        if let Some(v) = &self.solid_fill {
366            v.write_to(writer);
367        }
368
369        // a:gradFill
370        if let Some(v) = &self.gradient_fill {
371            v.write_to(writer);
372        }
373
374        // a:round
375        if let Some(v) = &self.round {
376            v.write_to(writer);
377        }
378
379        // a:tailEnd
380        if let Some(v) = &self.tail_end {
381            v.write_to(writer);
382        }
383
384        // a:noFill
385        if let Some(v) = &self.no_fill {
386            v.write_to(writer);
387        }
388
389        // a:bevel
390        if let Some(v) = &self.bevel {
391            v.write_to(writer);
392        }
393
394        // a:prstDash
395        if let Some(v) = &self.preset_dash {
396            v.write_to(writer);
397        }
398
399        // a:miter
400        if let Some(v) = &self.miter {
401            v.write_to(writer);
402        }
403
404        write_end_tag(writer, "a:ln");
405    }
406}