zigrtiow: implement depth of field.

This commit is contained in:
Bill Thiede 2022-08-14 11:36:50 -07:00
parent 8d92cc861e
commit 62317d57ae
3 changed files with 33 additions and 5 deletions

View File

@ -5,6 +5,7 @@ const Ray = @import("./ray.zig").Ray;
const Point3 = vec.Point3;
const Vec3 = vec.Vec3;
const random_in_unit_disk = vec.random_in_unit_disk;
const math = std.math;
const pi = math.pi;
const tan = math.tan;
@ -20,6 +21,10 @@ pub const Camera = struct {
lower_left_corner: Point3,
horizontal: Vec3,
vertical: Vec3,
u: Vec3,
v: Vec3,
w: Vec3,
lens_radius: f32,
pub fn init(
lookfrom: Point3,
@ -27,6 +32,8 @@ pub const Camera = struct {
vup: Vec3,
vfov: f32, // vertical field-of-view in degrees
aspect_ratio: f32,
aperature: f32,
focus_dist: f32,
) Camera {
const theta = degrees_to_radians(vfov);
const h = tan(theta / 2);
@ -38,18 +45,26 @@ pub const Camera = struct {
const v = w.cross(u);
const origin = lookfrom;
const horizontal = u.scale(viewport_width);
const vertical = v.scale(viewport_height);
const lower_left_corner = origin.sub(horizontal.scale(0.5)).sub(vertical.scale(0.5)).sub(w);
const horizontal = u.scale(focus_dist * viewport_width);
const vertical = v.scale(focus_dist * viewport_height);
const lower_left_corner = origin.sub(horizontal.scale(0.5)).sub(vertical.scale(0.5)).sub(w.scale(focus_dist));
const lens_radius = aperature / 2;
return Camera{
.origin = origin,
.horizontal = horizontal,
.vertical = vertical,
.lower_left_corner = lower_left_corner,
.u = u,
.v = v,
.w = w,
.lens_radius = lens_radius,
};
}
pub fn get_ray(camera: Camera, s: f32, t: f32) Ray {
return Ray.init(camera.origin, camera.lower_left_corner.add(camera.horizontal.scale(s).add(camera.vertical.scale(t).sub(camera.origin))));
const rd = random_in_unit_disk().scale(camera.lens_radius);
const offset = camera.u.scale(rd.x()).add(camera.v.scale(rd.y()));
return Ray.init(camera.origin.add(offset), camera.lower_left_corner.add(camera.horizontal.scale(s).add(camera.vertical.scale(t).sub(camera.origin).sub(offset))));
}
};

View File

@ -108,7 +108,13 @@ pub fn main() anyerror!void {
const world = Hittable{ .hittable_list = tmp_world };
// Camera
const cam = Camera.init(Point3.init(-2, 2, 1), Point3.init(0, 0, -1), Vec3.init(0, 1, 0), 20, aspect_ratio);
const lookfrom = Point3.init(3, 3, 2);
const lookat = Point3.init(0, 0, -1);
const vup = Vec3.init(0, 1, 0);
const dist_to_focus = lookfrom.sub(lookat).length();
const aperature = 2;
const cam = Camera.init(lookfrom, lookat, vup, 20, aspect_ratio, aperature, dist_to_focus);
// Render
const Node = Queue(Task).Node;

View File

@ -66,6 +66,13 @@ pub const Vec3 = struct {
}
};
pub fn random_in_unit_disk() Vec3 {
while (true) {
const p = Vec3.init(rand.float(f32) * 2 - 1, rand.float(f32) * 2 - 1, 0);
if (p.length_squared() >= 1) continue;
return p;
}
}
pub fn random_in_unit_sphere() Vec3 {
while (true) {
const p = Vec3.random();