Skip to content

Commit ed69218

Browse files
authored
Fix metal fuzz factor
This was broken when we dropped the reflection vector normalization due to issue #1340. Resolves #1496.
1 parent 351a3fe commit ed69218

File tree

6 files changed

+26
-13
lines changed

6 files changed

+26
-13
lines changed

books/RayTracingInOneWeekend.html

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3203,11 +3203,15 @@
32033203

32043204
![Figure [reflect-fuzzy]: Generating fuzzed reflection rays](../images/fig-1.16-reflect-fuzzy.jpg)
32053205

3206-
The bigger the sphere, the fuzzier the reflections will be. This suggests adding a fuzziness
3206+
The bigger the fuzz sphere, the fuzzier the reflections will be. This suggests adding a fuzziness
32073207
parameter that is just the radius of the sphere (so zero is no perturbation). The catch is that for
32083208
big spheres or grazing rays, we may scatter below the surface. We can just have the surface absorb
32093209
those.
32103210

3211+
Also note that in order for the fuzz sphere to make sense, it needs to be consistently scaled
3212+
compared to the reflection vector, which can vary in length arbitrarily. To address this, we need to
3213+
normalize the reflected ray.
3214+
32113215
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++
32123216
class metal : public material {
32133217
public:
@@ -3219,8 +3223,9 @@
32193223
const override {
32203224
vec3 reflected = reflect(r_in.direction(), rec.normal);
32213225
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++ highlight
3222-
scattered = ray(rec.p, reflected + fuzz*random_unit_vector());
3226+
reflected = unit_vector(reflected) + (fuzz * random_unit_vector());
32233227
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++
3228+
scattered = ray(rec.p, reflected);
32243229
attenuation = albedo;
32253230
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++ highlight
32263231
return (dot(scattered.direction(), rec.normal) > 0);

books/RayTracingTheNextWeek.html

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -278,10 +278,12 @@
278278
bool scatter(const ray& r_in, const hit_record& rec, color& attenuation, ray& scattered)
279279
const override {
280280
vec3 reflected = reflect(r_in.direction(), rec.normal);
281+
reflected = unit_vector(reflected) + (fuzz * random_unit_vector());
281282
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++ highlight
282-
scattered = ray(rec.p, reflected + fuzz*random_unit_vector(), r_in.time());
283+
scattered = ray(rec.p, reflected, r_in.time());
283284
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++
284285
attenuation = albedo;
286+
285287
return (dot(scattered.direction(), rec.normal) > 0);
286288
}
287289
...

books/RayTracingTheRestOfYourLife.html

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -3320,16 +3320,20 @@
33203320

33213321
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++ highlight
33223322
bool scatter(const ray& r_in, const hit_record& rec, scatter_record& srec) const override {
3323+
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++
3324+
vec3 reflected = reflect(r_in.direction(), rec.normal);
3325+
reflected = unit_vector(reflected) + (fuzz * random_unit_vector());
3326+
3327+
3328+
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++ highlight
33233329
srec.attenuation = albedo;
33243330
srec.pdf_ptr = nullptr;
33253331
srec.skip_pdf = true;
3326-
3327-
vec3 reflected = reflect(r_in.direction(), rec.normal);
3328-
srec.skip_pdf_ray = ray(rec.p, reflected + fuzz*random_unit_vector(), r_in.time());
3332+
srec.skip_pdf_ray = ray(rec.p, reflected, r_in.time());
33293333

33303334
return true;
3331-
}
33323335
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ C++
3336+
}
33333337

33343338
private:
33353339
color albedo;

src/InOneWeekend/material.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -57,7 +57,8 @@ class metal : public material {
5757
bool scatter(const ray& r_in, const hit_record& rec, color& attenuation, ray& scattered)
5858
const override {
5959
vec3 reflected = reflect(r_in.direction(), rec.normal);
60-
scattered = ray(rec.p, reflected + fuzz*random_unit_vector());
60+
reflected = unit_vector(reflected) + (fuzz * random_unit_vector());
61+
scattered = ray(rec.p, reflected);
6162
attenuation = albedo;
6263
return (dot(scattered.direction(), rec.normal) > 0);
6364
}

src/TheNextWeek/material.h

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -64,9 +64,9 @@ class metal : public material {
6464
bool scatter(const ray& r_in, const hit_record& rec, color& attenuation, ray& scattered)
6565
const override {
6666
vec3 reflected = reflect(r_in.direction(), rec.normal);
67-
scattered = ray(rec.p, reflected + fuzz*random_unit_vector(), r_in.time());
67+
reflected = unit_vector(reflected) + (fuzz * random_unit_vector());
68+
scattered = ray(rec.p, reflected, r_in.time());
6869
attenuation = albedo;
69-
7070
return (dot(scattered.direction(), rec.normal) > 0);
7171
}
7272

src/TheRestOfYourLife/material.h

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -77,12 +77,13 @@ class metal : public material {
7777
metal(const color& albedo, double fuzz) : albedo(albedo), fuzz(fuzz < 1 ? fuzz : 1) {}
7878

7979
bool scatter(const ray& r_in, const hit_record& rec, scatter_record& srec) const override {
80+
vec3 reflected = reflect(r_in.direction(), rec.normal);
81+
reflected = unit_vector(reflected) + (fuzz * random_unit_vector());
82+
8083
srec.attenuation = albedo;
8184
srec.pdf_ptr = nullptr;
8285
srec.skip_pdf = true;
83-
84-
vec3 reflected = reflect(r_in.direction(), rec.normal);
85-
srec.skip_pdf_ray = ray(rec.p, reflected + fuzz*random_unit_vector(), r_in.time());
86+
srec.skip_pdf_ray = ray(rec.p, reflected, r_in.time());
8687

8788
return true;
8889
}

0 commit comments

Comments
 (0)