正确写法是在<img>标签中直接使用srcset="icon@2x.png 2x, icon@3x.png 3x"并配src="icon.png"作为1x fallback;若用<picture>,则每个<source>内srcset仅允许纯x描述符,且不可混用w单位。

picture标签里怎么写srcset才能正确加载2x和3x图片
直接写 srcset 时,必须同时提供像素密度描述符(2x、3x)和对应尺寸的图片资源,浏览器才按设备 DPR 自动选;只写宽度描述符(如 600w)或混用两种描述符会导致 fallback 或加载错误资源。
-
srcset中每个条目格式为:图片路径 x,比如icon@2x.png 2x、icon@3x.png 3x - 必须搭配
src属性作为基础 fallback,否则无 DPR 匹配能力的旧浏览器会空白 - 不要在同一个
source元素里混用w和x描述符——srcset="a.jpg 1x, b.jpg 2x, c.jpg 600w"是无效的 - 所有
2x/3x图片应与1x版本保持完全相同的构图和尺寸(CSS 渲染尺寸),仅分辨率不同
为什么用了2x/3x还是加载了1x图
常见原因是设备 DPR 没被识别,或资源未满足匹配条件。浏览器不会“优先加载高倍图”,而是严格按当前设备像素比选择最接近的 x 值。
- 检查设备实际 DPR:用
window.devicePixelRatio控制台输出确认,iOS 真机通常是2或3,Chrome 模拟器需开启“Device Pixel Ratio”设置,不能只靠响应式视口缩放 -
srcset中没写1x项?浏览器可能退回到src,而非跳到2x - 图片文件 404 或 MIME 类型错误(比如 .png 被服务端返回 text/plain)会导致加载失败后降级
- Safari 对
picture+x描述符支持完好,但某些安卓 WebView(尤其旧版)会忽略2x直接取src
picture里用source还是img的srcset更合适
如果只按屏幕密度切换(不涉及 art direction 或断点布局),**根本不用 source,直接在 img 上写 srcset 就够了**;picture 的价值在于配合 media 属性做不同构图的图片切换。
- 纯 DPR 切换 → 用
<img src="icon.png" srcset="icon@2x.png 2x, icon@3x.png 3x">,简洁且兼容性更好 - 需要为小屏换裁剪图、为横屏换宽幅图 → 才用
picture+ 多个source,每个带自己的media和srcset -
picture内部的img仍需有src,它不是可选的;没有src,整个picture在不支持picture的浏览器里会彻底不显示
如何验证2x/3x是否真被加载
别信 Network 面板里看到的第一个请求,要确认最终渲染用的是哪张图。
立即学习“前端免费学习笔记(深入)”;
- 在 Elements 面板中右键图片 → “Open in new tab”,看 URL 是否是
@2x或@3x路径 - 勾选 DevTools → Rendering → “Emulate CSS media features” → 设置
device-pixel-ratio为2或3,再刷新观察 Network 请求变化 - 用
getComputedStyle(img).backgroundImage不适用——这是针对 background-image 的,img标签得看currentSrc属性:document.querySelector('img').currentSrc - 注意:CDN 或构建工具(如 Webpack)可能自动重写图片路径,导致你写的
@2x.png实际被发布成哈希名,此时srcset里的路径必须同步更新



















