SimuLook · Notes from the camera

Noise reduction is not a slider

Most of the settings in a Fujifilm custom slot store something you could guess once you have seen two examples. The tone controls hold tenths: −1 is stored as −10, +2 as +20. Sharpness and colour follow the same rule. Colour temperature is stored in Kelvin.

Noise reduction is not like that.

What it actually stores

Here is the whole table, menu value against what the camera holds:

Menu +4 +3 +2 +1 0 −1 −2 −3 −4
Stored 20480 24576 0 4096 8192 12288 16384 28672 32768

Read down that row and the problem is obvious. It is not linear. It is not even monotonic. The value for +2 is zero, which is lower than every other entry. The value for +3 is larger than the value for +2, +1 and 0, but smaller than the one for −3.

There is no formula. It is a lookup table, and the only way to build a lookup table is to observe every entry.

Why it took so long

Because the obvious way to check it does not work.

The natural experiment is to develop the same frame at different noise reduction settings and see which rendering corresponds to which stored value. To compare the renderings you need a number, and the tempting number is file size — more noise reduction, smoother image, smaller JPEG.

That reasoning is sound and the measurement is useless, because JPEG size is dominated by what is in the frame. A slightly different exposure or a leaf moving between shots swamps the difference the setting makes. We ordered the table by file size and got an ordering that was confidently wrong.

What worked was measuring the actual thing the setting changes: the energy in the fine detail, the difference between neighbouring pixels across the whole frame. That is what noise reduction removes, so that is what to count. It gave a clean ordering where file size gave noise.

The two ends of the table are anchored by photographs shot at menu −4 and +4, so the extremes are not inferred from the middle.

Above the top it wraps

Push the stored value past 32768 and the behaviour does not continue upward — it comes back around and behaves like 8192, which is the menu’s zero. So the range is not a scale with room above it. It is a closed set of nine, and a value outside them is not a stronger setting, it is a different setting.

Which is a good reason for a tool not to interpolate. If an app is asked for a noise reduction position that is not one of the nine, the correct answer is to refuse rather than round to the nearest — because “nearest” in a table with this shape is not a meaningful idea. Our implementation refuses.

Someone else found the same nine numbers

Long after we finished, we found community documentation of the same protocol, derived independently from USB captures on different camera bodies.

Their noise reduction table matches ours on all nine values, including the out-of-order ones. Two separate efforts, different cameras, different methods, the same peculiar sequence.

That is the most useful kind of confirmation, and it also stings a little: we would have saved weeks by looking for prior work before starting. We had already learned that lesson twice on this project. Apparently twice was not enough.

Why any of this matters to a photographer

Mostly it does not — you turn the dial and the camera does the right thing.

It matters when software sits between you and the camera. An app that writes the menu number straight into that property sets your noise reduction to something you did not ask for, and the camera accepts it without complaint. Zero written as zero is not zero; it is +2.

That is the sort of error that never announces itself. Your photographs come back slightly different from what the recipe said and nothing anywhere reports a problem.


Written while building SimuLook, an app for reading and writing Fujifilm film simulation recipes. See which cameras are supported · Read the other notes