mirror of
https://codeberg.org/icewind/vbsp.git
synced 2026-06-03 10:44:07 +02:00
add pakfile support
This commit is contained in:
parent
7391f8124d
commit
dbce06b508
5 changed files with 70 additions and 1 deletions
|
|
@ -21,6 +21,7 @@ static_assertions = "1.1.0"
|
|||
num_enum = "0.5.6"
|
||||
vbsp-derive = { path = "derive", version = "*" }
|
||||
cgmath = "0.18.0"
|
||||
zip = { version = "0.5.13", path = "../zip", default-features = false, features = ["lzma"] }
|
||||
|
||||
[dev-dependencies]
|
||||
obj = "0.10"
|
||||
|
|
|
|||
|
|
@ -8,16 +8,21 @@ pub use self::entity::*;
|
|||
pub use self::game::*;
|
||||
pub use self::vector::*;
|
||||
use crate::bspfile::LumpType;
|
||||
use crate::StringError;
|
||||
use crate::{BspResult, StringError};
|
||||
use arrayvec::ArrayString;
|
||||
use binrw::io::SeekFrom;
|
||||
use binrw::{BinRead, BinResult, ReadOptions};
|
||||
use bitflags::bitflags;
|
||||
use bv::BitVec;
|
||||
use std::borrow::Cow;
|
||||
use std::fmt;
|
||||
use std::fmt::{Debug, Display, Formatter};
|
||||
use std::io::{Cursor, Read};
|
||||
use std::mem::{align_of, size_of};
|
||||
use std::ops::Index;
|
||||
use std::sync::Mutex;
|
||||
use zip::result::ZipError;
|
||||
use zip::ZipArchive;
|
||||
|
||||
#[cfg(test)]
|
||||
fn test_read_bytes<T: BinRead>()
|
||||
|
|
@ -410,3 +415,56 @@ impl VisData {
|
|||
visible_clusters
|
||||
}
|
||||
}
|
||||
|
||||
pub struct Packfile {
|
||||
zip: Mutex<ZipArchive<Cursor<Vec<u8>>>>,
|
||||
}
|
||||
|
||||
impl Clone for Packfile {
|
||||
fn clone(&self) -> Self {
|
||||
Packfile {
|
||||
zip: Mutex::new(self.zip.lock().unwrap().clone()),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl Debug for Packfile {
|
||||
fn fmt(&self, f: &mut Formatter<'_>) -> fmt::Result {
|
||||
f.debug_struct("Packfile")
|
||||
.field(
|
||||
"zip",
|
||||
&self
|
||||
.zip
|
||||
.lock()
|
||||
.unwrap()
|
||||
.file_names()
|
||||
.collect::<Vec<_>>()
|
||||
.join(", "),
|
||||
)
|
||||
.finish()
|
||||
}
|
||||
}
|
||||
|
||||
impl Packfile {
|
||||
pub fn read(data: Cow<[u8]>) -> BspResult<Self> {
|
||||
let reader = Cursor::new(data.into_owned());
|
||||
let zip = Mutex::new(ZipArchive::new(reader)?);
|
||||
Ok(Packfile { zip })
|
||||
}
|
||||
|
||||
pub fn get(&self, name: &str) -> BspResult<Option<Vec<u8>>> {
|
||||
let mut zip = self.zip.lock().unwrap();
|
||||
let mut entry = match zip.by_name(name) {
|
||||
Ok(entry) => entry,
|
||||
Err(ZipError::FileNotFound) => {
|
||||
return Ok(None);
|
||||
}
|
||||
Err(e) => {
|
||||
return Err(e.into());
|
||||
}
|
||||
};
|
||||
let mut buff = vec![0; entry.size() as usize];
|
||||
entry.read_exact(&mut buff)?;
|
||||
Ok(Some(buff))
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,6 +1,7 @@
|
|||
use crate::data::*;
|
||||
use std::num::{ParseFloatError, ParseIntError};
|
||||
use thiserror::Error;
|
||||
use zip::result::ZipError;
|
||||
|
||||
#[non_exhaustive]
|
||||
#[derive(Debug, Error)]
|
||||
|
|
@ -34,6 +35,8 @@ pub enum BspError {
|
|||
Validation(#[from] ValidationError),
|
||||
#[error(transparent)]
|
||||
LumpVersion(UnsupportedLumpVersion),
|
||||
#[error(transparent)]
|
||||
Zip(#[from] ZipError),
|
||||
}
|
||||
|
||||
impl From<binrw::Error> for BspError {
|
||||
|
|
|
|||
|
|
@ -177,6 +177,7 @@ pub struct Bsp {
|
|||
pub displacement_vertices: Vec<DisplacementVertex>,
|
||||
pub displacement_triangles: Vec<DisplacementTriangle>,
|
||||
pub static_props: PropStaticGameLump,
|
||||
pub pack: Packfile,
|
||||
}
|
||||
|
||||
impl Bsp {
|
||||
|
|
@ -241,6 +242,7 @@ impl Bsp {
|
|||
.lump_reader(LumpType::DisplacementTris)?
|
||||
.read_vec(|r| r.read())?;
|
||||
let game_lumps: GameLumpHeader = bsp_file.lump_reader(LumpType::GameLump)?.read()?;
|
||||
let pack = Packfile::read(bsp_file.lump_reader(LumpType::PakFile)?.into_data())?;
|
||||
|
||||
let static_props = game_lumps
|
||||
.find(data)
|
||||
|
|
@ -269,6 +271,7 @@ impl Bsp {
|
|||
displacement_vertices,
|
||||
displacement_triangles,
|
||||
static_props,
|
||||
pack,
|
||||
};
|
||||
bsp.validate()?;
|
||||
Ok(bsp)
|
||||
|
|
|
|||
|
|
@ -19,6 +19,10 @@ impl<'a> LumpReader<Cursor<Cow<'a, [u8]>>> {
|
|||
length,
|
||||
}
|
||||
}
|
||||
|
||||
pub fn into_data(self) -> Cow<'a, [u8]> {
|
||||
self.inner.into_inner()
|
||||
}
|
||||
}
|
||||
|
||||
impl<R: BinReaderExt + Read> LumpReader<R> {
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue