Re: [community-group] Native modes and theming support (#210)

This topic requires a lot of research, or basically the one I did for the past years and started to put into blog posts. I'm currently nearing ~10k words (so there is a substantial backup for what's to come). I hope to start releasing this series in late april.\
With the spoiler out of the way that there is more to come, I think this topic is very important and I can share parts I have ready already.

## Features / User Preferences

Let's start this from user preferences, this is what a user might wanna choose:

![user-preferences](https://user-images.githubusercontent.com/283700/228292579-566a6471-061d-4e2b-8a83-90d7c957db1f.png)

And the idea is, whatever the user is about to choose, will receive the respective value for that token. As theme authors we would call them **features**. A theme supports feature color-contrast or color-scheme, etc. 
Not all of these can be "System", as these may be product related options. See next section for more differentiation.

By the way, here is github:

<img width="666" alt="Bildschirmfoto 2023-03-28 um 18 15 21" src="https://user-images.githubusercontent.com/283700/228303583-89112059-4cb1-401f-9c01-05949fe56a81.png">

They don't have a "skin", but support all the other features from the user preferences menu above (in terms of color). You can even have dark appearance set when your system is light o_O.

## Behavior

There is a behavior involved in here:

- Adaptive: User chooses "System" and passes the choosing on to the Operating System
- Mode: User explicitely chooses a particular preference

In CSS:

```css
:root {
  --background: white;
}

/* Adaptaive */
@media (prefers-colors-scheme: dark) {
  :root {
    --background: black;
  }
}

/* Mode */
[theme-color-scheme="dark"] {
  :root {
    --background: black;
  }
}
```

The important thing: The behavior goes independent from the storage of values in the tokens file! This goes into the next step when values are extract from the tokens file and put into CSS or whatever else format

## References as Solutions in Development

In development we use references as solutions to this problem, here is one for colors:

<img width="930" alt="References as Solutions" src="https://user-images.githubusercontent.com/283700/228294880-4c18c2d3-3552-4b92-9f22-c01747510f20.png">

With that configuration above that is:

`intent-action-base-background` = 4 x 4 x 3 x 3 = 144

so the token can take 144 permutations in this example - if there was a value for all of them (which in reality I wouldn't expect).

## A Format to Structure Permutations

Modes is the wrong word to this - as this is something a user would opt into (see Raskin, J. (2008). _The Humane Interface: New Directions for Designing Interactive Systems_ (10th printing). Crawfordsville, Indiana: Addison-Wesley.) For example nowadays it would be dark color-scheme and not dark mode (that goes back to the old days, when it really was a *mode* - it still is but has moved to OS level).

I'm also not sure yet, what would be the best format to support this. It however needs to be defined on the token itself. It needs to be stored alongside the feature configuration. For example:

```json
{
  "$name": "intent-action-base-background",
  "$value": [
    {
      "$value": "white"
    },
    {
      "$value": "darkgrey",
      "color-scheme": "dark"
    },
    {
      "$value": "black",
      "color-scheme": "dark",
      "color-contrast": "high"
    }
  ]
}
```

The finding of tokens would be programmatical. Those with the highest match win:

```js
const token = tokens.find(t => t.name === 'intent-action-base-background');
const value = token.value.find({ 
  colorScheme: 'dark', 
  colorContrast: 'high' 
});
```

That is in fact no different than how tools currently work, as danny wrote in https://dbanks.design/blog/dark-mode-with-style-dictionary (Single Token Method)

An alternative to stick with the object approach would be (DON'T DO THIS):

```json
{
  "$name": "intent-action-base-background",
  "$value": {
    "": "white",
    "dark-": "darkgrey",
    "dark-high": "black"
  }
}
```

where features become the key within `$value` (This is how one needs to do that in figma right now, because styles don't support multiple values... hint hint :D). However, I'm heavily against this, as it would eliminate structural information and requires parsing.

In terms of scalability a format is required that can potentially scale up to ~150 permutations per token but we also know there will be maybe permutations based on 2 features with 2 permutations - as companies will already started to support color scheme and soon color contrast is to come (maybe because it only has two options? or because it has media query backup?). But once this wave is over, we probably will see adoption for chroma - Yes I'm very hypothetical here.

On the other hand the format shall be practical, this is why all (?) ideas so far use an object. This could easily end up in a nightmare nested tree as @NateBaldwinDesign showed (given the github use-case above) and practicability is gone.

I'm still with the array and it's configuration, but happy to read about better ideas.

---

Also, if I rushed over some of the topics, then please ask for more detailed explanation.

-- 
GitHub Notification of comment by gossi
Please view or discuss this issue at https://github.com/design-tokens/community-group/issues/210#issuecomment-1487246421 using your GitHub account


-- 
Sent via github-notify-ml as configured in https://github.com/w3c/github-notify-ml-config

Received on Tuesday, 28 March 2023 16:29:14 UTC