Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Clarify use of transfer functions #222

Merged
merged 7 commits into from
Feb 5, 2025
Merged

Conversation

MarkCallow
Copy link
Contributor

This is a rough draft for further discussion.

@MarkCallow MarkCallow marked this pull request as draft January 29, 2025 09:39
@MarkCallow
Copy link
Contributor Author

MarkCallow commented Jan 29, 2025

If we go ahead with this, I want to change the names of the options in ktx create from *-oetf to *-transfer. *-transfer-function is too long. We could make it shorter instead: *-tf*.

ktxspec.adoc Outdated Show resolved Hide resolved
ktxspec.adoc Outdated Show resolved Hide resolved
ktxspec.adoc Outdated Show resolved Hide resolved
@MarkCallow
Copy link
Contributor Author

Question for @fluppeteer. In our off-line discussions you suggested using OETF for HLG and EOTF for PG. This clarification proposes using both in the same way. Why did you propose different treatment and are you okay with using them both the same way?

@lexaknyazev
Copy link
Member

In the BT.2100 document, PQ is defined as EOTF and OOTF (with OETF being derived) while HLG is defined as OETF and OOTF (with EOTF being derived).

This difference does not seem to be important given that KTX (with this PR applied) unambiguously defines how all those enums are interpreted.

@MarkCallow MarkCallow force-pushed the clarify_transfer_functions branch 2 times, most recently from 8d7f3c3 to e260563 Compare February 1, 2025 03:20
@MarkCallow MarkCallow force-pushed the clarify_transfer_functions branch from e260563 to f158b4d Compare February 1, 2025 12:37
ktxspec.adoc Outdated Show resolved Hide resolved
@fluppeteer
Copy link

fluppeteer commented Feb 2, 2025

Question for @fluppeteer. In our off-line discussions you suggested using OETF for HLG and EOTF for PG. This clarification proposes using both in the same way. Why did you propose different treatment and are you okay with using them both the same way?

