Mixing multiple "env" maps

I would like to mix different environment maps into one single material.
I am looking for the possibility of creating a transition from one environment to another.

For the time being i’m only looking for a simple transition (linear interpolation from A to B).
Does anyone already achieve something similar ?
What is the straight forward solution ? Creating a second env map attribute, and a float attribute (mix) by overriding existing shader (say MeshPhysicalMaterial) ?

Also I’m still curious about the possibilities of a more complex, probe-based implementation. Does anyone know where to look ? or any paper to read ?

Thanks

EDIT :
For the probe based complex solution, this could be a good start:

1 Like

Thank you for pdf, very usefull. Also links for light probes:

three.js examples
three.js examples
three.js examples
Light probes | Unity Blog
https://github.com/mrdoob/three.js/issues/6251
https://github.com/mrdoob/three.js/issues/16228
https://github.com/mrdoob/three.js/pull/18371
three.js webgl - lights - light probe volume
https://github.com/mrdoob/three.js/compare/dev...donmccurdy:feat-lightprobevolume

Hi Chaser, thx for the links. There are some cool stuff on threejs with light probes.
However, this is not my first goal, which is mixing two env map (cube texture), from the first one to the second thanks to a float.
Do you have any idea how to do this?

I’m reading the source code of the MeshPhysicalMaterial, i think i can modify it, but it won’t be so easy…

I’ve handled this by making a brand new material following this article of pailhead on medium.
I’m extending the MeshPhysicalMaterial and provide an second envMap, judiciously called “envMap2” with a new uniforms called “envMapMix” to allow the mix in the shader:

vec4 envMapColor = mix(envMapColor1, envMapColor2, envMapMix);

If anyone is interested on this simple implementation, just ping me.

3 Likes

Good to know you’ve implemented mixing 2 env maps within the object shader.

Depending on the final use case (or maybe replicating matterport), I would reccomend going beyond that:

  • if you intend to “mix multiple env maps” (i.e. more than 2)
  • if you are thinking in populating the scene with more than 1 object (you don’t want to redundantly perform this exact mix in every object shader)
  • if you are considering in using the mixed env map for applying parallax-corrected cubemaps (and not only reflection but also refraction, illumination, and even shadows!)

For all that cases, the more efficient way to go is performing env blending in a dedicated second shader, taking advantage of hardware acceleration.

Sebastian Legarde nailed this approach (not to say that his paper lead him to a research position inside Unity Labs). During my master thesis I wrote a full implementation with three.js - a lot of wiring to and from frame buffer objects. I am afraid currently is veery dated (rev 100 or so) but if you need I can give you more insights from my.own process

1 Like

Hi @Antonio, thx for your response.
In fact I just think that, as you suggest, rather than the previous solution, I need to have one texture that will blend the different envmap, mainly because that texture will be used on several materials.

So a dedicated shader means using “render to texture” right? Someone told me it could have an impact on performance because it implies two render by frame, but such a little shader should not have significant impact (even on mobile), what do you think about it ?

Since a cubemap is made of 6 textures, does it mean that i have to call 6 times render-to-texture? What about any optimization here? Rendering 6 planes with 6 textures into a one big texture, then? Copy the data to the 6 destination textures? Is it really worth it?

About render-to-texture, there is that example from threejs: webgl_rtt
Is it the best example i can get?