1. 介绍
本规范引入了三个与控制用户代理如何/何时自动调整颜色相关的新功能:
-
颜色方案和color-scheme属性, 用于控制页面UI的浏览器提供部分 是否遵循用户选择的颜色方案。
-
强制颜色模式和forced-color-adjust属性, 用于控制是否允许强制颜色模式 应用于给定的元素。
-
print-color-adjust属性, 用于控制是否允许浏览器 自动调整颜色以满足用户的性能偏好, 例如打印时抑制背景颜色以节省墨水。
结合prefers-color-scheme、prefers-contrast和forced-colors媒体查询[MEDIAQUERIES-5], 该模块允许在作者和用户之间进行颜色方案协商。
1.1. 值的定义
本规范遵循CSS属性定义惯例,来源于[CSS2],以及值定义语法,来源于[CSS-VALUES-3]。 本规范未定义的值类型定义在CSS值与单位[CSS-VALUES-3]中。 与其他CSS模块结合可能扩展这些值类型的定义。
除了定义中列出的特定属性值外, 本规范定义的所有属性 还接受CSS-wide关键字作为其属性值。 为了可读性,它们未被显式重复。
2. 首选颜色方案
操作系统和用户代理通常允许用户 为用户界面元素选择其首选颜色方案。 此颜色方案 通常反映在用户代理的导航界面渲染中, 以及页面内的界面元素中, 如表单控件和滚动条。
UA还可以允许用户表示对 他们查看的页面颜色方案的偏好, 请求作者根据这些颜色偏好调整页面。 (不需要表达这种偏好; 用户可以对操作系统界面颜色有偏好, 但不希望将其强加于页面。)
最常见的颜色方案 偏好是:
-
浅色方案(“日间模式”) 包括浅色背景和深色前景/文本颜色。
-
深色方案(“夜间模式”) 包括相反的颜色, 即深色背景和浅色前景/文本颜色。
浅色和深色颜色方案并不代表确切的调色板 (如黑白), 而是一系列可能的调色板。 要保证特定颜色,作者必须自己指定这些颜色。 另外需要注意, 因此, 将默认或<system-color>颜色与作者指定的颜色搭配 无法保证任何特定的对比度级别; 可能需要同时设置前景色和背景色, 以确保可读性[WCAG21]。
为了让页面能够适应用户的首选颜色方案, 用户代理将匹配prefers-color-scheme媒体查询 到用户的首选颜色方案。[MEDIAQUERIES-5] 与此相辅相成,本文档定义的color-scheme属性 让作者能够为UA提供的UI和页面中的颜色指明合适的颜色方案。
用户代理可能支持额外的颜色方案, 然而CSS不支持额外颜色方案的协商: 用户代理应追求这些方案的标准化, 以便prefers-color-scheme和color-scheme可以反映这些额外的值。
2.1. 选择首选颜色方案:color-scheme属性
名称: | color-scheme |
---|---|
值: | normal | [ light | dark | <custom-ident> ]+ && only? |
初始值: | normal |
适用于: | 所有元素和文本 |
是否继承: | 是 |
百分比: | 不适用 |
计算值: | 关键字normal,或指定颜色方案关键字的有序列表 |
规范顺序: | 按语法 |
动画类型: | 离散 |
测试
- color-scheme-computed.html (live test) (source)
- color-scheme-invalid.html (live test) (source)
- color-scheme-valid.html (live test) (source)
- color-scheme-change-checkbox.html (live test) (source)
- color-scheme-color-property.html (live test) (source)
- color-scheme-iframe-background-mismatch-alpha.html (live test) (source)
- color-scheme-iframe-background-mismatch-opaque-cross-origin.sub.html (live test) (source)
- color-scheme-iframe-background-mismatch-opaque.html (live test) (source)
- color-scheme-iframe-background-mismatch-used-preferred.html (live test) (source)
- color-scheme-iframe-background.html (live test) (source)
- color-scheme-iframe-dynamic.html (live test) (source)
- color-scheme-iframe-preferred-change.html (live test) (source)
- color-scheme-iframe-preferred-page-dark.html (live test) (source)
- color-scheme-iframe-preferred-page-light.html (live test) (source)
- color-scheme-iframe-preferred.html (live test) (source)
- color-scheme-link-crash.html (live test) (source)
- color-scheme-root-background.html (live test) (source)
- color-scheme-rule-cache.html (live test) (source)
- color-scheme-system-colors.html (live test) (source)
- color-scheme-table-border-currentcolor-responsive.html (live test) (source)
- color-scheme-visited-link-initial.html (live test) (source)
虽然prefers-color-scheme媒体特性 允许作者根据用户的首选颜色方案调整页面颜色, 但页面的许多部分并不在作者的控制范围内 (例如表单控件、滚动条等)。 color-scheme属性允许一个元素指明 它设计用于渲染的颜色方案。 这些值与用户的偏好进行协商, 产生一个使用的颜色方案, 它会影响诸如 表单控件和滚动条的默认颜色。 (参见§ 2.2 使用的颜色方案的影响。)
注意:由于许多页面是在颜色方案支持存在之前编写的, 用户代理无法自动调整其控制的元素中使用的颜色, 因为这可能导致与周围页面的颜色对比无法读取。
宿主语言可以定义页面支持的颜色方案, 即默认支持该页面上所有元素的颜色方案列表。
注意:[HTML]定义了一个color-scheme
meta
标签,可以用来设置页面支持的颜色方案。
值定义如下:
- normal
- light
-
表示该元素支持浅色方案。
- dark
-
表示该元素支持深色方案。
- only
-
禁止用户代理为该元素覆盖颜色方案。
- <custom-ident>
-
<custom-ident>值没有意义, 它们仅存在于未来兼容性, 以便未来添加的颜色方案不会使旧版用户代理中的color-scheme声明无效。 用户代理不得将任何<custom-ident>值解释为有意义; 任何额外的可识别颜色方案 必须明确添加到该属性的语法中。
注意:为了避免混淆, 作者教程和参考资料 应省略<custom-ident>。
normal、light、dark和only关键字 在该属性中不是有效的<custom-ident>。
注意:浅色和深色颜色方案并不是特定的调色板。 例如, 一个强烈的黑色-白色方案和一个棕褐色背景的深褐色方案 都可以被视为浅色方案。 要确保特定的前景色或背景色, 需要明确指定它们。
-
如果用户的首选颜色方案, 根据prefers-color-scheme媒体特性指示, 存在于列出的颜色方案中, 且被用户代理支持, 则这是元素的使用颜色方案。
-
否则, 如果用户已表明对其选定的颜色方案的覆盖偏好, 且only关键字未出现在元素的color-scheme中, 用户代理必须使用用户的首选颜色方案覆盖颜色方案。 参见§ 2.3 覆盖颜色方案。
注意:用户代理不要求支持任何特定的颜色方案, 因此仅使用单个关键字, 例如color-scheme: dark, 来指示所需的颜色方案仍然不能保证对元素的渲染产生任何效果。
:root{ color-scheme : light dark; }
如果页面仅限于使用仅<system-color>, 上述color-scheme声明 将支持用户的首选颜色方案, 即使在作者无需使用@media的情况下。
如果页面的颜色方案主要是明亮的, 以下将明确指示:
:root{ color-scheme : light; }
而如果页面主要是黑暗的, 明确指示这一点也会使页面看起来更加一致:
:root{ color-scheme : dark; }
然而,当然更好的是支持这两种颜色方案。
例如, 样式指南可能会给出多个使用明亮或黑暗颜色的UI示例, 专门展示明亮或黑暗主题。 这可以表示为:
:root{ color-scheme : light dark; } .light-theme-example{ color-scheme : light; } .dark-theme-example{ color-scheme : dark; }
仅根植于.light-theme-example或.dark-theme-example的子部分将被明确选择进入light或dark主题; 页面其余部分将尊重用户的偏好。
注意:重复关键字,例如color-scheme: light light, 是有效的但不会产生超出关键字首次出现所提供效果的额外影响。
2.2. 已用颜色方案的影响
对于所有元素, 用户代理必须将以下内容与已用颜色方案匹配:
-
滚动条和其他交互式UI的默认颜色
-
表单控件和其他“特殊渲染”元素的默认颜色
-
其他浏览器提供的UI(例如“拼写检查”下划线)的默认颜色
在根元素上, 已用颜色方案 还必须影响 画布 和视口滚动条的表面颜色。
为了保持预期的颜色对比,
在通常通过透明画布(例如通过HTML
iframe
元素提供的文档嵌入)呈现的嵌入文档的情况下,
如果该元素的已用颜色方案
与嵌入文档根元素的已用颜色方案不匹配,
则UA必须使用一个不透明的画布,该画布使用与嵌入文档的
已用颜色方案相适应的Canvas颜色,
而不是透明画布。
此规则不适用于通过用于图形的元素嵌入的文档
(例如
img
元素嵌入一个SVG文档)。
注意:除了上述的小范围调整外, 用户代理通常不会进一步调整页面 以匹配用户的首选颜色方案, 因为无意间破坏页面的可能性太高。 然而,当用户需要特定的颜色选择时 (例如出于无障碍原因), 可能会应用更具侵入性的更改; 参见§ 3 强制调色板。
2.3. 覆盖颜色方案
如果用户表明对特定颜色方案有覆盖偏好, 并且作者未通过使用only关键字禁止此操作, 用户代理可以覆盖颜色方案, 强制已用颜色方案为用户的 首选颜色方案。 如果该元素不支持该颜色方案, 用户代理还必须自动调整其他颜色以适应所选的颜色方案, 例如通过反转其亮度, 同时保持页面可读性所需的颜色对比。 在这种情况下,UA还可以在替换元素、背景图像和其他外部资源中自动调整颜色。
注意:此类自动调整的具体细节由UA定义, 并且可能因UA而异。 但并非旨在将所有颜色强制为固定的调色板, 如强制颜色模式那样, 仅是将页面上的所有颜色 强制为符合深色或浅色颜色方案。
对于已支持深色颜色方案的页面,
并通过color-scheme属性
或
color-scheme
meta
名称指明了这一点,
除了报告dark值
给prefers-color-scheme媒体查询,
并选择一个深色已用颜色方案,
此外没有其他影响。
但对于未明确支持深色颜色方案的页面, 并且未通过指定color-scheme: only light 明确禁止此自动调整的页面, 此模式将触发页面颜色的自动调整, 以强制页面符合所需的深色颜色方案。
3. 强制调色板
强制颜色模式是一种无障碍功能, 旨在通过颜色对比提高文本的可读性。 视力有限的用户 通常在前景色和背景色之间 存在特定类型的对比时, 会感到阅读内容更加舒适。
操作系统可以提供内置的颜色主题, 例如Windows的高对比度黑底白字 和高对比度白底黑字主题。 用户还可以自定义自己的主题, 例如提供低对比度或色调对比。
在强制颜色模式下, 用户代理在页面上强制实施用户首选的调色板, 覆盖作者为特定属性选择的颜色, 参见§ 3.1 强制颜色模式影响的属性。 它还可以在文本下方强制添加“底板” (类似于在::selection伪元素上绘制背景的方式), 以确保足够的对比度以提高可读性。
为了使页面适应强制颜色模式, 用户代理将匹配forced-colors媒体查询, 并且必须通过CSS系统颜色 提供所需的调色板 (参见[CSS-COLOR-4])。 此外, 如果UA根据Lab亮度确定, Canvas颜色 明显是深色(L < 33%)或浅色(L > 67%), 则它必须匹配 prefers-color-scheme媒体查询的适当值, 并表达对应的用户首选 color-scheme。 这将允许支持浅色/深色颜色方案的页面 自动调整以更接近匹配 强制颜色方案。 上述深色与浅色阈值之间的行为 由UA定义, 并可能导致假设用户的首选颜色方案为 light或dark。
如果获取模拟的强制颜色主题数据不是
"none
",
用户代理应绕过上述操作系统颜色主题,
而是表现为用户已启用
强制颜色模式,
并使用为
模拟的强制颜色主题数据
的结果值定义的
强制颜色模式模拟调色板。
3.1. 强制颜色模式影响的属性
当强制颜色模式处于激活状态,且元素上的forced-color-adjust属性为auto(见下文), 元素上所有属性的<color>组件将被强制调整为用户首选的颜色调色板。
对于属性的每个<color>组件, 如果其计算值是除系统颜色以外的颜色, 其使用值将被强制为以下的系统颜色:
-
特别是对于background-color, 它将被强制为 color属性的系统颜色值的相反颜色 (参见系统颜色配对), 使用CanvasText作为Canvas的对立面。 然而,其alpha通道取自 原background-color值, 以确保透明背景保持透明。
-
在所有其他情况下,用户代理(UA)决定 合适的强制系统颜色——应该匹配在没有任何作者样式表时,元素的所有受影响属性 也由UA确定时的颜色。
另外:
-
background-image计算为none,除非原始值包含url()函数
-
color-scheme计算为light dark
-
如果font-variant-emoji计算为normal或unicode, UA应强制将页面上的任何表情符号转换为其单色版本(如果有)。
UA可以进一步调整这些强制颜色模式的启发式规则 以提供更好的用户体验。
.example{ color : color-mix ( in srgb, CanvasText, Canvas); }
对于color,其计算值将是CanvasText和Canvas系统颜色的50-50混合。
该值将继承给后代并通过如computedStyleMap()
等API观察。
对于color,其使用值将是UA选择的系统颜色,例如CanvasText。
3.2. 退出强制颜色调色板:forced-color-adjust 属性
名称: | forced-color-adjust |
---|---|
值: | auto | none | preserve-parent-color |
初始值: | auto |
适用于: | 所有元素和文本 |
是否继承: | 是 |
百分比: | 不适用 |
计算值: | 与指定值一致 |
规范顺序: | 根据语法 |
动画类型: | 不可动画 |
forced-color-adjust 属性 允许作者将特定元素 从强制颜色模式中排除, 使 CSS 完全控制颜色。 值的含义如下:
- auto
-
在强制颜色模式下, 元素的颜色会由 UA 自动调整。
- none
-
在强制颜色模式下, 元素的颜色不会由 UA 自动调整。
作者仅在自己调整颜色以支持用户的颜色和对比度需求, 并需要更改 UA 的默认调整以为这些元素提供更适合的用户体验时,才应使用此值。
- preserve-parent-color
-
在强制颜色模式中, 如果color 属性从其父元素继承 (即没有级联值或级联值为currentColor、inherit, 或其他从父元素继承的关键字), 则其计算值为其父元素使用的color值的颜色。
在其他方面,其行为与none 相同。
注意: 此值仅用于从嵌入的 SVG 元素中获得合理的行为, 这些元素期望接收外部文档的文本颜色 (并与强制颜色模式的调整保持一致), 同时默认情况下使 SVG 保持其确切颜色, 因为强制颜色模式通常无法有效应用于插图。
为了不破坏 SVG 内容, UA 预计会在其 UA 样式表中添加以下规则:
@namespace "http://www.w3.org/2000/svg" ; svg|svg{ forced-color-adjust : preserve-parent-color; } svg|foreignObject{ forced-color-adjust : auto; }
UA 必须将设置在根元素上的 forced-color-adjust 值
传播到文档视口
(例如它能影响画布背景)。
请注意,forced-color-adjust不会
从 HTML 的
body
传播。
测试
4. 基于性能的颜色调整
在大多数显示器上, 作者选择的颜色对设备性能没有显著影响; 显示白色背景或黑色背景的文档几乎同样容易。
然而,一些设备由于限制和其他特性使得这一假设不成立。 例如, 打印机通常在白纸上打印; 因此白色背景的文档无需耗费墨水来绘制背景, 而黑色背景的文档则需要耗费大量墨水填充背景颜色。 这通常效果较差, 有时还会对纸张产生不良的物理影响, 更不用说额外墨水消耗所导致的大幅增加的打印成本。 即使是较小的差异, 例如将文本颜色设置为黑色与深灰色, 在打印时也可能有很大的不同, 因为这会从使用单一黑色墨水切换为使用青色、洋红色和黄色墨水的混合, 从而增加墨水使用量并降低分辨率。
因此,在某些情况下,用户代理会根据特定情境调整作者指定的样式, 使其更适合输出设备, 并满足他们认为用户可能偏好的设置。 然而,在某些情况下,文档可能以重要且深思熟虑的方式使用颜色, 用户会欣赏这种设计, 因此文档希望有某种方式提示用户代理尊重页面的颜色选择。 本节定义了用于控制这些自动调整的属性。
4.1. 墨水经济性: print-color-adjust 属性
名称: | print-color-adjust |
---|---|
值: | economy | exact |
初始值: | economy |
适用于: | 所有元素 |
是否继承: | 是 |
百分比: | 不适用 |
计算值: | 指定的关键字 |
规范顺序: | 根据语法 |
动画类型: | 离散 |
print-color-adjust 属性为用户代理提供了一个提示, 说明在打印机或类似设备上可能代价高昂或通常不明智的颜色和样式选择(例如在深色背景上使用浅色文本)应如何处理。 如果用户代理允许用户控制文档显示的这一方面, 则用户偏好必须比由print-color-adjust提供的提示更优先。
- economy
-
用户代理应根据输出设备的需要和审慎性对页面样式进行调整。
例如,如果文档正在打印, 用户代理可能会忽略任何背景 并调整文本颜色使其足够暗, 以最小化墨水使用。
- exact
-
该值表示页面在指定的元素上使用颜色和样式的方式是重要且有意义的,
不应被调整或更改,除非用户请求。
例如, 一个提供打印指引的地图网站 可能会在指引步骤中交替使用白色和浅灰色背景的“斑马条纹”样式。 丢失这些斑马条纹并使用纯白背景 会使指引在分心的驾驶情况下快速阅读变得更加困难。
用户代理必须将根元素上设置的print-color-adjust值
传播到文档视口
(例如它能影响画布背景)。
请注意,print-color-adjust不会
从 HTML 的
body
传播。
4.2. color-adjust 简写
名称: | color-adjust |
---|---|
值: | <'print-color-adjust'> |
初始值: | 参见个别属性 |
适用于: | 参见个别属性 |
是否继承: | 参见个别属性 |
百分比: | 参见个别属性 |
计算值: | 参见个别属性 |
动画类型: | 参见个别属性 |
规范顺序: | 根据语法 |
color-adjust 简写允许作者 在一个声明中设置所有基于性能的颜色调整属性。 (目前,只有一个这样的属性——print-color-adjust—— 但未来可能会添加更多。)
color-adjust 简写目前已 弃用。 作者应使用更具体的print-color-adjust 属性, 以避免在目标上下文之外意外重置基于性能的颜色调整。
测试
5. 仿真
为了用户代理自动化和应用测试的目的,本文档定义了以下仿真。5.1. 仿真强制颜色模式
每个顶级遍历对象都有一个关联的仿真强制颜色主题数据,它是表示ForcedColorsModeAutomationTheme
的数据,
初始值为"none
"。
enum {
ForcedColorsModeAutomationTheme ,
"none" ,
"light" };
"dark"
要设置仿真强制颜色主题数据,给定可导航对象navigable和一个emulatedThemeData:
-
断言emulatedThemeData是
ForcedColorsModeAutomationTheme
。 -
令traversable为navigable的顶级遍历对象。
-
如果traversable不为null:
-
将traversable的关联仿真强制颜色主题数据设置为 emulatedThemeData。
-
UA必须将此视为需要重新计算样式的更改。
-
要获取仿真强制颜色主题数据,给定ForcedColorsModeAutomationTheme
theme:
-
如果navigable为null,则返回null。
-
令traversable为navigable的顶级遍历对象。
-
如果traversable为null,则返回null。
-
返回traversable的关联仿真强制颜色主题数据。
5.2. 强制颜色模式调色板
为了用户代理自动化和应用测试的目的,本文档 定义了以下强制颜色模式仿真调色板。<system-color> 关键字 | 值 |
---|---|
AccentColor | #FFFFFF |
AccentColorText | #000000 |
ActiveText | #00009F |
ButtonBorder | #000000 |
ButtonFace | #FFFFFF |
ButtonText | #000000 |
Canvas | #FFFFFF |
CanvasText | #000000 |
Field | #FFFFFF |
FieldText | #000000 |
GrayText | #600000 |
Highlight | #37006E |
HighlightText | #FFFFFF |
LinkText | #00009F |
Mark | N/A - 此系统颜色关键字不应调整。 |
MarkText | N/A - 此系统颜色关键字不应调整。 |
SelectedItem | #37006E |
SelectedItemText | #FFFFFF |
VisitedText | #00009F |
<system-color> 关键字 | 值 |
---|---|
AccentColor | #000000 |
AccentColorText | #FFFFFF |
ActiveText | #FFFF00 |
ButtonBorder | #000000 |
ButtonFace | #000000 |
ButtonText | #FFFFFF |
Canvas | #000000 |
CanvasText | #FFFFFF |
Field | #000000 |
FieldText | #FFFFFF |
GrayText | #3FF23F |
Highlight | #1AEBFF |
HighlightText | #000000 |
LinkText | #FFFF00 |
Mark | N/A - 此系统颜色关键字不应调整。 |
MarkText | N/A - 此系统颜色关键字不应调整。 |
SelectedItem | #1AEBFF |
SelectedItemText | #000000 |
VisitedText | #FFFF00 |
6. 隐私注意事项
通过颜色方案或强制颜色模式应用用户颜色偏好,会通过getComputedStyle()
暴露用户的颜色偏好,从而增加指纹识别的可能性。
-
将系统颜色保留为关键字直到实际值生成的时间 会破坏大量已部署的脚本, 因为color的初始值已经是系统颜色 (但大量脚本隐式期望从color中看到RGB颜色)
-
通过脚本API对系统颜色撒谎 (假装它们总是一些静态值) 可能导致任何从页面颜色计算得出的颜色 在与实际系统颜色一起使用时不可读。
有关此主题的讨论,请参见Issue 5710。
7. 安全注意事项
嵌入的文档可能通过时间攻击来判断其color-scheme是否与其嵌入的
iframe
匹配。
8. 致谢
本规范的实现 离不开Apple、Google和Microsoft 在各种颜色调整功能上的开发努力, 以及在www-style上有关打印调整的讨论。 特别是,CSS工作组想要感谢: Alison Maher, François Remy, イアンフェッティ
在此列出其他来自Microsoft / Apple / Google的贡献者。
9. 变更
自2022年2月10日候选推荐快照以来的变更:
- 移除color() 回退系统颜色的特殊处理,因为该功能已从[CSS-COLOR-4]中移除。 (Issue 7007)
- 增加了对强制颜色模式进行改进测试的仿真支持。 (Issue 11824)
- 更新了在强制颜色模式中适用的属性,以更通用地适用于所有属性的<color>组件, 并将具体已知的属性移动到注释中。 (Issue 11857)
- 为强制颜色模式添加了字体表情符号回退逻辑。 (Issue 8064)
另请参见候选推荐之前的变更。