mod readers; mod utils; pub use utils::validate_wad; use crate::lumps::{Lump, LumpType}; use std::{fs::File, io::Read, path::Path}; use super::header::Header; use crate::utils::{read_ascii, read_i16_le, read_u32_le}; pub struct WADFile { pub path: String, pub wad_id: String, pub num_lumps: u32, pub dir_offset: u32, pub directory: Vec, pub data: Vec, } impl WADFile { pub fn new(path: String) -> Self { if !(validate_wad(path.as_str()).unwrap()) { panic!(); } let file_path = Path::new(path.as_str()); let mut wad_file = File::open(file_path).unwrap(); let file_size = wad_file.metadata().unwrap().len() as usize; let mut file_buffer: Vec = Vec::with_capacity(file_size); wad_file.read_to_end(&mut file_buffer).unwrap(); let wad_header = Header::read_data(&file_buffer[0..12]); let mut lump_dir: Vec = Vec::with_capacity(wad_header.num_lumps as usize); let offset = wad_header.dir_offset; for entry in 0..wad_header.num_lumps { let startpos = (offset + 16 * entry) as usize; let lump_offset = read_u32_le(&file_buffer[startpos..startpos + 4]); let size = read_u32_le(&file_buffer[startpos + 4..startpos + 8]); let name = read_ascii(&file_buffer[startpos + 8..startpos + 16]); let lump_type = match name.as_str() { "VERTEXES" => LumpType::Vertex, "LINEDEFS" => LumpType::Linedef, "SIDEDEFS" => LumpType::Sidedef, "THINGS" => LumpType::Thing, _ => LumpType::Unknown, }; lump_dir.push(Lump { name, offset: lump_offset, lump_type, size, }); } Self { path, wad_id: wad_header.wad_id, num_lumps: wad_header.num_lumps, dir_offset: wad_header.dir_offset, directory: lump_dir, data: file_buffer, } } }