Skip to main content

easyofd_core/graphics2d/
ofd_graphics_document.rs

1//! OFD 图形文档。
2//!
3//! 对应 Java: org.ofdrw.graphics2d.OFDGraphicsDocument
4//!
5//! Java 版中继承 `java.awt.Graphics2D` 体系,依赖 AWT 渲染管线。
6//! Rust 版提供简化结构,保留核心元数据字段,不包含 AWT 渲染逻辑。
7
8/// OFD 图形文档。
9///
10/// 对应 Java: org.ofdrw.graphics2d.OFDGraphicsDocument
11///
12/// 表示一个可通过图形 API 绘制的 OFD 文档容器。
13/// Java 版依赖 AWT;Rust 版保留文档级元数据。
14#[derive(Debug, Clone)]
15pub struct OfdGraphicsDocument {
16    /// 文档宽度(mm)。
17    pub width: f64,
18    /// 文档高度(mm)。
19    pub height: f64,
20    /// 文档标题。
21    pub title: Option<String>,
22    /// 作者。
23    pub author: Option<String>,
24    /// 已创建的页面数。
25    pub page_count: u32,
26}
27
28impl OfdGraphicsDocument {
29    /// 创建新的图形文档(A4 默认尺寸)。
30    #[must_use]
31    pub fn new() -> Self {
32        Self {
33            width: 210.0,
34            height: 297.0,
35            title: None,
36            author: None,
37            page_count: 0,
38        }
39    }
40
41    /// 创建指定尺寸的图形文档。
42    #[must_use]
43    pub fn with_size(width: f64, height: f64) -> Self {
44        Self {
45            width,
46            height,
47            title: None,
48            author: None,
49            page_count: 0,
50        }
51    }
52
53    /// 设置文档标题。
54    #[must_use]
55    pub fn title(mut self, title: impl Into<String>) -> Self {
56        self.title = Some(title.into());
57        self
58    }
59
60    /// 设置作者。
61    #[must_use]
62    pub fn author(mut self, author: impl Into<String>) -> Self {
63        self.author = Some(author.into());
64        self
65    }
66
67    /// 获取文档宽度(mm)。
68    #[must_use]
69    pub fn width(&self) -> f64 {
70        self.width
71    }
72
73    /// 获取文档高度(mm)。
74    #[must_use]
75    pub fn height(&self) -> f64 {
76        self.height
77    }
78
79    /// 获取已创建的页面数。
80    #[must_use]
81    pub fn page_count(&self) -> u32 {
82        self.page_count
83    }
84
85    /// 新增一页并返回页码。
86    pub fn new_page(&mut self) -> u32 {
87        self.page_count += 1;
88        self.page_count
89    }
90}
91
92impl Default for OfdGraphicsDocument {
93    fn default() -> Self {
94        Self::new()
95    }
96}
97
98#[cfg(test)]
99mod tests {
100    use super::*;
101
102    #[test]
103    fn test_new_default_a4() {
104        let doc = OfdGraphicsDocument::new();
105        assert!((doc.width - 210.0).abs() < f64::EPSILON);
106        assert!((doc.height - 297.0).abs() < f64::EPSILON);
107        assert!(doc.title.is_none());
108        assert_eq!(doc.page_count(), 0);
109    }
110
111    #[test]
112    fn test_with_size() {
113        let doc = OfdGraphicsDocument::with_size(100.0, 200.0);
114        assert!((doc.width() - 100.0).abs() < f64::EPSILON);
115        assert!((doc.height() - 200.0).abs() < f64::EPSILON);
116    }
117
118    #[test]
119    fn test_builder() {
120        let doc = OfdGraphicsDocument::new()
121            .title("测试文档")
122            .author("easyofd");
123        assert_eq!(doc.title.as_deref(), Some("测试文档"));
124        assert_eq!(doc.author.as_deref(), Some("easyofd"));
125    }
126
127    #[test]
128    fn test_new_page() {
129        let mut doc = OfdGraphicsDocument::new();
130        assert_eq!(doc.new_page(), 1);
131        assert_eq!(doc.new_page(), 2);
132        assert_eq!(doc.page_count(), 2);
133    }
134
135    #[test]
136    fn test_default() {
137        let doc = OfdGraphicsDocument::default();
138        assert_eq!(doc.page_count(), 0);
139    }
140
141    #[test]
142    fn test_clone_debug() {
143        let doc = OfdGraphicsDocument::new().title("x");
144        let doc2 = doc.clone();
145        assert_eq!(doc2.title.as_deref(), Some("x"));
146        assert!(format!("{doc:?}").contains("OfdGraphicsDocument"));
147    }
148}