aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorYann Herklotz <git@yannherklotz.com>2020-04-30 15:11:21 +0100
committerYann Herklotz <git@yannherklotz.com>2020-04-30 15:11:21 +0100
commitdd5ac7c5fe336e9cac794cfa72d139613a99b466 (patch)
treeaedc5d53bdb83404b6fb426b55756c66755adb80 /src
parent60ae11a9271534a4f0b6c44d1fd967777855c52d (diff)
downloadleela-dd5ac7c5fe336e9cac794cfa72d139613a99b466.tar.gz
leela-dd5ac7c5fe336e9cac794cfa72d139613a99b466.zip
Add threads using Rayon
Diffstat (limited to 'src')
-rw-r--r--src/hittable.rs5
-rw-r--r--src/main.rs9
-rw-r--r--src/render.rs37
-rw-r--r--src/scene.rs4
-rw-r--r--src/sphere.rs4
5 files changed, 38 insertions, 21 deletions
diff --git a/src/hittable.rs b/src/hittable.rs
index 1c61872..dcc5006 100644
--- a/src/hittable.rs
+++ b/src/hittable.rs
@@ -7,11 +7,12 @@ pub struct Hit<'a> {
pub p: Vector3<f64>,
pub normal: Vector3<f64>,
pub front_face: bool,
- pub material: &'a (dyn Material)
+ pub material: &'a (dyn Material + std::marker::Sync)
}
impl<'a> Hit<'a> {
- pub fn new(ray: &Ray, t: f64, out_normal: Vector3<f64>, material: &'a(dyn Material)) -> Hit<'a> {
+ pub fn new(ray: &Ray, t: f64, out_normal: Vector3<f64>, material: &'a(dyn Material + std::marker::Sync))
+ -> Hit<'a> {
let front_face = dot(ray.dir, out_normal) < 0.0;
let normal = if front_face { out_normal } else { -out_normal };
let p = ray.at(t);
diff --git a/src/main.rs b/src/main.rs
index 1a0b001..f1a627f 100644
--- a/src/main.rs
+++ b/src/main.rs
@@ -59,9 +59,10 @@ pub fn random_scene(rng: &mut ThreadRng) -> scene::Scene {
}
fn main() {
- let image_width = 1200;
- let image_height = 800;
- let samples = 100;
+ let image_width = 400;
+ let image_height = 200;
+ let samples = 50;
+ let threads = 1;
let max_depth = 50;
let aspect_ratio = image_width as f64 / image_height as f64;
@@ -78,7 +79,7 @@ fn main() {
let camera = camera::Camera::new(&lookfrom, &lookat, &vup,
20.0 * PI / 180.0, aspect_ratio, aperture, dist_to_focus);
- render::render(&scene, camera, image_height, image_width, samples, max_depth, &mut rng);
+ render::render(&scene, &camera, image_height, image_width, samples, max_depth, threads);
eprintln!("\nDone")
}
diff --git a/src/render.rs b/src/render.rs
index 740c3eb..47c6698 100644
--- a/src/render.rs
+++ b/src/render.rs
@@ -1,6 +1,7 @@
use cgmath::prelude::*;
use cgmath::{Vector3, vec3};
use rand::prelude::*;
+use rayon::prelude::*;
use std::f64::INFINITY;
use crate::camera::Camera;
use crate::scene::Scene;
@@ -23,20 +24,34 @@ fn ray_colour(rng: &mut ThreadRng, ray: &Ray, scene: &Scene, depth: i32) -> Vect
}
}
-pub fn render(world: &Scene, camera: Camera, image_height: i32, image_width: i32,
- samples: i32, max_depth: i32, rng: &mut ThreadRng) {
+pub fn thread_render(world: &Scene, camera: &Camera, rng: &mut ThreadRng, image_height: i32,
+ image_width: i32, samples: i32, max_depth: i32, i: i32, j: i32) -> Vector3<f64> {
+ let mut colour = vec3(0.0, 0.0, 0.0);
+ for _ in 0 .. samples {
+ let ru: f64 = rng.gen();
+ let rv: f64 = rng.gen();
+ let u = (i as f64 + ru) / image_width as f64;
+ let v = ((image_height - 1 - j) as f64 + rv) / image_height as f64;
+ let ray = camera.get_ray(rng, u, v);
+ colour += ray_colour(rng, &ray, &world, max_depth);
+ }
+ colour
+}
+
+pub fn render(world: &Scene, camera: &Camera, image_height: i32, image_width: i32,
+ samples: i32, max_depth: i32, threads: i32) {
for j in 0 .. image_height {
eprint!("\rScanlines: {:3} / {:3}", j+1, image_height);
for i in 0 .. image_width {
- let mut colour = vec3(0.0, 0.0, 0.0);
- for _ in 0 .. samples {
- let ru: f64 = rng.gen();
- let rv: f64 = rng.gen();
- let u = (i as f64 + ru) / image_width as f64;
- let v = ((image_height - 1 - j) as f64 + rv) / image_height as f64;
- let ray = camera.get_ray(rng, u, v);
- colour += ray_colour(rng, &ray, &world, max_depth);
- }
+ let colours = (0 .. threads)
+ .into_par_iter()
+ .map(|_| {
+ let mut trng = thread_rng();
+ thread_render(
+ world, camera, &mut trng, image_height, image_width,
+ samples / threads, max_depth, i, j)
+ });
+ let colour = colours.sum::<Vector3<f64>>();
print_colour(&colour, samples);
}
}
diff --git a/src/scene.rs b/src/scene.rs
index 368c784..0aa775c 100644
--- a/src/scene.rs
+++ b/src/scene.rs
@@ -2,7 +2,7 @@ use crate::hittable::{Hittable, Hit};
use crate::ray::Ray;
pub struct Scene {
- objects: Vec<Box<dyn Hittable>>
+ objects: Vec<Box<dyn Hittable + std::marker::Sync>>
}
impl Scene {
@@ -10,7 +10,7 @@ impl Scene {
Scene { objects: Vec::new() }
}
- pub fn add(&mut self, obj: Box<dyn Hittable>) {
+ pub fn add(&mut self, obj: Box<dyn Hittable + std::marker::Sync>) {
self.objects.push(obj)
}
diff --git a/src/sphere.rs b/src/sphere.rs
index 9ea9081..f1c88b6 100644
--- a/src/sphere.rs
+++ b/src/sphere.rs
@@ -8,11 +8,11 @@ use crate::ray::Ray;
pub struct Sphere {
center: Vector3<f64>,
radius: f64,
- material: Box<dyn Material>
+ material: Box<dyn Material + std::marker::Sync>
}
impl Sphere {
- pub fn new(center: Vector3<f64>, radius: f64, material: Box<dyn Material>) -> Sphere {
+ pub fn new(center: Vector3<f64>, radius: f64, material: Box<dyn Material + std::marker::Sync>) -> Sphere {
Sphere { center, radius, material }
}
}