<p>When implementing transmission into a path tracer you have to keep in mind that neither BRDF's nor your previous sampling method are gonna cut it. You will need to think about what happens to light on both sides of your surface, which is where BTDF's and, more generally, BSDF's come in (the T and the S stand for Transmittance and Scattering, respectively).</p>

<p>It can be somewhat non-trivial to implement transmission to a path tracer that currently only supports reflection.</p>

<p>While i can't offer help with implementation details i can give you a few starting points and things you might want to read while you embarc on implementing this capabilty on your path tracer.</p>

<h1>On refraction.</h1>

<p>Pure and/or glossy refraction is a very common way of transmission, it is the type of transmission that happens on glass and probably what you are looking to implement.</p>

<h2><a href="https://en.wikipedia.org/wiki/Snell%27s_law" rel="nofollow noreferrer">Snell's Law.</a></h2>

<p>Light directions in refraction follow a simple mathematical law.</p>

<p>$$n_1\sin(\theta_1)=n_2\sin(\theta_2)$$</p>

<p>this reads as: the sine of the transmitted angle $\theta_2$ equals the sine of the incoming direction $\theta_1$ times the ratio of the "outside" <a href="https://en.wikipedia.org/wiki/Refractive_index" rel="nofollow noreferrer">index of refraction</a> and the "inside" index of refraction $\frac{n_1}{n_2}$</p>

<h2><a href="https://www.cs.cornell.edu/~srm/publications/EGSR07-btdf.pdf" rel="nofollow noreferrer">The GGX paper.</a></h2>

<p>There is a wonderful paper titled "Microfacet Models for Refraction through Rough Surfaces" that goes over a good piece of the theory behind microfacet models for refraction and presents a really quite good model for it.</p>

<h1>Fresnel and Monte-Carlo.</h1>

<p>when rendering a material that has both reflective and transmissive components there are a few different approaches that you can take to mix the two.</p>

<p>two main ways come to mind</p>

<h2>1. The Monte-Carlo way</h2>

<p>Do a "coin flip" with probabilities weighted according to the calculated fresnel value for each rendered point. Depending on the result you do transmission or reflection</p>

<h2>2. The recursive branching way</h2>

<p>Generate a reflected ray and path trace.
Generate a transmitted ray and path trace.
Mix the two found color values according to Fresnel value for every rendered point.</p>

<hr>

<p>I really hope this information is of use in solving your issue, and good luck! Great to see new users on the site.</p>

CC BY-SA 3.0
2018-02-15T06:16:06.530Z
2018-02-15T06:16:06.530Z
Sebastián Mestre
<p>I am trying to implement a path tracer, but I have some problem. The class <code>Spectrum</code> is color. I implemented a mirror material like this:</p>

<pre><code>Spectrum MirrorBSDF::f(const Vector3D&amp; wo, const Vector3D&amp; wi) 
{
    return reflectance * (1.0 / abs_cos_theta(wo));
}
</code></pre>

<p>The reflectance is a Spectrum variable. And now I want to add a material "Glass" that can reflect and refract. It meets the Fresnel theorem. Can someone teach me how to implement this? The function <code>f</code> is used like this:           </p>

<pre><code>Spectrum light_L = light-&gt;sample_L(hit_p, &amp;dir_to_light, &amp;dist_to_light, &amp;pdf);

// convert direction into coordinate space of the surface, where surface normal is [0 0 1]
Vector3D w_in = w2o * dir_to_light;
double cos_theta = std::max(0.0, w_in[2]);
Spectrum f = isect.bsdf-&gt;f(w_out, w_in);

// TODO: Construct a shadow ray and compute whether the intersected surface is
// in shadow and accumulate reflected radiance
Ray shadow_ray(hit_p + EPS_D * dir_to_light, dir_to_light, 
               dist_to_light - (EPS_D * dir_to_light).norm(), 0);
if (!bvh-&gt;intersect(shadow_ray))
{
    L_out += (f * light_L * (cos_theta * scale / pdf));
}
</code></pre>

<p>I implemented it.But something is error.Where is error?
<a href="https://i.sstatic.net/XuvAJ.jpg" rel="nofollow noreferrer"><img src="https://i.sstatic.net/XuvAJ.jpg" alt="enter image description here"></a></p>

