demo · v150
light-dark() + image-set() combo
Combining light-dark() with image-set() lets a single CSS declaration serve four image variants at once: light@1x, light@2x, dark@1x, dark@2x. The browser picks the right variant based on both color scheme and device pixel ratio — no media queries, no JavaScript, no class toggling.
This demo simulates the four variants using inline SVG data URIs with distinct colors and DPR markers. In production, these would be real
url() paths.
Select theme and device pixel ratio to see which variant is active:
Theme:
Device pixel ratio:
Light · 1×
✓ selectedLight · 2×
✓ selectedDark · 1×
✓ selectedDark · 2×
✓ selected| CSS function | Selects by | Scope |
|---|---|---|
light-dark(A, B) | color-scheme (prefers-color-scheme) | Outer — picks which image-set to use |
image-set(url 1x, url 2x) | device pixel ratio | Inner — picks resolution variant |
| Combined | both color scheme + DPR | 4 variants from a single declaration |
/* Chrome 150: combine light-dark() with image-set() */
.brand-logo {
background-image: light-dark(
/* Light theme: standard and HiDPI variants */
image-set(
url("logo-light.png") 1x,
url("logo-light@2x.png") 2x
),
/* Dark theme: standard and HiDPI variants */
image-set(
url("logo-dark.png") 1x,
url("logo-dark@2x.png") 2x
)
);
background-repeat: no-repeat;
background-size: contain;
}
/* Also works with SVG for scalable graphics */
.icon {
background-image: light-dark(
url("icon-light.svg"),
url("icon-dark.svg")
);
/* SVG is resolution-independent, no image-set() needed */
}
see also
implementation reference
Need the exact API surface, compatibility boundaries, errors, lifecycle, and source links? Read the matching gendn reference ↗