summaryrefslogtreecommitdiff
path: root/racer-tracer/src/scene.rs
diff options
context:
space:
mode:
Diffstat (limited to 'racer-tracer/src/scene.rs')
-rw-r--r--racer-tracer/src/scene.rs111
1 files changed, 16 insertions, 95 deletions
diff --git a/racer-tracer/src/scene.rs b/racer-tracer/src/scene.rs
index c0c6bb7..12e2296 100644
--- a/racer-tracer/src/scene.rs
+++ b/racer-tracer/src/scene.rs
@@ -1,13 +1,10 @@
-use std::{collections::HashMap, path::Path, sync::Arc};
-
-use config::File;
-use serde::Deserialize;
+pub mod none;
+pub mod random;
+pub mod yml;
use crate::{
- error::TracerError,
- geometry::{sphere::Sphere, Hittable},
- material::{dialectric::Dialectric, lambertian::Lambertian, metal::Metal, SharedMaterial},
- vec3::{Color, Vec3},
+ config::SceneLoader as CSLoader, error::TracerError, geometry::Hittable,
+ scene::none::NoneLoader, scene::random::Random, scene::yml::YmlLoader,
};
pub struct Scene {
@@ -16,20 +13,14 @@ pub struct Scene {
impl Scene {
#[allow(dead_code)]
- pub fn new() -> Self {
- Self {
- objects: Vec::new(),
- }
+ pub fn try_new(loader: Box<dyn SceneLoader>) -> Result<Self, TracerError> {
+ loader.load().map(|objects| Self { objects })
}
#[allow(dead_code)]
pub fn add(&mut self, hittable: Box<dyn Hittable>) {
self.objects.push(hittable);
}
-
- pub fn from_file<P: AsRef<Path>>(file: P) -> Result<Self, TracerError> {
- SceneData::from_file(file)?.try_into()
- }
}
impl Hittable for Scene {
@@ -53,86 +44,16 @@ impl Hittable for Scene {
}
}
-#[derive(Debug, Deserialize)]
-enum MaterialData {
- Lambertian { color: Color },
- Metal { color: Color, fuzz: f64 },
- Dialectric { refraction_index: f64 },
-}
-
-#[derive(Debug, Deserialize)]
-enum GeometryData {
- Sphere {
- pos: Vec3,
- radius: f64,
- material: String,
- },
-}
-
-#[derive(Deserialize)]
-struct SceneData {
- materials: HashMap<String, MaterialData>,
- geometry: Vec<GeometryData>,
-}
-
-impl SceneData {
- pub fn from_file<P: AsRef<Path>>(file: P) -> Result<Self, TracerError> {
- config::Config::builder()
- .add_source(File::from(file.as_ref()))
- .build()
- .map_err(|e| {
- TracerError::Configuration(
- file.as_ref().to_string_lossy().into_owned(),
- e.to_string(),
- )
- })?
- .try_deserialize()
- .map_err(|e| {
- TracerError::Configuration(
- file.as_ref().to_string_lossy().into_owned(),
- e.to_string(),
- )
- })
- }
+pub trait SceneLoader: Send + Sync {
+ fn load(&self) -> Result<Vec<Box<dyn Hittable>>, TracerError>;
}
-impl TryInto<Scene> for SceneData {
- type Error = TracerError;
- fn try_into(self) -> Result<Scene, TracerError> {
- let mut materials: HashMap<String, SharedMaterial> = HashMap::new();
- self.materials
- .into_iter()
- .for_each(|(id, material)| match material {
- MaterialData::Lambertian { color } => {
- materials.insert(id, Arc::new(Box::new(Lambertian::new(color))));
- }
- MaterialData::Metal { color, fuzz } => {
- materials.insert(id, Arc::new(Box::new(Metal::new(color, fuzz))));
- }
- MaterialData::Dialectric { refraction_index } => {
- materials.insert(id, Arc::new(Box::new(Dialectric::new(refraction_index))));
- }
- });
-
- let geometry: Vec<Box<dyn Hittable>> = self
- .geometry
- .into_iter()
- .map(|geo| match geo {
- GeometryData::Sphere {
- pos,
- radius,
- material,
- } => materials
- .get(&material)
- .ok_or(TracerError::UnknownMaterial(material))
- .map(|mat| {
- let apa: Box<dyn Hittable> =
- Box::new(Sphere::new(pos, radius, Arc::clone(mat)));
- apa
- }),
- })
- .collect::<Result<Vec<Box<dyn Hittable>>, TracerError>>()?;
-
- Ok(Scene { objects: geometry })
+impl From<&CSLoader> for Box<dyn SceneLoader> {
+ fn from(loader: &CSLoader) -> Self {
+ match loader {
+ CSLoader::Yml { path } => Box::new(YmlLoader::new(path.clone())),
+ CSLoader::Random => Box::new(Random::new()),
+ CSLoader::None => Box::new(NoneLoader::new()),
+ }
}
}