In both cases (indeed, in the case of any colour space) the application is responsible for converting to a suitable linear colour space for subsequent processing (if that's what it intends to do). Since the OOTF is often non-linear, it's up to the application to decide whether processing should be performed in the space of the captured scene, or that of the output display - although in almost all cases the OOTF as specified is a relatively mild non-linear transform intended to allow for the variation of the human visual system when acting under different viewing conditions, so it doesn't matter nearly as much as compensating for the EOTF or OETF.

In the case of HLG and PQ, the OOTF is explicit in the specification, so having both transforms documented is useful. In both cases the encoded content is "HLG" or "PQ", but it may be useful for an application to be aware of the space in which the content was authored (which would typically be the scene, and thus OETF, for HLG, and the display, hence the EOTF, for PQ). This is a pretty subtle nuance, and just using the OETF for HLG and EOTF for PQ would cover most cases if you wanted to simplify, as @lexaknyazev suggests; keeping both names in the KDFS enums is intended to simplify reference to the relevant functions in the KDFS.

Does that help?

ktxspec.adoc Outdated
@@ -1014,6 +1014,45 @@ Still, `KHR_DF_PRIMARIES_BT709` / `KHR_DF_PRIMARIES_SRGB` is recommended
for standard dynamic range, standard gamut images.
====

==== Use of Transfer Functions
The majority of transfer functions listed in Chapter 13 _Transfer

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think that's true. Most of the transfer functions correspond only to either the OETF or the EOTF, with a small number of exceptions where the two are the same. BT.601/709/2020 don't comment on the reference display, for example - that's what BT.1886 does. Equally, while the sRGB description does talk about how it can be integrated into a BT.709-based authoring environment, it is of itself only documenting the EOTF - it is for displaying computer content, so there is no concept of a camera capturing a scene in sRGB itself.

@lexaknyazev
Copy link
Member

This is a pretty subtle nuance, and just using the OETF for HLG and EOTF for PQ would cover most cases if you wanted to simplify, as @lexaknyazev suggests; keeping both names in the KDFS enums is intended to simplify reference to the relevant functions in the KDFS.

I didn't suggest to simplify them. Having both versions explicitly signalled is essential for KTX.

@fluppeteer
Copy link

This is a pretty subtle nuance, and just using the OETF for HLG and EOTF for PQ would cover most cases if you wanted to simplify, as @lexaknyazev suggests; keeping both names in the KDFS enums is intended to simplify reference to the relevant functions in the KDFS.

I didn't suggest to simplify them. Having both versions explicitly signalled is essential for KTX.

Ah, apologies for the misunderstanding. Did you just mean that discussing the derivation via the OOTF isn't necessary? Or that people being aware of the origin space isn't important? I'm confused.

ktxspec.adoc Outdated
filtering;
* mipmap generation should use the path EOTF → scaling → OETF.

These transfer functions have no suffix in their enumerator names.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The KDFS enumerators without a disambiguating either EOTF or OETF in the name indicate that the originating specification defines only an EOTF (such as sRGB), only an OETF (such as BT.709), or there is a linear OOTF. The proposed updated enum aliases clarify this.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

there is a linear OOTF

I think this is the only thing KTX cares about in practice.

ktxspec.adoc Outdated
The majority of transfer functions listed in Chapter 13 _Transfer
functions_ of <<KDF13>>, with corresponding enumerators given in
Chapter 5 _transferFunction_, have a linear opto-optical transfer
function (OOTF). That is the opto-electrical transfer function

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nitpick: the EOTF or OETF doesn't "have" an OOTF - they are defined in specifications which define an OOTF.

ktxspec.adoc Outdated

* applications should use the EOTF to decode prior to sampling and
filtering;
* mipmap generation should use the path EOTF → scaling → OETF.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

By definition, if the OOTF is linear, the EOTF is the OETF-1 and the OETF is the EOTF-1. If they're symmetrical, they also have the same enum. That does mean this processing path is correct, although I would find it a little confusing to state it that way.

ktxspec.adoc Outdated
These transfer functions have no suffix in their enumerator names.

The sRGB transfer function is one of these, defining an EOTF. EOTF^-1^
is used as the OETF.
Copy link

@fluppeteer fluppeteer Feb 2, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not true (there is no OETF in sRGB, and no defined OOTF, unless combined with a scene-referred standard such as BT.709).

ktxspec.adoc Outdated
Some transfer functions have a non-linear OOTF. That is the OETF
is not the inverse of the EOTF. These have two separate enumerators,
one with an `OETF` suffix, the other with an `EOTF` suffix. When a
KTX file has an explicit OETF

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

"Has an explicit OETF" means the enum chosen corresponds to the OETF defined by the specification, yes?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It means that the DFD enum has the _OETF suffix.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think "some transfer functions have a non-linear OOTF" read strangely to me - the OOTF is one transfer function, the OETF is another, the EOTF is a third, so they don't "have" each other. Perhaps "some color spaces", or "some standards"?

ktxspec.adoc Outdated
filtering;
* mipmap generation should use the path OETF^-1^ → scaling → OETF.

When a KTX file has an explicit EOTF

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Correspondingly, this means the enum identifies the EOTF defined by a specification? I think it's sufficient to say that KTX tools will process in the display-linear space or scene-linear space, determined by the enum encoding (for any enum that identifies either an EOTF or OETF; it would require additional information to specify the corresponding function for specifications that only define one transfer function). Applications creating a KTX file should indicate the authoring space that they used to create the content, whether that is scene- or display-referred.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Correspondingly, this means the enum identifies the EOTF defined by a specification?

Ditto. It means that the DFD enum has the _EOTF suffix.

Applications creating a KTX file should indicate the authoring space that they used to create the content, whether that is scene- or display-referred.

The KTX header defines how to process the file, not how it was created. The intention is to use _EOTF and _OETF enum suffixes to disambiguate the scene vs display linearity for cases when the OOTF is not linear..

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The KTX header defines how to process the file, not how it was created. The intention is to use _EOTF and _OETF enum suffixes to disambiguate the scene vs display linearity for cases when the OOTF is not linear..

I'm expecting it to affect the tooling, on the assumption that any mip chain generation probably shouldn't change the colour space identifiers and that this is a useful way to pass that information to the tool chain. If this documents how user applications might wish to receive similar instructions, sure. For an application converting content to screen space for display, it should always find an EOTF to use, whatever that EOTF may be. If converting to content that is part of a LDR video stream, it should be following the OETF instead. Hopefully the application knows what it's doing, and can make that decision.

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Hopefully the application knows what it's doing, and can make that decision.

Yes and that's out of the KTX scope. Remember that KTX is not a general-purpose image or video format related to cameras or screens.

One could say that _EOTF files would be "images to be displayed" and _OETF files would be "material textures to be sampled from".

@lexaknyazev
Copy link
Member

Did you just mean that discussing the derivation via the OOTF isn't necessary? Or that people being aware of the origin space isn't important? I'm confused.

The BT.2100 document defines:

  1. Reference PQ EOTF via explicit math
  2. Reference PQ OOTF via explicit math
  3. Reference PQ OETF as the combination of the corresponding OOTF and EOTF-1
  4. Reference HLG OETF via explicit math
  5. Reference HLG OOTF via explicit math
  6. Reference HLG EOTF as the combination of the corresponding OOTF and OETF-1

The fact that definitions 3 and 6 are not explicit does not make them any worse than the definitions 1 and 4 for the KTX purposes, so we can ignore that spec detail and treat all four functions equally.

@fluppeteer
Copy link

Did you just mean that discussing the derivation via the OOTF isn't necessary? Or that people being aware of the origin space isn't important? I'm confused.

The BT.2100 document defines:

  1. Reference PQ EOTF via explicit math
  2. Reference PQ OOTF via explicit math
  3. Reference PQ OETF as the combination of the corresponding OOTF and EOTF-1
  4. Reference HLG OETF via explicit math
  5. Reference HLG OOTF via explicit math
  6. Reference HLG EOTF as the combination of the corresponding OOTF and OETF-1

The fact that definitions 3 and 6 are not explicit does not make them any worse than the definitions 1 and 4 for the KTX purposes, so we can ignore that spec detail and treat all four functions equally.

Ah, agreed. I think the distinction is that most HLG content in the wild will have been created in a scene-referred context, and most PQ content will be display-referred, so the PQ EOTF and HLG OETF enums are likely to be more common than the PQ OETF and HLG EOTF ones. But no more valid, I just thought it was useful for people to have guidance on tagging content handed to them. (Again, it'll be rare use cases that actually need to make the distinction.)

@MarkCallow
Copy link
Contributor Author

I've rewritten the section following my best understanding of the comments, which may be flawed. See 8f18ab5. Please review again and suggest improvements.. I've listed all cases explicitly which may be overkill.

@MarkCallow
Copy link
Contributor Author

The addition of the transfer function aliases raises the question which names should ktx create support:

  1. just the decorated names;
  2. just the undecorated names;
  3. both decorated and undecorated?

The only non-linear TF supported until now has been "srgb". If we want to go for no. 1, it is not an issue to keep "srgb" for backward compatibility while adding "srgb-eotf".

@fluppeteer
Copy link

I've rewritten the section following my best understanding of the comments, which may be flawed. See 8f18ab5. Please review again and suggest improvements.. I've listed all cases explicitly which may be overkill.

Looks much better to me (at least by my understanding!)

Re. the command line, I wouldn't lose too much sleep unless support for all (or most) other transfer functions is added; "sRGB" is unambiguous, and the main benefit of the enums including the EOTF/OETF suffixes is to help developers keep track of which to use in which circumstances. Not that it would be harmful to future-proof an alias if you wanted to.

@MarkCallow
Copy link
Contributor Author

Re. the command line, I wouldn't lose too much sleep unless support for all (or most) other transfer functions is added;

We are adding support for most of the other transfer functions because the spec. now allows them to be used with non-_SRGB formats, except for "srgb" if there is an _SRGB format equivalent to the _UNORM format you are trying to use. I'm leaning towards 1. while also keeping "srgb" for backwards compatibility.

@MarkCallow
Copy link
Contributor Author

Thanks for the approval @lexaknyazev. What is your take on the following?

The addition of the transfer function aliases raises the question which names should ktx create support:

  1. just the decorated names;
  2. just the undecorated names;
  3. both decorated and undecorated?

@MarkCallow MarkCallow marked this pull request as ready for review February 3, 2025 11:53
@lexaknyazev
Copy link
Member

I'd say both because both variants are going to be valid DFD enums.

@fluppeteer
Copy link

FWIW, I'm still a little philosophically uncomfortable with the "applications are intended to..." statements. My feeling is that metadata in a file format should describe what's in the format, not dictate an application's use of it. For example, if someone wants to do screen-space filtering of a BT.601 image (e.g. a decoded JPEG), they should probably be doing so in a display-referred space (either sRGB or BT.1886). That said, the OOTF is typically subtle, almost all Vulkan code will probably be doing this wrong (the Y'CbCr functionality doesn't provide advice on applying an OOTF to the decoded content), and I don't know enough about users of KTX to know whether I'm thinking of this in the right way.

That said, this does make me wonder whether the introductory section on chroma reconstruction in the KDFS ought to mention a choice of transfer function. I've just spotted that there's already a typo there... (fix coming).

@lexaknyazev
Copy link
Member

FWIW, I'm still a little philosophically uncomfortable with the "applications are intended to..." statements. My feeling is that metadata in a file format should describe what's in the format, not dictate an application's use of it.

The file format spec technically cannot dictate anything to apps - it merely describes the expected behavior. An app can do whatever it wants because it's not bound by the KTX spec anyway.

@MarkCallow
Copy link
Contributor Author

FWIW, I'm still a little philosophically uncomfortable with the "applications are intended to..." statements.

The spec text doesn't say that. It says "applications should", i.e. recommendations.

@fluppeteer
Copy link

FWIW, I'm still a little philosophically uncomfortable with the "applications are intended to..." statements. My feeling is that metadata in a file format should describe what's in the format, not dictate an application's use of it.

The file format spec technically cannot dictate anything to apps - it merely describes the expected behavior. An app can do whatever it wants because it's not bound by the KTX spec anyway.

Yes, I guess it's just that whether it's "expected" depends on what the app is doing. I don't know that it's even the majority case to apply the BT.709 OETF-1, for example - arguably applying the sRGB EOTF would make more sense for a lot of applications. But it doesn't matter that much.

The spec text doesn't say that. It says "applications should", i.e. recommendations.

I guess I'm just not a rebel. :-)

@MarkCallow
Copy link
Contributor Author

MarkCallow commented Feb 4, 2025

I'd say both because both variants are going to be valid DFD enums.

In the CLI should we use e.g, srgb-eotf or srgb_eotf, --assign-tf srgb-eotf or --assign-tf srgb_eotf? Since multi-word option names are written with "-", I propose to do that with the transfer function names too even though it differs from the names in `khr_df.h.

When converting a transfer function enumeration to text, e.g. in ktx info, should I use the undecorated name, which is what KDFS layout indicates is the main name, or the decorated names, which KDFS describes as aliases. Some of the values have multiple aliases, e.g. ITU so I am leaning towards printing the undecorated name. The drawback, what ever we choose, is that there will be unavoidable cases where what is printed is different from what the use gave as the argument to --assign-tf.

@lexaknyazev
Copy link
Member

  • The CLI option values should be consistent across different parameters. If Vulkan format enums are accepted with underscores, so should be the DFD enums.

  • The ktx info should output the most "canonical" strings, whatever that means.

@MarkCallow MarkCallow merged commit a5fedc4 into main Feb 5, 2025
4 checks passed
@MarkCallow MarkCallow deleted the clarify_transfer_functions branch February 5, 2025 09:18
@MarkCallow
Copy link
Contributor Author

One last, hopefully, question particularly for @lexaknyazev. In the changes to ktx create that I am working on I am using the option names --assign-tf and --convert-tf. Before I get to much further into updating the tests I'd like to know if anyone has an allergic reaction to using the short tf and would prefer transfer or verbosely transfer-function. (The old names *-oetf are still supported but deprecated.)

@lexaknyazev
Copy link
Member

Since it was *-oetf before, changing it to *-tf is okay by extension.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants