use std::{ io::{BufReader, Cursor}, sync::Arc, }; use stl::STL; use crate::{ bvh_triangles::BVHTriangles, camera::Camera, cuboid::Cuboid, hitable::Hit, hitable_list::HitableList, kdtree::KDTree, material::{Dielectric, Lambertian, Metal}, renderer::{Opt, Scene}, sphere::Sphere, texture::{ConstantTexture, EnvMap}, translate::Translate, vec3::Vec3, }; pub fn new(opt: &Opt) -> Scene { let lookfrom = Vec3::new(0., 40., -100.); let lookat = Vec3::new(0., 10., 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.), 45., 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, 0.4, 0.4)) }; let glass = Dielectric::new(1.5); let metal = Metal::new(Vec3::new(0.8, 0.8, 0.8), 0.2); let red = Lambertian::new(ConstantTexture::new(Vec3::new(1.0, 0.2, 0.2))); //let box_material = glass; let _ = glass; let _ = metal; let _ = red; let stl_cube = STL::parse( BufReader::new(Cursor::new(include_bytes!("../../stls/cube.stl"))), false, ) .expect("failed to parse cube"); let objects: Vec> = vec![ // Light from above - white // Earth sized sphere Box::new(Sphere::new( Vec3::new(0., -10000., 0.), 10000., Lambertian::new(ground_color), )), Box::new(Sphere::new( Vec3::new(0., 20., -40.), 10., Lambertian::new(ConstantTexture::new(Vec3::new(1., 0.2, 1.))), )), // Blue sphere Box::new(Sphere::new( Vec3::new(0., 20., 40.), 20., Lambertian::new(ConstantTexture::new(Vec3::new(0.2, 0.2, 1.))), )), Box::new(Sphere::new( Vec3::new(40., 20., 40.), 20., //Metal::new(Vec3::new(0.8, 0.8, 0.8), 0.2), Lambertian::new(ConstantTexture::new(Vec3::new(0.2, 1.0, 0.2))), )), Box::new(Sphere::new( Vec3::new(-40., 20., 40.), 20., //Metal::new(Vec3::new(0.8, 0.8, 0.8), 0.2), Lambertian::new(ConstantTexture::new(Vec3::new(1.0, 0.2, 0.2))), )), // STL Mesh Box::new(Translate::new( BVHTriangles::new(&stl_cube, glass), [0., 10., 0.], )), //Box::new(BVHTriangles::new(&stl_cube, box_material.clone())), Box::new(Cuboid::new( [-20., 0., 0.].into(), [0., 20., 20.].into(), Arc::new(red), )), ]; let world: Box = if opt.use_accel { Box::new(KDTree::new(objects, time_min, time_max)) } else { Box::new(HitableList::new(objects)) }; let skybox_bytes = include_bytes!("../../images/envmap.jpg"); let skybox = image::load_from_memory(skybox_bytes).unwrap().to_rgb(); Scene { camera, world, subsamples: opt.subsamples, num_threads: opt.num_threads, width: opt.width, height: opt.height, global_illumination: true, env_map: Some(EnvMap::new(skybox)), ..Default::default() } }