More error handling
This commit is contained in:
parent
5b5e491cb2
commit
b56f952e9b
1 changed files with 145 additions and 35 deletions
|
|
@ -31,7 +31,7 @@ enum Statement {
|
|||
WorldBegin,
|
||||
Include(String),
|
||||
ConcatTransform(AffineTransform),
|
||||
Shape(ShapeType),
|
||||
Shape(ShapeType, ShapeAlpha),
|
||||
Unknown(String, Vec<String>),
|
||||
Transform(AffineTransform),
|
||||
}
|
||||
|
|
@ -56,24 +56,34 @@ fn parse_shape(iter: &mut Tokenizer) -> Result<Statement> {
|
|||
let zmin = -radius;
|
||||
let zmax = radius;
|
||||
let phimax = 360.0;
|
||||
let mut alpha = ShapeAlpha::None;
|
||||
|
||||
while let Some(p) = iter.next_if(|p| p.starts_with('"')).transpose()? {
|
||||
match p.as_str() {
|
||||
"\"float radius\"" => {
|
||||
radius = iter.parse_parameter()?;
|
||||
}
|
||||
"\"float alpha\"" => {
|
||||
alpha = ShapeAlpha::Value(iter.parse_parameter()?);
|
||||
}
|
||||
"\"texture alpha\"" => {
|
||||
alpha = ShapeAlpha::Texture(iter.parse_parameter()?);
|
||||
}
|
||||
_ => {
|
||||
bail!("unknown argument {}", p)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Ok(Statement::Shape(ShapeType::Sphere {
|
||||
radius,
|
||||
zmin,
|
||||
zmax,
|
||||
phimax,
|
||||
}))
|
||||
Ok(Statement::Shape(
|
||||
ShapeType::Sphere {
|
||||
radius,
|
||||
zmin,
|
||||
zmax,
|
||||
phimax,
|
||||
},
|
||||
alpha,
|
||||
))
|
||||
}
|
||||
"\"trianglemesh\"" => {
|
||||
let mut indices = Vec::new();
|
||||
|
|
@ -81,6 +91,7 @@ fn parse_shape(iter: &mut Tokenizer) -> Result<Statement> {
|
|||
let mut n = Vec::new();
|
||||
let mut s = Vec::new();
|
||||
let mut uv = Vec::new();
|
||||
let mut alpha = ShapeAlpha::None;
|
||||
|
||||
while let Some(q) = iter.next_if(|p| p.starts_with('"')).transpose()? {
|
||||
match q.as_str() {
|
||||
|
|
@ -99,6 +110,12 @@ fn parse_shape(iter: &mut Tokenizer) -> Result<Statement> {
|
|||
"\"point2 uv\"" => {
|
||||
iter.parse_list_2(&mut uv, |u, v| [u, v])?;
|
||||
}
|
||||
"\"float alpha\"" => {
|
||||
alpha = ShapeAlpha::Value(iter.parse_parameter()?);
|
||||
}
|
||||
"\"texture alpha\"" => {
|
||||
alpha = ShapeAlpha::Texture(iter.parse_parameter()?);
|
||||
}
|
||||
_ => {
|
||||
bail!("unknown argument {}", q)
|
||||
}
|
||||
|
|
@ -128,19 +145,23 @@ fn parse_shape(iter: &mut Tokenizer) -> Result<Statement> {
|
|||
if !uv.is_empty() && uv.len() != p.len() {
|
||||
bail!("Number of uvs not equal to number of positions.")
|
||||
}
|
||||
Ok(Statement::Shape(ShapeType::TriangleMesh {
|
||||
indices,
|
||||
p,
|
||||
n,
|
||||
s,
|
||||
uv,
|
||||
}))
|
||||
Ok(Statement::Shape(
|
||||
ShapeType::TriangleMesh {
|
||||
indices,
|
||||
p,
|
||||
n,
|
||||
s,
|
||||
uv,
|
||||
},
|
||||
alpha,
|
||||
))
|
||||
}
|
||||
"\"bilinearmesh\"" => {
|
||||
let mut indices = Vec::new();
|
||||
let mut p = Vec::new();
|
||||
let mut n = Vec::new();
|
||||
let mut uv = Vec::new();
|
||||
let mut alpha = ShapeAlpha::None;
|
||||
|
||||
while let Some(q) = iter.next_if(|p| p.starts_with('"')).transpose()? {
|
||||
match q.as_str() {
|
||||
|
|
@ -156,6 +177,12 @@ fn parse_shape(iter: &mut Tokenizer) -> Result<Statement> {
|
|||
"\"vector N\"" => {
|
||||
iter.parse_list_3(&mut n, Dir3::new)?;
|
||||
}
|
||||
"\"float alpha\"" => {
|
||||
alpha = ShapeAlpha::Value(iter.parse_parameter()?);
|
||||
}
|
||||
"\"texture alpha\"" => {
|
||||
alpha = ShapeAlpha::Texture(iter.parse_parameter()?);
|
||||
}
|
||||
_ => {
|
||||
bail!("unknown argument {}", q)
|
||||
}
|
||||
|
|
@ -183,12 +210,10 @@ fn parse_shape(iter: &mut Tokenizer) -> Result<Statement> {
|
|||
if !uv.is_empty() && uv.len() != p.len() {
|
||||
bail!("Number of uvs not equal to number of positions.")
|
||||
}
|
||||
Ok(Statement::Shape(ShapeType::BilinearMesh {
|
||||
indices,
|
||||
p,
|
||||
n,
|
||||
uv,
|
||||
}))
|
||||
Ok(Statement::Shape(
|
||||
ShapeType::BilinearMesh { indices, p, n, uv },
|
||||
alpha,
|
||||
))
|
||||
}
|
||||
|
||||
"\"loopsubdiv\"" => {
|
||||
|
|
@ -196,6 +221,7 @@ fn parse_shape(iter: &mut Tokenizer) -> Result<Statement> {
|
|||
let mut indices = Vec::new();
|
||||
|
||||
let mut p = Vec::new();
|
||||
let mut alpha = ShapeAlpha::None;
|
||||
|
||||
while let Some(q) = iter.next_if(|p| p.starts_with('"')).transpose()? {
|
||||
match q.as_str() {
|
||||
|
|
@ -208,6 +234,12 @@ fn parse_shape(iter: &mut Tokenizer) -> Result<Statement> {
|
|||
"\"integer levels\"" => {
|
||||
levels = iter.parse_parameter()?;
|
||||
}
|
||||
"\"float alpha\"" => {
|
||||
alpha = ShapeAlpha::Value(iter.parse_parameter()?);
|
||||
}
|
||||
"\"texture alpha\"" => {
|
||||
alpha = ShapeAlpha::Texture(iter.parse_parameter()?);
|
||||
}
|
||||
_ => {
|
||||
bail!("unknown argument {}", q)
|
||||
}
|
||||
|
|
@ -222,17 +254,17 @@ fn parse_shape(iter: &mut Tokenizer) -> Result<Statement> {
|
|||
bail!("p is a required field")
|
||||
}
|
||||
|
||||
Ok(Statement::Shape(ShapeType::LoopSubDiv {
|
||||
levels,
|
||||
indices,
|
||||
p,
|
||||
}))
|
||||
Ok(Statement::Shape(
|
||||
ShapeType::LoopSubDiv { levels, indices, p },
|
||||
alpha,
|
||||
))
|
||||
}
|
||||
"\"disk\"" => {
|
||||
let mut height = 0.0;
|
||||
let mut radius = 1.0;
|
||||
let mut innerradius = 0.0;
|
||||
let mut phimax = 360.0;
|
||||
let mut alpha = ShapeAlpha::None;
|
||||
|
||||
while let Some(q) = iter.next_if(|p| p.starts_with('"')).transpose()? {
|
||||
match q.as_str() {
|
||||
|
|
@ -240,18 +272,57 @@ fn parse_shape(iter: &mut Tokenizer) -> Result<Statement> {
|
|||
"\"float radius\"" => radius = iter.parse_parameter()?,
|
||||
"\"float innerradius\"" => innerradius = iter.parse_parameter()?,
|
||||
"\"float phimax\"" => phimax = iter.parse_parameter()?,
|
||||
"\"float alpha\"" => {
|
||||
alpha = ShapeAlpha::Value(iter.parse_parameter()?);
|
||||
}
|
||||
"\"texture alpha\"" => {
|
||||
alpha = ShapeAlpha::Texture(iter.parse_parameter()?);
|
||||
}
|
||||
_ => {
|
||||
bail!("unknown argument {}", q)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Ok(Statement::Shape(ShapeType::Disk {
|
||||
height,
|
||||
radius,
|
||||
innerradius,
|
||||
phimax,
|
||||
}))
|
||||
Ok(Statement::Shape(
|
||||
ShapeType::Disk {
|
||||
height,
|
||||
radius,
|
||||
innerradius,
|
||||
phimax,
|
||||
},
|
||||
alpha,
|
||||
))
|
||||
}
|
||||
"\"plymesh\"" => {
|
||||
let mut filename = String::new();
|
||||
let mut displacement = None;
|
||||
let mut edgelength = 1.0;
|
||||
let mut alpha = ShapeAlpha::None;
|
||||
while let Some(q) = iter.next_if(|p| p.starts_with('"')).transpose()? {
|
||||
match q.as_str() {
|
||||
"\"string filename\"" => filename = dbg!(iter.parse_parameter()?),
|
||||
"\"texture displacement\"" => displacement = Some(iter.parse_parameter()?),
|
||||
"\"float edgelength\"" => edgelength = iter.parse_parameter()?,
|
||||
"\"float alpha\"" => {
|
||||
alpha = ShapeAlpha::Value(iter.parse_parameter()?);
|
||||
}
|
||||
"\"texture alpha\"" => {
|
||||
alpha = ShapeAlpha::Texture(iter.parse_parameter()?);
|
||||
}
|
||||
_ => {
|
||||
bail!("unknown argument {}", q)
|
||||
}
|
||||
}
|
||||
}
|
||||
Ok(Statement::Shape(
|
||||
ShapeType::PlyMesh {
|
||||
filename,
|
||||
displacement,
|
||||
edgelength,
|
||||
},
|
||||
alpha,
|
||||
))
|
||||
}
|
||||
_ => Err(miette!("Unknown shape {}", shape_type)),
|
||||
}
|
||||
|
|
@ -426,7 +497,6 @@ struct Parser<P> {
|
|||
|
||||
impl<P: AsRef<Path> + std::fmt::Debug> Parser<P> {
|
||||
fn new(path: P) -> Result<Self> {
|
||||
dbg!(&path);
|
||||
Ok(Self {
|
||||
iter: Lexer::new(path.as_ref())?,
|
||||
path,
|
||||
|
|
@ -489,6 +559,18 @@ enum ShapeType {
|
|||
innerradius: f64,
|
||||
phimax: f64,
|
||||
},
|
||||
PlyMesh {
|
||||
filename: String,
|
||||
displacement: Option<String>,
|
||||
edgelength: Float,
|
||||
},
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
enum ShapeAlpha {
|
||||
None,
|
||||
Value(Float),
|
||||
Texture(String),
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
|
|
@ -496,6 +578,7 @@ struct Shape {
|
|||
ctm: AffineTransform,
|
||||
material: usize,
|
||||
obj: ShapeType,
|
||||
alpha: ShapeAlpha,
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
|
|
@ -545,7 +628,12 @@ fn inner_parse_pbrt(
|
|||
|
||||
let mut pbrt = Pbrt::new();
|
||||
|
||||
while let Some(p) = parser.next(context.last().unwrap()).transpose()? {
|
||||
// parse global settings
|
||||
|
||||
loop {
|
||||
let p = parser
|
||||
.next(context.last().unwrap())
|
||||
.ok_or_else(|| miette!(""))??;
|
||||
// dbg!(&p);
|
||||
match p {
|
||||
Statement::AttributeBegin => context.push(context.last().ok_or(miette!(""))?.clone()),
|
||||
|
|
@ -559,17 +647,39 @@ fn inner_parse_pbrt(
|
|||
Statement::Transform(affine_transform) => {
|
||||
context.last_mut().ok_or(miette!(""))?.ctm = dbg!(affine_transform)
|
||||
}
|
||||
Statement::Shape(shape_type) => {
|
||||
Statement::Unknown(s, items) => {
|
||||
eprintln!("Unknown statement: {s}")
|
||||
}
|
||||
Statement::WorldBegin => break,
|
||||
s => bail!("unexpected statemnet in global settings: {s:?}"),
|
||||
}
|
||||
}
|
||||
|
||||
while let Some(p) = parser.next(context.last().unwrap()).transpose()? {
|
||||
match p {
|
||||
Statement::AttributeBegin => context.push(context.last().ok_or(miette!(""))?.clone()),
|
||||
Statement::AttributeEnd => {
|
||||
context.pop();
|
||||
}
|
||||
Statement::Include(_) => unreachable!(),
|
||||
Statement::ConcatTransform(affine_transform) => {
|
||||
context.last_mut().ok_or(miette!(""))?.ctm *= affine_transform
|
||||
}
|
||||
Statement::Transform(affine_transform) => {
|
||||
context.last_mut().ok_or(miette!(""))?.ctm = dbg!(affine_transform)
|
||||
}
|
||||
Statement::Shape(shape_type, shape_alpha) => {
|
||||
pbrt.scene.shapes.push(Shape {
|
||||
ctm: context.last().unwrap().ctm,
|
||||
material: 0,
|
||||
obj: shape_type,
|
||||
alpha: shape_alpha,
|
||||
});
|
||||
}
|
||||
Statement::Unknown(s, items) => {
|
||||
eprintln!("Unknown statement: {s}")
|
||||
}
|
||||
Statement::WorldBegin => (),
|
||||
s => bail!("unexpected statemnet in world settings: {s:?}"),
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue