bsp_loader: move loader files to map-tool + remove hardcoded file reads

This commit is contained in:
2026-03-02 09:23:03 -08:00
parent e0d1ad48a8
commit 99d38a6eae
5 changed files with 35 additions and 60 deletions

View File

@@ -1,9 +1,6 @@
use strafesnet_deferred_loader::deferred_loader::{LoadFailureMode,MeshDeferredLoader,RenderConfigDeferredLoader};
mod bsp;
mod mesh;
pub mod bsp;
pub mod mesh;
mod brush;
pub mod loader;
const VALVE_SCALE:f32=1.0/16.0;
pub(crate) fn valve_transform_dist(d:f32)->strafesnet_common::integer::Planar64{
@@ -28,28 +25,6 @@ impl std::fmt::Display for ReadError{
}
impl std::error::Error for ReadError{}
#[derive(Debug)]
pub enum LoadError{
Texture(loader::TextureError),
Mesh(loader::MeshError),
}
impl std::fmt::Display for LoadError{
fn fmt(&self,f:&mut std::fmt::Formatter<'_>)->std::fmt::Result{
write!(f,"{self:?}")
}
}
impl std::error::Error for LoadError{}
impl From<loader::TextureError> for LoadError{
fn from(value:loader::TextureError)->Self{
Self::Texture(value)
}
}
impl From<loader::MeshError> for LoadError{
fn from(value:loader::MeshError)->Self{
Self::Mesh(value)
}
}
pub struct Bsp{
bsp:vbsp::Bsp,
case_folded_file_names:std::collections::HashMap<String,String>,
@@ -84,28 +59,6 @@ impl Bsp{
None=>Ok(None),
}
}
pub fn to_snf(&self,failure_mode:LoadFailureMode,vpk_list:&[Vpk])->Result<strafesnet_common::map::CompleteMap,LoadError>{
let mut texture_deferred_loader=RenderConfigDeferredLoader::new();
let mut mesh_deferred_loader=MeshDeferredLoader::new();
let map_step1=bsp::convert(
self,
&mut texture_deferred_loader,
&mut mesh_deferred_loader,
);
let mut mesh_loader=loader::MeshLoader::new(loader::BspFinder{bsp:self,vpks:vpk_list},&mut texture_deferred_loader);
let prop_meshes=mesh_deferred_loader.into_meshes(&mut mesh_loader,failure_mode).map_err(LoadError::Mesh)?;
let map_step2=map_step1.add_prop_meshes(prop_meshes);
let mut texture_loader=loader::TextureLoader::new();
let render_configs=texture_deferred_loader.into_render_configs(&mut texture_loader,failure_mode).map_err(LoadError::Texture)?;
let map=map_step2.add_render_configs_and_textures(render_configs);
Ok(map)
}
}
pub struct Vpk{
vpk:vpk::VPK,

View File

@@ -1,163 +0,0 @@
use std::{borrow::Cow, io::Read};
use strafesnet_common::model::Mesh;
use strafesnet_deferred_loader::{loader::Loader,texture::Texture};
use crate::{Bsp,Vpk};
#[derive(Debug)]
pub enum TextureError{
Io(std::io::Error),
}
impl std::fmt::Display for TextureError{
fn fmt(&self,f:&mut std::fmt::Formatter<'_>)->std::fmt::Result{
write!(f,"{self:?}")
}
}
impl std::error::Error for TextureError{}
impl From<std::io::Error> for TextureError{
fn from(value:std::io::Error)->Self{
Self::Io(value)
}
}
pub struct TextureLoader;
impl TextureLoader{
pub fn new()->Self{
Self
}
}
impl Loader for TextureLoader{
type Error=TextureError;
type Index<'a>=Cow<'a,str>;
type Resource=Texture;
fn load(&mut self,index:Self::Index<'_>)->Result<Self::Resource,Self::Error>{
let file_name=format!("textures/{}.dds",index);
let mut file=std::fs::File::open(file_name)?;
let mut data=Vec::new();
file.read_to_end(&mut data)?;
Ok(Texture::ImageDDS(data))
}
}
#[derive(Debug)]
pub enum MeshError{
Io(std::io::Error),
VMDL(vmdl::ModelError),
VBSP(vbsp::BspError),
MissingMdl(String),
MissingVtx,
MissingVvd,
}
impl std::fmt::Display for MeshError{
fn fmt(&self,f:&mut std::fmt::Formatter<'_>)->std::fmt::Result{
write!(f,"{self:?}")
}
}
impl std::error::Error for MeshError{}
impl From<std::io::Error> for MeshError{
fn from(value:std::io::Error)->Self{
Self::Io(value)
}
}
impl From<vmdl::ModelError> for MeshError{
fn from(value:vmdl::ModelError)->Self{
Self::VMDL(value)
}
}
impl From<vbsp::BspError> for MeshError{
fn from(value:vbsp::BspError)->Self{
Self::VBSP(value)
}
}
#[derive(Clone,Copy)]
pub struct BspFinder<'bsp,'vpk>{
pub bsp:&'bsp Bsp,
pub vpks:&'vpk [Vpk],
}
impl<'bsp,'vpk> BspFinder<'bsp,'vpk>{
pub fn find<'a>(&self,path:&str)->Result<Option<Cow<'a,[u8]>>,vbsp::BspError>
where
'bsp:'a,
'vpk:'a,
{
// search bsp
if let Some(data)=self.bsp.pack_get(path)?{
return Ok(Some(Cow::Owned(data)));
}
//search each vpk
for vpk in self.vpks{
if let Some(vpk_entry)=vpk.tree_get(path){
return Ok(Some(vpk_entry.get()?));
}
}
Ok(None)
}
}
pub struct ModelLoader<'bsp,'vpk>{
finder:BspFinder<'bsp,'vpk>,
}
impl ModelLoader<'_,'_>{
#[inline]
pub const fn new<'bsp,'vpk>(
finder:BspFinder<'bsp,'vpk>,
)->ModelLoader<'bsp,'vpk>{
ModelLoader{
finder,
}
}
}
impl Loader for ModelLoader<'_,'_>{
type Error=MeshError;
type Index<'a>=&'a str where Self:'a;
type Resource=vmdl::Model;
fn load<'a>(&'a mut self,index:Self::Index<'a>)->Result<Self::Resource,Self::Error>{
let mdl_path_lower=index.to_lowercase();
//.mdl, .vvd, .dx90.vtx
let path=std::path::PathBuf::from(mdl_path_lower.as_str());
let mut vvd_path=path.clone();
let mut vtx_path=path;
vvd_path.set_extension("vvd");
vtx_path.set_extension("dx90.vtx");
// TODO: search more packs, possibly using an index of multiple packs
let mdl=self.finder.find(mdl_path_lower.as_str())?.ok_or(MeshError::MissingMdl(mdl_path_lower))?;
let vtx=self.finder.find(vtx_path.as_os_str().to_str().unwrap())?.ok_or(MeshError::MissingVtx)?;
let vvd=self.finder.find(vvd_path.as_os_str().to_str().unwrap())?.ok_or(MeshError::MissingVvd)?;
Ok(vmdl::Model::from_parts(
vmdl::mdl::Mdl::read(mdl.as_ref())?,
vmdl::vtx::Vtx::read(vtx.as_ref())?,
vmdl::vvd::Vvd::read(vvd.as_ref())?,
))
}
}
pub struct MeshLoader<'bsp,'vpk,'load,'str>{
finder:BspFinder<'bsp,'vpk>,
deferred_loader:&'load mut strafesnet_deferred_loader::deferred_loader::RenderConfigDeferredLoader<Cow<'str,str>>,
}
impl MeshLoader<'_,'_,'_,'_>{
#[inline]
pub const fn new<'bsp,'vpk,'load,'str>(
finder:BspFinder<'bsp,'vpk>,
deferred_loader:&'load mut strafesnet_deferred_loader::deferred_loader::RenderConfigDeferredLoader<Cow<'str,str>>,
)->MeshLoader<'bsp,'vpk,'load,'str>{
MeshLoader{
finder,
deferred_loader
}
}
}
impl Loader for MeshLoader<'_,'_,'_,'_>{
type Error=MeshError;
type Index<'a>=&'a str where Self:'a;
type Resource=Mesh;
fn load<'a>(&'a mut self,index:Self::Index<'a>)->Result<Self::Resource,Self::Error>{
let model=ModelLoader::new(self.finder).load(index)?;
let mesh=crate::mesh::convert_mesh(model,&mut self.deferred_loader);
Ok(mesh)
}
}

View File

@@ -5,6 +5,8 @@ use strafesnet_deferred_loader::deferred_loader::RenderConfigDeferredLoader;
use crate::valve_transform;
pub use model::Mesh;
fn ingest_vertex(mb:&mut model::MeshBuilder,vertex:&vmdl::vvd::Vertex,color:model::ColorId)->model::VertexId{
let pos=mb.acquire_pos_id(valve_transform(vertex.position.into()));
let normal=mb.acquire_normal_id(valve_transform(vertex.normal.into()));
@@ -17,7 +19,7 @@ fn ingest_vertex(mb:&mut model::MeshBuilder,vertex:&vmdl::vvd::Vertex,color:mode
})
}
pub fn convert_mesh(model:vmdl::Model,deferred_loader:&mut RenderConfigDeferredLoader<Cow<str>>)->model::Mesh{
pub fn convert_mesh(model:vmdl::Model,deferred_loader:&mut RenderConfigDeferredLoader<Cow<str>>)->Mesh{
let texture_paths=model.texture_directories();
if texture_paths.len()!=1{
println!("WARNING: multiple texture paths");