amzn / style-dictionary

A build system for creating cross-platform styles.
https://styledictionary.com
Apache License 2.0
3.93k stars 558 forks source link

CSS variables with light-dark()? #1377

Open brian-patrick-3 opened 3 weeks ago

brian-patrick-3 commented 3 weeks ago

Having a light and a dark theme, is it possible to generate variables using the CSS light-dark() syntax?

Ex desired output:

:root {
  /* palette tokens */
  --kd-color-black: #000;
  --kd-color-white: #fff;

  /* named tokens */
  --kd-color-text: light-dark(var(--kd-color-black), var(--kd-color-white));
  --kd-color-background: light-dark(var(--kd-color-white), var(--kd-color-black));
}

If yes, how would we need to structure the tokens JSON files? Using Tokens Studio for Figma, how could we get there?

jorenbroekema commented 3 weeks ago

Might be possible if https://github.com/amzn/style-dictionary/issues/1063 feature gets added, but as of now it's not possible

equinusocio commented 1 week ago

Just a question: How do you respect the active theme chosen by the user with light-dark()? This function refers to the OS theme or the browser-forced one. How would you handle it in CSS if users want to use a light theme while using a dark OS theme (like outdoor)?

brian-patrick-3 commented 1 week ago

This article explains it in depth: https://css-tricks.com/come-to-the-light-dark-side/

Basically, set a meta color-scheme tag with value of dark, light or light dark (auto/user preference). Then maybe give them a setting to choose between those 3 options.

I ended up writing a custom node script to parse the token JSON into light dark syntax rather than use style dictionary.

equinusocio commented 1 week ago

Basically, set a meta color-scheme tag with value of dark, light or light dark (auto/user preference). Then maybe give them a setting to choose between those 3 options.

👍🏻

About the issue, I had the same, and we write a custom transform that parses specific key names to return light-dark. In our case we use two SD setup, one for raw tokens (fixed values) and one for themed tokens, all the theme tokens are rendered with light-dark() value

Something like this:

{
 "global-background": {
   "$type": "color-theme",
   "light": "#fff",
   "dark": "#000"
 }
}

so our transform generates --global-foreground: light-dark(#fff, #000);