wgtk/space/section/
bwtb.rs1use std::fmt::{self, Formatter};
2use std::collections::HashMap;
3use std::io::Read;
4
5use super::{SectionId};
6use crate::util::io::WgReadExt;
7
8
9pub struct BWTB {
12 pub root: SectionMeta,
13 pub sections: Vec<SectionMeta>,
14 sections_from_id: HashMap<SectionId, usize>
15}
16
17impl BWTB {
18
19 pub fn decode<R: Read>(read: &mut R) -> std::io::Result<BWTB> {
20
21 let root = SectionMeta::decode(read)?;
22 assert_eq!(&root.id, b"BWTB");
23
24 let mut sections = Vec::with_capacity(root.sections_count);
25 for _ in 0..root.sections_count {
26 sections.push(SectionMeta::decode(read)?);
27 }
28
29 Ok(BWTB {
30 root,
31 sections_from_id: sections.iter()
32 .enumerate()
33 .map(|(i, r)| (r.id.clone(), i))
34 .collect(),
35 sections,
36 })
37
38 }
39
40 pub fn get_section_meta(&self, id: &SectionId) -> Option<&SectionMeta> {
42 self.sections.get(*self.sections_from_id.get(id)?)
43 }
44
45}
46
47
48pub struct SectionMeta {
51 pub id: SectionId,
52 pub off: usize,
53 pub len: usize,
54 pub sections_count: usize
55}
56
57impl SectionMeta {
58
59 fn decode<R: Read>(read: &mut R) -> std::io::Result<SectionMeta> {
60
61 let mut id = [0; 4];
62 read.read_exact(&mut id)?;
63
64 read.read_u32()?;
65 let off = read.read_u32()? as usize;
66 read.read_u32()?;
67 let len = read.read_u32()? as usize;
68 let rows_count = read.read_u32()? as usize;
69
70 Ok(SectionMeta {
71 id,
72 off,
73 len,
74 sections_count: rows_count
75 })
76
77 }
78
79}
80
81impl fmt::Debug for SectionMeta {
82
83 fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
84 f.debug_struct("SectionMeta")
85 .field("id", &self.id.iter().map(|&c| c as char).collect::<String>())
86 .field("off", &self.off)
87 .field("len", &self.len)
88 .finish()
89 }
90
91}