How to use ambient occlusion maps

For now I am not going to elaborate on what ambient occlusion is but the very simplified explanation from Wikipedia is:

Ambient occlusion is a shading and rendering technique used to calculate how exposed each point in a scene is to ambient lighting. For example, the interior of a tube is typically more occluded (and hence darker) than the exposed outer surfaces, and becomes darker the deeper inside the tube one goes.

This is generally related to using AO directly from GLTF models, You can also use material overrides to apply AO map to a model and FBX may work too but I have not tested it.

Overte does have “realtime” Ambient occlusion (I think it’s SSAO), but it is very subtle, way too subtitle to make a meaningful difference in my opinion.

Luckily it also supports ambient occlusion maps, It is a grayscale texture map that tells the rendering engine how strongly each part should react to light, and it works very well.

No AO map(left). with AO map(right)

Especially in darker scenes with big cavities like this it looks a lot better not to have all that ambient light in there.

The downside is that you will have to bake an AO map for your model. If you use something like Substance Painter it is pretty easy, just add the AO map tp the list of desired output maps and tweak setting is needed.
In Blender, baking texture maps can be a bit cumbersome and I would explain here how to set it up except I don’t remember anymore, I use an addon called Simple Bake that does it all in a few clicks, but it is a paid addon though.

How to export a model with AO.

Once you have your AO map setting it up to export with GLTF is quite easy, although a bit weird.
Sine the Principled BSDF shader does not have a AO input the way they did is is that the exporter looks for a node group with an “Occlusion” input and a texture plugged into that. It does not have to be connected to any output and I don’t think it matter what it is called:

That is it really, This should export with the AO properly connected and show in Overte. To get that node group you can either make it yourself, like this:
Or you can just get a blend file that already has it, that is what Khronos themselves recommend getting this gltf example:
Water bottle.glb

Or you could get the example blend file I used here:
MergerSponge_AO_Example_with Embedded_textures.blend

It has a few extra bits, for example, since the node group is not connected to the material output, it will not show the effect of of the AO map in blender. In my example I mix it in with the Albedo to sort of simulate it. It is OK to leave those extra node in there since they do not export anyway.

Secondary UV for the AO map works for GLTF.

If you look at the Merger sponge Blender file above you will see that while the Concrete material is tiled many times over the model, the AO map is not and is unwrapped 1:! with no tiling, as it would generally need to be to work correctly.
That is because it has 2 UV maps, one for the AO map (SimpleBake) and one for all the other maps (UVmap).

The Overte GLTF import does support using a secondary UV for the AO map witch is very handy, it does however do it in a very non-standard way.
In the material nodes of the blend file you can see that I plugged an UV node into each of the texture maps to indicate which UV each texture map should use:

This is fully supported in the exported GLTF files, but sadly, the importer completely ignores it and instead applies the simple rule that, if a secondary UV exists, use that for AO, otherwise use the primary(only) UV map.
I still advise putting the UV nodes in for compatibility with other engines (and Overte once it get’s fixed)

I like how AO maps makes things pop a lot more :smile: even on smaller details so I really think that sometimes it is worth the extra effort.
Here is a JSON of the assets used in the video clip if you want to load it and see for yourself: