1use crate::{
7 BlockFormat, BlockInfo, DocumentStats, FindMatch, FindOptions, FrameFormat, TextFormat,
8};
9
10pub fn to_i64(v: usize) -> i64 {
13 debug_assert!(v <= i64::MAX as usize, "position overflow: {v}");
14 v as i64
15}
16
17pub fn to_usize(v: i64) -> usize {
18 assert!(v >= 0, "negative position: {v}");
19 v as usize
20}
21
22impl From<&frontend::document_inspection::DocumentStatsDto> for DocumentStats {
25 fn from(dto: &frontend::document_inspection::DocumentStatsDto) -> Self {
26 Self {
27 character_count: to_usize(dto.character_count),
28 word_count: to_usize(dto.word_count),
29 block_count: to_usize(dto.block_count),
30 frame_count: to_usize(dto.frame_count),
31 image_count: to_usize(dto.image_count),
32 list_count: to_usize(dto.list_count),
33 }
34 }
35}
36
37impl From<&frontend::document_inspection::BlockInfoDto> for BlockInfo {
40 fn from(dto: &frontend::document_inspection::BlockInfoDto) -> Self {
41 Self {
42 block_id: to_usize(dto.block_id),
43 block_number: to_usize(dto.block_number),
44 start: to_usize(dto.block_start),
45 length: to_usize(dto.block_length),
46 }
47 }
48}
49
50impl FindOptions {
53 pub(crate) fn to_find_text_dto(
54 &self,
55 query: &str,
56 start_position: usize,
57 ) -> frontend::document_search::FindTextDto {
58 frontend::document_search::FindTextDto {
59 query: query.into(),
60 case_sensitive: self.case_sensitive,
61 whole_word: self.whole_word,
62 use_regex: self.use_regex,
63 search_backward: self.search_backward,
64 start_position: to_i64(start_position),
65 }
66 }
67
68 pub(crate) fn to_find_all_dto(&self, query: &str) -> frontend::document_search::FindAllDto {
69 frontend::document_search::FindAllDto {
70 query: query.into(),
71 case_sensitive: self.case_sensitive,
72 whole_word: self.whole_word,
73 use_regex: self.use_regex,
74 }
75 }
76
77 pub(crate) fn to_replace_dto(
78 &self,
79 query: &str,
80 replacement: &str,
81 replace_all: bool,
82 ) -> frontend::document_search::ReplaceTextDto {
83 frontend::document_search::ReplaceTextDto {
84 query: query.into(),
85 replacement: replacement.into(),
86 case_sensitive: self.case_sensitive,
87 whole_word: self.whole_word,
88 use_regex: self.use_regex,
89 replace_all,
90 }
91 }
92}
93
94pub fn find_result_to_match(dto: &frontend::document_search::FindResultDto) -> Option<FindMatch> {
95 if dto.found {
96 Some(FindMatch {
97 position: to_usize(dto.position),
98 length: to_usize(dto.length),
99 })
100 } else {
101 None
102 }
103}
104
105pub fn find_all_to_matches(dto: &frontend::document_search::FindAllResultDto) -> Vec<FindMatch> {
106 dto.positions
107 .iter()
108 .zip(dto.lengths.iter())
109 .map(|(&pos, &len)| FindMatch {
110 position: to_usize(pos),
111 length: to_usize(len),
112 })
113 .collect()
114}
115
116use frontend::document_formatting::dtos as fmt_dto;
125
126fn underline_style_to_dto(v: &crate::UnderlineStyle) -> fmt_dto::UnderlineStyle {
127 match v {
128 crate::UnderlineStyle::NoUnderline => fmt_dto::UnderlineStyle::NoUnderline,
129 crate::UnderlineStyle::SingleUnderline => fmt_dto::UnderlineStyle::SingleUnderline,
130 crate::UnderlineStyle::DashUnderline => fmt_dto::UnderlineStyle::DashUnderline,
131 crate::UnderlineStyle::DotLine => fmt_dto::UnderlineStyle::DotLine,
132 crate::UnderlineStyle::DashDotLine => fmt_dto::UnderlineStyle::DashDotLine,
133 crate::UnderlineStyle::DashDotDotLine => fmt_dto::UnderlineStyle::DashDotDotLine,
134 crate::UnderlineStyle::WaveUnderline => fmt_dto::UnderlineStyle::WaveUnderline,
135 crate::UnderlineStyle::SpellCheckUnderline => fmt_dto::UnderlineStyle::SpellCheckUnderline,
136 }
137}
138
139fn vertical_alignment_to_dto(v: &crate::CharVerticalAlignment) -> fmt_dto::CharVerticalAlignment {
140 match v {
141 crate::CharVerticalAlignment::Normal => fmt_dto::CharVerticalAlignment::Normal,
142 crate::CharVerticalAlignment::SuperScript => fmt_dto::CharVerticalAlignment::SuperScript,
143 crate::CharVerticalAlignment::SubScript => fmt_dto::CharVerticalAlignment::SubScript,
144 crate::CharVerticalAlignment::Middle => fmt_dto::CharVerticalAlignment::Middle,
145 crate::CharVerticalAlignment::Bottom => fmt_dto::CharVerticalAlignment::Bottom,
146 crate::CharVerticalAlignment::Top => fmt_dto::CharVerticalAlignment::Top,
147 crate::CharVerticalAlignment::Baseline => fmt_dto::CharVerticalAlignment::Baseline,
148 }
149}
150
151fn alignment_to_dto(v: &crate::Alignment) -> fmt_dto::Alignment {
152 match v {
153 crate::Alignment::Left => fmt_dto::Alignment::Left,
154 crate::Alignment::Right => fmt_dto::Alignment::Right,
155 crate::Alignment::Center => fmt_dto::Alignment::Center,
156 crate::Alignment::Justify => fmt_dto::Alignment::Justify,
157 }
158}
159
160fn marker_to_dto(v: &crate::MarkerType) -> fmt_dto::MarkerType {
161 match v {
162 crate::MarkerType::NoMarker => fmt_dto::MarkerType::NoMarker,
163 crate::MarkerType::Unchecked => fmt_dto::MarkerType::Unchecked,
164 crate::MarkerType::Checked => fmt_dto::MarkerType::Checked,
165 }
166}
167
168impl TextFormat {
174 pub(crate) fn to_set_dto(
175 &self,
176 position: usize,
177 anchor: usize,
178 ) -> frontend::document_formatting::SetTextFormatDto {
179 frontend::document_formatting::SetTextFormatDto {
180 position: to_i64(position),
181 anchor: to_i64(anchor),
182 font_family: self.font_family.clone(),
183 font_point_size: self.font_point_size.map(|v| v as i64),
184 font_weight: self.font_weight.map(|v| v as i64),
185 font_bold: self.font_bold,
186 font_italic: self.font_italic,
187 font_underline: self.font_underline,
188 font_overline: self.font_overline,
189 font_strikeout: self.font_strikeout,
190 letter_spacing: self.letter_spacing.map(|v| v as i64),
191 word_spacing: self.word_spacing.map(|v| v as i64),
192 underline_style: self.underline_style.as_ref().map(underline_style_to_dto),
193 vertical_alignment: self
194 .vertical_alignment
195 .as_ref()
196 .map(vertical_alignment_to_dto),
197 }
198 }
199
200 pub(crate) fn to_merge_dto(
201 &self,
202 position: usize,
203 anchor: usize,
204 ) -> frontend::document_formatting::MergeTextFormatDto {
205 frontend::document_formatting::MergeTextFormatDto {
206 position: to_i64(position),
207 anchor: to_i64(anchor),
208 font_family: self.font_family.clone(),
209 font_bold: self.font_bold,
210 font_italic: self.font_italic,
211 font_underline: self.font_underline,
212 }
213 }
214}
215
216impl From<&frontend::inline_element::dtos::InlineElementDto> for TextFormat {
219 fn from(el: &frontend::inline_element::dtos::InlineElementDto) -> Self {
220 Self {
221 font_family: el.fmt_font_family.clone(),
222 font_point_size: el.fmt_font_point_size.map(|v| v as u32),
223 font_weight: el.fmt_font_weight.map(|v| v as u32),
224 font_bold: el.fmt_font_bold,
225 font_italic: el.fmt_font_italic,
226 font_underline: el.fmt_font_underline,
227 font_overline: el.fmt_font_overline,
228 font_strikeout: el.fmt_font_strikeout,
229 letter_spacing: el.fmt_letter_spacing.map(|v| v as i32),
230 word_spacing: el.fmt_word_spacing.map(|v| v as i32),
231 underline_style: el.fmt_underline_style.clone(),
232 vertical_alignment: el.fmt_vertical_alignment.clone(),
233 anchor_href: el.fmt_anchor_href.clone(),
234 anchor_names: el.fmt_anchor_names.clone(),
235 is_anchor: el.fmt_is_anchor,
236 tooltip: el.fmt_tooltip.clone(),
237 }
238 }
239}
240
241impl BlockFormat {
244 pub(crate) fn to_set_dto(
245 &self,
246 position: usize,
247 anchor: usize,
248 ) -> frontend::document_formatting::SetBlockFormatDto {
249 frontend::document_formatting::SetBlockFormatDto {
250 position: to_i64(position),
251 anchor: to_i64(anchor),
252 alignment: self.alignment.as_ref().map(alignment_to_dto),
253 heading_level: self.heading_level.map(|v| v as i64),
254 indent: self.indent.map(|v| v as i64),
255 marker: self.marker.as_ref().map(marker_to_dto),
256 }
257 }
258}
259
260impl From<&frontend::block::dtos::BlockDto> for BlockFormat {
261 fn from(b: &frontend::block::dtos::BlockDto) -> Self {
262 Self {
263 alignment: b.fmt_alignment.clone(),
264 top_margin: b.fmt_top_margin.map(|v| v as i32),
265 bottom_margin: b.fmt_bottom_margin.map(|v| v as i32),
266 left_margin: b.fmt_left_margin.map(|v| v as i32),
267 right_margin: b.fmt_right_margin.map(|v| v as i32),
268 heading_level: b.fmt_heading_level.map(|v| v as u8),
269 indent: b.fmt_indent.map(|v| v as u8),
270 text_indent: b.fmt_text_indent.map(|v| v as i32),
271 marker: b.fmt_marker.clone(),
272 tab_positions: b.fmt_tab_positions.iter().map(|&v| v as i32).collect(),
273 }
274 }
275}
276
277impl FrameFormat {
280 pub(crate) fn to_set_dto(
281 &self,
282 position: usize,
283 anchor: usize,
284 frame_id: usize,
285 ) -> frontend::document_formatting::SetFrameFormatDto {
286 frontend::document_formatting::SetFrameFormatDto {
287 position: to_i64(position),
288 anchor: to_i64(anchor),
289 frame_id: to_i64(frame_id),
290 height: self.height.map(|v| v as i64),
291 width: self.width.map(|v| v as i64),
292 top_margin: self.top_margin.map(|v| v as i64),
293 bottom_margin: self.bottom_margin.map(|v| v as i64),
294 left_margin: self.left_margin.map(|v| v as i64),
295 right_margin: self.right_margin.map(|v| v as i64),
296 padding: self.padding.map(|v| v as i64),
297 border: self.border.map(|v| v as i64),
298 }
299 }
300}