7.Moving Camera Code Into Its Own Class
8.Antialiasing
This commit is contained in:
+33
-11
@@ -1,5 +1,8 @@
|
||||
use crate::hittable::HittableList;
|
||||
use crate::math_utils::clamp;
|
||||
use crate::types_defined::{Camera, Color, Point, Ray, Vec3};
|
||||
use rand::rngs::ThreadRng;
|
||||
use rand::{Rng, thread_rng};
|
||||
|
||||
impl Camera {
|
||||
pub fn new(
|
||||
@@ -8,6 +11,7 @@ impl Camera {
|
||||
viewport_height: f32,
|
||||
camera_center: Point,
|
||||
focal_length: Vec3,
|
||||
sample_times: i8,
|
||||
) -> Self {
|
||||
let image_height = ((image_width as f32 / aspect_ratio) as i32).max(1);
|
||||
let viewport_width = viewport_height * (image_width as f32 / image_height as f32);
|
||||
@@ -41,6 +45,7 @@ impl Camera {
|
||||
viewport_u_delta,
|
||||
viewport_v_delta,
|
||||
viewport_top_left_pixel_center,
|
||||
sample_times: sample_times,
|
||||
}
|
||||
}
|
||||
|
||||
@@ -53,18 +58,30 @@ impl Camera {
|
||||
}
|
||||
|
||||
for i in 0..self.image_width {
|
||||
// every pixcel's position
|
||||
let pixel_center = self.viewport_top_left_pixel_center
|
||||
+ (i as f32 * self.viewport_u_delta)
|
||||
+ (j as f32 * self.viewport_v_delta);
|
||||
// Vector(camera, pixcel)
|
||||
let ray_direction = pixel_center - self.camera_center;
|
||||
// ray
|
||||
let r = Ray::new(self.camera_center, ray_direction);
|
||||
// determind color
|
||||
let color = self.ray_color(&r, world);
|
||||
// color
|
||||
let mut color = Color::new(0.0, 0.0, 0.0);
|
||||
let rng = &mut thread_rng();
|
||||
for s in 0..self.sample_times {
|
||||
let bias = self.random_square(rng);
|
||||
let pix_sample = self.viewport_top_left_pixel_center
|
||||
+ (i as f32 + bias.x) * self.viewport_u_delta
|
||||
+ (j as f32 + bias.y) * self.viewport_v_delta;
|
||||
let r = Ray::new(self.camera_center, pix_sample - self.camera_center);
|
||||
let sample_color = self.ray_color(&r, world);
|
||||
color = color + sample_color;
|
||||
}
|
||||
// color * each sample color
|
||||
color = color * (1.0 / self.sample_times as f32);
|
||||
|
||||
// clamp color rgb
|
||||
let color_clamped = Color::new(
|
||||
clamp(color.x, 0.0, 1.0),
|
||||
clamp(color.y, 0.0, 1.0),
|
||||
clamp(color.z, 0.0, 1.0),
|
||||
);
|
||||
|
||||
// content
|
||||
img_content.push_str(color.to_color().as_str());
|
||||
img_content.push_str(color_clamped.to_color().as_str());
|
||||
img_content.push('\n');
|
||||
}
|
||||
}
|
||||
@@ -88,4 +105,9 @@ impl Camera {
|
||||
// return background color.
|
||||
(1.0 - a) * Color::new(1.0, 1.0, 1.0) + a * Color::new(0.5, 0.7, 1.0)
|
||||
}
|
||||
|
||||
// -> [x, y, 0]
|
||||
fn random_square(&self, rng: &mut ThreadRng) -> Vec3 {
|
||||
Vec3::new(rng.gen_range(-0.5..0.1), rng.gen_range(-0.5..0.1), 0.0)
|
||||
}
|
||||
}
|
||||
|
||||
+3
-1
@@ -9,6 +9,7 @@ mod sphere;
|
||||
mod types_defined;
|
||||
mod vec3;
|
||||
mod write_file_util;
|
||||
mod math_utils;
|
||||
|
||||
fn main() {
|
||||
camera_render();
|
||||
@@ -16,11 +17,12 @@ fn main() {
|
||||
|
||||
fn camera_render() {
|
||||
let camera = Camera::new(
|
||||
800,
|
||||
400,
|
||||
16.0 / 9.0,
|
||||
2.0,
|
||||
Point::new(0.0, 0.0, 0.0),
|
||||
Vec3::new(0.0, 0.0, -1.0),
|
||||
10
|
||||
);
|
||||
// world
|
||||
// world objects(spheres)
|
||||
|
||||
@@ -0,0 +1,10 @@
|
||||
|
||||
pub fn clamp(value: f32, low: f32, high: f32) -> f32 {
|
||||
if value < low {
|
||||
return low;
|
||||
}
|
||||
if value > high {
|
||||
return high;
|
||||
}
|
||||
return value;
|
||||
}
|
||||
@@ -41,6 +41,9 @@ pub struct Camera {
|
||||
pub viewport_u_delta: Vec3,
|
||||
pub viewport_v_delta: Vec3,
|
||||
pub viewport_top_left_pixel_center: Vec3,
|
||||
|
||||
// sample times
|
||||
pub sample_times: i8
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
Reference in New Issue
Block a user