-
Notifications
You must be signed in to change notification settings - Fork 656
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
[css-color-adjust-1] Is forced color computed or used value? #4915
Comments
It has to be at used-value time, due to the system color keywords not resolving until then, right? |
If the adjusted |
It would be a little weird if all the other forced-color effects are available at computed time, but background-color is naively reported without adjustments.
Yes, but the other colors at least compute correctly to a system color. Ideally, we would define the computed value of background-color using one of the Colors Level 5 mixing functions: this system color, but adjusted to use that alpha.
This is also true, and trickier to work around. Logically, we want to treat A comparison would be But of course, the difference is that system fonts are substituted at computed time, and they do have longhand properties that can inherit only part of that value. So, I'm not sure we can reuse that model without a serious re-think to all this. |
The CSS Working Group just discussed
The full IRC log of that discussion<dael> Topic: Is forced background-color computed or used value?<dael> github: https://github.com//issues/4915 <dael> Rossen_: This is in the context of forced-colors-adjust. <dael> Rossen_: Short summary is in the previous impl of what used to be ms-high-contrast and is now forced-colors we were reverting colors incl background and override with system color <dael> Rossen_: At the time at MS we didn't consider taking in the alpha channel of the color value. <dael> Rossen_: That meant simply all overrides were stable during computed and alpha was always opauqe <dael> Rossen_: When working on focred-colors one addition to the feature is addition of considering alpha channel of the color. For background-color it means we now have to compute the final color value during used time <dael> Rossen_: That's how issue came about. Is it supposed to be computed or used. <dael> Rossen_: Is amelia_br or fantasai on? <dael> TabAtkins: We have me and I commented <dael> TabAtkins: Seems clear this needs to be used value time transformation <dael> TabAtkins: because we can't do anything with a system color until we resolve it which is at used value time b/c need to know color scheme <dael> TabAtkins: This is to make it reasonably work. Amelia's comment brings up the very good point that color mix function would be useful for this. <dael> TabAtkins: If you want to define a computed value that's this system color but with the other alpha you can do it simply with color mix function. <dael> TabAtkins: We could and should define computed value of color becomes a color mix function with alpha from previous color and mix with system color <dael> Rossen_: What do we serialize in OM? used value? <dael> TabAtkins: All current properties do used <dael> Rossen_: Okay, that continues to work <dael> TabAtkins: Not 100% clear/remember what happens in image properties. But plain colors do used value. <dael> Rossen_: The ones covered by color-adjust are covered. <dael> TabAtkins: Yeah <dael> emilio: Not quite used value because :visited and so on <dael> Rossen_: sure <dael> TabAtkins: Ignoring :visited hacks they are always used values <dael> Rossen_: Sounds like a good path forward for this behavior <dael> Rossen_: Any other considerations or proposals to consider? <dael> TabAtkins: If we go with this is means impl should prioritize color mix. <dael> TabAtkins: Also solves that you can't transition system colors since you can use color mix for that. <dael> Rossen_: Sounds good <dael> Rossen_: Looking for your summary <TabAtkins> color-mix(appropriate-system-color, specified-color a(100%)) <dael> Rossen_: Prop: The color computed values are defined as used values using the color mix function <dael> Rossen_: Objections? <dael> RESOLVED: The color computed values are defined as used values using the color mix function |
@tabatkins wrote:
As specified, that will do the [color interpolation(https://drafts.csswg.org/css-color-5/#interpolation) in the LCH colorspace, which is the default. That might not be what is wanted however. I can think of two other options:
That will mix in the (gamma corrected, i.e. non-linear-light) sRGB colorspace, which is what the current implementations do when mixing colors. It gives the wrong (too dark) result but is compatible with lots of software which also does it the wrong way :) It is also constrained to the sRGB gamut, which is temporarily fine but won't be over time as some system colors may be specified in, for example,
That will get you linear-light mixing, ie the correct result for the physical mixture of two lights, and avoids gamut mapping. It gives the same result as mixing in linear-light sRGB, except without the gamut limitation. |
This might be moot anyway (if it's specified as happening at used-value time, from other issues), but if we do keep with "forced-colors mode causes the computed value to be a color-mix() function", it's only mixing alpha (and "mixing" only in a degenerate sense; it's just taking the source color's alpha entirely); the rest of the channels are taken solely from the system color. So the colorspace we mix in is moot. |
Given the resolutions to adopt @FremyCompany's proposals in #4915, I would like to re-open this issue (see #4178 (comment)). The concept we adopted in #4178 was to treat non-system colors as “out of gamut”, effectively. Mapping out-of-gamut colors is a used-value time operation, not a computed-value time operation. There's an added benefit to making this a used-value time operation: it also makes the question of transitions and interpolation (see #5419) go away. So my proposal is that we go with making this a used-value time operation rather than a computed-value time operation. Next question is, should we do the same for the other affected properties (which are not color properties) and force their used values to the initial value, instead of their computed values? |
Another (important, imho) benefit of forcing colors at used-value time is that they will inherit as the author-specified value, so if a subtree opts out of forced colors, it will use the author-specified colors, not a mix of author-specified and forced colors. |
I wanted to +1 @fantasai's point in the above comment. In particular, forcing at used-value time will likely be helpful for the following case:
We set If we were to force colors at used-value time, instead, the text fill would pick up So although changing this to used-value time may complicate the implementation a bit, I do think that there is value in changing this to a used-value time operation. |
The CSS Working Group just discussed
The full IRC log of that discussion<emilio> topic: [css-color-adjust-1] Is forced color computed or used value?<fantasai> github: https://github.com//issues/4915#issuecomment-701674628 <emilio> fantasai: I reopened in light on the resolutions we took to adopt fremy's proposal in the previous issue <emilio> ... we decided than rather than a cascade-time revert and consider them out-of-gamut for non-system colors <emilio> ... which is a different technique <emilio> ... but out-of-gamut mapping is a used-time op, not computed-time <emilio> ... by doing it at computed-value time we got weird behavior wrt ?? <emilio> s/??/inheritance <emilio> fantasai: when you do it at computed value then it'll change it to system color and then inherit <emilio> ... if you have a forced-color-adjust: none section down the page <emilio> ... expecting a particular inherited color <emilio> ... but instead you get a random system color which might be unreadable <emilio> ... if we do this mapping at used value time <florian> q+ <emilio> ... then it inherits the color properly <fremy> q+ <emilio> ... but the ancestor with forced colors will get the system color at used value time <emilio> q+ <emilio> TabAtkins: I think I agree on this, makes much more sense <TabAtkins> s/think I/strongly/ <emilio> Rossen_: it also avoids the dependency with color-mix() <florian> q- <emilio> fantasai: yeah prevents all the interpolation / transitions issues <Rossen_> ack fremy <emilio> fremy: I think it does make a lot of sense but I want to make sure something is recorded <emilio> ... if you have a disabled button, the default style will have some color <emilio> ... let's say `text` -> `disabledtext` <emilio> ... so it can be made at used value time <emilio> ... but for children you need to walk the parent chain to know which color to reset <emilio> ... basically what you map to depends on the UA stylesheets <emilio> ... so you kinda need to remember this in a way <emilio> florian: [restates the issue] <emilio> TabAtkins: it is indeed a separate concern <emilio> fremy: I wanted to make sure it's mentioned because it's an important impl detail <emilio> fantasai: Yeah we should note that in the spec <emilio> florian: if we were doing it at computed value time you wouldn't have to do it so it's the same issue, not separate <Rossen_> q <Rossen_> ack emilio <fantasai> emilio: Wanted to mention related point <fantasai> emilio: this is a problem, even if you don't account for children <fantasai> emilio: if you specify color on the button <fantasai> emilio: in order to know what to revert to, need to do the cascade again <fantasai> emilio: to find the original value to revert to <fantasai> emilio: that would be my main concern <fantasai> emilio: I think it could be addressed with something like an internal CSS property <fantasai> emilio: but different from what browsers currently do <fantasai> fremy: similar to :visited <fantasai> emilio: similar, but different <fantasai> fremy: this is what Edge did, we tracked a separate value <fantasai> s/value/value for :visited <fantasai> Rossen_: We had a cascaded value alongside, for anything that was overridden, so that we didn't have to go and recascade <fantasai> Rossen_: we would have it at hand, ready to use as needed. <fantasai> Rossen_: Added a little bit of memory, but relatively insignificant <fantasai> Rossen_: so from impl pov, this is very doable, not much additional context needed <fantasai> Rossen_: but fremy's point that it's not automatic is relevant <emilio> RESOLVED: Forced colors happens at used value time. Add a note to the spec about implementation |
When forced color mode was introduced in Chrome 89, the default user agent styles for SVGs were set to `forced-color-adjust: none` in line with the CSS Color Adjustment specification at the time [1]. Unfortunately, this means that using currentColor for stroke and fill in SVGs no longer works as expected in forced color mode. As per the comment in Chromium bug #1164162 [2]: > This is the result of one of the recent spec changes. The spec was updated to force colors at used value time rather than computed value time, which means elements that have "forced-color-adjust: none" set (like svg elements) will inherit their non-forced color values, resulting in a different currentcolor used for stroke and fill in this case than you would get if forcing was done at computed value time. > > See spec issue resolution for more details: w3c/csswg-drafts#4915 It looks like this has since been flagged as an issue with the CSS working group [3] and the spec has been updated to resolve it [4] but it’s going to take a while before that change is reflected in browsers. In the meantime, we can explicitly set `forced-color-adjust: auto` on the OGL logo in order for it to correctly inherit the color from the parent [5]. Once Chromium has been updated so that the default UA styles for SVGs use the new `forced-color-adjust: preserve-parent-color` keyword, and traffic to older versions has dropped off, we can then consider removing this. [1]: https://www.w3.org/TR/2021/WD-css-color-adjust-1-20210520/#forced-color-adjust-prop [2]: https://bugs.chromium.org/p/chromium/issues/detail?id=1164162#c4 [3]: w3c/csswg-drafts#6310 [4]: https://www.w3.org/TR/2021/WD-css-color-adjust-1-20210616/#forced-color-adjust-prop [5]: w3c/csswg-drafts#6310 (comment)
When forced color mode was introduced in Chrome 89, the default user agent styles for SVGs were set to `forced-color-adjust: none` in line with the CSS Color Adjustment specification at the time [1]. Unfortunately, this means that using currentColor for stroke and fill in SVGs no longer works as expected in forced color mode. As per the comment in Chromium bug #1164162 [2]: > This is the result of one of the recent spec changes. The spec was updated to force colors at used value time rather than computed value time, which means elements that have "forced-color-adjust: none" set (like svg elements) will inherit their non-forced color values, resulting in a different currentcolor used for stroke and fill in this case than you would get if forcing was done at computed value time. > > See spec issue resolution for more details: w3c/csswg-drafts#4915 It looks like this has since been flagged as an issue with the CSS working group [3] and the spec has been updated to resolve it [4] but it’s going to take a while before that change is reflected in browsers. In the meantime, we can explicitly set `forced-color-adjust: auto` on the OGL logo in order for it to correctly inherit the color from the parent [5]. Once Chromium has been updated so that the default UA styles for SVGs use the new `forced-color-adjust: preserve-parent-color` keyword, and traffic to older versions has dropped off, we can then consider removing this. [1]: https://www.w3.org/TR/2021/WD-css-color-adjust-1-20210520/#forced-color-adjust-prop [2]: https://bugs.chromium.org/p/chromium/issues/detail?id=1164162#c4 [3]: w3c/csswg-drafts#6310 [4]: https://www.w3.org/TR/2021/WD-css-color-adjust-1-20210616/#forced-color-adjust-prop [5]: w3c/csswg-drafts#6310 (comment)
When forced color mode was introduced in Chrome 89, the default user agent styles for SVGs were set to `forced-color-adjust: none` in line with the CSS Color Adjustment specification at the time [1]. Unfortunately, this means that using currentColor for stroke and fill in SVGs no longer works as expected in forced color mode. As per the comment in Chromium bug #1164162 [2]: > This is the result of one of the recent spec changes. The spec was updated to force colors at used value time rather than computed value time, which means elements that have "forced-color-adjust: none" set (like svg elements) will inherit their non-forced color values, resulting in a different currentcolor used for stroke and fill in this case than you would get if forcing was done at computed value time. > > See spec issue resolution for more details: w3c/csswg-drafts#4915 It looks like this has since been flagged as an issue with the CSS working group [3] and the spec has been updated to resolve it [4] but it’s going to take a while before that change is reflected in browsers. In the meantime, we can explicitly set `forced-color-adjust: auto` on the chevron SVG in order for it to correctly inherit the color from the parent [5]. This mimics the fix for the OGL logo in the footer made in 850c0b7. Once Chromium has been updated so that the default UA styles for SVGs use the new `forced-color-adjust: preserve-parent-color` keyword, and traffic to older versions has dropped off, we can then consider removing this. [1]: https://www.w3.org/TR/2021/WD-css-color-adjust-1-20210520/#forced-color-adjust-prop [2]: https://bugs.chromium.org/p/chromium/issues/detail?id=1164162#c4 [3]: w3c/csswg-drafts#6310 [4]: https://www.w3.org/TR/2021/WD-css-color-adjust-1-20210616/#forced-color-adjust-prop [5]: w3c/csswg-drafts#6310 (comment)
When forced color mode was introduced in Chrome 89, the default user agent styles for SVGs were set to `forced-color-adjust: none` in line with the CSS Color Adjustment specification at the time [1]. Unfortunately, this means that using currentColor for stroke and fill in SVGs no longer works as expected in forced color mode. As per the comment in Chromium bug #1164162 [2]: > This is the result of one of the recent spec changes. The spec was updated to force colors at used value time rather than computed value time, which means elements that have "forced-color-adjust: none" set (like svg elements) will inherit their non-forced color values, resulting in a different currentcolor used for stroke and fill in this case than you would get if forcing was done at computed value time. > > See spec issue resolution for more details: w3c/csswg-drafts#4915 It looks like this has since been flagged as an issue with the CSS working group [3] and the spec has been updated to resolve it [4] but it’s going to take a while before that change is reflected in browsers. In the meantime, we can explicitly set `forced-color-adjust: auto` on the chevron SVG in order for it to correctly inherit the color from the parent [5]. This mimics the fix for the OGL logo in the footer made in 850c0b7. Once Chromium has been updated so that the default UA styles for SVGs use the new `forced-color-adjust: preserve-parent-color` keyword, and traffic to older versions has dropped off, we can then consider removing this. [1]: https://www.w3.org/TR/2021/WD-css-color-adjust-1-20210520/#forced-color-adjust-prop [2]: https://bugs.chromium.org/p/chromium/issues/detail?id=1164162#c4 [3]: w3c/csswg-drafts#6310 [4]: https://www.w3.org/TR/2021/WD-css-color-adjust-1-20210616/#forced-color-adjust-prop [5]: w3c/csswg-drafts#6310 (comment)
When forced color mode was introduced in Chrome 89, the default user agent styles for SVGs were set to `forced-color-adjust: none` in line with the CSS Color Adjustment specification at the time [1]. Unfortunately, this means that using currentColor for stroke and fill in SVGs no longer works as expected in forced color mode. As per the comment in Chromium bug #1164162 [2]: > This is the result of one of the recent spec changes. The spec was updated to force colors at used value time rather than computed value time, which means elements that have "forced-color-adjust: none" set (like svg elements) will inherit their non-forced color values, resulting in a different currentcolor used for stroke and fill in this case than you would get if forcing was done at computed value time. > > See spec issue resolution for more details: w3c/csswg-drafts#4915 It looks like this has since been flagged as an issue with the CSS working group [3] and the spec has been updated to resolve it [4] but it’s going to take a while before that change is reflected in browsers. In the meantime, we can explicitly set `forced-color-adjust: auto` on the chevron SVG in order for it to correctly inherit the color from the parent [5]. This mimics the fix for the OGL logo in the footer made in 850c0b7. Once Chromium has been updated so that the default UA styles for SVGs use the new `forced-color-adjust: preserve-parent-color` keyword, and traffic to older versions has dropped off, we can then consider removing this. [1]: https://www.w3.org/TR/2021/WD-css-color-adjust-1-20210520/#forced-color-adjust-prop [2]: https://bugs.chromium.org/p/chromium/issues/detail?id=1164162#c4 [3]: w3c/csswg-drafts#6310 [4]: https://www.w3.org/TR/2021/WD-css-color-adjust-1-20210616/#forced-color-adjust-prop [5]: w3c/csswg-drafts#6310 (comment)
Follow-up to #4175
We are now computing
background-color
based on the computed 'color' value. (Specifically, we're keying off the computedcolor
to find a color, and forcing all but the author’s specified alpha channel to match that color.)Is this computation at computed-value time or used-value time for
background-color
?The text was updated successfully, but these errors were encountered: