Cycles PBR thin film interference, iridescence and metals

UPDATE 2.0: Updated for my presentation at the Blender Conference 2022

I updated the OSL script to use the current language features and made GPU-compatible nodes from it with OSLPy. The output is fully benchmarked against optical models I used as a scientific researcher in nanophotonics. Get the Node group (Blender 3.3) plus all materials shown below here:

OSL Scripts used to generate the node:

Note: you’ll need a modified OSLPy in order to generate the node groups.

This post will be updated over the course of the week!

Example output:

Blend file

The colors of soap bubbles is caused by a phenomenon called thin-film interference. Cycles does not natively support the calculation of this effect, but I have implemented a model which, within the limitations of Cycles, gives accurate results. In order to calculate accurate results, the Node Group needs the refractive index of the materials involved.

Next to soap bubbles and other glassy materials, oxide layers on metals can also be accurately calculated. Below the heating of iron is shown, where an increased temperature corresponds to a thicker oxide layer, which in turn causes the color to change.


The blend file above has the following material presets (change the material of the test object to view)

These materials are examples of how the Node Group can be used to calculate common interference phenomena in Blender.

Using the Node Groups:
To be updated, but you can watch the presentation

1.3 Outputs:

  • R: reflected percentage of the light, per color (RGB), at the angle between the normal and the ray of light.
  • T: transmitted percentage of light, per color. Can be hooked up to a refractive shader.

By hooking these up to glossy and refractive shaders, metallic and glass-like materials can be made. Examples are present in the blend file.

2.1 Choosing values for n and k

The shader allows you to enter the values to use for the refractive index (n) and the extinction coefficient (k) for the red, green and blue channels. These values are often listed as a function of the wavelength of the light, for example at The node groups use:

  • 650 nm for red
  • 532 nm for green
  • 450 nm for blue

2.2 Optimized values of n and k for metals

So-called spectral renderers use the tabulated n and k values for each wavelength in the visible light spectrum to calculate what a material should look like. Cycles on the other hand only uses three color channels, one for red, one for green and one for blue. You might wonder what n and k values would best approximate the results of a spectral renderer. I have optimized the values of n and k for the metals that are included in the blend file to look as close as possible to the output from a spectral renderer, when the metal is illuminated with white light (D65 white point).


Thank you.

Just another example:

Do you have to do anything to get this script working.

I copied the text - pasted it into the text editor, named it - then added the script node and tried to load it - however the code just keeps throwing an “invalid syntax” error on line 1.

nice looking

can you give the math model followed for this effect
to understand what the model is

happy cl

Video showing angle-dependent color (smooth glossy shader for speed):

Did you try the .blend file that I also put online?

Thanks :slight_smile:

Here’s a starter:

Not how I implemented it, though. I implemented this formula:

where r(p,s) is the complex reflection amplitude for light of a certain wavelength at a certain angle. This depends on the reflection coefficients of light at the interface with the film (r12), the reflection coefficient at the interface with the substrate (r23) and the thickness (d). See also, for example, L. Novotny & B. Hecht, Principles of Nano-optics, Ch. 2 & ch. 10.

Yes - it’s ok - muppet me hadn’t ticked the OSL checkbox on the render tab

edit: Just been having a play - very cool.

Glad to hear! :slight_smile:

any chance this could be use to do some other effects like sea shells surface ?

happy cl

Yes, I think you can get quite far, though I don’t have the exact behavior of mother of pearl firmly in my head.

but your OSL does only circular shapes I think so this might require some re shaping or deformations to look like mother pearl !

happy cl

You can modify the thickness d as a function of location. Set it to 0 to turn off interference, set it to some value to turn it on. Set it to a specific thickness to get a certain color at a certain angle. You could even use one of the colors (R, G or B) to drive another color map. I’m not sure how far you can push it, but it would be a start.

Edit: for the soap bubble animation I started out with a homogeneous thickness across the bubble, slowly decreasing the thickness at the top and increasing it at the bottom to simulate gravity. It’s just an example of what you could do

I did not learn a lot on OSL so cannot really begin to find a logical way to do it !

happy cl

You don’t need OSL to change the thickness, just plug something into the connector for d and you’re done :slight_smile: Look at my blend file, where I’ve added nodes to locally change the thickness in the last scene in the file.

I will try it tomorrow got other problems to solve for today! LOL

happy cl

do you know there is a thread for all OSL things
you should add your in that thread too

happy cl

Yes, I will do that, thanks! :slight_smile:

I also fixed a bug, so I’ve updated the OSL script. See first post for the update (blend file and script)

for the 2 files or only first one ?

I mean does it affect the other PBR metal too ?

happy bl