I want to make a node group so I can enter a F0 value instead of the IOR value for fresnel.
The purpose is to make a fresnel node group for metallic shaders, since default fresnel isn't suitable for metallics.
Already tried
I've already tried curves with facing node, but I'm searching an alternative without curves since they aren't easyly/quickly modifiable (in my opinion).
Starting point
I've started with a fresnel node with an IOR of 1.6, it gives me a nice curve to work on. Then I put a power math node to have a max value of 1 and adjust the curve's F0, it works like I want, but it isn't intuitive to enter a power value of 0.01 for a F0 of 97%.
Test scene
Color management set to none (pure datas)
Orthographic camera
An arched mesh to apply the shader, I know that the progression of the angle related to the camera isn't linear, so the end of my curve will tend to be x compressed.
Emission shader to see the curve in the waveform tool of the compositor

With this base, let say I want a F0 = 45% (0.45 is good too), what node group must I set to have the 45% (or 0.45) value driving the power of the fresnel 1.6 IOR value?
Since it's for metallics I don't need to go under the 1.6 IOR base.
And I used the terme driving but if possible I want to avoid drivers.

Edit: To expose a bit more about the fresnel issue with metallics.
This is a fresnel curve from default fresnel IOR=1.6 (F0=6%). Good behavior for dielectrics. fresnel_f0_6%

This one is a default fresnel IOR=18 (F0=80%). Here you see the drop down of the curve, certainly why people use edge tint.

This one is a default fresnel IOR=1.6 with a power of 0.072 (F0=80%). This time the curve is correct (don't know if it's 100% but nice enough). No darkening of the grazing angles fresnel_f0_80%_custom

It's why I need a convertion from F0 to the value that powered the fresnel curve IOR of 1.6 (or better, an IOR value of x)


1 Answer 1


Update 1:


The built in Fresnel node contains the equation for dielectrics, not metals. However in most cases the the curve is almost identical.

It is possible to implement metallic Fresnel using nodes, but it's complicated and not worth it in my opinion.

Each RGB component of the specular color is treated as its own $F_0$. (make sure all RGB values are greater than zero, otherwise it will not converge to white at the edges)

I derived an equation that relates $F_0$ to $n$ (index of refraction) from this equation (Derived from Snell's law):

$$ F_0 = \left( \frac{n_1 - n_2}{n_1 + n_2} \right)^2 $$

Where $n_1$ is the index of refraction of the material the light is coming from and $n_2$ is the index of refraction of the material the light is hitting. In most cases air, which has an index of refraction of approximately one, by substitution in the equation:

$$ F_0 = \left( \frac{1 - n_2}{1 + n_2} \right)^2 $$

And since $n_2$ is the index of refraction of the material the light is hitting:

$$ F_0 = \left( \frac{1 - n}{1 + n} \right)^2 $$

Using algebra we can rearrange the equation to find $n$:

$$ n = \frac{1+\sqrt{f_0}}{1 - \sqrt{f_0}} $$

$n$ is not an independent variable. This means $F_0$ and $n$ can not be controlled separately. Changing them independently would cause an incorrect curve. (Yes, that means the Fresnel in the layer weight node is incorrect)

Unfortunately Blenders implementation of the Fresnel equation does not take into account roughness. This would be an easy fix if we knew the direction to the light source, but we don't have a node with that info. So we just have to approximate it as best we can. This is what Cynicat's roughness hack does.

I have exposed the index of refraction in the Fresnel node group because it's useful for things like refraction.

If you want an edge tint like some metals have you can approximate it by mixing two colors based on the facing value in the layer weight node, then passing that color into the specular slot.

If you want some specular values for materials there is a small list here "Background: Physics and Math of Shading" on page 17. [make sure you use the linear values not the SRGB ones]

Update 2:

Perhaps you could try Schlick's approximation. It's what most game engines use. It doesn't have that downward curve with high $F_0$ values.

Schlick's approximation

  • $\begingroup$ Nice step forward, thanks, can you explain a bit about the formula? I'm not a math guy but this one looks easy to understand. The problem is that it use the default fresnel formula, result is it still not correct fresnel for metallics. But perhapse with some more nodes... the goal is to do that but to keep the shape of a fresnel curve with an IOR of 1.6 (same behavior of pluging a power behind the default fresnel). I'll try the fresnel of Cynicat, but it's a different aproach, don't now yet if it fits my workflow. $\endgroup$
    – Mareck
    Commented Feb 8, 2017 at 22:25
  • $\begingroup$ Ah, I understand what you're trying to do now. I will make a more detailed node setup for you when I get home in a few hours. $\endgroup$ Commented Feb 9, 2017 at 3:09
  • $\begingroup$ Thanks for the detailed answer and informations, you perfectly understood the finality with separate RGB driving color, but I've edit my question to better visualise what the problem with the default fresnel is, and why I need a curve powered by a value driven by the F0 (A good and easy visual aproximation for me). $\endgroup$
    – Mareck
    Commented Feb 12, 2017 at 23:41
  • $\begingroup$ @Mareck I have updated my answer to include Schlick's approximation. $\endgroup$ Commented Feb 13, 2017 at 2:14
  • $\begingroup$ I've maked your answer as accepted even if it doesn't completly fill my needs because, it's a good answer, it helped me and I don't know if power an IOR by a F0 is doable. Little feedback for the schilck's aproximation, it's a nice F0 workflow and a good aproximation, in my case I'll stay with an IOR power, for maximum realism. $\endgroup$
    – Mareck
    Commented Feb 18, 2017 at 5:40

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .