@fusion.dev/helix-docs 0.131.0 → 0.133.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.
@@ -206,6 +206,25 @@ frame.addEventListener('helix-graph-filter', (event) => {
206
206
  The legend is drawn where the notes have two groups or more. On a frame
207
207
  narrower than 40rem it is one row, which scrolls.
208
208
 
209
+ ## Find groups in the links
210
+
211
+ Notes without a `group` are drawn in one color. Where your data has no groups,
212
+ `groupByCommunity` finds them in the links: notes that link mostly to each other
213
+ become one group, named after its most linked note. Hand its result to the frame,
214
+ and the drawing colors the groups and the legend names them:
215
+
216
+ ```ts
217
+ import { groupByCommunity } from '@fusion.dev/helix-graph'
218
+
219
+ frame.nodes = groupByCommunity(notes, links)
220
+ frame.links = links
221
+ ```
222
+
223
+ A note that has a `group` keeps it. Communities of fewer than three notes share
224
+ one group, named `Other`. Set `fewest` and `rest` to change either. The same
225
+ notes and links give the same groups every time. On 20,000 notes it takes about
226
+ 65 milliseconds.
227
+
209
228
  ## Select a note
210
229
 
211
230
  Pressing a note selects it, and pressing where no note is clears the selection.
@@ -28,7 +28,8 @@ computed from `brand` or from the Helix design language. A theme that sets only
28
28
  |---|---|
29
29
  | `brand` | Your main brand color. Required |
30
30
  | `accent` | The second emphasis color. Defaults to the brand color. `{ from: 'brand', rotate: 180 }` gives the complementary color |
31
- | `neutral` | The gray ramp, which can be tinted toward the brand |
31
+ | `background` | The page's color, `{ light, dark }`, for a page that is not pure white or pure black. The surfaces keep their contrast with it, and the grays take its tint. A page no text color can reach the contrast target on is refused |
32
+ | `neutral` | The gray ramp, which can be tinted toward the brand. With `background`, it takes the page's tint |
32
33
  | `status` | `info`, `success`, `warning`, and `danger`. A color pins one. An object adjusts its hue while it keeps its meaning |
33
34
  | `chroma` | How saturated the palette is, independent of hue |
34
35
  | `scheme` | `'light'` or `'dark'`, for a theme that has only one mode |
@@ -58,10 +58,10 @@ either barrel. The per-component tables show what your page pays.
58
58
  | Package | Raw | Gzip | Brotli | |
59
59
  |---|---|---|---|---|
60
60
  | `@fusion.dev/helix-core` | 183,735 | 58,230 | 49,473 | The element base class, mixins, decorators, and floating positioning. |
61
- | `@fusion.dev/helix-headless` | 745,966 | 193,214 | 149,903 | Every headless family. The barrel entry includes all of them. |
61
+ | `@fusion.dev/helix-headless` | 746,304 | 193,314 | 149,776 | Every headless family. The barrel entry includes all of them. |
62
62
  | `@fusion.dev/helix-icons` | 55,565 | 17,727 | 14,864 | The whole glyph set. |
63
63
  | `@fusion.dev/helix-theme` | 3,626 | 1,597 | 1,384 | The derivation engine. Most sites run it at build time, and a theme switcher runs it in the browser. |
64
- | `@fusion.dev/helix` | 1,291,029 | 301,797 | 220,733 | Every styled family. |
64
+ | `@fusion.dev/helix` | 1,291,679 | 302,007 | 220,657 | Every styled family. |
65
65
  | `lit` | 15,394 | 6,118 | 5,460 | Lit itself, listed so you can subtract it from every row above. |
66
66
 
67
67
  ## Stylesheets
@@ -84,11 +84,11 @@ shows the whole cost of using the base layer on its own.
84
84
 
85
85
  **Most of your first component is the shared runtime.** The median styled family is 21,372 bytes gzipped alone, and it adds 2,254 to a page that already has Helix. The shared runtime is 89 percent of the first component, and the component itself is 11 percent. Ten typical components cost the first number once, plus nine of the added number. The two columns in the tables below let you work that out for your own components.
86
86
 
87
- Across the 104 styled components, the smallest is `code` at 9,928 bytes gzipped alone, and the largest is `data-table` at 63,813. Every family together is 301,797.
87
+ Across the 104 styled components, the smallest is `code` at 9,928 bytes gzipped alone, and the largest is `data-table` at 63,813. Every family together is 302,007.
88
88
 
89
- No family imports a barrel. The `barrels` rule in `fusion workspace` enforces that. `@fusion.dev/helix-headless` marks every module in `dist` as having side effects, which is true of a file that calls `customElements.define`. A bundler can remove none of it. One `import { HelixHeadlessButton } from '@fusion.dev/helix-headless'` costs 193,214 bytes gzipped, whatever else the page imports. That is 9 times the median family above. All 104 styled families import the headless family they extend directly. The rule checks the shape of the import, so it applies to any package that sets `sideEffects`, whatever its name.
89
+ No family imports a barrel. The `barrels` rule in `fusion workspace` enforces that. `@fusion.dev/helix-headless` marks every module in `dist` as having side effects, which is true of a file that calls `customElements.define`. A bundler can remove none of it. One `import { HelixHeadlessButton } from '@fusion.dev/helix-headless'` costs 193,314 bytes gzipped, whatever else the page imports. That is 9 times the median family above. All 104 styled families import the headless family they extend directly. The rule checks the shape of the import, so it applies to any package that sets `sideEffects`, whatever its name.
90
90
 
91
- The headless tier never had the problem, so it serves as the control. `@fusion.dev/helix-core` is `sideEffects: false`, and the median headless family is 21,928 bytes gzipped alone.
91
+ The headless tier never had the problem, so it serves as the control. `@fusion.dev/helix-core` is `sideEffects: false`, and the median headless family is 21,942 bytes gzipped alone.
92
92
 
93
93
  ## Compared with other systems
94
94
 
@@ -100,7 +100,7 @@ The table has no whole-library row. That row would compare how many components e
100
100
 
101
101
  | Component | System | Raw | Gzip | Brotli |
102
102
  |---|---|---|---|---|
103
- | `button` | **Helix** | 43,806 | 12,554 | 11,023 |
103
+ | `button` | **Helix** | 43,982 | 12,620 | 11,082 |
104
104
  | | Carbon | 133,058 | 20,959 | 17,685 |
105
105
  | | Material Web | 47,060 | 14,173 | 12,591 |
106
106
  | | Shoelace | 62,628 | 18,287 | 15,805 |
@@ -189,7 +189,7 @@ Structure, accessibility, state, and form participation. It has no presentation
189
189
  | `bar-chart` | 81,076 | 26,555 | 23,488 | 12,644 | 3,701 | 3,035 |
190
190
  | `blockquote` | 33,053 | 10,175 | 8,938 | 774 | 176 | 128 |
191
191
  | `breadcrumbs` | 88,957 | 28,651 | 23,520 | 1,965 | 451 | 379 |
192
- | `button` | 37,713 | 11,437 | 10,046 | 3,182 | 812 | 670 |
192
+ | `button` | 37,725 | 11,440 | 10,034 | 3,194 | 814 | 619 |
193
193
  | `button-group` | 32,909 | 10,061 | 8,843 | 661 | 137 | 34 |
194
194
  | `callout` | 88,077 | 28,508 | 23,396 | 914 | 233 | 168 |
195
195
  | `canvas` | 94,126 | 27,730 | 24,309 | 50,034 | 14,930 | 12,613 |
@@ -199,14 +199,14 @@ Structure, accessibility, state, and form participation. It has no presentation
199
199
  | `checkbox` | 42,424 | 12,472 | 10,962 | 2,703 | 748 | 514 |
200
200
  | `checkbox-group` | 45,548 | 13,159 | 11,549 | 5,307 | 1,316 | 1,017 |
201
201
  | `code` | 31,528 | 9,644 | 8,470 | 451 | 77 | -1 |
202
- | `code-block` | 133,803 | 43,664 | 36,792 | 17,288 | 4,490 | 3,847 |
203
- | `color-input` | 151,779 | 47,718 | 40,233 | 25,691 | 5,998 | 4,976 |
204
- | `color-picker` | 118,224 | 37,113 | 30,494 | 19,588 | 4,689 | 3,874 |
205
- | `combobox` | 146,691 | 46,408 | 38,900 | 21,146 | 5,230 | 4,258 |
202
+ | `code-block` | 133,832 | 43,676 | 36,796 | 17,317 | 4,502 | 3,798 |
203
+ | `color-input` | 151,907 | 47,747 | 40,241 | 25,819 | 6,027 | 5,016 |
204
+ | `color-picker` | 118,278 | 37,129 | 30,542 | 19,642 | 4,706 | 4,026 |
205
+ | `combobox` | 146,722 | 46,415 | 38,946 | 21,177 | 5,239 | 4,380 |
206
206
  | `command` | 116,641 | 36,394 | 29,750 | 18,065 | 4,588 | 3,719 |
207
- | `copy-button` | 128,401 | 42,039 | 35,305 | 11,883 | 2,933 | 2,322 |
207
+ | `copy-button` | 128,413 | 42,045 | 35,300 | 11,895 | 2,938 | 2,421 |
208
208
  | `data-table` | 186,894 | 56,878 | 48,021 | 57,295 | 14,485 | 11,997 |
209
- | `date-input` | 144,949 | 45,900 | 38,587 | 19,177 | 4,830 | 4,067 |
209
+ | `date-input` | 144,981 | 45,912 | 38,562 | 19,209 | 4,845 | 4,000 |
210
210
  | `date-picker` | 100,136 | 32,351 | 26,467 | 9,900 | 2,714 | 2,336 |
211
211
  | `description-list` | 33,012 | 10,012 | 8,793 | 1,132 | 182 | 155 |
212
212
  | `dialog` | 36,561 | 11,114 | 9,752 | 2,717 | 765 | 587 |
@@ -215,13 +215,13 @@ Structure, accessibility, state, and form participation. It has no presentation
215
215
  | `drawer` | 35,314 | 10,755 | 9,427 | 1,761 | 466 | 446 |
216
216
  | `drilldown` | 97,002 | 31,492 | 25,596 | 5,704 | 1,481 | 1,170 |
217
217
  | `empty` | 33,506 | 10,310 | 9,098 | 956 | 233 | 140 |
218
- | `file-input` | 100,449 | 32,330 | 26,417 | 6,215 | 1,787 | 1,429 |
218
+ | `file-input` | 100,500 | 32,345 | 26,387 | 6,266 | 1,803 | 1,479 |
219
219
  | `filter-input` | 157,243 | 49,107 | 41,347 | 28,023 | 6,779 | 5,542 |
220
220
  | `format-date` | 36,522 | 11,235 | 9,940 | 2,867 | 684 | 532 |
221
221
  | `graph` | 114,708 | 36,466 | 29,953 | 11,479 | 3,233 | 2,708 |
222
222
  | `heatmap` | 78,430 | 25,372 | 22,403 | 10,872 | 2,982 | 2,366 |
223
223
  | `icon` | 87,644 | 28,324 | 23,220 | 1,018 | 245 | 126 |
224
- | `icon-button` | 38,112 | 11,466 | 10,070 | 3,581 | 852 | 646 |
224
+ | `icon-button` | 38,124 | 11,469 | 10,075 | 3,593 | 854 | 670 |
225
225
  | `image` | 35,082 | 10,613 | 9,334 | 3,156 | 809 | 657 |
226
226
  | `input` | 99,537 | 31,813 | 25,941 | 4,745 | 1,288 | 938 |
227
227
  | `kbd` | 34,863 | 10,848 | 9,529 | 2,976 | 922 | 855 |
@@ -238,7 +238,7 @@ Structure, accessibility, state, and form participation. It has no presentation
238
238
  | `navigation` | 34,843 | 10,709 | 9,395 | 1,361 | 301 | 226 |
239
239
  | `notifications` | 104,181 | 33,078 | 26,996 | 11,383 | 2,637 | 2,263 |
240
240
  | `number-input` | 102,465 | 32,630 | 26,674 | 7,670 | 2,010 | 1,515 |
241
- | `object-inspector` | 141,502 | 46,264 | 38,895 | 19,550 | 5,225 | 4,370 |
241
+ | `object-inspector` | 141,531 | 46,276 | 38,905 | 19,579 | 5,236 | 4,304 |
242
242
  | `option` | 35,204 | 10,629 | 9,352 | 2,958 | 646 | 543 |
243
243
  | `outline` | 38,267 | 11,902 | 10,469 | 4,628 | 1,320 | 1,075 |
244
244
  | `pagination` | 150,818 | 47,121 | 39,598 | 27,821 | 6,525 | 5,229 |
@@ -259,20 +259,20 @@ Structure, accessibility, state, and form participation. It has no presentation
259
259
  | `speed-dial` | 118,638 | 39,539 | 33,189 | 3,743 | 915 | 719 |
260
260
  | `splitter` | 42,714 | 12,692 | 11,214 | 10,282 | 2,596 | 2,223 |
261
261
  | `stat` | 33,397 | 10,120 | 8,906 | 1,148 | 193 | 173 |
262
- | `steps` | 97,187 | 31,106 | 25,374 | 6,264 | 1,479 | 1,106 |
262
+ | `steps` | 97,217 | 31,122 | 25,454 | 6,294 | 1,492 | 1,245 |
263
263
  | `switch` | 41,773 | 12,384 | 10,883 | 1,650 | 497 | 338 |
264
264
  | `table` | 99,327 | 32,297 | 26,296 | 10,158 | 2,798 | 2,311 |
265
265
  | `tabs` | 41,013 | 12,219 | 10,747 | 3,925 | 834 | 594 |
266
- | `tag` | 88,357 | 28,573 | 23,333 | 895 | 192 | 113 |
266
+ | `tag` | 88,370 | 28,577 | 23,348 | 908 | 197 | 161 |
267
267
  | `textarea` | 43,960 | 12,892 | 11,311 | 3,996 | 1,070 | 755 |
268
- | `time-input` | 158,079 | 49,121 | 41,337 | 29,016 | 7,045 | 5,755 |
268
+ | `time-input` | 158,111 | 49,133 | 41,350 | 29,048 | 7,058 | 5,895 |
269
269
  | `time-picker` | 117,196 | 37,094 | 30,330 | 19,136 | 5,104 | 4,148 |
270
270
  | `timeline` | 88,806 | 28,574 | 23,446 | 1,809 | 380 | 300 |
271
271
  | `toast` | 92,163 | 29,709 | 24,315 | 4,078 | 951 | 820 |
272
272
  | `toggle` | 45,957 | 13,403 | 11,795 | 3,342 | 816 | 583 |
273
273
  | `toolbar` | 35,003 | 10,814 | 9,482 | 2,624 | 717 | 552 |
274
274
  | `tooltip` | 64,751 | 21,220 | 18,782 | 6,369 | 1,715 | 1,350 |
275
- | `tour` | 70,570 | 22,635 | 19,952 | 11,032 | 2,719 | 2,232 |
275
+ | `tour` | 70,633 | 22,663 | 19,991 | 11,095 | 2,741 | 2,236 |
276
276
  | `tree` | 99,021 | 31,924 | 25,969 | 7,223 | 1,882 | 1,539 |
277
277
  | `trend` | 87,684 | 28,370 | 23,291 | 1,056 | 289 | 243 |
278
278
  | `video` | 155,346 | 48,784 | 41,231 | 32,520 | 7,642 | 6,463 |
@@ -295,7 +295,7 @@ The headless tier plus presentation. `bun add @fusion.dev/helix` installs this t
295
295
  | `bar-chart` | 93,880 | 29,107 | 25,756 | 25,425 | 6,313 | 5,329 |
296
296
  | `blockquote` | 34,209 | 10,468 | 9,196 | 1,914 | 467 | 315 |
297
297
  | `breadcrumbs` | 92,523 | 29,466 | 24,178 | 5,518 | 1,244 | 1,129 |
298
- | `button` | 43,806 | 12,554 | 11,023 | 9,257 | 1,937 | 1,505 |
298
+ | `button` | 43,982 | 12,620 | 11,082 | 9,433 | 1,995 | 1,639 |
299
299
  | `button-group` | 34,585 | 10,450 | 9,174 | 2,320 | 528 | 375 |
300
300
  | `callout` | 90,078 | 29,063 | 23,826 | 2,899 | 756 | 687 |
301
301
  | `canvas` | 114,431 | 31,475 | 27,500 | 70,328 | 18,720 | 15,791 |
@@ -305,14 +305,14 @@ The headless tier plus presentation. `bun add @fusion.dev/helix` installs this t
305
305
  | `checkbox` | 49,050 | 13,927 | 12,237 | 9,313 | 2,208 | 1,876 |
306
306
  | `checkbox-group` | 47,829 | 13,751 | 12,052 | 7,574 | 1,903 | 1,474 |
307
307
  | `code` | 32,605 | 9,928 | 8,729 | 1,511 | 377 | 380 |
308
- | `code-block` | 150,253 | 46,548 | 39,158 | 33,717 | 7,215 | 6,126 |
309
- | `color-input` | 185,460 | 52,861 | 44,724 | 59,352 | 11,295 | 9,511 |
310
- | `color-picker` | 146,202 | 41,656 | 34,488 | 47,560 | 9,284 | 7,867 |
311
- | `combobox` | 161,799 | 49,039 | 41,252 | 36,231 | 7,906 | 6,471 |
308
+ | `code-block` | 150,282 | 46,558 | 39,136 | 33,746 | 7,230 | 6,118 |
309
+ | `color-input` | 185,752 | 52,943 | 44,844 | 59,644 | 11,374 | 9,743 |
310
+ | `color-picker` | 146,420 | 41,723 | 34,558 | 47,778 | 9,346 | 8,013 |
311
+ | `combobox` | 161,978 | 49,085 | 41,270 | 36,410 | 7,955 | 6,615 |
312
312
  | `command` | 127,393 | 38,493 | 31,618 | 28,803 | 6,694 | 5,583 |
313
- | `copy-button` | 138,405 | 43,830 | 36,878 | 21,871 | 4,664 | 3,877 |
313
+ | `copy-button` | 138,417 | 43,836 | 36,896 | 21,883 | 4,669 | 3,882 |
314
314
  | `data-table` | 225,180 | 63,813 | 53,600 | 95,314 | 21,365 | 17,447 |
315
- | `date-input` | 160,960 | 48,876 | 41,238 | 35,177 | 7,843 | 6,678 |
315
+ | `date-input` | 161,140 | 48,929 | 41,318 | 35,357 | 7,899 | 6,643 |
316
316
  | `date-picker` | 105,753 | 33,518 | 27,415 | 15,499 | 3,859 | 3,238 |
317
317
  | `description-list` | 35,390 | 10,586 | 9,287 | 3,502 | 768 | 694 |
318
318
  | `dialog` | 40,938 | 12,132 | 10,723 | 7,079 | 1,782 | 1,494 |
@@ -321,7 +321,7 @@ The headless tier plus presentation. `bun add @fusion.dev/helix` installs this t
321
321
  | `drawer` | 39,577 | 11,767 | 10,345 | 6,007 | 1,482 | 1,263 |
322
322
  | `drilldown` | 101,699 | 32,584 | 26,513 | 10,393 | 2,528 | 2,071 |
323
323
  | `empty` | 34,946 | 10,764 | 9,445 | 2,380 | 678 | 489 |
324
- | `file-input` | 111,827 | 34,613 | 28,369 | 17,594 | 4,020 | 3,366 |
324
+ | `file-input` | 112,026 | 34,672 | 28,381 | 17,793 | 4,076 | 3,392 |
325
325
  | `filter-input` | 185,579 | 53,639 | 45,210 | 56,353 | 11,398 | 9,498 |
326
326
  | `flex` | 33,966 | 10,295 | 9,062 | 2,078 | 445 | 296 |
327
327
  | `format-date` | 37,170 | 11,382 | 10,030 | 3,497 | 860 | 608 |
@@ -329,7 +329,7 @@ The headless tier plus presentation. `bun add @fusion.dev/helix` installs this t
329
329
  | `grid` | 34,559 | 10,478 | 9,220 | 2,667 | 630 | 522 |
330
330
  | `heatmap` | 85,228 | 26,779 | 23,661 | 17,648 | 4,434 | 3,682 |
331
331
  | `icon` | 88,350 | 28,509 | 23,354 | 1,707 | 422 | 288 |
332
- | `icon-button` | 44,127 | 12,484 | 10,977 | 9,582 | 1,854 | 1,563 |
332
+ | `icon-button` | 44,139 | 12,487 | 10,941 | 9,594 | 1,856 | 1,555 |
333
333
  | `image` | 36,784 | 11,092 | 9,750 | 4,840 | 1,285 | 1,066 |
334
334
  | `input` | 105,902 | 33,263 | 27,153 | 11,104 | 2,685 | 2,139 |
335
335
  | `kbd` | 36,275 | 11,305 | 9,919 | 4,373 | 1,361 | 1,190 |
@@ -346,7 +346,7 @@ The headless tier plus presentation. `bun add @fusion.dev/helix` installs this t
346
346
  | `navigation` | 36,224 | 11,110 | 9,735 | 2,726 | 713 | 628 |
347
347
  | `notifications` | 117,292 | 35,506 | 29,125 | 24,486 | 5,059 | 4,265 |
348
348
  | `number-input` | 107,345 | 33,815 | 27,626 | 12,539 | 3,150 | 2,570 |
349
- | `object-inspector` | 155,139 | 48,519 | 40,992 | 33,167 | 7,563 | 6,311 |
349
+ | `object-inspector` | 155,168 | 48,532 | 40,983 | 33,196 | 7,574 | 6,373 |
350
350
  | `option` | 38,458 | 11,533 | 10,163 | 6,201 | 1,574 | 1,257 |
351
351
  | `orb` | 43,162 | 13,930 | 12,278 | 8,623 | 3,224 | 2,742 |
352
352
  | `outline` | 42,007 | 12,688 | 11,173 | 8,351 | 2,127 | 1,739 |
@@ -369,21 +369,21 @@ The headless tier plus presentation. `bun add @fusion.dev/helix` installs this t
369
369
  | `speed-dial` | 126,270 | 41,059 | 34,489 | 11,356 | 2,382 | 1,920 |
370
370
  | `splitter` | 48,786 | 13,681 | 12,145 | 16,336 | 3,627 | 3,136 |
371
371
  | `stat` | 36,822 | 10,836 | 9,555 | 4,565 | 915 | 730 |
372
- | `steps` | 110,828 | 33,587 | 27,521 | 19,894 | 3,918 | 3,257 |
372
+ | `steps` | 111,022 | 33,661 | 27,603 | 20,088 | 3,981 | 3,398 |
373
373
  | `switch` | 46,139 | 13,459 | 11,778 | 6,001 | 1,568 | 1,279 |
374
374
  | `table` | 104,921 | 33,482 | 27,341 | 15,746 | 3,981 | 3,421 |
375
375
  | `tabs` | 47,249 | 13,492 | 11,867 | 10,154 | 2,155 | 1,927 |
376
- | `tag` | 91,560 | 29,474 | 24,113 | 4,083 | 1,013 | 827 |
376
+ | `tag` | 91,721 | 29,528 | 24,083 | 4,244 | 1,063 | 870 |
377
377
  | `text` | 36,086 | 10,644 | 9,325 | 4,200 | 880 | 692 |
378
378
  | `textarea` | 47,395 | 13,733 | 12,034 | 7,418 | 1,928 | 1,528 |
379
- | `time-input` | 179,569 | 52,698 | 44,403 | 50,488 | 10,697 | 8,990 |
379
+ | `time-input` | 179,749 | 52,754 | 44,471 | 50,668 | 10,753 | 8,930 |
380
380
  | `time-picker` | 128,924 | 39,284 | 32,256 | 30,852 | 7,322 | 6,068 |
381
381
  | `timeline` | 92,119 | 29,344 | 24,098 | 5,110 | 1,130 | 917 |
382
382
  | `toast` | 99,696 | 31,426 | 25,725 | 11,599 | 2,601 | 2,189 |
383
383
  | `toggle` | 51,152 | 14,607 | 12,844 | 8,525 | 2,066 | 1,725 |
384
384
  | `toolbar` | 36,295 | 11,108 | 9,755 | 3,899 | 1,022 | 824 |
385
385
  | `tooltip` | 67,829 | 21,974 | 19,470 | 9,429 | 2,451 | 2,085 |
386
- | `tour` | 80,121 | 24,220 | 21,448 | 20,565 | 4,378 | 3,738 |
386
+ | `tour` | 80,348 | 24,304 | 21,526 | 20,792 | 4,456 | 3,750 |
387
387
  | `tree` | 104,871 | 33,337 | 27,201 | 13,069 | 3,306 | 2,728 |
388
388
  | `trend` | 90,903 | 29,129 | 23,898 | 4,271 | 985 | 862 |
389
389
  | `video` | 174,764 | 52,259 | 44,284 | 51,918 | 11,165 | 9,570 |
@@ -401,11 +401,11 @@ stripped column shows the bytes we removed.
401
401
  | Package | Unpacked | Files | Source maps stripped | Runtime dependencies |
402
402
  |---|---|---|---|---|
403
403
  | `@fusion.dev/helix-core` | 1,192,742 | 171 | 267,144 | `@floating-ui/dom`, `@fusion.dev/helix-icons` |
404
- | `@fusion.dev/helix-headless` | 13,506,127 | 510 | 1,077,660 | `@fusion.dev/helix-core`, `@fusion.dev/helix-icons`, `uqr` |
404
+ | `@fusion.dev/helix-headless` | 13,515,038 | 510 | 1,077,677 | `@fusion.dev/helix-core`, `@fusion.dev/helix-icons`, `uqr` |
405
405
  | `@fusion.dev/helix-icons` | 150,162 | 21 | 50,346 | `svgo` |
406
406
  | `@fusion.dev/helix-styles` | 102,155 | 6 | 0 | none |
407
- | `@fusion.dev/helix-theme` | 500,416 | 8 | 5,191 | none |
408
- | `@fusion.dev/helix` | 14,618,004 | 876 | 373,795 | `@fusion.dev/helix-core`, `@fusion.dev/helix-headless`, `@fusion.dev/helix-styles` |
407
+ | `@fusion.dev/helix-theme` | 514,288 | 8 | 5,300 | none |
408
+ | `@fusion.dev/helix` | 14,628,121 | 876 | 373,810 | `@fusion.dev/helix-core`, `@fusion.dev/helix-headless`, `@fusion.dev/helix-styles` |
409
409
 
410
410
  ## Not measured yet
411
411
 
@@ -15,53 +15,65 @@ a theme from a few inputs, and the theme builder shows you the result.
15
15
 
16
16
  You enter the same inputs that `derive()` takes:
17
17
 
18
- - a brand color
19
- - a chroma ceiling
20
- - a radius
21
- - a density
22
- - a contrast target
23
- - a motion character
24
-
25
- The theme builder runs the full derivation. It shows you every token, and the
26
- components drawn with them.
27
-
28
- It shows light and dark at the same time. `[data-color-mode]` works on any
29
- element, so the two previews are two subtrees of one document. See
30
- [Color modes](./color-modes).
31
-
32
- ## The contrast column
33
-
34
- The contrast column lists every color pair Helix computed. Each pair shows its
35
- ratio, measured against the background it is painted on. A pair has one of
36
- three states:
37
-
38
- - **Met.** The pair reaches the target.
39
- - **Unverifiable.** The background is translucent, so there is no known color
40
- to measure against. The pair neither passes nor fails. This is the cost of a
41
- translucent material, and the theme builder reports it.
42
- - **Pinned.** You set the color yourself. The engine did not compute it, so its
43
- contrast is not guaranteed.
44
-
45
- A column of `unverifiable` pairs means your theme makes a trade. The column lets
46
- you see that you made it.
47
-
48
- ## What the theme builder exports
49
-
50
- The theme builder gives you the token block as CSS, to paste into your own
18
+ - **Color:** the brand, the color scheme, the contrast target, the saturation,
19
+ the accent angle, and the page's color in light and in dark
20
+ - **Shape and type:** the density, the corner radius, the three faces, the body
21
+ size, and the type scale
22
+ - **Status:** how far the status colors follow the palette, and how far their
23
+ hues may move
24
+ - **Motion, separation, and material:** the motion character, how surfaces are
25
+ set apart, and how floating surfaces are blurred and see-through
26
+
27
+ The theme builder runs the full derivation on every change. It shows a page
28
+ drawn with the theme, and the stylesheet the theme generates beside it.
29
+
30
+ The Color scheme field picks which half you see: light, dark, or the site's own
31
+ mode. See [Color modes](./color-modes).
32
+
33
+ ## A page of your own color
34
+
35
+ The Light page and Dark page fields give the page a color, such as a warm cream
36
+ or a deep teal. They start at pure white and pure black, the page Helix draws
37
+ without one. The surfaces keep the contrast with the page they keep with white
38
+ or black, the grays take its tint, and every text color is solved against it. A
39
+ page that no text color can reach the contrast target on is left out of the
40
+ preview, and a caption under the fields says so.
41
+
42
+ **Color the figures band** gives one section of the Marketing site layout a
43
+ color of its own, as its own theme. The band is dark or light by whichever text
44
+ reads better on it, and its block follows the page's in the generated
45
+ stylesheet. See [Color one section](./theming#color-one-section).
46
+
47
+ ## The audit
48
+
49
+ The audit lists every color pair Helix computed. Each pair shows its ratio,
50
+ measured against the background it is painted on, and either passes or fails
51
+ its target. Its three tabs are:
52
+
53
+ - **Contrast.** The pairs that fail, or a line saying that every pair passes.
54
+ - **Collisions.** Colors too close to each other to tell apart, such as the
55
+ primary color and a status color.
56
+ - **Unverifiable.** Pairs whose background is translucent, so there is no known
57
+ color to measure against. This is the cost of a translucent material, and
58
+ the theme builder reports it.
59
+
60
+ ## What the theme builder gives you
61
+
62
+ The generated stylesheet is the token block as CSS, to paste into your own
51
63
  stylesheet:
52
64
 
53
65
  ```css
54
- :root {
55
- --helix-color-primary: oklch(…);
66
+ [data-theme="preview"] {
67
+ --helix-color-background: #f7f2eb;
56
68
  …
57
69
  }
58
70
  ```
59
71
 
60
- It also gives you the intent object, to keep in your repository and derive the
61
- theme from again:
72
+ The page's link holds every input you changed, so a link is the theme. To derive
73
+ the theme in your own build, write the same inputs as an intent object:
62
74
 
63
75
  ```ts
64
- export const theme = { brand: '#2563eb', chroma: { ceiling: 0.1 }, radius: 2 }
76
+ export const theme = { background: { light: '#f7f2eb' }, brand: '#ff6200' }
65
77
  ```
66
78
 
67
79
  **Keep the intent object in your repository.** The tokens are the output of a
@@ -110,6 +110,39 @@ console.log(css[':root'])
110
110
  A value that is not a color and still changes with the mode, such as the edge
111
111
  of a floating surface, is set by rules after the block, one for each mode.
112
112
 
113
+ ## Color one section
114
+
115
+ A section in a color of its own, such as a deep teal band on a cream page, is a
116
+ theme of its own. Derive it from the same intent, with the section's color as
117
+ its page, under a selector for the section:
118
+
119
+ ```ts
120
+ const band = engine.derive(
121
+ { ...intent, background: { dark: '#0b2a33' }, scheme: 'dark' },
122
+ ['[data-band]'],
123
+ )
124
+ ```
125
+
126
+ Choose the scheme the color needs: `dark` for a color light text reads on, and
127
+ `light` for one dark text reads on. A color no text can reach the contrast
128
+ target on is refused, as a page is.
129
+
130
+ Mark the section so the stylesheet derives its own colors there from the
131
+ section's seeds, in the section's mode, and paint it with its page color:
132
+
133
+ ```html
134
+ <section data-band data-color-mode="dark" data-helix-theme>…</section>
135
+ ```
136
+
137
+ ```css
138
+ [data-band] {
139
+ background-color: var(--helix-color-background);
140
+ color: var(--helix-color-foreground);
141
+ }
142
+ ```
143
+
144
+ Write the section's block after the page's, so it wins inside the section.
145
+
113
146
  ## Why Helix uses OKLCH
114
147
 
115
148
  Equal numeric steps in sRGB do not look like equal steps. That makes scales and
@@ -1790,6 +1790,25 @@ frame.addEventListener('helix-graph-filter', (event) => {
1790
1790
  The legend is drawn where the notes have two groups or more. On a frame
1791
1791
  narrower than 40rem it is one row, which scrolls.
1792
1792
 
1793
+ ## Find groups in the links
1794
+
1795
+ Notes without a \`group\` are drawn in one color. Where your data has no groups,
1796
+ \`groupByCommunity\` finds them in the links: notes that link mostly to each other
1797
+ become one group, named after its most linked note. Hand its result to the frame,
1798
+ and the drawing colors the groups and the legend names them:
1799
+
1800
+ \`\`\`ts
1801
+ import { groupByCommunity } from '@fusion.dev/helix-graph'
1802
+
1803
+ frame.nodes = groupByCommunity(notes, links)
1804
+ frame.links = links
1805
+ \`\`\`
1806
+
1807
+ A note that has a \`group\` keeps it. Communities of fewer than three notes share
1808
+ one group, named \`Other\`. Set \`fewest\` and \`rest\` to change either. The same
1809
+ notes and links give the same groups every time. On 20,000 notes it takes about
1810
+ 65 milliseconds.
1811
+
1793
1812
  ## Select a note
1794
1813
 
1795
1814
  Pressing a note selects it, and pressing where no note is clears the selection.
@@ -2309,7 +2328,8 @@ computed from \`brand\` or from the Helix design language. A theme that sets onl
2309
2328
  |---|---|
2310
2329
  | \`brand\` | Your main brand color. Required |
2311
2330
  | \`accent\` | The second emphasis color. Defaults to the brand color. \`{ from: 'brand', rotate: 180 }\` gives the complementary color |
2312
- | \`neutral\` | The gray ramp, which can be tinted toward the brand |
2331
+ | \`background\` | The page's color, \`{ light, dark }\`, for a page that is not pure white or pure black. The surfaces keep their contrast with it, and the grays take its tint. A page no text color can reach the contrast target on is refused |
2332
+ | \`neutral\` | The gray ramp, which can be tinted toward the brand. With \`background\`, it takes the page's tint |
2313
2333
  | \`status\` | \`info\`, \`success\`, \`warning\`, and \`danger\`. A color pins one. An object adjusts its hue while it keeps its meaning |
2314
2334
  | \`chroma\` | How saturated the palette is, independent of hue |
2315
2335
  | \`scheme\` | \`'light'\` or \`'dark'\`, for a theme that has only one mode |
@@ -3345,10 +3365,10 @@ either barrel. The per-component tables show what your page pays.
3345
3365
  | Package | Raw | Gzip | Brotli | |
3346
3366
  |---|---|---|---|---|
3347
3367
  | \`@fusion.dev/helix-core\` | 183,735 | 58,230 | 49,473 | The element base class, mixins, decorators, and floating positioning. |
3348
- | \`@fusion.dev/helix-headless\` | 745,966 | 193,214 | 149,903 | Every headless family. The barrel entry includes all of them. |
3368
+ | \`@fusion.dev/helix-headless\` | 746,304 | 193,314 | 149,776 | Every headless family. The barrel entry includes all of them. |
3349
3369
  | \`@fusion.dev/helix-icons\` | 55,565 | 17,727 | 14,864 | The whole glyph set. |
3350
3370
  | \`@fusion.dev/helix-theme\` | 3,626 | 1,597 | 1,384 | The derivation engine. Most sites run it at build time, and a theme switcher runs it in the browser. |
3351
- | \`@fusion.dev/helix\` | 1,291,029 | 301,797 | 220,733 | Every styled family. |
3371
+ | \`@fusion.dev/helix\` | 1,291,679 | 302,007 | 220,657 | Every styled family. |
3352
3372
  | \`lit\` | 15,394 | 6,118 | 5,460 | Lit itself, listed so you can subtract it from every row above. |
3353
3373
 
3354
3374
  ## Stylesheets
@@ -3371,11 +3391,11 @@ shows the whole cost of using the base layer on its own.
3371
3391
 
3372
3392
  **Most of your first component is the shared runtime.** The median styled family is 21,372 bytes gzipped alone, and it adds 2,254 to a page that already has Helix. The shared runtime is 89 percent of the first component, and the component itself is 11 percent. Ten typical components cost the first number once, plus nine of the added number. The two columns in the tables below let you work that out for your own components.
3373
3393
 
3374
- Across the 104 styled components, the smallest is \`code\` at 9,928 bytes gzipped alone, and the largest is \`data-table\` at 63,813. Every family together is 301,797.
3394
+ Across the 104 styled components, the smallest is \`code\` at 9,928 bytes gzipped alone, and the largest is \`data-table\` at 63,813. Every family together is 302,007.
3375
3395
 
3376
- No family imports a barrel. The \`barrels\` rule in \`fusion workspace\` enforces that. \`@fusion.dev/helix-headless\` marks every module in \`dist\` as having side effects, which is true of a file that calls \`customElements.define\`. A bundler can remove none of it. One \`import { HelixHeadlessButton } from '@fusion.dev/helix-headless'\` costs 193,214 bytes gzipped, whatever else the page imports. That is 9 times the median family above. All 104 styled families import the headless family they extend directly. The rule checks the shape of the import, so it applies to any package that sets \`sideEffects\`, whatever its name.
3396
+ No family imports a barrel. The \`barrels\` rule in \`fusion workspace\` enforces that. \`@fusion.dev/helix-headless\` marks every module in \`dist\` as having side effects, which is true of a file that calls \`customElements.define\`. A bundler can remove none of it. One \`import { HelixHeadlessButton } from '@fusion.dev/helix-headless'\` costs 193,314 bytes gzipped, whatever else the page imports. That is 9 times the median family above. All 104 styled families import the headless family they extend directly. The rule checks the shape of the import, so it applies to any package that sets \`sideEffects\`, whatever its name.
3377
3397
 
3378
- The headless tier never had the problem, so it serves as the control. \`@fusion.dev/helix-core\` is \`sideEffects: false\`, and the median headless family is 21,928 bytes gzipped alone.
3398
+ The headless tier never had the problem, so it serves as the control. \`@fusion.dev/helix-core\` is \`sideEffects: false\`, and the median headless family is 21,942 bytes gzipped alone.
3379
3399
 
3380
3400
  ## Compared with other systems
3381
3401
 
@@ -3387,7 +3407,7 @@ The table has no whole-library row. That row would compare how many components e
3387
3407
 
3388
3408
  | Component | System | Raw | Gzip | Brotli |
3389
3409
  |---|---|---|---|---|
3390
- | \`button\` | **Helix** | 43,806 | 12,554 | 11,023 |
3410
+ | \`button\` | **Helix** | 43,982 | 12,620 | 11,082 |
3391
3411
  | | Carbon | 133,058 | 20,959 | 17,685 |
3392
3412
  | | Material Web | 47,060 | 14,173 | 12,591 |
3393
3413
  | | Shoelace | 62,628 | 18,287 | 15,805 |
@@ -3476,7 +3496,7 @@ Structure, accessibility, state, and form participation. It has no presentation
3476
3496
  | \`bar-chart\` | 81,076 | 26,555 | 23,488 | 12,644 | 3,701 | 3,035 |
3477
3497
  | \`blockquote\` | 33,053 | 10,175 | 8,938 | 774 | 176 | 128 |
3478
3498
  | \`breadcrumbs\` | 88,957 | 28,651 | 23,520 | 1,965 | 451 | 379 |
3479
- | \`button\` | 37,713 | 11,437 | 10,046 | 3,182 | 812 | 670 |
3499
+ | \`button\` | 37,725 | 11,440 | 10,034 | 3,194 | 814 | 619 |
3480
3500
  | \`button-group\` | 32,909 | 10,061 | 8,843 | 661 | 137 | 34 |
3481
3501
  | \`callout\` | 88,077 | 28,508 | 23,396 | 914 | 233 | 168 |
3482
3502
  | \`canvas\` | 94,126 | 27,730 | 24,309 | 50,034 | 14,930 | 12,613 |
@@ -3486,14 +3506,14 @@ Structure, accessibility, state, and form participation. It has no presentation
3486
3506
  | \`checkbox\` | 42,424 | 12,472 | 10,962 | 2,703 | 748 | 514 |
3487
3507
  | \`checkbox-group\` | 45,548 | 13,159 | 11,549 | 5,307 | 1,316 | 1,017 |
3488
3508
  | \`code\` | 31,528 | 9,644 | 8,470 | 451 | 77 | -1 |
3489
- | \`code-block\` | 133,803 | 43,664 | 36,792 | 17,288 | 4,490 | 3,847 |
3490
- | \`color-input\` | 151,779 | 47,718 | 40,233 | 25,691 | 5,998 | 4,976 |
3491
- | \`color-picker\` | 118,224 | 37,113 | 30,494 | 19,588 | 4,689 | 3,874 |
3492
- | \`combobox\` | 146,691 | 46,408 | 38,900 | 21,146 | 5,230 | 4,258 |
3509
+ | \`code-block\` | 133,832 | 43,676 | 36,796 | 17,317 | 4,502 | 3,798 |
3510
+ | \`color-input\` | 151,907 | 47,747 | 40,241 | 25,819 | 6,027 | 5,016 |
3511
+ | \`color-picker\` | 118,278 | 37,129 | 30,542 | 19,642 | 4,706 | 4,026 |
3512
+ | \`combobox\` | 146,722 | 46,415 | 38,946 | 21,177 | 5,239 | 4,380 |
3493
3513
  | \`command\` | 116,641 | 36,394 | 29,750 | 18,065 | 4,588 | 3,719 |
3494
- | \`copy-button\` | 128,401 | 42,039 | 35,305 | 11,883 | 2,933 | 2,322 |
3514
+ | \`copy-button\` | 128,413 | 42,045 | 35,300 | 11,895 | 2,938 | 2,421 |
3495
3515
  | \`data-table\` | 186,894 | 56,878 | 48,021 | 57,295 | 14,485 | 11,997 |
3496
- | \`date-input\` | 144,949 | 45,900 | 38,587 | 19,177 | 4,830 | 4,067 |
3516
+ | \`date-input\` | 144,981 | 45,912 | 38,562 | 19,209 | 4,845 | 4,000 |
3497
3517
  | \`date-picker\` | 100,136 | 32,351 | 26,467 | 9,900 | 2,714 | 2,336 |
3498
3518
  | \`description-list\` | 33,012 | 10,012 | 8,793 | 1,132 | 182 | 155 |
3499
3519
  | \`dialog\` | 36,561 | 11,114 | 9,752 | 2,717 | 765 | 587 |
@@ -3502,13 +3522,13 @@ Structure, accessibility, state, and form participation. It has no presentation
3502
3522
  | \`drawer\` | 35,314 | 10,755 | 9,427 | 1,761 | 466 | 446 |
3503
3523
  | \`drilldown\` | 97,002 | 31,492 | 25,596 | 5,704 | 1,481 | 1,170 |
3504
3524
  | \`empty\` | 33,506 | 10,310 | 9,098 | 956 | 233 | 140 |
3505
- | \`file-input\` | 100,449 | 32,330 | 26,417 | 6,215 | 1,787 | 1,429 |
3525
+ | \`file-input\` | 100,500 | 32,345 | 26,387 | 6,266 | 1,803 | 1,479 |
3506
3526
  | \`filter-input\` | 157,243 | 49,107 | 41,347 | 28,023 | 6,779 | 5,542 |
3507
3527
  | \`format-date\` | 36,522 | 11,235 | 9,940 | 2,867 | 684 | 532 |
3508
3528
  | \`graph\` | 114,708 | 36,466 | 29,953 | 11,479 | 3,233 | 2,708 |
3509
3529
  | \`heatmap\` | 78,430 | 25,372 | 22,403 | 10,872 | 2,982 | 2,366 |
3510
3530
  | \`icon\` | 87,644 | 28,324 | 23,220 | 1,018 | 245 | 126 |
3511
- | \`icon-button\` | 38,112 | 11,466 | 10,070 | 3,581 | 852 | 646 |
3531
+ | \`icon-button\` | 38,124 | 11,469 | 10,075 | 3,593 | 854 | 670 |
3512
3532
  | \`image\` | 35,082 | 10,613 | 9,334 | 3,156 | 809 | 657 |
3513
3533
  | \`input\` | 99,537 | 31,813 | 25,941 | 4,745 | 1,288 | 938 |
3514
3534
  | \`kbd\` | 34,863 | 10,848 | 9,529 | 2,976 | 922 | 855 |
@@ -3525,7 +3545,7 @@ Structure, accessibility, state, and form participation. It has no presentation
3525
3545
  | \`navigation\` | 34,843 | 10,709 | 9,395 | 1,361 | 301 | 226 |
3526
3546
  | \`notifications\` | 104,181 | 33,078 | 26,996 | 11,383 | 2,637 | 2,263 |
3527
3547
  | \`number-input\` | 102,465 | 32,630 | 26,674 | 7,670 | 2,010 | 1,515 |
3528
- | \`object-inspector\` | 141,502 | 46,264 | 38,895 | 19,550 | 5,225 | 4,370 |
3548
+ | \`object-inspector\` | 141,531 | 46,276 | 38,905 | 19,579 | 5,236 | 4,304 |
3529
3549
  | \`option\` | 35,204 | 10,629 | 9,352 | 2,958 | 646 | 543 |
3530
3550
  | \`outline\` | 38,267 | 11,902 | 10,469 | 4,628 | 1,320 | 1,075 |
3531
3551
  | \`pagination\` | 150,818 | 47,121 | 39,598 | 27,821 | 6,525 | 5,229 |
@@ -3546,20 +3566,20 @@ Structure, accessibility, state, and form participation. It has no presentation
3546
3566
  | \`speed-dial\` | 118,638 | 39,539 | 33,189 | 3,743 | 915 | 719 |
3547
3567
  | \`splitter\` | 42,714 | 12,692 | 11,214 | 10,282 | 2,596 | 2,223 |
3548
3568
  | \`stat\` | 33,397 | 10,120 | 8,906 | 1,148 | 193 | 173 |
3549
- | \`steps\` | 97,187 | 31,106 | 25,374 | 6,264 | 1,479 | 1,106 |
3569
+ | \`steps\` | 97,217 | 31,122 | 25,454 | 6,294 | 1,492 | 1,245 |
3550
3570
  | \`switch\` | 41,773 | 12,384 | 10,883 | 1,650 | 497 | 338 |
3551
3571
  | \`table\` | 99,327 | 32,297 | 26,296 | 10,158 | 2,798 | 2,311 |
3552
3572
  | \`tabs\` | 41,013 | 12,219 | 10,747 | 3,925 | 834 | 594 |
3553
- | \`tag\` | 88,357 | 28,573 | 23,333 | 895 | 192 | 113 |
3573
+ | \`tag\` | 88,370 | 28,577 | 23,348 | 908 | 197 | 161 |
3554
3574
  | \`textarea\` | 43,960 | 12,892 | 11,311 | 3,996 | 1,070 | 755 |
3555
- | \`time-input\` | 158,079 | 49,121 | 41,337 | 29,016 | 7,045 | 5,755 |
3575
+ | \`time-input\` | 158,111 | 49,133 | 41,350 | 29,048 | 7,058 | 5,895 |
3556
3576
  | \`time-picker\` | 117,196 | 37,094 | 30,330 | 19,136 | 5,104 | 4,148 |
3557
3577
  | \`timeline\` | 88,806 | 28,574 | 23,446 | 1,809 | 380 | 300 |
3558
3578
  | \`toast\` | 92,163 | 29,709 | 24,315 | 4,078 | 951 | 820 |
3559
3579
  | \`toggle\` | 45,957 | 13,403 | 11,795 | 3,342 | 816 | 583 |
3560
3580
  | \`toolbar\` | 35,003 | 10,814 | 9,482 | 2,624 | 717 | 552 |
3561
3581
  | \`tooltip\` | 64,751 | 21,220 | 18,782 | 6,369 | 1,715 | 1,350 |
3562
- | \`tour\` | 70,570 | 22,635 | 19,952 | 11,032 | 2,719 | 2,232 |
3582
+ | \`tour\` | 70,633 | 22,663 | 19,991 | 11,095 | 2,741 | 2,236 |
3563
3583
  | \`tree\` | 99,021 | 31,924 | 25,969 | 7,223 | 1,882 | 1,539 |
3564
3584
  | \`trend\` | 87,684 | 28,370 | 23,291 | 1,056 | 289 | 243 |
3565
3585
  | \`video\` | 155,346 | 48,784 | 41,231 | 32,520 | 7,642 | 6,463 |
@@ -3582,7 +3602,7 @@ The headless tier plus presentation. \`bun add @fusion.dev/helix\` installs this
3582
3602
  | \`bar-chart\` | 93,880 | 29,107 | 25,756 | 25,425 | 6,313 | 5,329 |
3583
3603
  | \`blockquote\` | 34,209 | 10,468 | 9,196 | 1,914 | 467 | 315 |
3584
3604
  | \`breadcrumbs\` | 92,523 | 29,466 | 24,178 | 5,518 | 1,244 | 1,129 |
3585
- | \`button\` | 43,806 | 12,554 | 11,023 | 9,257 | 1,937 | 1,505 |
3605
+ | \`button\` | 43,982 | 12,620 | 11,082 | 9,433 | 1,995 | 1,639 |
3586
3606
  | \`button-group\` | 34,585 | 10,450 | 9,174 | 2,320 | 528 | 375 |
3587
3607
  | \`callout\` | 90,078 | 29,063 | 23,826 | 2,899 | 756 | 687 |
3588
3608
  | \`canvas\` | 114,431 | 31,475 | 27,500 | 70,328 | 18,720 | 15,791 |
@@ -3592,14 +3612,14 @@ The headless tier plus presentation. \`bun add @fusion.dev/helix\` installs this
3592
3612
  | \`checkbox\` | 49,050 | 13,927 | 12,237 | 9,313 | 2,208 | 1,876 |
3593
3613
  | \`checkbox-group\` | 47,829 | 13,751 | 12,052 | 7,574 | 1,903 | 1,474 |
3594
3614
  | \`code\` | 32,605 | 9,928 | 8,729 | 1,511 | 377 | 380 |
3595
- | \`code-block\` | 150,253 | 46,548 | 39,158 | 33,717 | 7,215 | 6,126 |
3596
- | \`color-input\` | 185,460 | 52,861 | 44,724 | 59,352 | 11,295 | 9,511 |
3597
- | \`color-picker\` | 146,202 | 41,656 | 34,488 | 47,560 | 9,284 | 7,867 |
3598
- | \`combobox\` | 161,799 | 49,039 | 41,252 | 36,231 | 7,906 | 6,471 |
3615
+ | \`code-block\` | 150,282 | 46,558 | 39,136 | 33,746 | 7,230 | 6,118 |
3616
+ | \`color-input\` | 185,752 | 52,943 | 44,844 | 59,644 | 11,374 | 9,743 |
3617
+ | \`color-picker\` | 146,420 | 41,723 | 34,558 | 47,778 | 9,346 | 8,013 |
3618
+ | \`combobox\` | 161,978 | 49,085 | 41,270 | 36,410 | 7,955 | 6,615 |
3599
3619
  | \`command\` | 127,393 | 38,493 | 31,618 | 28,803 | 6,694 | 5,583 |
3600
- | \`copy-button\` | 138,405 | 43,830 | 36,878 | 21,871 | 4,664 | 3,877 |
3620
+ | \`copy-button\` | 138,417 | 43,836 | 36,896 | 21,883 | 4,669 | 3,882 |
3601
3621
  | \`data-table\` | 225,180 | 63,813 | 53,600 | 95,314 | 21,365 | 17,447 |
3602
- | \`date-input\` | 160,960 | 48,876 | 41,238 | 35,177 | 7,843 | 6,678 |
3622
+ | \`date-input\` | 161,140 | 48,929 | 41,318 | 35,357 | 7,899 | 6,643 |
3603
3623
  | \`date-picker\` | 105,753 | 33,518 | 27,415 | 15,499 | 3,859 | 3,238 |
3604
3624
  | \`description-list\` | 35,390 | 10,586 | 9,287 | 3,502 | 768 | 694 |
3605
3625
  | \`dialog\` | 40,938 | 12,132 | 10,723 | 7,079 | 1,782 | 1,494 |
@@ -3608,7 +3628,7 @@ The headless tier plus presentation. \`bun add @fusion.dev/helix\` installs this
3608
3628
  | \`drawer\` | 39,577 | 11,767 | 10,345 | 6,007 | 1,482 | 1,263 |
3609
3629
  | \`drilldown\` | 101,699 | 32,584 | 26,513 | 10,393 | 2,528 | 2,071 |
3610
3630
  | \`empty\` | 34,946 | 10,764 | 9,445 | 2,380 | 678 | 489 |
3611
- | \`file-input\` | 111,827 | 34,613 | 28,369 | 17,594 | 4,020 | 3,366 |
3631
+ | \`file-input\` | 112,026 | 34,672 | 28,381 | 17,793 | 4,076 | 3,392 |
3612
3632
  | \`filter-input\` | 185,579 | 53,639 | 45,210 | 56,353 | 11,398 | 9,498 |
3613
3633
  | \`flex\` | 33,966 | 10,295 | 9,062 | 2,078 | 445 | 296 |
3614
3634
  | \`format-date\` | 37,170 | 11,382 | 10,030 | 3,497 | 860 | 608 |
@@ -3616,7 +3636,7 @@ The headless tier plus presentation. \`bun add @fusion.dev/helix\` installs this
3616
3636
  | \`grid\` | 34,559 | 10,478 | 9,220 | 2,667 | 630 | 522 |
3617
3637
  | \`heatmap\` | 85,228 | 26,779 | 23,661 | 17,648 | 4,434 | 3,682 |
3618
3638
  | \`icon\` | 88,350 | 28,509 | 23,354 | 1,707 | 422 | 288 |
3619
- | \`icon-button\` | 44,127 | 12,484 | 10,977 | 9,582 | 1,854 | 1,563 |
3639
+ | \`icon-button\` | 44,139 | 12,487 | 10,941 | 9,594 | 1,856 | 1,555 |
3620
3640
  | \`image\` | 36,784 | 11,092 | 9,750 | 4,840 | 1,285 | 1,066 |
3621
3641
  | \`input\` | 105,902 | 33,263 | 27,153 | 11,104 | 2,685 | 2,139 |
3622
3642
  | \`kbd\` | 36,275 | 11,305 | 9,919 | 4,373 | 1,361 | 1,190 |
@@ -3633,7 +3653,7 @@ The headless tier plus presentation. \`bun add @fusion.dev/helix\` installs this
3633
3653
  | \`navigation\` | 36,224 | 11,110 | 9,735 | 2,726 | 713 | 628 |
3634
3654
  | \`notifications\` | 117,292 | 35,506 | 29,125 | 24,486 | 5,059 | 4,265 |
3635
3655
  | \`number-input\` | 107,345 | 33,815 | 27,626 | 12,539 | 3,150 | 2,570 |
3636
- | \`object-inspector\` | 155,139 | 48,519 | 40,992 | 33,167 | 7,563 | 6,311 |
3656
+ | \`object-inspector\` | 155,168 | 48,532 | 40,983 | 33,196 | 7,574 | 6,373 |
3637
3657
  | \`option\` | 38,458 | 11,533 | 10,163 | 6,201 | 1,574 | 1,257 |
3638
3658
  | \`orb\` | 43,162 | 13,930 | 12,278 | 8,623 | 3,224 | 2,742 |
3639
3659
  | \`outline\` | 42,007 | 12,688 | 11,173 | 8,351 | 2,127 | 1,739 |
@@ -3656,21 +3676,21 @@ The headless tier plus presentation. \`bun add @fusion.dev/helix\` installs this
3656
3676
  | \`speed-dial\` | 126,270 | 41,059 | 34,489 | 11,356 | 2,382 | 1,920 |
3657
3677
  | \`splitter\` | 48,786 | 13,681 | 12,145 | 16,336 | 3,627 | 3,136 |
3658
3678
  | \`stat\` | 36,822 | 10,836 | 9,555 | 4,565 | 915 | 730 |
3659
- | \`steps\` | 110,828 | 33,587 | 27,521 | 19,894 | 3,918 | 3,257 |
3679
+ | \`steps\` | 111,022 | 33,661 | 27,603 | 20,088 | 3,981 | 3,398 |
3660
3680
  | \`switch\` | 46,139 | 13,459 | 11,778 | 6,001 | 1,568 | 1,279 |
3661
3681
  | \`table\` | 104,921 | 33,482 | 27,341 | 15,746 | 3,981 | 3,421 |
3662
3682
  | \`tabs\` | 47,249 | 13,492 | 11,867 | 10,154 | 2,155 | 1,927 |
3663
- | \`tag\` | 91,560 | 29,474 | 24,113 | 4,083 | 1,013 | 827 |
3683
+ | \`tag\` | 91,721 | 29,528 | 24,083 | 4,244 | 1,063 | 870 |
3664
3684
  | \`text\` | 36,086 | 10,644 | 9,325 | 4,200 | 880 | 692 |
3665
3685
  | \`textarea\` | 47,395 | 13,733 | 12,034 | 7,418 | 1,928 | 1,528 |
3666
- | \`time-input\` | 179,569 | 52,698 | 44,403 | 50,488 | 10,697 | 8,990 |
3686
+ | \`time-input\` | 179,749 | 52,754 | 44,471 | 50,668 | 10,753 | 8,930 |
3667
3687
  | \`time-picker\` | 128,924 | 39,284 | 32,256 | 30,852 | 7,322 | 6,068 |
3668
3688
  | \`timeline\` | 92,119 | 29,344 | 24,098 | 5,110 | 1,130 | 917 |
3669
3689
  | \`toast\` | 99,696 | 31,426 | 25,725 | 11,599 | 2,601 | 2,189 |
3670
3690
  | \`toggle\` | 51,152 | 14,607 | 12,844 | 8,525 | 2,066 | 1,725 |
3671
3691
  | \`toolbar\` | 36,295 | 11,108 | 9,755 | 3,899 | 1,022 | 824 |
3672
3692
  | \`tooltip\` | 67,829 | 21,974 | 19,470 | 9,429 | 2,451 | 2,085 |
3673
- | \`tour\` | 80,121 | 24,220 | 21,448 | 20,565 | 4,378 | 3,738 |
3693
+ | \`tour\` | 80,348 | 24,304 | 21,526 | 20,792 | 4,456 | 3,750 |
3674
3694
  | \`tree\` | 104,871 | 33,337 | 27,201 | 13,069 | 3,306 | 2,728 |
3675
3695
  | \`trend\` | 90,903 | 29,129 | 23,898 | 4,271 | 985 | 862 |
3676
3696
  | \`video\` | 174,764 | 52,259 | 44,284 | 51,918 | 11,165 | 9,570 |
@@ -3688,11 +3708,11 @@ stripped column shows the bytes we removed.
3688
3708
  | Package | Unpacked | Files | Source maps stripped | Runtime dependencies |
3689
3709
  |---|---|---|---|---|
3690
3710
  | \`@fusion.dev/helix-core\` | 1,192,742 | 171 | 267,144 | \`@floating-ui/dom\`, \`@fusion.dev/helix-icons\` |
3691
- | \`@fusion.dev/helix-headless\` | 13,506,127 | 510 | 1,077,660 | \`@fusion.dev/helix-core\`, \`@fusion.dev/helix-icons\`, \`uqr\` |
3711
+ | \`@fusion.dev/helix-headless\` | 13,515,038 | 510 | 1,077,677 | \`@fusion.dev/helix-core\`, \`@fusion.dev/helix-icons\`, \`uqr\` |
3692
3712
  | \`@fusion.dev/helix-icons\` | 150,162 | 21 | 50,346 | \`svgo\` |
3693
3713
  | \`@fusion.dev/helix-styles\` | 102,155 | 6 | 0 | none |
3694
- | \`@fusion.dev/helix-theme\` | 500,416 | 8 | 5,191 | none |
3695
- | \`@fusion.dev/helix\` | 14,618,004 | 876 | 373,795 | \`@fusion.dev/helix-core\`, \`@fusion.dev/helix-headless\`, \`@fusion.dev/helix-styles\` |
3714
+ | \`@fusion.dev/helix-theme\` | 514,288 | 8 | 5,300 | none |
3715
+ | \`@fusion.dev/helix\` | 14,628,121 | 876 | 373,810 | \`@fusion.dev/helix-core\`, \`@fusion.dev/helix-headless\`, \`@fusion.dev/helix-styles\` |
3696
3716
 
3697
3717
  ## Not measured yet
3698
3718
 
@@ -5584,53 +5604,65 @@ a theme from a few inputs, and the theme builder shows you the result.
5584
5604
 
5585
5605
  You enter the same inputs that \`derive()\` takes:
5586
5606
 
5587
- - a brand color
5588
- - a chroma ceiling
5589
- - a radius
5590
- - a density
5591
- - a contrast target
5592
- - a motion character
5607
+ - **Color:** the brand, the color scheme, the contrast target, the saturation,
5608
+ the accent angle, and the page's color in light and in dark
5609
+ - **Shape and type:** the density, the corner radius, the three faces, the body
5610
+ size, and the type scale
5611
+ - **Status:** how far the status colors follow the palette, and how far their
5612
+ hues may move
5613
+ - **Motion, separation, and material:** the motion character, how surfaces are
5614
+ set apart, and how floating surfaces are blurred and see-through
5593
5615
 
5594
- The theme builder runs the full derivation. It shows you every token, and the
5595
- components drawn with them.
5616
+ The theme builder runs the full derivation on every change. It shows a page
5617
+ drawn with the theme, and the stylesheet the theme generates beside it.
5596
5618
 
5597
- It shows light and dark at the same time. \`[data-color-mode]\` works on any
5598
- element, so the two previews are two subtrees of one document. See
5599
- [Color modes](./color-modes).
5619
+ The Color scheme field picks which half you see: light, dark, or the site's own
5620
+ mode. See [Color modes](./color-modes).
5600
5621
 
5601
- ## The contrast column
5622
+ ## A page of your own color
5602
5623
 
5603
- The contrast column lists every color pair Helix computed. Each pair shows its
5604
- ratio, measured against the background it is painted on. A pair has one of
5605
- three states:
5624
+ The Light page and Dark page fields give the page a color, such as a warm cream
5625
+ or a deep teal. They start at pure white and pure black, the page Helix draws
5626
+ without one. The surfaces keep the contrast with the page they keep with white
5627
+ or black, the grays take its tint, and every text color is solved against it. A
5628
+ page that no text color can reach the contrast target on is left out of the
5629
+ preview, and a caption under the fields says so.
5606
5630
 
5607
- - **Met.** The pair reaches the target.
5608
- - **Unverifiable.** The background is translucent, so there is no known color
5609
- to measure against. The pair neither passes nor fails. This is the cost of a
5610
- translucent material, and the theme builder reports it.
5611
- - **Pinned.** You set the color yourself. The engine did not compute it, so its
5612
- contrast is not guaranteed.
5631
+ **Color the figures band** gives one section of the Marketing site layout a
5632
+ color of its own, as its own theme. The band is dark or light by whichever text
5633
+ reads better on it, and its block follows the page's in the generated
5634
+ stylesheet. See [Color one section](./theming#color-one-section).
5613
5635
 
5614
- A column of \`unverifiable\` pairs means your theme makes a trade. The column lets
5615
- you see that you made it.
5636
+ ## The audit
5616
5637
 
5617
- ## What the theme builder exports
5638
+ The audit lists every color pair Helix computed. Each pair shows its ratio,
5639
+ measured against the background it is painted on, and either passes or fails
5640
+ its target. Its three tabs are:
5618
5641
 
5619
- The theme builder gives you the token block as CSS, to paste into your own
5642
+ - **Contrast.** The pairs that fail, or a line saying that every pair passes.
5643
+ - **Collisions.** Colors too close to each other to tell apart, such as the
5644
+ primary color and a status color.
5645
+ - **Unverifiable.** Pairs whose background is translucent, so there is no known
5646
+ color to measure against. This is the cost of a translucent material, and
5647
+ the theme builder reports it.
5648
+
5649
+ ## What the theme builder gives you
5650
+
5651
+ The generated stylesheet is the token block as CSS, to paste into your own
5620
5652
  stylesheet:
5621
5653
 
5622
5654
  \`\`\`css
5623
- :root {
5624
- --helix-color-primary: oklch(…);
5655
+ [data-theme="preview"] {
5656
+ --helix-color-background: #f7f2eb;
5625
5657
  …
5626
5658
  }
5627
5659
  \`\`\`
5628
5660
 
5629
- It also gives you the intent object, to keep in your repository and derive the
5630
- theme from again:
5661
+ The page's link holds every input you changed, so a link is the theme. To derive
5662
+ the theme in your own build, write the same inputs as an intent object:
5631
5663
 
5632
5664
  \`\`\`ts
5633
- export const theme = { brand: '#2563eb', chroma: { ceiling: 0.1 }, radius: 2 }
5665
+ export const theme = { background: { light: '#f7f2eb' }, brand: '#ff6200' }
5634
5666
  \`\`\`
5635
5667
 
5636
5668
  **Keep the intent object in your repository.** The tokens are the output of a
@@ -5757,6 +5789,39 @@ console.log(css[':root'])
5757
5789
  A value that is not a color and still changes with the mode, such as the edge
5758
5790
  of a floating surface, is set by rules after the block, one for each mode.
5759
5791
 
5792
+ ## Color one section
5793
+
5794
+ A section in a color of its own, such as a deep teal band on a cream page, is a
5795
+ theme of its own. Derive it from the same intent, with the section's color as
5796
+ its page, under a selector for the section:
5797
+
5798
+ \`\`\`ts
5799
+ const band = engine.derive(
5800
+ { ...intent, background: { dark: '#0b2a33' }, scheme: 'dark' },
5801
+ ['[data-band]'],
5802
+ )
5803
+ \`\`\`
5804
+
5805
+ Choose the scheme the color needs: \`dark\` for a color light text reads on, and
5806
+ \`light\` for one dark text reads on. A color no text can reach the contrast
5807
+ target on is refused, as a page is.
5808
+
5809
+ Mark the section so the stylesheet derives its own colors there from the
5810
+ section's seeds, in the section's mode, and paint it with its page color:
5811
+
5812
+ \`\`\`html
5813
+ <section data-band data-color-mode="dark" data-helix-theme>…</section>
5814
+ \`\`\`
5815
+
5816
+ \`\`\`css
5817
+ [data-band] {
5818
+ background-color: var(--helix-color-background);
5819
+ color: var(--helix-color-foreground);
5820
+ }
5821
+ \`\`\`
5822
+
5823
+ Write the section's block after the page's, so it wins inside the section.
5824
+
5760
5825
  ## Why Helix uses OKLCH
5761
5826
 
5762
5827
  Equal numeric steps in sRGB do not look like equal steps. That makes scales and
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "@fusion.dev/helix-docs",
3
3
  "description": "Versioned documentation content and registry for Helix.",
4
- "version": "0.131.0",
4
+ "version": "0.133.0",
5
5
  "license": "MIT",
6
6
  "author": "Ross Sheppard <ross.sheppard@fusion.dev>",
7
7
  "repository": {
@@ -36,14 +36,14 @@
36
36
  },
37
37
  "bugs": "https://github.com/project-fusion/fusion/issues",
38
38
  "devDependencies": {
39
- "@fusion.dev/helix": "0.131.0",
40
- "@fusion.dev/helix-cem": "0.131.0",
41
- "@fusion.dev/helix-headless": "0.131.0",
42
- "@fusion.dev/helix-icons": "0.131.0",
43
- "@fusion.dev/helix-map": "0.131.0",
44
- "@fusion.dev/helix-styles": "0.131.0",
45
- "@fusion.dev/helix-testing": "0.131.0",
46
- "@fusion.dev/helix-theme": "0.131.0",
39
+ "@fusion.dev/helix": "0.133.0",
40
+ "@fusion.dev/helix-cem": "0.133.0",
41
+ "@fusion.dev/helix-headless": "0.133.0",
42
+ "@fusion.dev/helix-icons": "0.133.0",
43
+ "@fusion.dev/helix-map": "0.133.0",
44
+ "@fusion.dev/helix-styles": "0.133.0",
45
+ "@fusion.dev/helix-testing": "0.133.0",
46
+ "@fusion.dev/helix-theme": "0.133.0",
47
47
  "@fusion.dev/scripts": "0.0.0-dev",
48
48
  "lit": "^3.2.1",
49
49
  "playwright": "^1.62.1"