torque_tracker_engine/file/
mod.rs1use err::LoadErr;
2use impulse_format::{header, pattern};
3
4use crate::project::song::Song;
5
6pub mod err;
7pub mod impulse_format;
8
9#[derive(Debug, Clone, Copy)]
10pub struct InFilePtr(pub(crate) std::num::NonZeroU32);
11
12impl InFilePtr {
13 pub fn move_to_self<S: std::io::Seek>(self, seeker: &mut S) -> Result<(), std::io::Error> {
15 seeker
16 .seek(std::io::SeekFrom::Start(self.0.get().into()))
17 .map(|_| ())
18 }
19}
20
21pub fn parse_song<R: std::io::Read + std::io::Seek>(reader: &mut R) -> Result<Song, LoadErr> {
26 let mut defect_handler = |_| ();
28 let header = header::ImpulseHeader::parse(reader, &mut defect_handler)?;
29 let mut song = Song::default();
30 song.copy_values_from_header(&header);
31
32 for (idx, ptr) in header
34 .pattern_offsets
35 .iter()
36 .enumerate()
37 .flat_map(|(idx, ptr)| ptr.map(|ptr| (idx, ptr)))
38 {
39 ptr.move_to_self(reader)?;
40 let pattern = pattern::parse_pattern(reader, &mut defect_handler)?;
41 song.patterns[idx] = pattern;
42 }
43
44 Ok(song)
45}