oxihuman_export/
ao_map_export.rs1#![allow(dead_code)]
3
4#[allow(dead_code)]
7#[derive(Debug, Clone)]
8pub struct AoMapConfig {
9 pub width: usize,
10 pub height: usize,
11 pub samples: usize,
12}
13
14#[allow(dead_code)]
15#[derive(Debug, Clone)]
16pub struct AoMapExport {
17 pub pixels: Vec<f32>,
18 pub width: usize,
19 pub height: usize,
20}
21
22#[allow(dead_code)]
23pub fn default_ao_map_config() -> AoMapConfig {
24 AoMapConfig {
25 width: 256,
26 height: 256,
27 samples: 16,
28 }
29}
30#[allow(dead_code)]
31pub fn new_ao_map(config: &AoMapConfig) -> AoMapExport {
32 AoMapExport {
33 pixels: vec![1.0; config.width * config.height],
34 width: config.width,
35 height: config.height,
36 }
37}
38#[allow(dead_code)]
39pub fn ao_set_pixel(map: &mut AoMapExport, x: usize, y: usize, val: f32) {
40 if x < map.width && y < map.height {
41 map.pixels[y * map.width + x] = val.clamp(0.0, 1.0);
42 }
43}
44#[allow(dead_code)]
45pub fn ao_get_pixel(map: &AoMapExport, x: usize, y: usize) -> f32 {
46 if x < map.width && y < map.height {
47 map.pixels[y * map.width + x]
48 } else {
49 0.0
50 }
51}
52#[allow(dead_code)]
53pub fn ao_pixel_count(map: &AoMapExport) -> usize {
54 map.pixels.len()
55}
56#[allow(dead_code)]
57pub fn ao_average(map: &AoMapExport) -> f32 {
58 if map.pixels.is_empty() {
59 0.0
60 } else {
61 map.pixels.iter().sum::<f32>() / map.pixels.len() as f32
62 }
63}
64#[allow(dead_code)]
65pub fn ao_to_bytes(map: &AoMapExport) -> Vec<u8> {
66 map.pixels.iter().map(|&v| (v * 255.0) as u8).collect()
67}
68#[allow(dead_code)]
69pub fn ao_to_json(map: &AoMapExport) -> String {
70 format!(
71 "{{\"width\":{},\"height\":{},\"pixels\":{}}}",
72 map.width,
73 map.height,
74 map.pixels.len()
75 )
76}
77#[allow(dead_code)]
78pub fn ao_validate(map: &AoMapExport) -> bool {
79 map.pixels.len() == map.width * map.height && map.pixels.iter().all(|v| (0.0..=1.0).contains(v))
80}
81
82pub struct AoMap {
85 pub width: u32,
86 pub height: u32,
87 pub data: Vec<f32>,
88}
89
90pub fn new_ao_map_req(w: u32, h: u32) -> AoMap {
91 AoMap {
92 width: w,
93 height: h,
94 data: vec![1.0; (w * h) as usize],
95 }
96}
97
98pub fn ao_set(m: &mut AoMap, x: u32, y: u32, v: f32) {
99 if x < m.width && y < m.height {
100 m.data[(y * m.width + x) as usize] = v.clamp(0.0, 1.0);
101 }
102}
103
104pub fn ao_get(m: &AoMap, x: u32, y: u32) -> f32 {
105 if x < m.width && y < m.height {
106 m.data[(y * m.width + x) as usize]
107 } else {
108 0.0
109 }
110}
111
112pub fn ao_to_u8(m: &AoMap) -> Vec<u8> {
113 m.data.iter().map(|&v| (v * 255.0) as u8).collect()
114}
115
116pub fn ao_mean(m: &AoMap) -> f32 {
117 if m.data.is_empty() {
118 return 0.0;
119 }
120 m.data.iter().sum::<f32>() / m.data.len() as f32
121}
122
123pub fn ao_to_bytes_req(m: &AoMap) -> Vec<u8> {
124 let mut b = Vec::new();
125 b.extend_from_slice(&m.width.to_le_bytes());
126 b.extend_from_slice(&m.height.to_le_bytes());
127 for &v in &m.data {
128 b.extend_from_slice(&v.to_le_bytes());
129 }
130 b
131}
132
133#[cfg(test)]
134mod tests {
135 use super::*;
136 #[test]
137 fn test_default() {
138 let c = default_ao_map_config();
139 assert_eq!(c.width, 256);
140 }
141 #[test]
142 fn test_new() {
143 let m = new_ao_map(&default_ao_map_config());
144 assert_eq!(m.pixels.len(), 256 * 256);
145 }
146 #[test]
147 fn test_set_get() {
148 let mut m = new_ao_map(&AoMapConfig {
149 width: 4,
150 height: 4,
151 samples: 1,
152 });
153 ao_set_pixel(&mut m, 1, 1, 0.5);
154 assert!((ao_get_pixel(&m, 1, 1) - 0.5).abs() < 1e-6);
155 }
156 #[test]
157 fn test_pixel_count() {
158 let m = new_ao_map(&AoMapConfig {
159 width: 4,
160 height: 4,
161 samples: 1,
162 });
163 assert_eq!(ao_pixel_count(&m), 16);
164 }
165 #[test]
166 fn test_average() {
167 let m = new_ao_map(&AoMapConfig {
168 width: 2,
169 height: 2,
170 samples: 1,
171 });
172 assert!((ao_average(&m) - 1.0).abs() < 1e-6);
173 }
174 #[test]
175 fn test_to_bytes() {
176 let m = new_ao_map(&AoMapConfig {
177 width: 2,
178 height: 2,
179 samples: 1,
180 });
181 let b = ao_to_bytes(&m);
182 assert_eq!(b.len(), 4);
183 }
184 #[test]
185 fn test_to_json() {
186 let m = new_ao_map(&AoMapConfig {
187 width: 2,
188 height: 2,
189 samples: 1,
190 });
191 assert!(ao_to_json(&m).contains("width"));
192 }
193 #[test]
194 fn test_validate() {
195 let m = new_ao_map(&AoMapConfig {
196 width: 2,
197 height: 2,
198 samples: 1,
199 });
200 assert!(ao_validate(&m));
201 }
202 #[test]
203 fn test_clamp() {
204 let mut m = new_ao_map(&AoMapConfig {
205 width: 2,
206 height: 2,
207 samples: 1,
208 });
209 ao_set_pixel(&mut m, 0, 0, 2.0);
210 assert!((ao_get_pixel(&m, 0, 0) - 1.0).abs() < 1e-6);
211 }
212 #[test]
213 fn test_oob() {
214 let m = new_ao_map(&AoMapConfig {
215 width: 2,
216 height: 2,
217 samples: 1,
218 });
219 assert!((ao_get_pixel(&m, 99, 99)).abs() < 1e-6);
220 }
221}