# FXAA and sRGB

This topic is 2403 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

## Recommended Posts

I recently added the FXAA 3.9 shader into my application. In the original paper it is mentioned that special care needs to be taken in case of sRGB targets.
So I use a sRGB view when tonemapping and a RGB view when passing that texture to the FXAA. The FXAA renders to a RGB view of the sRGB backbuffer. Comparing this with just using sRGB views all the time I can not really see any difference. What should I be expecting?

Generally it seems to work just fine. Performance is great, but on the other hand it is relatively easy to find edges where it completely fails, at least in the scenes I tried.

##### Share on other sites
I think the newer versions have a define in the shader that you enable if you want to work in linear space (which means you use SRGB targets and textures).

##### Share on other sites
Comparing this with just using sRGB views all the time I can not really see any difference. What should I be expecting?
The intensity/luminosity calculations will produce slightly different results in linear VS sRGB. Doing it in sRGB will either over or under-estimate the actual intensity differences between two values.

e.g. say you've got two greyscale pixels next to each other, one at 100% intensity and the other at 50% intensity"
In 8-bit sRGB, those values correspond to 255 and 186.
In 8-bit linear, those values correspond to 255 and 127.

So, if you do your edge-detection calculations in sRGB, you'll incorrectly calculate that there's only a 27% difference in intensity, instead of the correct 50% difference.

Likewise, if we have two pixels at 50% and 0%:
In 8-bit sRGB, those values correspond to 186 and 0.
In 8-bit linear, those values correspond to 127 and 0.
If you do your edge-detection calculations in sRGB, you'll incorrectly calculate that there's a 73% difference in intensity, instead of the correct 50% difference.

Although, I'm a bit confused by this, because I was reading the latest version of the FXAA source code today, and it explicitly asks you to feed gamma-space luminance values into the algorithm...

##### Share on other sites

I was reading the latest version of the FXAA source code today, and it explicitly asks you to feed gamma-space luminance values into the algorithm...

My tone mapping ends like this:

 //... return float4(color, luminance(color)); } static const float3 g_luminanceVector = float3(0.299f, 0.587f, 0.114f); float luminance(float3 color) { return dot(color, g_luminanceVector) + 0.0001f; } 

I render this to an sRGB target, which is then fed to the FXAA shader. Is this what you are talking about, or am I doing it wrong. Your explanation of the difference between targets makes sense to me, yet I cannot see the difference in the actual results.

##### Share on other sites

I recently added the FXAA 3.9 shader into my application. In the original paper it is mentioned that special care needs to be taken in case of sRGB targets.
So I use a sRGB view when tonemapping and a RGB view when passing that texture to the FXAA. The FXAA renders to a RGB view of the sRGB backbuffer. Comparing this with just using sRGB views all the time I can not really see any difference. What should I be expecting?

I've tried it both ways too and I confirm that there's no visible difference between sRGB and non-SRGB colors. Anyway, do it with sRGB just to be sure you get optimal quality all the time.

Generally it seems to work just fine. Performance is great, but on the other hand it is relatively easy to find edges where it completely fails, at least in the scenes I tried.

Actually, I think it works almost flawlessly. Yes, it fails some edges but its not that common and in general FXAA is a real image quality booster for a reduced performance impact.

##### Share on other sites
I found out what was wrong. When storing the luminance in the alpha channel it should be
 sqrt(luminance(color)) 
but I was only doing
 luminance(color) 
instead. Fixing this improved the quality in virtually all places where I saw problems before.

##### Share on other sites
For longer edges and better quality I would suggest using the latest FXAA 3.11: http://timothylottes.blogspot.com/2011/07/fxaa-311-released.html

The 3.10 release increased the quality on long edges and added back presets so the quality and performance can be tuned.

Absolutely for luma packed in the alpha channel, FXAA requires a non-linear luma. This can be confusing. FXAA 3 finds end-of-edge condition by checking how much the average of 2 or 4 pixels changes from an edge threshold which was computed near to the source pixel getting processed. This average is done by a fractional texel offset when sampling. Since end-of-edge is a visual test, the average needs to be perceptual (gamma 2.0 works well and is fast). Linear encoding will not work correctly as the linear average does not account for the fact that humans see a larger difference between intensity in darker colors than in lighter colors.