ASC-CDL color adjustments in PhotoFlow

(Carmelo Dr Raw) #1

Following the original discussion regarding the new color balance module in Darktable, and this other related discussion, I have started to implement a color correction tool in PhotoFlow that tries to follow the ASC-CDL standard.

The definition and range of the controls directly follow the DT implementation. Therefore, the DT and PhF results should in principle be equivalent (i.e. same parameters = some output) and interchangeable.
For each adjustment, there is one main slider that is applied simultaneously to the three RGB channels, plus separate R, G & B adjustments.

Some important details:

  • the tool does not make any assumption regarding the input colorspace. It is up to the user to provide linear RGB data. ACES or ACEScg primaries are recommended.
  • there is an additional saturation adjustment, that is applied after the slope/offset/power part
  • a checkbox allows to convert the input linear data to log (using the ACEScc formulas). The saturation is however in this case applied after converting the log values back to linear RGB

Here is an example of the new tool in action:

What do you think?


I think that you are skilled!

Have fun!
Claes in Lund, Sweden

(Elle Stone) #3

I just rebuilt PhotoFlow, fired it up, and see the new Color Correction module - thanks!

Any chance the tool could be relabeled in the user interface “Color” dropdown to something like “ACES/CDL adjustments” instead of “Color Correction”? A fair variety of other editing operations could also be considered color correction operations - I was actually just guessing “Color Correction” might be the right thing to choose - wasn’t sure until I saw the sliders.

(Elle Stone) #4

OK, obviously I don’t have a clue what that CDL thing is supposed to do. I though that “slope” on linear RGB would be the equivalent of multiplying by a color. I set the R/G/B values to 0.981, 0.883, 0.677, expecting the image to get slightly darker and more yellow. But instead it got a lot brighter. So what does this “slope” on linear RGB actually do if it doesn’t multiply the channel values by the given inputs?

Also, where is the place to set the color space (I mean apart from whether to use the log curve)? Are the operations done in the actual input color space, so choosing a different color space means using an actual color profile conversion layer?


– Would it be a good idea for modules like this to inform the user that a linear space is required?
– As discussed before, ACES or ACEScg aren’t generally recommended for other operations. Wouldn’t it be bad practice to start from sRGB or Rec2020, convert the image to ACES or ACEScg, use this module and then go back again?

– What was your final decision on offset’s math?
– Yes, I typically do saturation after as well in my G’MIC adventures.


There is a colour space conversion module if you need to convert anytime after the original input file conversion.

(Elle Stone) #7

@afre - thanks! Actualy I already knew about that module :slight_smile: which is why I asked if that module should be used. For some reason I assumed there would be a dropdown box in the CDL module that defaulted to ACEScg for linear, ACEScc for log, with an additional option to choose a color space from disk, sort of like when choosing a camera input profile. But that clearly isn’t the case.

What happens if the user selects ACEScg and clicks the “log” checkbox? I’m assuming (but so many of my assumptions have been wrong!) that the channel values are turned from linear to log.

But what if the image was in a non-linear color space to begin with and the user checks the log box?

Edit: Ah, @afre has already asked the same question:

Which raises an aside - I don’t supply any ICC profiles with log TRCs because I don’t know how to make this type of profile. Does anyone supply such ICC profiles? There’s an LCMS plug-in that probably could be used, but the math is not something I want to tackle.


ACEScg is supposed to be a nice RGB working space, just a bit larger than Rec.2020, but not with the crazy shape and imaginary G and B primaries like ACES has.


The more I think about the “log” checkbox, the more that I am unsure about it. Ideally, thinking on the spot, the module would adapt itself to the “input” colour space and encoding. If we used ACEScc and checked “log”, we would have nonononos happening, wouldn’t we? That said, @Carmelo_DrRaw is super capable. Maybe he already solved it. :wink:

I am still not certain about ACEScg. “A Working Space for CGI Render and Compositing” isn’t exactly what photographers or people in this forum would generally use… PS Oh, that is no longer true: #software:natron :slight_smile:

(Carmelo Dr Raw) #9

@Elle @afre
Let me answer all points alltogether…

  • colorspaces:
    given the current lack of consensus regarding “which primaries are recommended for the ASC-CDL adjustments”, I decided to keep the tool as flexible as possible for the moment and to accept whatever RGB data comes in, with no assumptions.
    In PhF there is currently no option for using log-encoded colorspaces. Therefore it is not possible to feed log-encoded data to the CDL tool. The RGB data can only be linear, perceptually uniform (Lab L encoding) or with the specific encoding of the colorspace of choice (for ex. gamma=2.2 for AdobeRGB).
    As Afre already said, the input to the CDL tool can be specified by putting a colorspace conversion layer just before, and selecting for example “ACEScg with linear TRC”.
    I agree with Elle that such a choice could be embedded in the tool itself, but I prefer to reserve this for the final version.
    Regarding the log checkbox, it is clear that the conversion only makes sense when the original input data are linear, however it is for the moment up to the user to make sure this is the case. Again, a colorspace conversion layer is the right tool for that.
  • ACEScg as an editing colorspace:
    as Elle pointed out, ACEScg is just slightly wider than Rec.2020, and my guess is that it is equally appropriate (if not better) for photographic editing. In fact, my understanding is that Rec.2020 is a standard driven by the display technology, while ACEScg has been optimized for color manipulation. Is that correct?
  • range of sliders:
    as already mentioned, the current sliders follow the same logic as those in Darktable, in order to have some common ground. In particular:
    • slope = slider + 1
      a value of “0” in the slider corresponds to slope=1, i.e. no change
      a value of “+1” corresponds to slope=2
      a value of “-1” corresponds to slope=0, i.e. pure black
    • power = 1 - slider
      in this way, the mid-tones become brighter when moving in the positive direction, and darker when moving in the negative direction, which is more intuitive

All this is of course open for discussion!

(Elle Stone) #10

Putting darktable to one side, I’m just trying to understand what these sliders are supposed to do. I can’t emulate a log2 curve in GIMP, but when working on linear RGB, I was assuming that modifying the slope in each channel individually is the same as multiplying by a color:

But multiplying the image by a color in GIMP and moving the sliders as shown in the screenshot in PhotoFlow still doesn’t produce the same result, even after subtracting the multipliers from 1.0:

Why is there a difference? Did I type in the wrong values in PhotoFlow? What is CDL slope on linear RGB if it’s not multiplying by a color?

(Carmelo Dr Raw) #11

Looks like you are missing one decimal point in the red multiplier value, it should be -0.019
Hopefully this is enough to solve the inconsistencies…

(Elle Stone) #12

I did indeed type the Red channel incorrectly (sorry!), but changing the Red channel still doesn’t make results match

Should results match? If not, what is slope on linear?

(Carmelo Dr Raw) #13

Hi @Elle
the difference might be due to the working colorspace.
In PhotoFlow, the opened images are by default converted to linear Rec.2020, unless you specify differently in the “background” layer.

Could this be the case?

(Elle Stone) #14

Yes, that’s the case when using PhotoFlow directly, which is what I was doing - changing to use the input profile does match GIMP results - thanks! So per channel slope on linear RGB really is just multiplying by a color. Whew!

As an aside and just now checking, when using PhotoFlow via the GIMP plug-in, PhotoFlow defaults to using the embedded profile, so results already match GIMP results.