CC BY-SA 3.0
2018-03-06T15:49:42.347Z
Please, do not add another question to this post. If there is anything else you need help with, then post another question.
Sebastián Mestre
<raytracing><brdf><material>
How can I implement this BSDF?
bin guo
# How can I implement this BSDF?

(Asked by: username_0 on 2018-01-18)

I am trying to implement a path tracer, but I have some problem. The class `Spectrum` is color. I implemented a mirror material like this:

```
Spectrum MirrorBSDF::f(const Vector3D& wo, const Vector3D& wi) 
{
    return reflectance * (1.0 / abs_cos_theta(wo));
}

```

The reflectance is a Spectrum variable. And now I want to add a material "Glass" that can reflect and refract. It meets the Fresnel theorem. Can someone teach me how to implement this? The function `f` is used like this:

```
Spectrum light_L = light->sample_L(hit_p, &dir_to_light, &dist_to_light, &pdf);

// convert direction into coordinate space of the surface, where surface normal is [0 0 1]
Vector3D w_in = w2o * dir_to_light;
double cos_theta = std::max(0.0, w_in[2]);
Spectrum f = isect.bsdf->f(w_out, w_in);

// TODO: Construct a shadow ray and compute whether the intersected surface is
// in shadow and accumulate reflected radiance
Ray shadow_ray(hit_p + EPS_D * dir_to_light, dir_to_light, 
               dist_to_light - (EPS_D * dir_to_light).norm(), 0);
if (!bvh->intersect(shadow_ray))
{
    L_out += (f * light_L * (cos_theta * scale / pdf));
}

```

I implemented it.But something is error.Where is error?
[![enter image description here](https://i.sstatic.net/XuvAJ.jpg)](https://i.sstatic.net/XuvAJ.jpg)

**Tags:** raytracing, brdf, material

> **Comments:**
> **username_1**: Please, do not add another question to this post. If there is anything else you need help with, then post another question.  

---

## 1 answers

### Answer by username_1 on 2018-02-15. Score: 4

When implementing transmission into a path tracer you have to keep in mind that neither BRDF's nor your previous sampling method are gonna cut it. You will need to think about what happens to light on both sides of your surface, which is where BTDF's and, more generally, BSDF's come in (the T and the S stand for Transmittance and Scattering, respectively).

It can be somewhat non-trivial to implement transmission to a path tracer that currently only supports reflection.

While i can't offer help with implementation details i can give you a few starting points and things you might want to read while you embarc on implementing this capabilty on your path tracer.

# On refraction.

Pure and/or glossy refraction is a very common way of transmission, it is the type of transmission that happens on glass and probably what you are looking to implement.

## [Snell's Law.](https://en.wikipedia.org/wiki/Snell%27s_law)

Light directions in refraction follow a simple mathematical law.

$$n\_1\sin(\theta\_1)=n\_2\sin(\theta\_2)$$

this reads as: the sine of the transmitted angle $\theta\_2$ equals the sine of the incoming direction $\theta\_1$ times the ratio of the "outside" [index of refraction](https://en.wikipedia.org/wiki/Refractive_index) and the "inside" index of refraction $\frac{n\_1}{n\_2}$

## [The GGX paper.](https://www.cs.cornell.edu/~srm/publications/EGSR07-btdf.pdf)

There is a wonderful paper titled "Microfacet Models for Refraction through Rough Surfaces" that goes over a good piece of the theory behind microfacet models for refraction and presents a really quite good model for it.

# Fresnel and Monte-Carlo.

when rendering a material that has both reflective and transmissive components there are a few different approaches that you can take to mix the two.

two main ways come to mind

## 1. The Monte-Carlo way

Do a "coin flip" with probabilities weighted according to the calculated fresnel value for each rendered point. Depending on the result you do transmission or reflection

## 2. The recursive branching way

Generate a reflected ray and path trace.
Generate a transmitted ray and path trace.
Mix the two found color values according to Fresnel value for every rendered point.

---

I really hope this information is of use in solving your issue, and good luck! Great to see new users on the site.


---

