Skip to content

Commit ea16faa

Browse files
committed
Update theRestOfYourLife book new hittable_list
1 parent 31f4f2a commit ea16faa

File tree

1 file changed

+127
-64
lines changed

1 file changed

+127
-64
lines changed

books/RayTracingTheRestOfYourLife.html

Lines changed: 127 additions & 64 deletions
Original file line numberDiff line numberDiff line change
@@ -728,33 +728,43 @@
728728
our Cornell Box scene again, and let’s generate the camera in the function that generates the model:
729729

730730
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++
731-
void cornell_box(hittable **scene, camera **cam, double aspect) {
732-
material *red = new lambertian( new constant_texture(vec3(0.65, 0.05, 0.05)) );
733-
material *white = new lambertian( new constant_texture(vec3(0.73, 0.73, 0.73)) );
734-
material *green = new lambertian( new constant_texture(vec3(0.12, 0.45, 0.15)) );
735-
material *light = new diffuse_light( new constant_texture(vec3(15, 15, 15)) );
736-
737-
hittable **list = new hittable*[8];
738-
int i = 0;
739-
list[i++] = new flip_normals(new yz_rect(0, 555, 0, 555, 555, green));
740-
list[i++] = new yz_rect(0, 555, 0, 555, 0, red);
741-
list[i++] = new xz_rect(213, 343, 227, 332, 554, light);
742-
list[i++] = new flip_normals(new xz_rect(0, 555, 0, 555, 555, white));
743-
list[i++] = new xz_rect(0, 555, 0, 555, 0, white);
744-
list[i++] = new flip_normals(new xy_rect(0, 555, 0, 555, 555, white));
745-
list[i++] = new translate(new rotate_y(
746-
new box(vec3(0, 0, 0), vec3(165, 165, 165), white), -18), vec3(130,0,65));
747-
list[i++] = new translate(new rotate_y(
748-
new box(vec3(0, 0, 0), vec3(165, 330, 165), white), 15), vec3(265,0,295));
749-
*scene = new hittable_list(list,i);
731+
hittable_list cornell_box(camera& cam, double aspect) {
732+
hittable_list world;
733+
734+
auto *red = new lambertian(new constant_texture(vec3(0.65, 0.05, 0.05)));
735+
auto *white = new lambertian(new constant_texture(vec3(0.73, 0.73, 0.73)));
736+
auto *green = new lambertian(new constant_texture(vec3(0.12, 0.45, 0.15)));
737+
auto *light = new diffuse_light(new constant_texture(vec3(15, 15, 15)));
738+
739+
world.add(new flip_normals(new yz_rect(0, 555, 0, 555, 555, green)));
740+
world.add(new yz_rect(0, 555, 0, 555, 0, red));
741+
world.add(new xz_rect(213, 343, 227, 332, 554, light));
742+
world.add(new flip_normals(new xz_rect(0, 555, 0, 555, 555, white)));
743+
world.add(new xz_rect(0, 555, 0, 555, 0, white));
744+
world.add(new flip_normals(new xy_rect(0, 555, 0, 555, 555, white)));
745+
746+
hittable* box1 = new box(vec3(0,0,0), vec3(165,330,165), white);
747+
box1 = new rotate_y(box1, 15);
748+
box1 = new translate(box1, vec3(265,0,295));
749+
world.add(box1);
750+
751+
hittable* box2 = new box(vec3(0,0,0), vec3(165,165,165), white);
752+
box2 = new rotate_y(box2, -18);
753+
box2 = new translate(box2, vec3(130,0,65);
754+
world.add(box2);
750755

751756
vec3 lookfrom(278, 278, -800);
752757
vec3 lookat(278, 278, 0);
758+
vec3 up(0, 1, 0);
753759
auto dist_to_focus = 10.0;
754760
auto aperture = 0.0;
755761
auto vfov = 40.0;
756-
*cam = new camera(
757-
lookfrom, lookat, vec3(0,1,0), vfov, aspect, aperture, dist_to_focus, 0.0, 1.0);
762+
auto t0 = 0.0;
763+
auto t1 = 1.0;
764+
765+
cam = camera(lookfrom, lookat, up, vfov, aspect, aperture, dist_to_focus, t0, t1);
766+
767+
return world;
758768
}
759769
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
760770
[Listing [cornell-box]: <kbd>[main.cc]</kbd> Cornell box, refactored]
@@ -837,14 +847,22 @@
837847
And the color function gets a minor modification:
838848

839849
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++
840-
vec3 ray_color(const ray& r, hittable *world, int depth) {
850+
vec3 ray_color(const ray& r, hittable& world, int depth) {
841851
hit_record rec;
842-
if (depth <= 0 || !world->hit(r, 0.001, infinity, rec))
852+
853+
// If we've exceeded the ray bounce limit, no more light is gathered.
854+
if (depth <= 0)
855+
return vec3(0,0,0);
856+
857+
// If the ray hits nothing, return the background color.
858+
if (!world.hit(r, 0.001, infinity, rec))
843859
return vec3(0,0,0);
844860

845861
ray scattered;
846862
vec3 attenuation;
847863
vec3 emitted = rec.mat_ptr->emitted(rec.u, rec.v, rec.p);
864+
865+
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++ highlight
848866
double pdf;
849867
vec3 albedo;
850868

@@ -854,6 +872,7 @@
854872
return emitted
855873
+ albedo * rec.mat_ptr->scattering_pdf(r, rec, scattered)
856874
* ray_color(scattered, world, depth-1) / pdf;
875+
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++
857876
}
858877
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
859878
[Listing [ray-color-impsample]: <kbd>[main.cc]</kbd>
@@ -1284,7 +1303,13 @@
12841303
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++
12851304
vec3 ray_color(const ray& r, hittable *world, int depth) {
12861305
hit_record rec;
1287-
if (depth <= 0 || !world->hit(r, 0,001, infinity, rec))
1306+
1307+
// If we've exceeded the ray bounce limit, no more light is gathered.
1308+
if (depth <= 0)
1309+
return vec3(0,0,0);
1310+
1311+
// If the ray hits nothing, return the background color.
1312+
if (!world.hit(r, 0.001, infinity, rec))
12881313
return vec3(0,0,0);
12891314

12901315
ray scattered;
@@ -1445,7 +1470,13 @@
14451470
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++
14461471
vec3 ray_color(const ray& r, hittable *world, int depth) {
14471472
hit_record rec;
1448-
if (depth <= 0 || !world->hit(r, 0.001, infinity, rec))
1473+
1474+
// If we've exceeded the ray bounce limit, no more light is gathered.
1475+
if (depth <= 0)
1476+
return vec3(0,0,0);
1477+
1478+
// If the ray hits nothing, return the background color.
1479+
if (!world.hit(r, 0.001, infinity, rec))
14491480
return vec3(0,0,0);
14501481

14511482
ray scattered;
@@ -1564,7 +1595,13 @@
15641595
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++
15651596
vec3 ray_color(const ray& r, hittable *world, int depth) {
15661597
hit_record rec;
1567-
if (depth <= 0 || !world->hit(r, 0.001, infinity, rec))
1598+
1599+
// If we've exceeded the ray bounce limit, no more light is gathered.
1600+
if (depth <= 0)
1601+
return vec3(0,0,0);
1602+
1603+
// If the ray hits nothing, return the background color.
1604+
if (!world.hit(r, 0.001, infinity, rec))
15681605
return vec3(0,0,0);
15691606

15701607
ray scattered;
@@ -1630,7 +1667,13 @@
16301667
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++
16311668
vec3 ray_color(const ray& r, hittable *world, hittable *light_shape, int depth) {
16321669
hit_record rec;
1633-
if (depth <= 0 || !world->hit(r, 0.001, infinity, rec))
1670+
1671+
// If we've exceeded the ray bounce limit, no more light is gathered.
1672+
if (depth <= 0)
1673+
return vec3(0,0,0);
1674+
1675+
// If the ray hits nothing, return the background color.
1676+
if (!world.hit(r, 0.001, infinity, rec))
16341677
return vec3(0,0,0);
16351678

16361679
ray scattered;
@@ -1813,9 +1856,14 @@
18131856
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++
18141857
vec3 ray_color(const ray& r, hittable *world, hittable *light_shape, int depth) {
18151858
hit_record rec;
1816-
if (depth <= 0 || !world->hit(r, 0.001, infinity, rec))
1859+
1860+
// If we've exceeded the ray bounce limit, no more light is gathered.
1861+
if (depth <= 0)
18171862
return vec3(0,0,0);
18181863

1864+
// If the ray hits nothing, return the background color.
1865+
if (!world.hit(r, 0.001, infinity, rec))
1866+
return vec3(0,0,0);
18191867

18201868
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++ highlight
18211869
scatter_record srec;
@@ -1876,7 +1924,13 @@
18761924
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++
18771925
vec3 ray_color(const ray& r, hittable *world, hittable *light_shape, int depth) {
18781926
hit_record rec;
1879-
if (depth <= 0 || !world->hit(r, 0.001, infinity, rec))
1927+
1928+
// If we've exceeded the ray bounce limit, no more light is gathered.
1929+
if (depth <= 0)
1930+
return vec3(0,0,0);
1931+
1932+
// If the ray hits nothing, return the background color.
1933+
if (!world.hit(r, 0.001, infinity, rec))
18801934
return vec3(0,0,0);
18811935

18821936
scatter_record srec;
@@ -1910,37 +1964,46 @@
19101964
We also need to change the block to metal.
19111965

19121966
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++
1913-
void cornell_box(hittable **scene, camera **cam, double aspect) {
1914-
int i = 0;
1915-
hittable **list = new hittable*[8];
1916-
material *red = new lambertian( new constant_texture(vec3(0.65, 0.05, 0.05)) );
1917-
material *white = new lambertian( new constant_texture(vec3(0.73, 0.73, 0.73)) );
1918-
material *green = new lambertian( new constant_texture(vec3(0.12, 0.45, 0.15)) );
1919-
material *light = new diffuse_light( new constant_texture(vec3(15, 15, 15)) );
1920-
list[i++] = new flip_normals(new yz_rect(0, 555, 0, 555, 555, green));
1921-
list[i++] = new yz_rect(0, 555, 0, 555, 0, red);
1922-
list[i++] = new flip_normals(new xz_rect(213, 343, 227, 332, 554, light));
1923-
list[i++] = new flip_normals(new xz_rect(0, 555, 0, 555, 555, white));
1924-
list[i++] = new xz_rect(0, 555, 0, 555, 0, white);
1925-
list[i++] = new flip_normals(new xy_rect(0, 555, 0, 555, 555, white));
1926-
list[i++] = new translate(
1927-
new rotate_y(new box(vec3(0, 0, 0), vec3(165, 165, 165), white), -18),
1928-
vec3(130,0,65));
1967+
hittable_list cornell_box(camera& cam, double aspect) {
1968+
hittable_list world;
1969+
1970+
auto *red = new lambertian(new constant_texture(vec3(0.65, 0.05, 0.05)));
1971+
auto *white = new lambertian(new constant_texture(vec3(0.73, 0.73, 0.73)));
1972+
auto *green = new lambertian(new constant_texture(vec3(0.12, 0.45, 0.15)));
1973+
auto *light = new diffuse_light(new constant_texture(vec3(15, 15, 15)));
1974+
1975+
world.add(new flip_normals(new yz_rect(0, 555, 0, 555, 555, green)));
1976+
world.add(new yz_rect(0, 555, 0, 555, 0, red));
1977+
world.add(new xz_rect(213, 343, 227, 332, 554, light));
1978+
world.add(new flip_normals(new xz_rect(0, 555, 0, 555, 555, white)));
1979+
world.add(new xz_rect(0, 555, 0, 555, 0, white));
1980+
world.add(new flip_normals(new xy_rect(0, 555, 0, 555, 555, white)));
1981+
19291982
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++ highlight
19301983
material *aluminum = new metal(vec3(0.8, 0.85, 0.88), 0.0);
1931-
list[i++] = new translate(
1932-
new rotate_y(new box(vec3(0, 0, 0), vec3(165, 330, 165), aluminum), 15),
1933-
vec3(265,0,295));
1984+
hittable* box1 = new box(vec3(0,0,0), vec3(165,330,165), aluminum);
19341985
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++
1935-
*scene = new hittable_list(list,i);
1986+
box1 = new rotate_y(box1, 15);
1987+
box1 = new translate(box1, vec3(265,0,295));
1988+
world.add(box1);
1989+
1990+
hittable* box2 = new box(vec3(0,0,0), vec3(165,165,165), white);
1991+
box2 = new rotate_y(box2, -18);
1992+
box2 = new translate(box2, vec3(130,0,65);
1993+
world.add(box2);
19361994

19371995
vec3 lookfrom(278, 278, -800);
1938-
vec3 lookat(278,278,0);
1996+
vec3 lookat(278, 278, 0);
1997+
vec3 up(0, 1, 0);
19391998
auto dist_to_focus = 10.0;
19401999
auto aperture = 0.0;
19412000
auto vfov = 40.0;
1942-
*cam = new camera(
1943-
lookfrom, lookat, vec3(0,1,0), vfov, aspect, aperture, dist_to_focus, 0.0, 1.0);
2001+
auto t0 = 0.0;
2002+
auto t1 = 1.0;
2003+
2004+
cam = camera(lookfrom, lookat, up, vfov, aspect, aperture, dist_to_focus, t0, t1);
2005+
2006+
return world;
19442007
}
19452008
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
19462009
[Listing [scene-cornell-al]: <kbd>[main.cc]</kbd> Cornell box scene with aluminum material]
@@ -2100,31 +2163,31 @@
21002163

21012164
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++
21022165
double hittable_list::pdf_value(const vec3& o, const vec3& v) const {
2103-
auto weight = 1.0/list_size;
2166+
auto weight = 1.0/objects.size();
21042167
auto sum = 0.0;
2105-
for (int i = 0; i < list_size; i++)
2106-
sum += weight*list[i]->pdf_value(o, v);
2168+
2169+
for (auto object : objects)
2170+
sum += weight * object->pdf_value(o, v);
2171+
21072172
return sum;
21082173
}
21092174

21102175
vec3 hittable_list::random(const vec3& o) const {
2111-
int index = random_int(0, list_size-1);
2112-
return list[ index ]->random(o);
2176+
auto int_size = static_cast<int>(objects.size());
2177+
auto index = static_cast<size_t>(random_int(0, int_size-1));
2178+
return objects[index]->random(o);
21132179
}
21142180
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
21152181
[Listing [density-mixture]: <kbd>[hittable_list.h]</kbd> Creating a mixture of densities]
21162182
</div>
21172183

21182184
<div class='together'>
2119-
We assemble a list to pass in to `ray_color()`.
2185+
We assemble a list to pass to `ray_color()` `from main()`:
21202186

21212187
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++
2122-
hittable *light_shape = new xz_rect(213, 343, 227, 332, 554, 0);
2123-
hittable *glass_sphere = new sphere(vec3(190, 90, 190), 90, 0);
2124-
hittable *a[2];
2125-
a[0] = light_shape;
2126-
a[1] = glass_sphere;
2127-
hittable_list hlist(a,2);
2188+
hittable_list lights;
2189+
lights.add(new xz_rect(213, 343, 227, 332, 554, 0));
2190+
lights.add(new sphere(vec3(190, 90, 190), 90, 0));
21282191
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
21292192
[Listing [scene-density-mixture]: <kbd>[main.cc]</kbd> Updating the scene]
21302193
</div>

0 commit comments

Comments
 (0)