1#![allow(dead_code)]
4
5#[allow(dead_code)]
8#[derive(Debug, Clone, Copy, PartialEq, Eq, Default)]
9pub struct EdgeFlags {
10 pub is_seam: bool,
11 pub is_sharp: bool,
12 pub is_crease: bool,
13 pub is_freestyle: bool,
14}
15
16#[allow(dead_code)]
17#[derive(Debug, Clone)]
18pub struct MarkedEdge {
19 pub v0: u32,
20 pub v1: u32,
21 pub flags: EdgeFlags,
22 pub crease_value: f32,
23}
24
25#[allow(dead_code)]
26#[derive(Debug, Clone)]
27pub struct EdgeMarkExport {
28 pub edges: Vec<MarkedEdge>,
29}
30
31#[allow(dead_code)]
32pub fn new_edge_mark_export() -> EdgeMarkExport {
33 EdgeMarkExport { edges: Vec::new() }
34}
35
36#[allow(dead_code)]
37pub fn add_marked_edge(exp: &mut EdgeMarkExport, v0: u32, v1: u32, flags: EdgeFlags) {
38 exp.edges.push(MarkedEdge {
39 v0,
40 v1,
41 flags,
42 crease_value: 0.0,
43 });
44}
45
46#[allow(dead_code)]
47pub fn marked_edge_count(exp: &EdgeMarkExport) -> usize {
48 exp.edges.len()
49}
50
51#[allow(dead_code)]
52pub fn seam_edge_count_em(exp: &EdgeMarkExport) -> usize {
53 exp.edges.iter().filter(|e| e.flags.is_seam).count()
54}
55
56#[allow(dead_code)]
57pub fn sharp_edge_count_em(exp: &EdgeMarkExport) -> usize {
58 exp.edges.iter().filter(|e| e.flags.is_sharp).count()
59}
60
61#[allow(dead_code)]
62pub fn crease_edge_count_em(exp: &EdgeMarkExport) -> usize {
63 exp.edges.iter().filter(|e| e.flags.is_crease).count()
64}
65
66#[allow(dead_code)]
67pub fn set_crease_value(exp: &mut EdgeMarkExport, v0: u32, v1: u32, value: f32) {
68 for e in &mut exp.edges {
69 let (ea, eb) = if e.v0 < e.v1 {
70 (e.v0, e.v1)
71 } else {
72 (e.v1, e.v0)
73 };
74 let (qa, qb) = if v0 < v1 { (v0, v1) } else { (v1, v0) };
75 if ea == qa && eb == qb {
76 e.crease_value = value.clamp(0.0, 1.0);
77 }
78 }
79}
80
81#[allow(dead_code)]
82pub fn edge_mark_to_json(exp: &EdgeMarkExport) -> String {
83 format!(
84 "{{\"edge_count\":{},\"seams\":{},\"sharp\":{}}}",
85 marked_edge_count(exp),
86 seam_edge_count_em(exp),
87 sharp_edge_count_em(exp),
88 )
89}
90
91#[allow(dead_code)]
92pub fn avg_crease_value(exp: &EdgeMarkExport) -> f32 {
93 let creased: Vec<f32> = exp
94 .edges
95 .iter()
96 .filter(|e| e.flags.is_crease)
97 .map(|e| e.crease_value)
98 .collect();
99 if creased.is_empty() {
100 return 0.0;
101 }
102 creased.iter().sum::<f32>() / creased.len() as f32
103}
104
105#[cfg(test)]
106mod tests {
107 use super::*;
108
109 #[test]
110 fn test_empty() {
111 let exp = new_edge_mark_export();
112 assert_eq!(marked_edge_count(&exp), 0);
113 }
114
115 #[test]
116 fn test_add_edge() {
117 let mut exp = new_edge_mark_export();
118 add_marked_edge(
119 &mut exp,
120 0,
121 1,
122 EdgeFlags {
123 is_seam: true,
124 ..Default::default()
125 },
126 );
127 assert_eq!(marked_edge_count(&exp), 1);
128 }
129
130 #[test]
131 fn test_seam_count() {
132 let mut exp = new_edge_mark_export();
133 add_marked_edge(
134 &mut exp,
135 0,
136 1,
137 EdgeFlags {
138 is_seam: true,
139 ..Default::default()
140 },
141 );
142 add_marked_edge(&mut exp, 1, 2, EdgeFlags::default());
143 assert_eq!(seam_edge_count_em(&exp), 1);
144 }
145
146 #[test]
147 fn test_sharp_count() {
148 let mut exp = new_edge_mark_export();
149 add_marked_edge(
150 &mut exp,
151 0,
152 1,
153 EdgeFlags {
154 is_sharp: true,
155 ..Default::default()
156 },
157 );
158 assert_eq!(sharp_edge_count_em(&exp), 1);
159 }
160
161 #[test]
162 fn test_crease_count() {
163 let mut exp = new_edge_mark_export();
164 add_marked_edge(
165 &mut exp,
166 0,
167 1,
168 EdgeFlags {
169 is_crease: true,
170 ..Default::default()
171 },
172 );
173 assert_eq!(crease_edge_count_em(&exp), 1);
174 }
175
176 #[test]
177 fn test_set_crease_value() {
178 let mut exp = new_edge_mark_export();
179 add_marked_edge(
180 &mut exp,
181 0,
182 1,
183 EdgeFlags {
184 is_crease: true,
185 ..Default::default()
186 },
187 );
188 set_crease_value(&mut exp, 0, 1, 0.8);
189 assert!((exp.edges[0].crease_value - 0.8).abs() < 1e-5);
190 }
191
192 #[test]
193 fn test_json_output() {
194 let exp = new_edge_mark_export();
195 let j = edge_mark_to_json(&exp);
196 assert!(j.contains("edge_count"));
197 }
198
199 #[test]
200 fn test_avg_crease_empty() {
201 let exp = new_edge_mark_export();
202 assert!((avg_crease_value(&exp)).abs() < 1e-6);
203 }
204
205 #[test]
206 fn test_avg_crease_value() {
207 let mut exp = new_edge_mark_export();
208 add_marked_edge(
209 &mut exp,
210 0,
211 1,
212 EdgeFlags {
213 is_crease: true,
214 ..Default::default()
215 },
216 );
217 set_crease_value(&mut exp, 0, 1, 1.0);
218 assert!((avg_crease_value(&exp) - 1.0).abs() < 1e-5);
219 }
220
221 #[test]
222 fn test_default_crease_zero() {
223 let mut exp = new_edge_mark_export();
224 add_marked_edge(&mut exp, 5, 6, EdgeFlags::default());
225 assert!((exp.edges[0].crease_value).abs() < 1e-6);
226 }
227}