@swiftsolve/rove-tokens 1.0.0 → 1.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/DESIGN.md +9 -8
- package/README.md +91 -20
- package/package.json +1 -2
- package/src/code-tokens.json +1 -18
- package/src/figma/variables.json +180 -0
- package/text-styles.css +1 -1
- package/tokens/code.tokens.json +1 -81
- package/tokens/layout.tokens.json +67 -0
- package/tokens/motion.tokens.json +28 -0
- package/tokens/spacing.tokens.json +8 -0
- package/tokens/typography.tokens.json +14 -0
- package/tokens.css +22 -16
package/DESIGN.md
CHANGED
|
@@ -64,7 +64,7 @@ Disabled controls use `--opacity-disabled`.
|
|
|
64
64
|
### Focus and motion
|
|
65
65
|
|
|
66
66
|
- Keyboard focus is `outline: var(--focus-outline)` with `outline-offset: var(--focus-offset)`. Rows flush with a card's edge draw it inside instead, with `--focus-inset`.
|
|
67
|
-
- Animate with `--ease-out` (or `--ease-in-out`) over `--duration-fast` or `--duration-normal`. A looping pulse uses `--ease-pulse`, which is symmetric, so it fades out and back in alike.
|
|
67
|
+
- Animate with `--ease-out` (or `--ease-in-out`) over `--duration-fast` or `--duration-normal`. A panel resizing to its content springs, with `var(--duration-spring) var(--ease-spring)`: it arrives within `--duration-normal`, and its slight overshoot settles after. A looping pulse uses `--ease-pulse`, which is symmetric, so it fades out and back in alike.
|
|
68
68
|
|
|
69
69
|
### Icons
|
|
70
70
|
|
|
@@ -74,7 +74,7 @@ Disabled controls use `--opacity-disabled`.
|
|
|
74
74
|
|
|
75
75
|
## Changing the design
|
|
76
76
|
|
|
77
|
-
Figma is the source of truth. Change a token in the Rove Design System Figma file, export it with the plugin in `figma-plugin/` into `src/figma/`, then run `npm run build` (see the [README](README.md#update-the-tokens)). Don't edit `tokens.css`, `tokens/` or the values in `src/figma/` by hand. What Figma can't hold (shadows,
|
|
77
|
+
Figma is the source of truth. Change a token in the Rove Design System Figma file, export it with the plugin in `figma-plugin/` into `src/figma/`, then run `npm run build` (see the [README](README.md#update-the-tokens)). Don't edit `tokens.css`, `tokens/` or the values in `src/figma/` by hand. What Figma can't hold (shadows, easing curves, the focus outline) lives in `src/code-tokens.json`.
|
|
78
78
|
|
|
79
79
|
Everything below the next line is rewritten by `npm run build`; edit only above it.
|
|
80
80
|
|
|
@@ -101,8 +101,12 @@ Names and uses, from Figma. The values are in `tokens.css`; Dark and Light diffe
|
|
|
101
101
|
- **Radius:** `--radius-xs` 5px, `--radius-sm` 8px, `--radius-md` 10px, `--radius-lg` 13px, `--radius-full` 999px
|
|
102
102
|
- **Font sizes:** `--font-size-2xs` 10px, `--font-size-xs` 11px, `--font-size-sm` 12px, `--font-size-md` 13px, `--font-size-lg` 14px, `--font-size-xl` 15px (dialog titles), `--font-size-2xl` 17px, `--font-size-3xl` 28px
|
|
103
103
|
- **Font families:** `--font-family-sans` Inter, `--font-family-numeric` Questrial
|
|
104
|
-
- **Focus:** `--focus-offset` 2px (focus ring offset)
|
|
104
|
+
- **Focus:** `--focus-ring-width` 1px (focus ring stroke), `--focus-offset` 2px (focus ring offset)
|
|
105
105
|
- **Opacity:** `--opacity-tint-xs` 8% (faintest tint), `--opacity-tint-sm` 10% (light tint), `--opacity-tint-md` 14% (tint), `--opacity-tint-lg` 22% (strong tint), `--opacity-tint-xl` 28% (strongest tint), `--opacity-high` 80% (nearly opaque), `--opacity-disabled` 40% (disabled controls)
|
|
106
|
+
- **Layout:** `--rail-item-size` 38px (rail items), `--titlebar-height` 56px (title bar)
|
|
107
|
+
- **Cards:** `--card-padding` `var(--spacing-14)` (card inset), `--card-header-padding-y` `var(--card-padding)`, `--card-header-padding-x` `var(--card-padding)`, `--card-header-min-height` 42px (compact card header), `--card-header-height` 44px (card header), `--card-body-padding` `var(--card-padding)`, `--row-padding-y` 8px (data row, above and below)
|
|
108
|
+
- **Font weights:** `--weight-regular` 400, `--weight-medium` 500, `--weight-semibold` 600
|
|
109
|
+
- **Motion:** `--duration-fast` 140ms (hovers, small changes), `--duration-normal` 220ms (panels, page changes), `--duration-spring` 450ms (a spring’s full run)
|
|
106
110
|
|
|
107
111
|
### Text styles
|
|
108
112
|
|
|
@@ -130,8 +134,5 @@ Apply a style with its class from `text-styles.css`. Each class reads four varia
|
|
|
130
134
|
What Figma variables can't hold, from `src/code-tokens.json`.
|
|
131
135
|
|
|
132
136
|
- **Shadows:** `--shadow-panel`, `--shadow-raised`, `--shadow-popover`
|
|
133
|
-
- **Focus:** `--focus-
|
|
134
|
-
- **
|
|
135
|
-
- **Cards:** `--card-padding` `var(--spacing-14)`, `--card-header-padding-y` `var(--card-padding)`, `--card-header-padding-x` `var(--card-padding)`, `--card-header-min-height` 42px, `--card-header-height` 44px, `--card-body-padding` `var(--card-padding)`, `--row-padding-y` 8px
|
|
136
|
-
- **Motion:** `--ease-out`, `--ease-in-out`, `--ease-pulse`, `--duration-fast` 140ms, `--duration-normal` 220ms
|
|
137
|
-
- **Font weights:** `--weight-regular` 400, `--weight-medium` 500, `--weight-semibold` 600
|
|
137
|
+
- **Focus:** `--focus-outline`, `--focus-inset`
|
|
138
|
+
- **Motion:** `--ease-out`, `--ease-in-out`, `--ease-pulse`, `--ease-spring`
|
package/README.md
CHANGED
|
@@ -12,6 +12,7 @@ Tokens for Rove, straight from the Rove Design System in Figma.
|
|
|
12
12
|
[](https://github.com/swiftsolve/rove-tokens/actions/workflows/presentation.yml)
|
|
13
13
|
[](https://github.com/swiftsolve/rove-tokens/tags)
|
|
14
14
|
[](https://www.figma.com/design/NoICIoyhWNOya9tOnNfEhH/Rove-Design-System)
|
|
15
|
+
|
|
15
16
|
[](https://www.designtokens.org/tr/2025.10/format/)
|
|
16
17
|
[](https://styledictionary.com/)
|
|
17
18
|
[](#-contrast)
|
|
@@ -23,22 +24,57 @@ Tokens for Rove, straight from the Rove Design System in Figma.
|
|
|
23
24
|
[📐 DESIGN.md](DESIGN.md) ·
|
|
24
25
|
[💡 Rationale](docs/rationale.md)
|
|
25
26
|
|
|
27
|
+
[📖 Tokens Storybook](https://rove.swiftsolve.net/storybook/tokens/) ·
|
|
28
|
+
[🧱 Components Storybook](https://rove.swiftsolve.net/storybook/)
|
|
29
|
+
|
|
26
30
|
</div>
|
|
27
31
|
|
|
28
32
|
---
|
|
29
33
|
|
|
30
|
-
Figma is the source of truth
|
|
34
|
+
Figma is the source of truth. A [Figma plugin](figma-plugin/) exports its variables and text styles, and this package turns them into DTCG token files, and those into CSS with [Style Dictionary](https://styledictionary.com/).
|
|
31
35
|
|
|
32
36
|
> [!TIP]
|
|
33
37
|
> **Building Rove UI?** [`DESIGN.md`](DESIGN.md) says which token to use for what, with every value. It ships in the package, so coding agents in Rove can read it from `node_modules/@swiftsolve/rove-tokens/DESIGN.md`.
|
|
34
38
|
|
|
39
|
+
## ⚙️ How it works
|
|
40
|
+
|
|
41
|
+
```mermaid
|
|
42
|
+
%%{init: {"themeCSS": ".cluster-label { translate: 236px 0; }", "theme": "base", "themeVariables": {"fontFamily": "Inter, -apple-system, Segoe UI, Helvetica, Arial, sans-serif", "fontSize": "14px", "primaryColor": "#151618", "primaryTextColor": "#eeeeef", "primaryBorderColor": "#2b2c2f", "lineColor": "#8e8f93", "clusterBkg": "#0b0b0c", "clusterBorder": "#3a69d5", "titleColor": "#5b8cff", "dropShadow": "none"}}}%%
|
|
43
|
+
flowchart TD
|
|
44
|
+
figma("<b>Figma file</b><br/>variables, styles"):::source
|
|
45
|
+
exports("<b>src/figma/*.json</b><br/>Figma plugin"):::file
|
|
46
|
+
code("<b>src/code‑tokens.json</b><br/>shadows, easings"):::file
|
|
47
|
+
slides("<b>Slideshow</b><br/>npm run present"):::ship
|
|
48
|
+
|
|
49
|
+
subgraph build ["npm run build"]
|
|
50
|
+
dtcg("<b>tokens/</b><br/>figma‑to‑dtcg.mjs"):::file
|
|
51
|
+
css("<b>tokens.css</b><br/>Style Dictionary"):::file
|
|
52
|
+
textCss("<b>text-styles.css</b><br/>dtcg‑to‑text‑styles.mjs"):::file
|
|
53
|
+
design("<b>DESIGN.md</b><br/>token‑reference.mjs"):::file
|
|
54
|
+
end
|
|
55
|
+
|
|
56
|
+
pkg("<b>npm package</b><br/>for Rove"):::ship
|
|
57
|
+
storybook("<b>Storybook</b><br/>both themes"):::ship
|
|
58
|
+
|
|
59
|
+
figma --> exports & slides
|
|
60
|
+
exports & code --> dtcg
|
|
61
|
+
dtcg --> css & textCss & design
|
|
62
|
+
build --> pkg & storybook
|
|
63
|
+
|
|
64
|
+
classDef source fill:#3a69d5,stroke:#5b8cff,color:#ffffff
|
|
65
|
+
classDef file fill:#151618,stroke:#2b2c2f,color:#eeeeef
|
|
66
|
+
classDef ship fill:#20263a,stroke:#5b8cff,color:#eeeeef
|
|
67
|
+
```
|
|
68
|
+
|
|
69
|
+
Under each file is what writes it: a script in `scripts/tokens/`, [Style Dictionary](https://styledictionary.com/) (run by `dtcg-to-css.mjs`), or the Figma plugin, which exports the file's variables and text styles. [What's where](#️-whats-where) has the details.
|
|
70
|
+
|
|
35
71
|
## 📦 Use
|
|
36
72
|
|
|
37
73
|
```bash
|
|
38
74
|
npm install @swiftsolve/rove-tokens
|
|
39
75
|
```
|
|
40
76
|
|
|
41
|
-
The package ships `tokens.css`, `text-styles.css` and `tokens/` built. You can also install straight from a version tag (`github:swiftsolve/rove-tokens#v1.
|
|
77
|
+
The package ships `tokens.css`, `text-styles.css` and `tokens/` built. You can also install straight from a version tag (`github:swiftsolve/rove-tokens#v1.1.0`); then npm builds them on install, which needs Node 22 (see `.nvmrc`).
|
|
42
78
|
|
|
43
79
|
```css
|
|
44
80
|
@import '@swiftsolve/rove-tokens/tokens.css';
|
|
@@ -47,6 +83,8 @@ The package ships `tokens.css`, `text-styles.css` and `tokens/` built. You can a
|
|
|
47
83
|
|
|
48
84
|
Dark values sit on `:root`, Light values on `:root.theme-light`. CSS names follow the Figma names: `bg/base` is `--bg-base`, `spacing/12` is `--spacing-12`.
|
|
49
85
|
|
|
86
|
+
Every colour lives once in the Palette collection (`neutral/850`, `blue/450`; higher numbers are darker; a see-through shade adds `-a` and its opacity, `neutral/850-a10`), and the Color tokens point at it. The Palette isn't in `tokens.css`: a token that points at a shade gets the shade's value there. Figma-only collections (Icon tone, Capability level) and variables without a code syntax aren't in `tokens.css` either.
|
|
87
|
+
|
|
50
88
|
Each Figma text style becomes four tokens: `--type-<style>-size`, `-weight`, `-line-height` (a unitless ratio) and `-letter-spacing` (in `em`). `Number/Display` gives `--type-number-display-size` and so on. A size bound to a variable comes through as that variable (`var(--font-size-3xl)`).
|
|
51
89
|
|
|
52
90
|
`text-styles.css` applies a style whole: `.type-heading-large` sets the font family and all four, plus the text case (Overline is uppercase). The classes set no colour and sit in `@layer components`, so Tailwind utilities on the same element still win.
|
|
@@ -59,9 +97,9 @@ Each Figma text style becomes four tokens: `--type-<style>-size`, `-weight`, `-l
|
|
|
59
97
|
| --- | --- |
|
|
60
98
|
| `palette.tokens.json` | Every colour, once |
|
|
61
99
|
| `color.dark.tokens.json`, `color.light.tokens.json` | The Color tokens in each theme, pointing at the palette (`{neutral.850}`) |
|
|
62
|
-
| `spacing.tokens.json`, `typography.tokens.json`, `opacity.tokens.json` | The other Figma collections |
|
|
100
|
+
| `spacing.tokens.json`, `typography.tokens.json`, `opacity.tokens.json`, `layout.tokens.json`, `motion.tokens.json` | The other Figma collections |
|
|
63
101
|
| `text-styles.tokens.json` | Each text style as a `typography` token |
|
|
64
|
-
| `code.tokens.json` | The code-only tokens (shadows,
|
|
102
|
+
| `code.tokens.json` | The code-only tokens (shadows, easing curves, the focus outline) |
|
|
65
103
|
|
|
66
104
|
A theme is every file plus one of the two color files. Paths follow the Figma names (`bg/base` is `bg.base`). Tokens that other tokens point at but that aren't CSS variables (the palette, the shadow colours) are marked `"$extensions": { "net.swiftsolve.rove-tokens": { "css": false } }`. CSS-only expressions (`--focus-inset`, a `calc()`) aren't in them.
|
|
67
105
|
|
|
@@ -71,19 +109,34 @@ The colours meet [WCAG 2.2](https://www.w3.org/TR/WCAG22/) level AA in both them
|
|
|
71
109
|
|
|
72
110
|
## 📖 Storybook
|
|
73
111
|
|
|
74
|
-
|
|
112
|
+
Two Storybooks are hosted on rove.swiftsolve.net:
|
|
113
|
+
|
|
114
|
+
- [**Rove Tokens**](https://rove.swiftsolve.net/storybook/tokens/): every token in both themes (colour, palette, type, spacing, radius, effects, motion and layout), built from this repo's `main`.
|
|
115
|
+
- [**Rove Components**](https://rove.swiftsolve.net/storybook/): the Rove app's UI library, built from the tokens.
|
|
116
|
+
|
|
117
|
+
To run Rove Tokens locally:
|
|
75
118
|
|
|
76
119
|
```bash
|
|
77
120
|
npm run storybook
|
|
78
121
|
```
|
|
79
122
|
|
|
80
|
-
It opens on <http://localhost:6007>; the Theme menu in the toolbar switches Dark and Light. The pages read the DTCG files in `tokens/` and are styled with `tokens.css`, so a new build shows up without editing them.
|
|
123
|
+
It opens on <http://localhost:6007>; the Theme menu in the toolbar switches Dark and Light. The pages read the DTCG files in `tokens/` and are styled with `tokens.css`, so a new build shows up without editing them.
|
|
124
|
+
|
|
125
|
+
## 🛠️ Scripts
|
|
126
|
+
|
|
127
|
+
| Script | What it does |
|
|
128
|
+
| --- | --- |
|
|
129
|
+
| `npm run build` | Figma export → DTCG → `tokens.css`, `text-styles.css` and the `DESIGN.md` reference. `npm install` and `npm publish` run it too. |
|
|
130
|
+
| `npm run storybook` | The Rove Tokens Storybook on port 6007 |
|
|
131
|
+
| `npm run build:storybook` | A static copy of it in `storybook-static/` |
|
|
132
|
+
| `npm run present` | Builds, then exports the Figma file's pages to the slideshow in `presentation/`. Needs `FIGMA_TOKEN` in `.env.local`. |
|
|
133
|
+
| `npm run present:publish` | Pushes that slideshow to GitHub Pages |
|
|
81
134
|
|
|
82
135
|
## 🔄 Update the tokens
|
|
83
136
|
|
|
84
137
|
1. Change the variables or text styles in Figma.
|
|
85
138
|
2. Export them to `src/figma/variables.json` and `src/figma/text-styles.json`, either with the plugin in `figma-plugin/` (Figma desktop: Plugins → Development → Import plugin from manifest; then **Export**) or by asking Claude to export them through the Figma connection.
|
|
86
|
-
3. Run `npm run build` (Node 22) and check `tokens.css`.
|
|
139
|
+
3. Run `npm run build` (Node 22) and check `tokens.css`. The build stops if a variable's code syntax doesn't match its name, or a DTCG reference doesn't resolve.
|
|
87
140
|
4. Commit the change.
|
|
88
141
|
|
|
89
142
|
## 🚀 Release
|
|
@@ -105,24 +158,42 @@ It opens on <http://localhost:6007>; the Theme menu in the toolbar switches Dark
|
|
|
105
158
|
|
|
106
159
|
## 🗂️ What's where
|
|
107
160
|
|
|
161
|
+
**From Figma**
|
|
162
|
+
|
|
108
163
|
| Path | What |
|
|
109
164
|
| --- | --- |
|
|
110
165
|
| `src/figma/variables.json` | Raw Figma export. Every variable with a Web code syntax becomes that CSS variable. |
|
|
111
166
|
| `src/figma/text-styles.json` | Raw export of the local text styles: font, size, weight, line height, letter spacing, text case (when set) and the variables bound to them. Each style becomes a `--type-*` group. |
|
|
112
|
-
| `figma-plugin/` |
|
|
113
|
-
| `src/code-tokens.json` | What Figma variables can't hold: font stacks for the font-family variables, shadows,
|
|
114
|
-
|
|
167
|
+
| `figma-plugin/` | Rove Tokens Export, the Figma plugin that writes the two exports: every local variable by collection and mode, aliases kept, in the variables panel's order, and every local text style with the variables bound to it. It previews both files, then downloads them; it has no network access. |
|
|
168
|
+
| `src/code-tokens.json` | What Figma variables can't hold: font stacks for the font-family variables, shadows, easing curves and the CSS expressions built on variables (`--focus-outline`). `{figma/name}` pulls a Figma value in per theme. |
|
|
169
|
+
|
|
170
|
+
**Build**
|
|
171
|
+
|
|
172
|
+
| Path | What |
|
|
173
|
+
| --- | --- |
|
|
115
174
|
| `scripts/tokens/build.mjs` | `npm run build`: runs the steps below and writes `tokens.css` and `text-styles.css` at the package root, where the import paths point. |
|
|
116
|
-
| `scripts/tokens/dtcg.mjs` | Figma export → the DTCG files in `tokens/`, checking that every reference resolves in both themes. |
|
|
117
|
-
| `scripts/tokens/css.mjs` | DTCG files → `tokens.css`, with Style Dictionary and a `rove/css` format: Dark on `:root`, what differs in Light on `:root.theme-light`, each text style as four `--type-*` variables (letter spacing included). |
|
|
118
|
-
| `scripts/tokens/text-styles.mjs` | DTCG text styles → `text-styles.css`: a `.type-<style>` class per style that reads its `--type-*` variables. |
|
|
119
|
-
| `scripts/tokens/
|
|
120
|
-
| `
|
|
121
|
-
|
|
122
|
-
|
|
175
|
+
| `scripts/tokens/figma-to-dtcg.mjs` | Figma export → the DTCG files in `tokens/`, checking that every reference resolves in both themes. |
|
|
176
|
+
| `scripts/tokens/dtcg-to-css.mjs` | DTCG files → `tokens.css`, with Style Dictionary and a `rove/css` format: Dark on `:root`, what differs in Light on `:root.theme-light`, each text style as four `--type-*` variables (letter spacing included). |
|
|
177
|
+
| `scripts/tokens/dtcg-to-text-styles.mjs` | DTCG text styles → `text-styles.css`: a `.type-<style>` class per style that reads its `--type-*` variables. |
|
|
178
|
+
| `scripts/tokens/token-reference.mjs` | Figma export and `tokens.css` → the token reference in `DESIGN.md`: every token by name and Figma description, with values for the scales (spacing, radius, type, opacity) but not the colours, so nobody copies a hex. |
|
|
179
|
+
| `DESIGN.md` | How to build Rove UI with the tokens. The rules at the top are written by hand; the token reference below the marker line is generated by the build. |
|
|
180
|
+
|
|
181
|
+
**Storybook and slideshow**
|
|
182
|
+
|
|
183
|
+
| Path | What |
|
|
184
|
+
| --- | --- |
|
|
185
|
+
| `.storybook/` | The Rove Tokens Storybook's config, and the Inter, Questrial and Geist Mono files it bundles. |
|
|
123
186
|
| `stories/` | Its pages, one file per sidebar group. `tokens.js` reads the DTCG files. |
|
|
187
|
+
| `scripts/presentation/export.mjs` | `npm run present`: exports the Figma file's pages to `presentation/index.html`, a slideshow styled with the tokens. Needs `FIGMA_TOKEN` (a Figma personal access token, `file_content:read`) in `.env.local`. |
|
|
124
188
|
| `scripts/presentation/publish.mjs` | `npm run present:publish`: pushes the exported presentation to the `gh-pages` branch, which GitHub Pages serves at <https://swiftsolve.github.io/rove-tokens/>. Each publish replaces the last. |
|
|
125
|
-
| `.github/workflows/presentation.yml` | Runs the export and publish on every `v*` tag, or by hand. Needs the `FIGMA_TOKEN` repository secret. |
|
|
126
|
-
| `docs/rationale.md` | Why the values are what they are (contrast targets, theme choices). |
|
|
127
189
|
|
|
128
|
-
|
|
190
|
+
**Workflows and docs**
|
|
191
|
+
|
|
192
|
+
A release tag is the `v1.2.0`-style git tag that `npm version` creates and `git push --follow-tags` pushes (see [Release](#-release)).
|
|
193
|
+
|
|
194
|
+
| Path | What |
|
|
195
|
+
| --- | --- |
|
|
196
|
+
| `.github/workflows/build.yml` | On each release tag, builds the tokens and checks `DESIGN.md` was rebuilt and committed. Run it by hand from Actions to check `main`. |
|
|
197
|
+
| `.github/workflows/publish.yml` | On each release tag, publishes that version to npm with trusted publishing, so the repo holds no npm token. |
|
|
198
|
+
| `.github/workflows/presentation.yml` | On each release tag, or by hand from Actions, exports the slideshow from Figma and publishes it. Needs the `FIGMA_TOKEN` repository secret. |
|
|
199
|
+
| `docs/rationale.md` | Why the values are what they are (contrast targets, theme choices). |
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@swiftsolve/rove-tokens",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.2.0",
|
|
4
4
|
"description": "Rove's design tokens, exported from the Rove Design System in Figma, as CSS and DTCG.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"license": "UNLICENSED",
|
|
@@ -24,7 +24,6 @@
|
|
|
24
24
|
"scripts": {
|
|
25
25
|
"build": "node scripts/tokens/build.mjs",
|
|
26
26
|
"present": "npm run build && node scripts/presentation/export.mjs",
|
|
27
|
-
"present:open": "node scripts/presentation/open.mjs",
|
|
28
27
|
"present:publish": "node scripts/presentation/publish.mjs",
|
|
29
28
|
"prepare": "npm run build",
|
|
30
29
|
"storybook": "storybook dev -p 6007",
|
package/src/code-tokens.json
CHANGED
|
@@ -9,29 +9,12 @@
|
|
|
9
9
|
"--shadow-raised": "0 12px 32px {shadow-color/raised}",
|
|
10
10
|
"--shadow-popover": "0 2px 6px {shadow-color/popover-1}, 0 6px 16px {shadow-color/popover-2}",
|
|
11
11
|
|
|
12
|
-
"--focus-ring-width": "1px",
|
|
13
12
|
"--focus-outline": "var(--focus-ring-width) solid var(--focus-ring)",
|
|
14
13
|
"--focus-inset": "calc(-1 * var(--focus-ring-width))",
|
|
15
14
|
|
|
16
|
-
"--titlebar-height": "56px",
|
|
17
|
-
"--rail-item-size": "38px",
|
|
18
|
-
|
|
19
|
-
"--card-padding": "var(--spacing-14)",
|
|
20
|
-
"--card-header-padding-y": "var(--card-padding)",
|
|
21
|
-
"--card-header-padding-x": "var(--card-padding)",
|
|
22
|
-
"--card-header-min-height": "42px",
|
|
23
|
-
"--card-header-height": "44px",
|
|
24
|
-
"--card-body-padding": "var(--card-padding)",
|
|
25
|
-
"--row-padding-y": "8px",
|
|
26
|
-
|
|
27
15
|
"--ease-out": "cubic-bezier(0.16, 1, 0.3, 1)",
|
|
28
16
|
"--ease-in-out": "cubic-bezier(0.4, 0, 0.2, 1)",
|
|
29
17
|
"--ease-pulse": "cubic-bezier(0.42, 0, 0.58, 1)",
|
|
30
|
-
"--
|
|
31
|
-
"--duration-normal": "220ms",
|
|
32
|
-
|
|
33
|
-
"--weight-regular": "400",
|
|
34
|
-
"--weight-medium": "500",
|
|
35
|
-
"--weight-semibold": "600"
|
|
18
|
+
"--ease-spring": "linear(0, 0.1896, 0.4943, 0.7351, 0.8834, 0.9602, 0.9936, 1.0046, 1.0062, 1.0047, 1.0028, 1.0014, 1.0006, 1, 1)"
|
|
36
19
|
}
|
|
37
20
|
}
|
package/src/figma/variables.json
CHANGED
|
@@ -56,6 +56,18 @@
|
|
|
56
56
|
"modes": [
|
|
57
57
|
"Value"
|
|
58
58
|
]
|
|
59
|
+
},
|
|
60
|
+
{
|
|
61
|
+
"name": "Layout",
|
|
62
|
+
"modes": [
|
|
63
|
+
"Value"
|
|
64
|
+
]
|
|
65
|
+
},
|
|
66
|
+
{
|
|
67
|
+
"name": "Motion",
|
|
68
|
+
"modes": [
|
|
69
|
+
"Value"
|
|
70
|
+
]
|
|
59
71
|
}
|
|
60
72
|
],
|
|
61
73
|
"variables": [
|
|
@@ -1902,6 +1914,174 @@
|
|
|
1902
1914
|
"alias": "neutral/850-a2"
|
|
1903
1915
|
}
|
|
1904
1916
|
}
|
|
1917
|
+
},
|
|
1918
|
+
{
|
|
1919
|
+
"name": "titlebar/height",
|
|
1920
|
+
"collection": "Layout",
|
|
1921
|
+
"type": "FLOAT",
|
|
1922
|
+
"code": "var(--titlebar-height)",
|
|
1923
|
+
"description": "Title bar",
|
|
1924
|
+
"values": {
|
|
1925
|
+
"Value": 56
|
|
1926
|
+
}
|
|
1927
|
+
},
|
|
1928
|
+
{
|
|
1929
|
+
"name": "rail/item-size",
|
|
1930
|
+
"collection": "Layout",
|
|
1931
|
+
"type": "FLOAT",
|
|
1932
|
+
"code": "var(--rail-item-size)",
|
|
1933
|
+
"description": "Rail items",
|
|
1934
|
+
"values": {
|
|
1935
|
+
"Value": 38
|
|
1936
|
+
}
|
|
1937
|
+
},
|
|
1938
|
+
{
|
|
1939
|
+
"name": "card/padding",
|
|
1940
|
+
"collection": "Layout",
|
|
1941
|
+
"type": "FLOAT",
|
|
1942
|
+
"code": "var(--card-padding)",
|
|
1943
|
+
"description": "Card inset",
|
|
1944
|
+
"values": {
|
|
1945
|
+
"Value": {
|
|
1946
|
+
"alias": "spacing/14"
|
|
1947
|
+
}
|
|
1948
|
+
}
|
|
1949
|
+
},
|
|
1950
|
+
{
|
|
1951
|
+
"name": "card/header-padding-y",
|
|
1952
|
+
"collection": "Layout",
|
|
1953
|
+
"type": "FLOAT",
|
|
1954
|
+
"code": "var(--card-header-padding-y)",
|
|
1955
|
+
"description": "",
|
|
1956
|
+
"values": {
|
|
1957
|
+
"Value": {
|
|
1958
|
+
"alias": "card/padding"
|
|
1959
|
+
}
|
|
1960
|
+
}
|
|
1961
|
+
},
|
|
1962
|
+
{
|
|
1963
|
+
"name": "card/header-padding-x",
|
|
1964
|
+
"collection": "Layout",
|
|
1965
|
+
"type": "FLOAT",
|
|
1966
|
+
"code": "var(--card-header-padding-x)",
|
|
1967
|
+
"description": "",
|
|
1968
|
+
"values": {
|
|
1969
|
+
"Value": {
|
|
1970
|
+
"alias": "card/padding"
|
|
1971
|
+
}
|
|
1972
|
+
}
|
|
1973
|
+
},
|
|
1974
|
+
{
|
|
1975
|
+
"name": "card/header-min-height",
|
|
1976
|
+
"collection": "Layout",
|
|
1977
|
+
"type": "FLOAT",
|
|
1978
|
+
"code": "var(--card-header-min-height)",
|
|
1979
|
+
"description": "Compact card header",
|
|
1980
|
+
"values": {
|
|
1981
|
+
"Value": 42
|
|
1982
|
+
}
|
|
1983
|
+
},
|
|
1984
|
+
{
|
|
1985
|
+
"name": "card/header-height",
|
|
1986
|
+
"collection": "Layout",
|
|
1987
|
+
"type": "FLOAT",
|
|
1988
|
+
"code": "var(--card-header-height)",
|
|
1989
|
+
"description": "Card header",
|
|
1990
|
+
"values": {
|
|
1991
|
+
"Value": 44
|
|
1992
|
+
}
|
|
1993
|
+
},
|
|
1994
|
+
{
|
|
1995
|
+
"name": "card/body-padding",
|
|
1996
|
+
"collection": "Layout",
|
|
1997
|
+
"type": "FLOAT",
|
|
1998
|
+
"code": "var(--card-body-padding)",
|
|
1999
|
+
"description": "",
|
|
2000
|
+
"values": {
|
|
2001
|
+
"Value": {
|
|
2002
|
+
"alias": "card/padding"
|
|
2003
|
+
}
|
|
2004
|
+
}
|
|
2005
|
+
},
|
|
2006
|
+
{
|
|
2007
|
+
"name": "row/padding-y",
|
|
2008
|
+
"collection": "Layout",
|
|
2009
|
+
"type": "FLOAT",
|
|
2010
|
+
"code": "var(--row-padding-y)",
|
|
2011
|
+
"description": "Data row, above and below",
|
|
2012
|
+
"values": {
|
|
2013
|
+
"Value": 8
|
|
2014
|
+
}
|
|
2015
|
+
},
|
|
2016
|
+
{
|
|
2017
|
+
"name": "focus/ring-width",
|
|
2018
|
+
"collection": "Spacing",
|
|
2019
|
+
"type": "FLOAT",
|
|
2020
|
+
"code": "var(--focus-ring-width)",
|
|
2021
|
+
"description": "Focus ring stroke",
|
|
2022
|
+
"values": {
|
|
2023
|
+
"Value": 1
|
|
2024
|
+
}
|
|
2025
|
+
},
|
|
2026
|
+
{
|
|
2027
|
+
"name": "weight/regular",
|
|
2028
|
+
"collection": "Typography",
|
|
2029
|
+
"type": "FLOAT",
|
|
2030
|
+
"code": "var(--weight-regular)",
|
|
2031
|
+
"description": "",
|
|
2032
|
+
"values": {
|
|
2033
|
+
"Value": 400
|
|
2034
|
+
}
|
|
2035
|
+
},
|
|
2036
|
+
{
|
|
2037
|
+
"name": "weight/medium",
|
|
2038
|
+
"collection": "Typography",
|
|
2039
|
+
"type": "FLOAT",
|
|
2040
|
+
"code": "var(--weight-medium)",
|
|
2041
|
+
"description": "",
|
|
2042
|
+
"values": {
|
|
2043
|
+
"Value": 500
|
|
2044
|
+
}
|
|
2045
|
+
},
|
|
2046
|
+
{
|
|
2047
|
+
"name": "weight/semibold",
|
|
2048
|
+
"collection": "Typography",
|
|
2049
|
+
"type": "FLOAT",
|
|
2050
|
+
"code": "var(--weight-semibold)",
|
|
2051
|
+
"description": "",
|
|
2052
|
+
"values": {
|
|
2053
|
+
"Value": 600
|
|
2054
|
+
}
|
|
2055
|
+
},
|
|
2056
|
+
{
|
|
2057
|
+
"name": "duration/fast",
|
|
2058
|
+
"collection": "Motion",
|
|
2059
|
+
"type": "FLOAT",
|
|
2060
|
+
"code": "var(--duration-fast)",
|
|
2061
|
+
"description": "Hovers, small changes",
|
|
2062
|
+
"values": {
|
|
2063
|
+
"Value": 140
|
|
2064
|
+
}
|
|
2065
|
+
},
|
|
2066
|
+
{
|
|
2067
|
+
"name": "duration/normal",
|
|
2068
|
+
"collection": "Motion",
|
|
2069
|
+
"type": "FLOAT",
|
|
2070
|
+
"code": "var(--duration-normal)",
|
|
2071
|
+
"description": "Panels, page changes",
|
|
2072
|
+
"values": {
|
|
2073
|
+
"Value": 220
|
|
2074
|
+
}
|
|
2075
|
+
},
|
|
2076
|
+
{
|
|
2077
|
+
"name": "duration/spring",
|
|
2078
|
+
"collection": "Motion",
|
|
2079
|
+
"type": "FLOAT",
|
|
2080
|
+
"code": "var(--duration-spring)",
|
|
2081
|
+
"description": "A spring’s full run",
|
|
2082
|
+
"values": {
|
|
2083
|
+
"Value": 450
|
|
2084
|
+
}
|
|
1905
2085
|
}
|
|
1906
2086
|
]
|
|
1907
2087
|
}
|
package/text-styles.css
CHANGED
package/tokens/code.tokens.json
CHANGED
|
@@ -107,68 +107,14 @@
|
|
|
107
107
|
}
|
|
108
108
|
]
|
|
109
109
|
},
|
|
110
|
-
"focus-ring-width": {
|
|
111
|
-
"$type": "dimension",
|
|
112
|
-
"$value": {
|
|
113
|
-
"value": 1,
|
|
114
|
-
"unit": "px"
|
|
115
|
-
}
|
|
116
|
-
},
|
|
117
110
|
"focus-outline": {
|
|
118
111
|
"$type": "border",
|
|
119
112
|
"$value": {
|
|
120
|
-
"width": "{focus
|
|
113
|
+
"width": "{focus.ring-width}",
|
|
121
114
|
"style": "solid",
|
|
122
115
|
"color": "{focus.ring}"
|
|
123
116
|
}
|
|
124
117
|
},
|
|
125
|
-
"titlebar-height": {
|
|
126
|
-
"$type": "dimension",
|
|
127
|
-
"$value": {
|
|
128
|
-
"value": 56,
|
|
129
|
-
"unit": "px"
|
|
130
|
-
}
|
|
131
|
-
},
|
|
132
|
-
"rail-item-size": {
|
|
133
|
-
"$type": "dimension",
|
|
134
|
-
"$value": {
|
|
135
|
-
"value": 38,
|
|
136
|
-
"unit": "px"
|
|
137
|
-
}
|
|
138
|
-
},
|
|
139
|
-
"card-padding": {
|
|
140
|
-
"$value": "{spacing.14}"
|
|
141
|
-
},
|
|
142
|
-
"card-header-padding-y": {
|
|
143
|
-
"$value": "{card-padding}"
|
|
144
|
-
},
|
|
145
|
-
"card-header-padding-x": {
|
|
146
|
-
"$value": "{card-padding}"
|
|
147
|
-
},
|
|
148
|
-
"card-header-min-height": {
|
|
149
|
-
"$type": "dimension",
|
|
150
|
-
"$value": {
|
|
151
|
-
"value": 42,
|
|
152
|
-
"unit": "px"
|
|
153
|
-
}
|
|
154
|
-
},
|
|
155
|
-
"card-header-height": {
|
|
156
|
-
"$type": "dimension",
|
|
157
|
-
"$value": {
|
|
158
|
-
"value": 44,
|
|
159
|
-
"unit": "px"
|
|
160
|
-
}
|
|
161
|
-
},
|
|
162
|
-
"card-body-padding": {
|
|
163
|
-
"$value": "{card-padding}"
|
|
164
|
-
},
|
|
165
|
-
"row-padding-y": {
|
|
166
|
-
"$type": "dimension",
|
|
167
|
-
"$value": {
|
|
168
|
-
"value": 8,
|
|
169
|
-
"unit": "px"
|
|
170
|
-
}
|
|
171
|
-
},
|
|
172
118
|
"ease-out": {
|
|
173
119
|
"$type": "cubicBezier",
|
|
174
120
|
"$value": [
|
|
@@ -195,31 +141,5 @@
|
|
|
195
141
|
0.58,
|
|
196
142
|
1
|
|
197
143
|
]
|
|
198
|
-
},
|
|
199
|
-
"duration-fast": {
|
|
200
|
-
"$type": "duration",
|
|
201
|
-
"$value": {
|
|
202
|
-
"value": 140,
|
|
203
|
-
"unit": "ms"
|
|
204
|
-
}
|
|
205
|
-
},
|
|
206
|
-
"duration-normal": {
|
|
207
|
-
"$type": "duration",
|
|
208
|
-
"$value": {
|
|
209
|
-
"value": 220,
|
|
210
|
-
"unit": "ms"
|
|
211
|
-
}
|
|
212
|
-
},
|
|
213
|
-
"weight-regular": {
|
|
214
|
-
"$type": "fontWeight",
|
|
215
|
-
"$value": 400
|
|
216
|
-
},
|
|
217
|
-
"weight-medium": {
|
|
218
|
-
"$type": "fontWeight",
|
|
219
|
-
"$value": 500
|
|
220
|
-
},
|
|
221
|
-
"weight-semibold": {
|
|
222
|
-
"$type": "fontWeight",
|
|
223
|
-
"$value": 600
|
|
224
144
|
}
|
|
225
145
|
}
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
{
|
|
2
|
+
"titlebar": {
|
|
3
|
+
"height": {
|
|
4
|
+
"$type": "dimension",
|
|
5
|
+
"$value": {
|
|
6
|
+
"value": 56,
|
|
7
|
+
"unit": "px"
|
|
8
|
+
},
|
|
9
|
+
"$description": "Title bar"
|
|
10
|
+
}
|
|
11
|
+
},
|
|
12
|
+
"rail": {
|
|
13
|
+
"item-size": {
|
|
14
|
+
"$type": "dimension",
|
|
15
|
+
"$value": {
|
|
16
|
+
"value": 38,
|
|
17
|
+
"unit": "px"
|
|
18
|
+
},
|
|
19
|
+
"$description": "Rail items"
|
|
20
|
+
}
|
|
21
|
+
},
|
|
22
|
+
"card": {
|
|
23
|
+
"padding": {
|
|
24
|
+
"$type": "dimension",
|
|
25
|
+
"$value": "{spacing.14}",
|
|
26
|
+
"$description": "Card inset"
|
|
27
|
+
},
|
|
28
|
+
"header-padding-y": {
|
|
29
|
+
"$type": "dimension",
|
|
30
|
+
"$value": "{card.padding}"
|
|
31
|
+
},
|
|
32
|
+
"header-padding-x": {
|
|
33
|
+
"$type": "dimension",
|
|
34
|
+
"$value": "{card.padding}"
|
|
35
|
+
},
|
|
36
|
+
"header-min-height": {
|
|
37
|
+
"$type": "dimension",
|
|
38
|
+
"$value": {
|
|
39
|
+
"value": 42,
|
|
40
|
+
"unit": "px"
|
|
41
|
+
},
|
|
42
|
+
"$description": "Compact card header"
|
|
43
|
+
},
|
|
44
|
+
"header-height": {
|
|
45
|
+
"$type": "dimension",
|
|
46
|
+
"$value": {
|
|
47
|
+
"value": 44,
|
|
48
|
+
"unit": "px"
|
|
49
|
+
},
|
|
50
|
+
"$description": "Card header"
|
|
51
|
+
},
|
|
52
|
+
"body-padding": {
|
|
53
|
+
"$type": "dimension",
|
|
54
|
+
"$value": "{card.padding}"
|
|
55
|
+
}
|
|
56
|
+
},
|
|
57
|
+
"row": {
|
|
58
|
+
"padding-y": {
|
|
59
|
+
"$type": "dimension",
|
|
60
|
+
"$value": {
|
|
61
|
+
"value": 8,
|
|
62
|
+
"unit": "px"
|
|
63
|
+
},
|
|
64
|
+
"$description": "Data row, above and below"
|
|
65
|
+
}
|
|
66
|
+
}
|
|
67
|
+
}
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
{
|
|
2
|
+
"duration": {
|
|
3
|
+
"fast": {
|
|
4
|
+
"$type": "duration",
|
|
5
|
+
"$value": {
|
|
6
|
+
"value": 140,
|
|
7
|
+
"unit": "ms"
|
|
8
|
+
},
|
|
9
|
+
"$description": "Hovers, small changes"
|
|
10
|
+
},
|
|
11
|
+
"normal": {
|
|
12
|
+
"$type": "duration",
|
|
13
|
+
"$value": {
|
|
14
|
+
"value": 220,
|
|
15
|
+
"unit": "ms"
|
|
16
|
+
},
|
|
17
|
+
"$description": "Panels, page changes"
|
|
18
|
+
},
|
|
19
|
+
"spring": {
|
|
20
|
+
"$type": "duration",
|
|
21
|
+
"$value": {
|
|
22
|
+
"value": 450,
|
|
23
|
+
"unit": "ms"
|
|
24
|
+
},
|
|
25
|
+
"$description": "A spring’s full run"
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
}
|
|
@@ -78,5 +78,19 @@
|
|
|
78
78
|
"sans-serif"
|
|
79
79
|
]
|
|
80
80
|
}
|
|
81
|
+
},
|
|
82
|
+
"weight": {
|
|
83
|
+
"regular": {
|
|
84
|
+
"$type": "fontWeight",
|
|
85
|
+
"$value": 400
|
|
86
|
+
},
|
|
87
|
+
"medium": {
|
|
88
|
+
"$type": "fontWeight",
|
|
89
|
+
"$value": 500
|
|
90
|
+
},
|
|
91
|
+
"semibold": {
|
|
92
|
+
"$type": "fontWeight",
|
|
93
|
+
"$value": 600
|
|
94
|
+
}
|
|
81
95
|
}
|
|
82
96
|
}
|
package/tokens.css
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
/* @swiftsolve/rove-tokens 1.
|
|
1
|
+
/* @swiftsolve/rove-tokens 1.2.0. Generated from Figma by scripts/tokens/build.mjs; do not edit. */
|
|
2
2
|
:root {
|
|
3
3
|
/* Color */
|
|
4
4
|
--bg-base: #0b0b0c; /* Backdrop */
|
|
@@ -44,6 +44,7 @@
|
|
|
44
44
|
|
|
45
45
|
/* Spacing */
|
|
46
46
|
--focus-offset: 2px; /* Focus ring offset */
|
|
47
|
+
--focus-ring-width: 1px; /* Focus ring stroke */
|
|
47
48
|
--spacing-2: 2px;
|
|
48
49
|
--spacing-4: 4px;
|
|
49
50
|
--spacing-6: 6px;
|
|
@@ -70,6 +71,9 @@
|
|
|
70
71
|
--font-size-3xl: 28px;
|
|
71
72
|
--font-family-sans: 'Inter', system-ui, -apple-system, 'Segoe UI', sans-serif;
|
|
72
73
|
--font-family-numeric: 'Questrial', ui-sans-serif, system-ui, sans-serif;
|
|
74
|
+
--weight-regular: 400;
|
|
75
|
+
--weight-medium: 500;
|
|
76
|
+
--weight-semibold: 600;
|
|
73
77
|
|
|
74
78
|
/* Opacity */
|
|
75
79
|
--opacity-tint-xs: 8%; /* Faintest tint */
|
|
@@ -80,30 +84,32 @@
|
|
|
80
84
|
--opacity-high: 80%; /* Nearly opaque */
|
|
81
85
|
--opacity-disabled: 40%; /* Disabled controls */
|
|
82
86
|
|
|
87
|
+
/* Layout */
|
|
88
|
+
--titlebar-height: 56px; /* Title bar */
|
|
89
|
+
--rail-item-size: 38px; /* Rail items */
|
|
90
|
+
--card-padding: var(--spacing-14); /* Card inset */
|
|
91
|
+
--card-header-padding-y: var(--card-padding);
|
|
92
|
+
--card-header-padding-x: var(--card-padding);
|
|
93
|
+
--card-header-min-height: 42px; /* Compact card header */
|
|
94
|
+
--card-header-height: 44px; /* Card header */
|
|
95
|
+
--card-body-padding: var(--card-padding);
|
|
96
|
+
--row-padding-y: 8px; /* Data row, above and below */
|
|
97
|
+
|
|
98
|
+
/* Motion */
|
|
99
|
+
--duration-fast: 140ms; /* Hovers, small changes */
|
|
100
|
+
--duration-normal: 220ms; /* Panels, page changes */
|
|
101
|
+
--duration-spring: 450ms; /* A spring’s full run */
|
|
102
|
+
|
|
83
103
|
/* Code-only */
|
|
84
104
|
--shadow-panel: 0 1px 2px rgba(0, 0, 0, 0.22), 0 4px 12px rgba(0, 0, 0, 0.1);
|
|
85
105
|
--shadow-raised: 0 12px 32px rgba(0, 0, 0, 0.22);
|
|
86
106
|
--shadow-popover: 0 2px 6px rgba(0, 0, 0, 0.22), 0 6px 16px rgba(0, 0, 0, 0.22);
|
|
87
|
-
--focus-ring-width: 1px;
|
|
88
107
|
--focus-outline: var(--focus-ring-width) solid var(--focus-ring);
|
|
89
|
-
--titlebar-height: 56px;
|
|
90
|
-
--rail-item-size: 38px;
|
|
91
|
-
--card-padding: var(--spacing-14);
|
|
92
|
-
--card-header-padding-y: var(--card-padding);
|
|
93
|
-
--card-header-padding-x: var(--card-padding);
|
|
94
|
-
--card-header-min-height: 42px;
|
|
95
|
-
--card-header-height: 44px;
|
|
96
|
-
--card-body-padding: var(--card-padding);
|
|
97
|
-
--row-padding-y: 8px;
|
|
98
108
|
--ease-out: cubic-bezier(0.16, 1, 0.3, 1);
|
|
99
109
|
--ease-in-out: cubic-bezier(0.4, 0, 0.2, 1);
|
|
100
110
|
--ease-pulse: cubic-bezier(0.42, 0, 0.58, 1);
|
|
101
|
-
--duration-fast: 140ms;
|
|
102
|
-
--duration-normal: 220ms;
|
|
103
|
-
--weight-regular: 400;
|
|
104
|
-
--weight-medium: 500;
|
|
105
|
-
--weight-semibold: 600;
|
|
106
111
|
--focus-inset: calc(-1 * var(--focus-ring-width));
|
|
112
|
+
--ease-spring: linear(0, 0.1896, 0.4943, 0.7351, 0.8834, 0.9602, 0.9936, 1.0046, 1.0062, 1.0047, 1.0028, 1.0014, 1.0006, 1, 1);
|
|
107
113
|
|
|
108
114
|
/* Type styles */
|
|
109
115
|
--type-heading-large-size: var(--font-size-2xl);
|