Skip to content

Commit 00e2c07

Browse files
committed
[css-color-4] Add srgb-linear color space, fix w3c#6087
1 parent 129575b commit 00e2c07

2 files changed

Lines changed: 101 additions & 2 deletions

File tree

css-color-4/Overview.bs

Lines changed: 62 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1126,12 +1126,17 @@ and there shall be no thousands separator.
11261126
For the predefined color spaces,
11271127
the <em>minimum</em> precision for round-tripping is as follows:
11281128

1129-
<table class="data">
1129+
<table class="data" id="predefined-precision-table">
11301130
<tr><th>color space</th><th>Minimum bits</th></tr>
11311131
<tr>
11321132
<td>''srgb''</td>
11331133
<td>10</td>
11341134
</tr>
1135+
<tr>
1136+
<td>''srgb-linear''</td>
1137+
<td>12</td>
1138+
<!-- see workings/srgb-lin-precision.js -->
1139+
</tr>
11351140
<tr>
11361141
<td>''display-p3''</td>
11371142
<td>10</td>
@@ -3593,6 +3598,60 @@ Predefined Color Spaces</h2>
35933598
</wpt>
35943599
</dl>
35953600

3601+
<h3 id="predefined-sRGB-linear">Predefined sRGB-linear space</h3>
3602+
3603+
3604+
The <dfn id='sRGB-linear-space' export>sRGB-linear</dfn> predefined colorspace
3605+
is the same as ''srgb''
3606+
<em>except</em> that the transfer function
3607+
is linear-light (there is no gamma-encoding).
3608+
3609+
<dl dfn-type=value dfn-for="color()">
3610+
<dt><dfn>srgb-linear</dfn>
3611+
<dd>
3612+
The ''srgb-linear'' [[!SRGB]] color space accepts three numeric parameters,
3613+
representing the red, green, and blue channels of the color.
3614+
In-gamut colors have all three components in the range [0, 1].
3615+
The whitepoint is [=D65=].
3616+
3617+
It has the following characteristics:
3618+
3619+
<table>
3620+
<thead><td></td><td>x</td><td>y</td></thead>
3621+
<tr><th>Red chromaticity</th><td>0.640</td><td>0.330</td></tr>
3622+
<tr><th>Green chromaticity</th><td>0.300</td><td>0.600</td></tr>
3623+
<tr><th>Blue chromaticity</th><td>0.150</td><td>0.060</td></tr>
3624+
<tr><th>White chromaticity</th> <td colspan="2">[=D65=]</td></tr>
3625+
<tr><th>Transfer function</th><td colspan="2">unity, see below</td></tr>
3626+
<tr><th>White luminance</th><td colspan="2">80.0 cd/m<sup>2</sup></td></tr>
3627+
<tr><th>Black luminance</th><td colspan="2">0.80 cd/m<sup>2</sup></td></tr>
3628+
<tr><th>Image state</th><td colspan="2">display-referred</td></tr>
3629+
<tr>
3630+
<th>Percentages</th>
3631+
<td colspan="2">Allowed for R, G and B</td>
3632+
</tr>
3633+
</table>
3634+
3635+
<pre class="lang-javascript">
3636+
cl = c;
3637+
</pre>
3638+
c is the red, green or blue component.
3639+
cl is the corresponding linear-light component, which is identical.
3640+
3641+
To avoid banding artifacts, a
3642+
<a href="#predefined-precision-table">higher precision is required</a>
3643+
for ''srgb-linear'' than for ''srgb''.
3644+
3645+
<div class="example" id="srgb-linear-swatches">
3646+
For example, these are the same color
3647+
<pre class="lang-css">
3648+
<span class="swatch" style="--color: rgb(69.1% 13.9% 25.9%)"></span> color(srgb 0.691 0.139 0.259)
3649+
<span class="swatch" style="--color: rgb(69.1% 13.9% 25.9%)"></span> color(srgb-linear 0.435 0.017 0.055)
3650+
</pre>
3651+
</div>
3652+
</dd>
3653+
</dl>
3654+
35963655
<h3 id="predefined-display-p3">Predefined display-p3 space</h3>
35973656

35983657
<dl dfn-type=value dfn-for="color()">
@@ -4844,7 +4903,8 @@ Changes</h2>
48444903
</h3>
48454904

48464905
<ul>
4847-
<!-- to 10 Nov 2021 -->
4906+
<!-- to 19 Nov 2021 -->
4907+
<li>Add srgb-linear color space</li>
48484908
<li>Moved @color-profile and device-cmyk to level 5 per CSSWG resolution</li>
48494909
<li>Defined interpolation color space</li>
48504910
<!-- to Oct 30 2021 -->
Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
// Find minimum bt dept to retain all 256 gamma-encoded sRGB values in srgb-linear
2+
// lin8: 183
3+
// lin10: 238
4+
// lin12: 256 = OK
5+
// lin14: 256
6+
// lin16: 256
7+
8+
let lin8 = new Set();
9+
let lin10 = new Set();
10+
let lin12 = new Set();
11+
let lin14 = new Set();
12+
let lin16 = new Set();
13+
14+
for (let i=0; i<=255; i++) {
15+
let gam = i / 255;
16+
let lin = toLin(gam);
17+
lin8.add(Math.round(lin * 255));
18+
lin10.add(Math.round(lin * 1023));
19+
lin12.add(Math.round(lin * 4095));
20+
lin14.add(Math.round(lin * 16383));
21+
lin16.add(Math.round(lin * 65535));
22+
}
23+
24+
console.log(lin8.size);
25+
console.log(lin10.size);
26+
console.log(lin12.size);
27+
console.log(lin14.size);
28+
console.log(lin16.size);
29+
30+
function toLin(val) {
31+
let sign = val < 0? -1 : 1;
32+
let abs = Math.abs(val);
33+
34+
if (abs < 0.04045) {
35+
return val / 12.92;
36+
}
37+
38+
return sign * (Math.pow((abs + 0.055) / 1.055, 2.4));
39+
}

0 commit comments

Comments
 (0)