complete mesh converter

This commit is contained in:
Quaternions 2024-03-12 21:11:04 -07:00
parent c1062449b2
commit 117546deeb

View File

@ -1,7 +1,7 @@
use std::collections::HashMap; use std::collections::HashMap;
use rbx_mesh::mesh::{Vertex2, Vertex2Truncated}; use rbx_mesh::mesh::{Vertex2, Vertex2Truncated};
use strafesnet_common::{integer::Planar64Vec3,model::{self,ColorId,IndexedVertex,NormalId,PolygonList,PositionId,TextureCoordinateId,VertexId}}; use strafesnet_common::{integer::Planar64Vec3,model::{self, ColorId, IndexedVertex, NormalId, PolygonGroup, PolygonList, PositionId, TextureCoordinateId, VertexId}};
#[derive(Debug)] #[derive(Debug)]
pub enum Error{ pub enum Error{
@ -80,6 +80,20 @@ where
))).collect::<Result<_,_>>()?) ))).collect::<Result<_,_>>()?)
} }
fn ingest_faces2_lods3(
polygon_groups:&mut Vec<PolygonGroup>,
vertex_id_map:&HashMap<rbx_mesh::mesh::VertexId2,VertexId>,
faces:&Vec<rbx_mesh::mesh::Face2>,
lods:&Vec<rbx_mesh::mesh::Lod3>
){
//faces have to be split into polygon groups based on lod
polygon_groups.extend(lods.windows(2).map(|lod_pair|
PolygonGroup::PolygonList(PolygonList::new(faces[lod_pair[0].0 as usize..lod_pair[1].0 as usize].iter().map(|face|
vec![vertex_id_map[&face.0],vertex_id_map[&face.1],vertex_id_map[&face.2]]
).collect()))
))
}
pub fn convert(roblox_mesh_bytes:crate::data::RobloxMeshBytes)->Result<model::Mesh,Error>{ pub fn convert(roblox_mesh_bytes:crate::data::RobloxMeshBytes)->Result<model::Mesh,Error>{
//generate that mesh boi //generate that mesh boi
let mut unique_pos=Vec::new(); let mut unique_pos=Vec::new();
@ -92,7 +106,7 @@ pub fn convert(roblox_mesh_bytes:crate::data::RobloxMeshBytes)->Result<model::Me
let mut color_id_from=HashMap::new(); let mut color_id_from=HashMap::new();
let mut unique_vertices=Vec::new(); let mut unique_vertices=Vec::new();
let mut vertex_id_from=HashMap::new(); let mut vertex_id_from=HashMap::new();
let mut polygon_groups=Vec::new();//only one group is created let mut polygon_groups=Vec::new();
let mut acquire_pos_id=|pos|{ let mut acquire_pos_id=|pos|{
let p=Planar64Vec3::try_from(pos).map_err(Error::Planar64Vec3)?; let p=Planar64Vec3::try_from(pos).map_err(Error::Planar64Vec3)?;
Ok(PositionId::new(*pos_id_from.entry(p).or_insert_with(||{ Ok(PositionId::new(*pos_id_from.entry(p).or_insert_with(||{
@ -135,7 +149,7 @@ pub fn convert(roblox_mesh_bytes:crate::data::RobloxMeshBytes)->Result<model::Me
match rbx_mesh::read_versioned(roblox_mesh_bytes.cursor()).map_err(Error::RbxMesh)?{ match rbx_mesh::read_versioned(roblox_mesh_bytes.cursor()).map_err(Error::RbxMesh)?{
rbx_mesh::mesh::VersionedMesh::Version1(mesh)=>{ rbx_mesh::mesh::VersionedMesh::Version1(mesh)=>{
let color_id=acquire_color_id([1.0f32;4]); let color_id=acquire_color_id([1.0f32;4]);
polygon_groups.push(model::PolygonGroup::PolygonList(PolygonList::new(mesh.vertices.chunks_exact(3).map(|trip|{ polygon_groups.push(PolygonGroup::PolygonList(PolygonList::new(mesh.vertices.chunks_exact(3).map(|trip|{
let mut ingest_vertex1=|vertex:rbx_mesh::mesh::Vertex1|Ok(acquire_vertex_id(IndexedVertex{ let mut ingest_vertex1=|vertex:rbx_mesh::mesh::Vertex1|Ok(acquire_vertex_id(IndexedVertex{
pos:acquire_pos_id(vertex.pos)?, pos:acquire_pos_id(vertex.pos)?,
tex:acquire_tex_id([vertex.tex[0],vertex.tex[1]]), tex:acquire_tex_id([vertex.tex[0],vertex.tex[1]]),
@ -154,6 +168,10 @@ pub fn convert(roblox_mesh_bytes:crate::data::RobloxMeshBytes)->Result<model::Me
}, },
rbx_mesh::mesh::SizeOfVertex2::Full=>ingest_vertices2(mesh.vertices,&mut acquire_pos_id,&mut acquire_tex_id,&mut acquire_normal_id,&mut acquire_color_id,&mut acquire_vertex_id)?, rbx_mesh::mesh::SizeOfVertex2::Full=>ingest_vertices2(mesh.vertices,&mut acquire_pos_id,&mut acquire_tex_id,&mut acquire_normal_id,&mut acquire_color_id,&mut acquire_vertex_id)?,
}; };
//one big happy group for all the faces
polygon_groups.push(PolygonGroup::PolygonList(PolygonList::new(mesh.faces.into_iter().map(|face|
vec![vertex_id_map[&face.0],vertex_id_map[&face.1],vertex_id_map[&face.2]]
).collect())));
}, },
rbx_mesh::mesh::VersionedMesh::Version3(mesh)=>{ rbx_mesh::mesh::VersionedMesh::Version3(mesh)=>{
let vertex_id_map=match mesh.header.sizeof_vertex{ let vertex_id_map=match mesh.header.sizeof_vertex{
@ -163,12 +181,15 @@ pub fn convert(roblox_mesh_bytes:crate::data::RobloxMeshBytes)->Result<model::Me
}, },
rbx_mesh::mesh::SizeOfVertex2::Full=>ingest_vertices2(mesh.vertices,&mut acquire_pos_id,&mut acquire_tex_id,&mut acquire_normal_id,&mut acquire_color_id,&mut acquire_vertex_id)?, rbx_mesh::mesh::SizeOfVertex2::Full=>ingest_vertices2(mesh.vertices,&mut acquire_pos_id,&mut acquire_tex_id,&mut acquire_normal_id,&mut acquire_color_id,&mut acquire_vertex_id)?,
}; };
ingest_faces2_lods3(&mut polygon_groups,&vertex_id_map,&mesh.faces,&mesh.lods);
}, },
rbx_mesh::mesh::VersionedMesh::Version4(mesh)=>{ rbx_mesh::mesh::VersionedMesh::Version4(mesh)=>{
let vertex_id_map=ingest_vertices2(mesh.vertices,&mut acquire_pos_id,&mut acquire_tex_id,&mut acquire_normal_id,&mut acquire_color_id,&mut acquire_vertex_id)?; let vertex_id_map=ingest_vertices2(mesh.vertices,&mut acquire_pos_id,&mut acquire_tex_id,&mut acquire_normal_id,&mut acquire_color_id,&mut acquire_vertex_id)?;
ingest_faces2_lods3(&mut polygon_groups,&vertex_id_map,&mesh.faces,&mesh.lods);
}, },
rbx_mesh::mesh::VersionedMesh::Version5(mesh)=>{ rbx_mesh::mesh::VersionedMesh::Version5(mesh)=>{
let vertex_id_map=ingest_vertices2(mesh.vertices,&mut acquire_pos_id,&mut acquire_tex_id,&mut acquire_normal_id,&mut acquire_color_id,&mut acquire_vertex_id)?; let vertex_id_map=ingest_vertices2(mesh.vertices,&mut acquire_pos_id,&mut acquire_tex_id,&mut acquire_normal_id,&mut acquire_color_id,&mut acquire_vertex_id)?;
ingest_faces2_lods3(&mut polygon_groups,&vertex_id_map,&mesh.faces,&mesh.lods);
}, },
} }
Ok(model::Mesh{ Ok(model::Mesh{
@ -178,6 +199,7 @@ pub fn convert(roblox_mesh_bytes:crate::data::RobloxMeshBytes)->Result<model::Me
unique_color, unique_color,
unique_vertices, unique_vertices,
polygon_groups, polygon_groups,
//these should probably be moved to the model...
graphics_groups:Vec::new(), graphics_groups:Vec::new(),
physics_groups:Vec::new(), physics_groups:Vec::new(),
}) })