picture 元素本身不感知暗黑模式,需通过 source 的 media="screen and (prefers-color-scheme: dark)" 显式声明;暗色 source 应置于明色 source 之前,img 的 src 作为 fallback 且应与首个 source 一致。

picture 元素本身不感知暗黑模式
<picture></picture> 只是容器,它不会读取 prefers-color-scheme,也不会自动切换图片。真正起作用的是里面的 <source></source> 的 media 属性——必须显式写媒体查询才能响应暗黑模式。
常见错误是只写了 <img> 却没配 <source></source>,或者 media 值写成 (prefers-color-scheme: dark) 但漏了括号外的 screen and,导致浏览器忽略该 source。
- 必须用
media="screen and (prefers-color-scheme: dark)"(注意screen and不可省) - 暗黑模式下的
<source></source>应放在明色模式之前,因为浏览器按顺序匹配,第一个满足条件的生效 -
<img>的src是 fallback,当所有<source></source>都不匹配时才用它,建议设为明色图
完整 HTML 结构示例
以下代码在支持 prefers-color-scheme 的浏览器中能正确切换:
<picture><source srcset="logo-dark.svg" media="screen and (prefers-color-scheme: dark)"><source srcset="logo-light.svg" media="screen and (prefers-color-scheme: light)"> @@##@@ </source></source></picture>
注意两点:一是两个 <source></source> 都带 media,二是 <img src="logo-light.svg" alt="Logo"> 的 src 和第一个 <source></source> 保持一致,避免无 JS 时加载错图。
- 若只支持暗黑/明色两种,可省略
light的<source></source>,靠<img>fallback 覆盖明色场景 -
srcset可换成src,但推荐用srcset便于后续加响应式 - SVG 是首选,无需额外适配尺寸;若用 PNG/JPEG,确保两套图宽高比一致,否则 layout shift
兼容性与降级要点
旧版 Safari(prefers-color-scheme,此时所有 <source></source> 的 media 都不匹配,最终走 <img> 的 src。这是预期行为,不是 bug。
- 不要依赖 JS 检测后动态改
<picture></picture>,既冗余又可能闪屏 - 若需支持 iOS 12 以下,可加一层
media="(any-pointer: coarse)"做粗略设备判断,但无法精确对应主题 - CSS 中的
color-scheme: light dark不影响<picture></picture>,它只控制表单控件和滚动条等系统 UI
为什么不用 CSS background-image 切换?
用 background-image + @media (prefers-color-scheme: dark) 看似简单,但它绕过了 <picture></picture> 的语义优势:无法提供 alt 文本、不被屏幕阅读器识别、不能被搜索引擎索引图片内容。
- 装饰性图片可用 CSS,但图标、logo、数据图表等有意义的图片必须用
<img>或<picture></picture> - CSS 方案在打印样式中默认不显示背景图,而
<picture></picture>中的<img>会正常打印 - 部分邮件客户端完全禁用 CSS,
<picture></picture>的 fallback 更可靠
screen and 这个前缀——少了它,整个 <source></source> 就静默失效,且控制台不报错。
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!











