Blender's missing shader, being in Octane and LuxCore for years now. After rigorously studying the physics, modelling the effect and calibrating the shader, I am now making it available for your Cycles or Eevee workflow too.
What is it?
This is a physically correct shader node, with presets, that models thin-film interference. The effect creates not only the lively colours of iridescence and pearlescence in materials like soap, oil or pearls. It also determines the hues of anodized metals, beetle shells (yes, really) and is the main part in colour-changing car paint. One shader node can do all of the above without being overcomplicated to use.
Besides the main node, the download includes 15 premade iridescent materials. Including all of the material types seen in the gallery.
Entering real world material properties (ones you can easily find online) will generate the actual colour of the material.
Why do you need it?
It works for any material that has any iridescence
- It makes photorealism possible
- Using this shader saves valuable time
- Almost no effort is required to get it working
- It doesn't just look real, you can rely on it being accurate
The shader is built on physics equations and considers concepts like Rayleigh scattering, wave interference, internal reflection and absorption.
What all this means is that after the values are set correctly, it will look correct in any environment. Besides, let's say you wanted to create an iridescent material the normal way. You might try to get close with a ColorRamp and some fresnel nodes. It might be recognizable as iridescence, but it won't look exactly right. It doesn't react to lighting like you'd expect, the colour doesn't change with angle exactly as it does in real life etc. This all gives away that it's a render. If the goal is photorealism, looking like the material, isn't enough, it needs to be the material. People can tell the difference!
It saves time
Even when Ignoring the realism of the result, the process to get there is much faster and more reliable. When recreating a material, one can spend a large amount of time tweaking and checking against references. The tweaks usually work against each other, starting a cycle of going back and forth just to get a single gradient to look right. When it's not physically correct you might even need to start over when changing the lighting.
With the thin film shader, you would look up the required values on internet within a single minute. After entering them and seeing the result looking like expected, you can safely leave the material behind and move on within minutes. No troubleshooting of improvised nodes, no endless tweaking and checking references, it is immensely more time-efficient and comfortable to work with.
How hard is it to use?
Use the node as the colour of a metallic or glossy shader. Then enter the IOR and film thickness values you found. Hook up a normal map and that's it!
For film on a transmissive base like water, glass or air, simply set the Transmission to 1. The colour will be corrected and a physically correct alpha mask is generated, you can use it directly as factor to mix with any non-opaque shader.
Alternatively you can simply use one of the included materials. Then adjust the settings from there if necessary.
Control and flexibility
The way the thin film node integrates into the shader workflow, it leaves almost all control to the end user. It can perform very well at modelling just the base thin film effect. For other cases:
- A texture can be used as film thickness to create detailed patterns
- Artificial override settings are available for more artistic control.
- The node's output can be manipulated and used for any shader you want
Because of this, it can be used for any material that would benefit from iridescence, not just the textbook examples.
The flexibility is demonstrated by the completely different materials in the featured gallery, all of them built on the same thin film node.
Why should I trust that it's accurate?
I can imagine that you'd ask this, I've said it to myself too. To be sure, I made a simple setup that created a thickness gradient along one axis. That could easily be compared to existing charts.
Here is one of the comparisons, the colours of soap against thickness.
Reference Chart (source):
Blender viewport cycles output (nodes):
In the example above the scale goes from 0-1000 nm in the reference, in the blender nodes it's 0-1 micrometer (so the same). The exact same pattern and scale appeared without any adjustments.
I won't clog the page with test results, but other materials I tested like anodized titanium or nacre (mother of pear) were also successful;.
To wrap up with an even more impressive result: this shader was able to render oil on water better than in a published scientific paper.
Figure from paper at p. 37:
Eevee realtime render (nodes):
The Eevee render has oil on a very thin layer of water, but the same effect applies. Note that the colours, especially in the center, are much closer to the real world reference than the result of the paper. And apart from some noise textures, by using the thin film node the shader isn't even that complex.