docx_rust/document/
bidir.rs

1use hard_xml::{XmlRead, XmlWrite};
2use std::borrow::Cow;
3
4use crate::{__setter, __xml_test_suites, document::Run};
5
6/// A bidirectional embedding, which can nest to more bidirectional embeddings
7#[derive(Debug, Default, XmlRead, XmlWrite, Clone)]
8#[cfg_attr(test, derive(PartialEq))]
9#[xml(tag = "w:dir")]
10pub struct BidirectionalEmbedding<'a> {
11    // A BidirectionalEmbedding can have a number of rich text runs
12    #[xml(child = "w:r")]
13    pub runs: Vec<Run<'a>>,
14    // A BidirectionalEmbedding can include nested embedding layers
15    #[xml(child = "w:dir")]
16    pub nested_levels: Vec<BidirectionalEmbedding<'a>>,
17}
18
19impl<'a> BidirectionalEmbedding<'a> {
20    __setter!(runs: Vec<Run<'a>>);
21    __setter!(nested_levels: Vec<BidirectionalEmbedding<'a>>);
22
23    pub fn iter_text(&self) -> Box<dyn Iterator<Item = &Cow<'a, str>> + '_> {
24        Box::new(
25            self.runs.iter().flat_map(|run| run.iter_text()).chain(
26                self.nested_levels
27                    .iter()
28                    .flat_map(|nested| nested.iter_text()),
29            ),
30        )
31    }
32
33    pub fn iter_text_mut(&mut self) -> Box<dyn Iterator<Item = &mut Cow<'a, str>> + '_> {
34        Box::new(
35            self.runs
36                .iter_mut()
37                .flat_map(|run| run.iter_text_mut())
38                .chain(
39                    self.nested_levels
40                        .iter_mut()
41                        .flat_map(|nested| nested.iter_text_mut()),
42                ),
43        )
44    }
45}
46
47__xml_test_suites!(
48    BidirectionalEmbedding,
49    BidirectionalEmbedding::default(),
50    r#"<w:dir/>"#,
51    BidirectionalEmbedding::default().runs(vec![Run::default(), Run::default().push_text("text")]),
52    r#"<w:dir><w:r/><w:r><w:t>text</w:t></w:r></w:dir>"#,
53    BidirectionalEmbedding::default().nested_levels(vec![
54        BidirectionalEmbedding::default().runs(vec![Run::default()])
55    ]),
56    r#"<w:dir><w:dir><w:r/></w:dir></w:dir>"#,
57);