use std::io::{BufReader, Cursor}; use stl::STL; use crate::{ camera::Camera, hitable::Hit, hitable_list::HitableList, kdtree::KDTree, material::{DiffuseLight, Lambertian, Metal}, rect::{XYRect, XZRect}, renderer::{Opt, Scene}, sphere::Sphere, texture::ConstantTexture, triangles::Triangles, vec3::Vec3, }; pub fn new(opt: &Opt) -> Scene { let lookfrom = Vec3::new(200., 200., 200.); let lookat = Vec3::new(0., 1., 0.); let dist_to_focus = 10.0; let aperture = 0.0; let time_min = 0.; let time_max = 1.; let camera = Camera::new( lookfrom, lookat, Vec3::new(0., 1., 0.), 20., opt.width as f32 / opt.height as f32, aperture, dist_to_focus, time_min, time_max, ); let ground_color = if opt.use_accel { ConstantTexture::new(Vec3::new(1.0, 0.4, 0.4)) } else { ConstantTexture::new(Vec3::new(0.4, 1.0, 0.4)) }; let stl_cube = STL::parse( BufReader::new(Cursor::new(include_bytes!("../../stls/20mm cube.stl"))), false, ) .expect("failed to parse cube"); let light_size = 50.; let light_height = 200.; let tri_mesh = Triangles::new( &stl_cube, Lambertian::new(ConstantTexture::new(Vec3::new(1., 0., 0.))), ); dbg!(&tri_mesh); let objects: Vec> = vec![ // Light from above Box::new(XZRect::new( -light_size, light_size, -light_size, light_size, light_height, DiffuseLight::new(ConstantTexture::new(Vec3::new(15., 15., 15.))), )), // Light from back Box::new(XYRect::new( -light_size, light_size, -light_size, light_size, -light_height, DiffuseLight::new(ConstantTexture::new(Vec3::new(1., 15., 1.))), )), // Light from front Box::new(XYRect::new( -light_size, light_size, -light_size, light_size, light_height, DiffuseLight::new(ConstantTexture::new(Vec3::new(1., 1., 15.))), )), // Earth sized sphere Box::new(Sphere::new( Vec3::new(0., -1200., 0.), 1000., Lambertian::new(ground_color), )), // Blue sphere Box::new(Sphere::new( Vec3::new(-40., 20., 0.), 20., Lambertian::new(ConstantTexture::new(Vec3::new(0.1, 0.2, 0.5))), )), // Shiny sphere Box::new(Sphere::new( Vec3::new(40., 20., 0.), 20., Metal::new(Vec3::new(0.8, 0.8, 0.8), 0.2), )), Box::new(tri_mesh), ]; let world: Box = if opt.use_accel { Box::new(KDTree::new(objects, time_min, time_max)) } else { Box::new(HitableList::new(objects)) }; Scene { camera, world, subsamples: opt.subsamples, num_threads: opt.num_threads, width: opt.width, height: opt.height, ..Default::default() } }