@crewlethq/ui 0.4.4 → 0.5.1

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.
Files changed (231) hide show
  1. package/README.md +888 -24
  2. package/dist/Accordion/index.js +2 -2
  3. package/dist/AddPill/index.js +1 -1
  4. package/dist/{AddPill-DFWXYLIQ.css → AddPill-IJQYCY6C.css} +9 -0
  5. package/dist/AppShell/AppShell.d.ts +26 -5
  6. package/dist/AppShell/index.js +3 -3
  7. package/dist/{AppShell-NVE6LHNI.css → AppShell-XARELGIH.css} +178 -25
  8. package/dist/Avatar/Avatar.d.ts +85 -40
  9. package/dist/Avatar/AvatarStack.d.ts +76 -0
  10. package/dist/Avatar/index.d.ts +5 -2
  11. package/dist/Avatar/index.js +1 -1
  12. package/dist/Avatar-XID7Z74C.css +200 -0
  13. package/dist/AvatarStack-GEJBNV7E.css +72 -0
  14. package/dist/BrandLockup/index.js +1 -1
  15. package/dist/{BrandLockup-6ISDEHPJ.css → BrandLockup-JKGXFCZF.css} +25 -19
  16. package/dist/Button/Button.d.ts +7 -2
  17. package/dist/Button/index.js +1 -1
  18. package/dist/{Button-D4J6B4MA.css → Button-X4B2TJAQ.css} +50 -19
  19. package/dist/Callout/index.js +1 -1
  20. package/dist/Canvas/index.js +4 -4
  21. package/dist/Card/Card.d.ts +9 -5
  22. package/dist/Card/index.js +1 -1
  23. package/dist/{Card-RLR254LD.css → Card-GLP7SUV6.css} +25 -18
  24. package/dist/Charts/BarList.d.ts +18 -1
  25. package/dist/Charts/ChartTooltip.d.ts +68 -0
  26. package/dist/Charts/StackedBar.d.ts +25 -7
  27. package/dist/Charts/StackedColumns.d.ts +112 -0
  28. package/dist/Charts/TimeSeries.d.ts +33 -2
  29. package/dist/Charts/dataColor.d.ts +22 -14
  30. package/dist/Charts/index.d.ts +6 -0
  31. package/dist/Charts/index.js +1 -1
  32. package/dist/Charts/useChartHover.d.ts +56 -0
  33. package/dist/Charts-B3YEF7R4.css +742 -0
  34. package/dist/Checkbox/index.js +1 -1
  35. package/dist/{Checkbox-VGW26YLQ.css → Checkbox-BOXQ747I.css} +2 -2
  36. package/dist/CodeBlock/index.js +4 -4
  37. package/dist/Combobox/index.js +5 -5
  38. package/dist/CommandPalette/CommandPalette.d.ts +97 -6
  39. package/dist/CommandPalette/index.d.ts +1 -1
  40. package/dist/CommandPalette/index.js +9 -7
  41. package/dist/CommandPalette-C5AMKGN2.css +259 -0
  42. package/dist/Copyable/index.js +3 -3
  43. package/dist/DataTable/index.js +7 -7
  44. package/dist/{DataTable-37UWTRN6.css → DataTable-OLHPF7D4.css} +35 -38
  45. package/dist/DataView/index.js +16 -16
  46. package/dist/{DataView-256YF32J.css → DataView-N6JX464S.css} +5 -4
  47. package/dist/DateTimePicker/index.js +5 -5
  48. package/dist/DiffList/index.js +1 -1
  49. package/dist/Disclosure/index.js +2 -2
  50. package/dist/EntityChip/EntityChip.d.ts +9 -12
  51. package/dist/EntityChip/index.d.ts +1 -1
  52. package/dist/EntityChip/index.js +2 -2
  53. package/dist/ErrorBoundary/index.js +2 -2
  54. package/dist/{ErrorBoundary-ME36CQTA.css → ErrorBoundary-U2PA3LY2.css} +4 -4
  55. package/dist/IconButton/index.js +1 -1
  56. package/dist/{IconButton-VQGNMJDI.css → IconButton-TVEUWK6L.css} +2 -2
  57. package/dist/ImageUpload/ImageUpload.d.ts +10 -7
  58. package/dist/ImageUpload/index.js +2 -2
  59. package/dist/{ImageUpload-HKFIZR6D.css → ImageUpload-YCHJMUGX.css} +24 -10
  60. package/dist/Input/index.js +2 -2
  61. package/dist/Kbd/Kbd.d.ts +14 -4
  62. package/dist/Kbd/index.js +1 -1
  63. package/dist/Kbd-JPLDVJIP.css +71 -0
  64. package/dist/Layer/index.js +1 -1
  65. package/dist/Link/index.js +1 -1
  66. package/dist/List/index.js +1 -1
  67. package/dist/{List-XTHESXLR.css → List-MYJIV6MP.css} +12 -2
  68. package/dist/ListInput/index.js +6 -6
  69. package/dist/Listbox/index.js +2 -2
  70. package/dist/Listbox/useListbox.d.ts +2 -0
  71. package/dist/{Listbox-ZXYYNN6U.css → Listbox-6WJNJQVQ.css} +32 -7
  72. package/dist/Menu/index.js +4 -4
  73. package/dist/Meter/Meter.d.ts +103 -16
  74. package/dist/Meter/index.d.ts +2 -2
  75. package/dist/Meter/index.js +1 -1
  76. package/dist/{Meter-SKOOXQBC.css → Meter-5VCSFMZW.css} +46 -7
  77. package/dist/Modal/index.js +4 -4
  78. package/dist/{Modal-XYQJ4BL6.css → Modal-JAYBS2KS.css} +13 -4
  79. package/dist/OrgLabel/OrgLabel.d.ts +60 -24
  80. package/dist/OrgLabel/index.d.ts +1 -1
  81. package/dist/OrgLabel/index.js +2 -1
  82. package/dist/{OrgLabel-D7U6QJZD.css → OrgLabel-CR233G34.css} +9 -18
  83. package/dist/OrgNode/index.js +3 -2
  84. package/dist/OrgTable/OrgTable.d.ts +2 -2
  85. package/dist/OrgTable/index.js +8 -7
  86. package/dist/Popover/index.js +2 -2
  87. package/dist/PricingCard/index.js +3 -3
  88. package/dist/{PricingCard-JFI7RYXP.css → PricingCard-7EFXRSD2.css} +4 -5
  89. package/dist/SearchTrigger/SearchTrigger.d.ts +23 -4
  90. package/dist/SearchTrigger/index.d.ts +1 -1
  91. package/dist/SearchTrigger/index.js +1 -1
  92. package/dist/SearchTrigger-Z5D4AAY7.css +112 -0
  93. package/dist/SegmentedControl/index.js +2 -2
  94. package/dist/SegmentedMeter/SegmentedMeter.d.ts +107 -0
  95. package/dist/SegmentedMeter/index.d.ts +3 -0
  96. package/dist/SegmentedMeter/index.js +2 -0
  97. package/dist/SegmentedMeter-KQNML2TW.css +109 -0
  98. package/dist/Select/index.js +3 -3
  99. package/dist/Shortcut/index.js +2 -2
  100. package/dist/SidebarNav/SidebarNav.d.ts +85 -25
  101. package/dist/SidebarNav/index.d.ts +1 -1
  102. package/dist/SidebarNav/index.js +1 -1
  103. package/dist/SidebarNav-X5NLZNWA.css +424 -0
  104. package/dist/StatCard/StatCard.d.ts +59 -12
  105. package/dist/StatCard/index.d.ts +1 -1
  106. package/dist/StatCard/index.js +1 -1
  107. package/dist/StatCard-KPAFD4E2.css +204 -0
  108. package/dist/StatGroup/index.js +1 -1
  109. package/dist/{StatGroup-TGB6AEKM.css → StatGroup-HVG6O62W.css} +8 -9
  110. package/dist/StatusDot/StatusDot.d.ts +24 -6
  111. package/dist/StatusDot/index.js +1 -1
  112. package/dist/StatusDot-7OMCQCZF.css +186 -0
  113. package/dist/Stepper/Stepper.d.ts +78 -0
  114. package/dist/Stepper/index.d.ts +3 -0
  115. package/dist/Stepper/index.js +4 -0
  116. package/dist/Stepper-HW4JM3YH.css +176 -0
  117. package/dist/Tabs/index.js +1 -1
  118. package/dist/{Tabs-MJ2E3VPK.css → Tabs-XCNPHA7B.css} +46 -26
  119. package/dist/Tag/Tag.d.ts +29 -22
  120. package/dist/Tag/index.js +2 -2
  121. package/dist/{Tag-VNZEYLB6.css → Tag-GBE7LQJP.css} +82 -83
  122. package/dist/TagsInput/index.js +7 -7
  123. package/dist/ThemeSwitcher/ThemeSwitcher.d.ts +53 -21
  124. package/dist/ThemeSwitcher/index.d.ts +3 -3
  125. package/dist/ThemeSwitcher/index.js +4 -3
  126. package/dist/ThemeSwitcher/preferences.d.ts +19 -5
  127. package/dist/ThemeToggle/ThemeToggle.d.ts +40 -0
  128. package/dist/ThemeToggle/index.d.ts +2 -0
  129. package/dist/ThemeToggle/index.js +5 -0
  130. package/dist/TimeWindowPicker/index.js +8 -8
  131. package/dist/Toaster/index.js +2 -2
  132. package/dist/Toolbar/index.js +2 -2
  133. package/dist/{Toolbar-IP6LXN45.css → Toolbar-HUOSMNTH.css} +3 -1
  134. package/dist/Tooltip/index.js +2 -2
  135. package/dist/Tree/index.d.ts +2 -2
  136. package/dist/Tree/index.js +1 -1
  137. package/dist/Tree/layout.d.ts +103 -28
  138. package/dist/TreeCanvas/TreeCanvas.d.ts +60 -14
  139. package/dist/TreeCanvas/index.d.ts +1 -1
  140. package/dist/TreeCanvas/index.js +6 -6
  141. package/dist/TreeCanvas/motion.d.ts +3 -2
  142. package/dist/{TreeCanvas-WBNQPHC7.css → TreeCanvas-HVOV4SQN.css} +154 -30
  143. package/dist/TreeGrid/index.js +4 -4
  144. package/dist/{chunk-F6OE5FH3.js → chunk-2FPENTCF.js} +1 -1
  145. package/dist/chunk-4AK52VHB.js +88 -0
  146. package/dist/{chunk-7EM5T4ME.js → chunk-4IQD3HUQ.js} +2 -2
  147. package/dist/{chunk-YODNNSZL.js → chunk-4PZ6FJKW.js} +43 -13
  148. package/dist/{chunk-F27EPQ7D.js → chunk-4UQ7SMPK.js} +1 -1
  149. package/dist/chunk-5QWIJSQM.js +73 -0
  150. package/dist/{chunk-KIC7BZYJ.js → chunk-6MU7HNB4.js} +6 -5
  151. package/dist/{chunk-S2XHHEW4.js → chunk-74KMX7YH.js} +4 -4
  152. package/dist/{chunk-WNI2WSJF.js → chunk-7KBNFFM3.js} +1 -1
  153. package/dist/{chunk-EFSG7HNU.js → chunk-AUS5FNQE.js} +1 -1
  154. package/dist/{chunk-CMEE37QJ.js → chunk-BMYPGGPV.js} +4 -4
  155. package/dist/{chunk-H4FBTAYS.js → chunk-BNCCEER3.js} +8 -8
  156. package/dist/chunk-C5WJUZVR.js +56 -0
  157. package/dist/{chunk-5WS6L6FA.js → chunk-CAIHUYXV.js} +9 -9
  158. package/dist/{chunk-5KSRXHOW.js → chunk-CQY5NTRS.js} +1 -1
  159. package/dist/{chunk-MW356IVK.js → chunk-D6EVJUGU.js} +2 -2
  160. package/dist/{chunk-7PEFUMQJ.js → chunk-DHPUMOTX.js} +2 -2
  161. package/dist/{chunk-HZ5XZNPS.js → chunk-DS2C73RJ.js} +3 -3
  162. package/dist/{chunk-GKHAKGOF.js → chunk-DSUY5F4E.js} +3 -3
  163. package/dist/{chunk-Q4ZPPART.js → chunk-EFYPAJT3.js} +3 -3
  164. package/dist/{chunk-PATXSJGR.js → chunk-ERVO6OUF.js} +17 -17
  165. package/dist/{chunk-BZYDZBAN.js → chunk-ETYEBKR4.js} +3 -3
  166. package/dist/{chunk-CC67MUUO.js → chunk-FD5UEN6X.js} +30 -30
  167. package/dist/{chunk-5SDBMKUO.js → chunk-FIFNP6PL.js} +3 -3
  168. package/dist/{chunk-7HPRF5XN.js → chunk-FUF52K7E.js} +98 -16
  169. package/dist/{chunk-5KPQ6D7N.js → chunk-FZVJDJFN.js} +2 -2
  170. package/dist/chunk-IA232OTU.js +156 -0
  171. package/dist/{chunk-2EOKFKHX.js → chunk-IG27QX7Q.js} +7 -7
  172. package/dist/chunk-IKB6HFGK.js +55 -0
  173. package/dist/{chunk-T43A26SD.js → chunk-IPVQKAHO.js} +6 -6
  174. package/dist/{chunk-3EYF6HKB.js → chunk-IVFJD7WY.js} +28 -9
  175. package/dist/{chunk-XJWXPRSK.js → chunk-JGRNTBF2.js} +11 -11
  176. package/dist/chunk-K3OWD7BJ.js +121 -0
  177. package/dist/{chunk-6KCO2D5C.js → chunk-KD4H66L6.js} +7 -20
  178. package/dist/{chunk-SFZOKW2G.js → chunk-KJ34ZBBI.js} +8 -3
  179. package/dist/{chunk-AQTBF4EB.js → chunk-LFHCXZO5.js} +5 -5
  180. package/dist/{chunk-LWKJQTOM.js → chunk-MICH6QSJ.js} +1 -1
  181. package/dist/chunk-N3DPO6HG.js +226 -0
  182. package/dist/{chunk-S4GZWSKR.js → chunk-OM5E3TTK.js} +1 -1
  183. package/dist/{chunk-3QRYCPXQ.js → chunk-OPKIKM35.js} +6 -6
  184. package/dist/{chunk-5EKIWVOR.js → chunk-PGRPNDWM.js} +2 -2
  185. package/dist/{chunk-FSOW3ARP.js → chunk-PQNILU27.js} +9 -9
  186. package/dist/{chunk-QNCVHRZL.js → chunk-QVAFL2LE.js} +1 -1
  187. package/dist/{chunk-Q3B66TJM.js → chunk-QY7UU5ZB.js} +1 -1
  188. package/dist/{chunk-ITHXJHBB.js → chunk-R25RGPUB.js} +1 -0
  189. package/dist/{chunk-KLJCCMF3.js → chunk-R6735B37.js} +2 -2
  190. package/dist/{chunk-3ZP55QZE.js → chunk-R6FBDTP3.js} +4 -4
  191. package/dist/{chunk-7FZ53WDJ.js → chunk-RIAZM6L3.js} +1 -1
  192. package/dist/chunk-RJM4QCGG.js +550 -0
  193. package/dist/{chunk-NTRZGNEX.js → chunk-S3BCVWTU.js} +215 -46
  194. package/dist/chunk-S7KW47IQ.js +121 -0
  195. package/dist/{chunk-KNYYCWMK.js → chunk-SJQ546ID.js} +4 -4
  196. package/dist/{chunk-D35VTV2Z.js → chunk-SV7QAONL.js} +1 -1
  197. package/dist/{chunk-IAJLHVUA.js → chunk-TIWAHZZ6.js} +1 -1
  198. package/dist/{chunk-2PRH365R.js → chunk-UA7O3KKJ.js} +1 -1
  199. package/dist/{chunk-NPZY6YYL.js → chunk-UG5ZMAXW.js} +6 -6
  200. package/dist/{chunk-NDCATSW7.js → chunk-V34H2YCY.js} +1 -1
  201. package/dist/chunk-WIATRXEJ.js +22 -0
  202. package/dist/{chunk-5C5YMZQU.js → chunk-WOFOMTGB.js} +16 -10
  203. package/dist/{chunk-QYOFACSP.js → chunk-WSOFKOLP.js} +3 -3
  204. package/dist/{chunk-MNAXYY3R.js → chunk-WUVZDFHS.js} +31 -11
  205. package/dist/{chunk-DB2VDLVR.js → chunk-YIMOT5OO.js} +10 -10
  206. package/dist/{chunk-2ZQMA2WB.js → chunk-ZPSOF6VL.js} +2 -2
  207. package/dist/generated/index.d.ts +3 -0
  208. package/dist/generated/index.js +70 -66
  209. package/dist/index.js +70 -66
  210. package/dist/styles.css +2538 -741
  211. package/dist/utils/index.d.ts +1 -1
  212. package/dist/utils/tone.d.ts +7 -12
  213. package/package.json +4 -4
  214. package/scripts/check-css-literals.mjs +159 -23
  215. package/scripts/check-css-variables.mjs +5 -3
  216. package/scripts/css-source.mjs +97 -5
  217. package/dist/Avatar-P2KRQM2B.css +0 -156
  218. package/dist/Charts-D7G2BSXH.css +0 -277
  219. package/dist/CommandPalette-CSJDUCQA.css +0 -115
  220. package/dist/Kbd-W66MXQI5.css +0 -61
  221. package/dist/SearchTrigger-QXOYAUUY.css +0 -79
  222. package/dist/SidebarNav-QGSFKZYA.css +0 -319
  223. package/dist/StatCard-KYPKZUWX.css +0 -111
  224. package/dist/StatusDot-HA2L2FSX.css +0 -84
  225. package/dist/chunk-22O7LAW2.js +0 -41
  226. package/dist/chunk-AJNCATWZ.js +0 -144
  227. package/dist/chunk-F4PJZ4ED.js +0 -245
  228. package/dist/chunk-PNFASD6F.js +0 -98
  229. package/dist/chunk-PZSWF74H.js +0 -15
  230. package/dist/chunk-R66KLW7S.js +0 -143
  231. /package/dist/{chunk-ZCR6YGQ4.js → chunk-PKIN4IMB.js} +0 -0
@@ -1,11 +1,14 @@
1
1
  import { type HTMLAttributes, type ReactNode } from 'react';
2
2
  import { type HeadingLevel } from '../utils/headingLevel.js';
3
3
  export type CardVariant =
4
- /** One step above the page. */
4
+ /**
5
+ * The card rung inside the default hairline, flat: no shadow and no rim.
6
+ * What finds it on the sheet is the rung's step and the hairline's.
7
+ */
5
8
  'default'
6
9
  /**
7
- * The TILE: the panel's ground with none of its lift, at the tighter inset,
8
- * for one of many records in a grid. Its default padding is `tight`.
10
+ * The TILE: the card at the tighter inset, for one of many records in a
11
+ * grid. Its default padding is `tight`.
9
12
  */
10
13
  | 'subtle'
11
14
  /** Transparent, with a strong border. */
@@ -23,8 +26,9 @@ export type CardVariant =
23
26
  /** Lifted off the page. */
24
27
  | 'elevated'
25
28
  /**
26
- * A dashed boundary: something that is not quite a record yet. A seat held
27
- * by a person rather than an agent, a slot waiting to be filled.
29
+ * A dashed boundary: something that is not quite a record yet, a slot
30
+ * waiting to be filled. Never a person: a seat a person holds is a record
31
+ * like any other, and its badge's circle is what says who holds it.
28
32
  */
29
33
  | 'dashed';
30
34
  /**
@@ -1,4 +1,4 @@
1
- export { Card } from '../chunk-NDCATSW7.js';
1
+ export { Card } from '../chunk-V34H2YCY.js';
2
2
  export { useCardHeaderSlot } from '../chunk-AV2DXAEL.js';
3
3
  import '../chunk-BHHIIK3M.js';
4
4
  import '../chunk-PQADV6P6.js';
@@ -27,23 +27,24 @@
27
27
  }
28
28
 
29
29
  /*
30
- * TWO GROUNDS, TWO DEVICES. On light the shadow is the elevation; on dark a
31
- * shadow over a dark page is nearly invisible, so the hairline along the top
32
- * edge does the job instead.
30
+ * THE CARD IS FLAT: the card rung inside the default hairline, at the 12px
31
+ * corner, and nothing else, which is the approved design's card in both
32
+ * palettes. It casts no shadow and draws no rim of light, because what finds a
33
+ * card on the sheet is the pair the palette suite holds together: the rung a
34
+ * visible step off the sheet, and the hairline a clear step off both. A
35
+ * shadow under every panel of a screen made a list of records into a relief
36
+ * map, and a rim along every top edge was a second hairline nobody measured.
37
+ * Lift belongs to what genuinely stands OVER the page, which is `elevated`.
33
38
  *
34
- * THE HAIRLINE IS ON ITS OWN ELEMENT, and that is the whole reason the rule is
35
- * two rules. `--shadow-hairline` is `none` in the light theme, and `none` is a
36
- * value a shadow list may not carry: `box-shadow: <shadow>, none` is invalid at
37
- * computed-value time, so the declaration is dropped and the light card loses
38
- * the elevation the list was built around. Alone on a pseudo element the same
39
- * token is valid in both themes, and it composes with the selection ring
40
- * rather than replacing whichever was declared last, exactly as the rail does.
39
+ * THE RIM IS ON ITS OWN ELEMENT where it is still drawn, and that is the whole
40
+ * reason the elevated card's rule is two rules. `--shadow-hairline` is `none`
41
+ * in the light theme, and `none` is a value a shadow list may not carry:
42
+ * `box-shadow: <shadow>, none` is invalid at computed-value time, so the
43
+ * declaration is dropped and the light card loses the elevation the list was
44
+ * built around. Alone on a pseudo element the same token is valid in both
45
+ * themes, and it composes with the selection ring rather than replacing
46
+ * whichever was declared last, exactly as the rail does.
41
47
  */
42
- .crewlet-card--default:not(.crewlet-card--flush) {
43
- box-shadow: var(--shadow-xs);
44
- }
45
-
46
- .crewlet-card--default:not(.crewlet-card--flush)::after,
47
48
  .crewlet-card--elevated::after {
48
49
  content: '';
49
50
  position: absolute;
@@ -58,8 +59,9 @@
58
59
  }
59
60
 
60
61
  /*
61
- * THE TILE: the panel's ground with none of its lift. One of many in a grid,
62
- * where a shadow under every card turns a list of records into a relief map.
62
+ * THE TILE: the card at the tile's tighter inset. One of many records in a
63
+ * grid, where at the panel's own step each tile spends a third of its height
64
+ * on air.
63
65
  *
64
66
  * It used to take the PAGE's ground, which is a card drawn in the colour of
65
67
  * the thing behind it: on the light palette a white tile on a white page, held
@@ -186,9 +188,14 @@
186
188
  box-shadow var(--motion-duration-base) var(--motion-easing-default);
187
189
  }
188
190
 
191
+ /*
192
+ * Under the pointer the hairline steps up and nothing lifts: a flat card that
193
+ * rose on hover would be the one shadow on the screen, and it would move as
194
+ * the pointer crossed a grid of them. The approved design's card answers the
195
+ * pointer with its boundary alone.
196
+ */
189
197
  .crewlet-card.is-interactive:hover {
190
198
  border-color: var(--color-border-hover);
191
- box-shadow: var(--shadow-md);
192
199
  }
193
200
 
194
201
  .crewlet-card.is-interactive:focus-visible {
@@ -21,8 +21,25 @@ export interface BarDatum {
21
21
  /** What pressing the row does, where it is not a destination. */
22
22
  onSelect?: () => void;
23
23
  }
24
+ /**
25
+ * Where a row's bar stands against its words.
26
+ *
27
+ * `stacked`, the default, is the UNDERLINE register: the label and its value
28
+ * on one line, and a thin bar across the whole row under them, for a list
29
+ * read as a list of names with a measure under each.
30
+ *
31
+ * `beside` is the design's own ranked figure, the Home screen's "Tokens by
32
+ * team" and Spend's "By model": the label (and its `sub`) in a column of its
33
+ * own, then a bar up to 12px thick, then the value at the bar's END, so a
34
+ * reader's eye runs from the name along the bar to the number. It draws no
35
+ * track: the bars share one baseline and the longest reaches the end of the
36
+ * scale, which is all a track would say.
37
+ */
38
+ export type BarListLayout = 'stacked' | 'beside';
24
39
  export interface BarListProps {
25
40
  data: BarDatum[];
41
+ /** Where the bar stands against the words: see the type. Defaults to `stacked`. */
42
+ layout?: BarListLayout;
26
43
  /** The value the longest bar stands for. Defaults to the largest present. */
27
44
  max?: number;
28
45
  /** How many rows to draw. The rest are counted by `moreLabel`. */
@@ -48,4 +65,4 @@ export interface BarListProps {
48
65
  * so the bar adds a shape to a number that is already readable, and a reader
49
66
  * who cannot see it has lost nothing.
50
67
  */
51
- export declare function BarList({ data, max, limit, moreLabel, emptyLabel, className, }: BarListProps): import("react").JSX.Element;
68
+ export declare function BarList({ data, layout, max, limit, moreLabel, emptyLabel, className, }: BarListProps): import("react").JSX.Element;
@@ -0,0 +1,68 @@
1
+ import type { ReactNode } from 'react';
2
+ export interface ChartTooltipRow {
3
+ /** The series this row reads, so a row keeps its node as the reading moves. */
4
+ id: string;
5
+ name: ReactNode;
6
+ /** The value, already formatted: "1.2M", "38 turns". */
7
+ value: ReactNode;
8
+ /**
9
+ * The series' colour, drawn as a SWATCH beside the name and never as the
10
+ * colour of any text: a data hue is a mark measured against the surface as
11
+ * a mark, and read as text it holds none of the contrast a word needs.
12
+ */
13
+ color?: string | undefined;
14
+ }
15
+ export interface ChartTooltipProps {
16
+ /** Whether a reading is showing. Closed, the live region stays and is empty. */
17
+ open: boolean;
18
+ /**
19
+ * Where the mark being read stands, as fractions of the plot's width: its
20
+ * `start` and `end` edges, or one `start` for a mark with no width (the
21
+ * crosshair on a time series). The tooltip stands beside the mark, on the
22
+ * side with more room, and never over it.
23
+ */
24
+ anchor?: {
25
+ start: number;
26
+ end?: number | undefined;
27
+ } | undefined;
28
+ /** The line naming what is read: the bucket's time, the column's label. */
29
+ title?: ReactNode;
30
+ rows?: readonly ChartTooltipRow[];
31
+ /** The sum, where the rows are parts of one whole. */
32
+ total?: {
33
+ label?: ReactNode;
34
+ value: ReactNode;
35
+ } | undefined;
36
+ className?: string;
37
+ }
38
+ /**
39
+ * The reading of one mark, beside it.
40
+ *
41
+ * POSITIONED BY A STYLE PROPERTY, NEVER BY A STYLE ELEMENT. The one value that
42
+ * varies (how far across the plot the mark stands) is set as `left` on the
43
+ * element React draws, which a strict Content-Security-Policy allows because it
44
+ * goes through the CSSOM rather than through markup the policy has to trust;
45
+ * everything else is a rule in the stylesheet. It is ABSOLUTE in the nearest
46
+ * positioned ancestor, which is the chart's plot frame, so a chart in a
47
+ * scrolled panel, a dialog or a transformed canvas needs no measuring at all.
48
+ *
49
+ * THE SIDE IS THE ROOMIER ONE. A mark in the first half of the plot has its
50
+ * tooltip after it and one in the second half before it, so the box never runs
51
+ * off the end of a plot that ends at the edge of a card, and it never covers
52
+ * the mark being read.
53
+ *
54
+ * TEXT TOKENS ONLY, ON GLASS. Every word is a text step: the title the
55
+ * tertiary step, a series' name the secondary and every number the primary.
56
+ * The box stands over the marks beside the one it reads, so its ground is the
57
+ * frosted glass rather than the card, which is translucent in the marketing
58
+ * palette and let a column's hue through the words; the palette suite holds
59
+ * each step over 4.5:1 on the glass with every data hue behind it.
60
+ * A series' hue is its swatch, which is a mark; painted into its name it would
61
+ * be a word at whatever contrast a chart hue happens to have.
62
+ *
63
+ * IT IS THE LIVE REGION. The element that is always there is polite, and the
64
+ * box is drawn inside it only while a reading shows, so a keyboard reader
65
+ * walking the marks hears each one as they land on it: the tooltip is what
66
+ * they would have read with their eyes, said once.
67
+ */
68
+ export declare function ChartTooltip({ open, anchor, title, rows, total, className }: ChartTooltipProps): import("react").JSX.Element;
@@ -17,22 +17,40 @@ export interface StackedBarProps {
17
17
  value: number;
18
18
  percent: number;
19
19
  }[]) => string;
20
+ /**
21
+ * How a value reads out, in the default sentence and in a part's reading.
22
+ * Defaults to the reader's own number format.
23
+ */
24
+ format?: (value: number) => string;
20
25
  className?: string;
21
26
  }
22
27
  /**
23
28
  * One whole, split into its parts.
24
29
  *
25
30
  * ALWAYS BESIDE ITS LEGEND. The bar carries no labels of its own, so without
26
- * a Legend the parts are anonymous colours; pair the two, always, and key
27
- * both from the same list.
31
+ * a Legend the parts are anonymous colours at a glance, and only a reader who
32
+ * stops on each one learns what it is; pair the two, always, and key both from
33
+ * the same list.
34
+ *
35
+ * THE PARTS STAND 2PX APART, and the gap comes out of the parts: each part
36
+ * GROWS by its value into the track's width less the gaps, rather than taking
37
+ * a percentage of the whole, which with a gap between them would add up to
38
+ * more than the track and push the last part out of it.
28
39
  *
29
40
  * A ZERO PART IS NOT DRAWN. Every segment used to get at least two pixels so
30
41
  * that it existed, which drew a phase that never ran as a thin slice of one
31
42
  * that did, and made the eleven-part bar of a quiet company look busy.
32
43
  *
33
- * THE VALUES ARE IN THE MARKUP, not only in a `title`. A tooltip on a
34
- * fragment of a bar is reachable by a mouse and by nothing else: no keyboard,
35
- * no screen reader, no touch. The summary sentence is what a reader who
36
- * cannot hover is left with, so it says everything the picture does.
44
+ * THE VALUES ARE IN THE MARKUP, not only in a tooltip. The summary sentence
45
+ * is what a reader who cannot see the bar is left with, so it says everything
46
+ * the picture does, and it is the NAME of the plot, so a keyboard reader who
47
+ * tabs onto the bar hears it before reading a single part.
48
+ *
49
+ * AND EACH PART CAN BE READ ON ITS OWN, by the reading layer every chart here
50
+ * shares (see `useChartHover`): pointing at a part, or walking the parts with
51
+ * ←/→ once the bar has focus, opens a tooltip beside it with the part's name,
52
+ * its value and share, and the whole. A part's colour is its place in
53
+ * `segments`, zero parts included, so the swatch in its reading is the hue the
54
+ * Legend keyed from the same list shows.
37
55
  */
38
- export declare function StackedBar({ segments, summary, className }: StackedBarProps): import("react").JSX.Element;
56
+ export declare function StackedBar({ segments, summary, format, className }: StackedBarProps): import("react").JSX.Element;
@@ -0,0 +1,112 @@
1
+ import type { ReactNode } from 'react';
2
+ export interface StackedColumnsSeries {
3
+ /** What the series is, as a stable identity: its colour and its node follow it. */
4
+ id: string;
5
+ name: string;
6
+ /** Defaults to the series' own place in `series`, in the data ramp. */
7
+ color?: string;
8
+ }
9
+ export interface StackedColumnsBucket {
10
+ /** The bucket's start, epoch milliseconds. It is the column's identity. */
11
+ t: number;
12
+ /** Each series' value in this bucket, by series id. A missing id is zero. */
13
+ values: Readonly<Record<string, number>>;
14
+ }
15
+ /**
16
+ * Where the chart draws its legend.
17
+ *
18
+ * `below`, the default, under the dates. `head` at the END of the chart's head
19
+ * row, top right, where the design's Spend card draws it beside the card's
20
+ * title: pass that title as `head` and the two share one line. `none` draws no
21
+ * legend, for a screen that names the series somewhere the chart cannot reach;
22
+ * the chart is then that screen's to caption, and a stacked figure without its
23
+ * legend is a picture of some numbers.
24
+ */
25
+ export type StackedColumnsLegend = 'below' | 'head' | 'none';
26
+ export interface StackedColumnsProps {
27
+ /**
28
+ * Every series the figure CAN draw, in stacking order: the first stands on
29
+ * the baseline. Filter with `hidden`, never by leaving one out of this list,
30
+ * because a series' colour is its place here.
31
+ */
32
+ series: readonly StackedColumnsSeries[];
33
+ /** One column per bucket, oldest first. */
34
+ buckets: readonly StackedColumnsBucket[];
35
+ /**
36
+ * The series not drawn, by id. They leave the columns, the scale, the
37
+ * tooltip and its total, and every other series keeps its colour.
38
+ */
39
+ hidden?: readonly string[];
40
+ /** What the chart is, read in place of the picture: "tokens per day by phase". */
41
+ label: string;
42
+ /** Where the legend goes: see the type. Defaults to `below`. */
43
+ legend?: StackedColumnsLegend;
44
+ /**
45
+ * The chart's head: a title and what qualifies it, drawn at the START of a
46
+ * row over the plot, with the legend at its end when `legend` is `head`.
47
+ */
48
+ head?: ReactNode;
49
+ /** How tall the plot is, as a CSS length. */
50
+ height?: string;
51
+ /** How a value reads out, on the scale and in the tooltip. Defaults to a compact number. */
52
+ format?: (value: number) => string;
53
+ /** How a bucket reads out, under the plot and in the tooltip. Defaults to the reader's date. */
54
+ formatTime?: (at: number) => string;
55
+ /** The chart's own sentence. The default names the window, the tallest column and each series' total. */
56
+ summary?: (facts: {
57
+ from: number | null;
58
+ to: number | null;
59
+ peak: number;
60
+ series: {
61
+ name: string;
62
+ total: number;
63
+ }[];
64
+ }) => string;
65
+ className?: string;
66
+ }
67
+ /**
68
+ * The scale's top and its step: a round number at or above the tallest
69
+ * column, in about four steps of 1, 2, 2.5 or 5 of a power of ten. A scale
70
+ * that stops at the peak itself labels its lines 0, 0.33M and 0.66M, which
71
+ * nobody reads at a glance.
72
+ */
73
+ export declare function niceScale(peak: number, steps?: number): {
74
+ top: number;
75
+ step: number;
76
+ };
77
+ /**
78
+ * A quantity per bucket over time, split into its parts: the column chart.
79
+ *
80
+ * A COLUMN IS ITS BUCKET'S TOTAL, and its parts share that height in
81
+ * proportion. The parts stand 2px apart, and the gap comes out of the parts
82
+ * rather than being added on top, so the column's top is exactly where its
83
+ * total reads on the scale. Only the VALUE END is rounded, the top of the
84
+ * topmost part, because the baseline is where every column starts and a
85
+ * rounded foot would lift it off the axis.
86
+ *
87
+ * COLOUR FOLLOWS THE SERIES ID. A series' hue is its place in `series`, and
88
+ * filtering is `hidden` rather than a shorter list, so hiding one part never
89
+ * repaints the survivors: the blue a reader learnt for "execute" is still
90
+ * "execute" after they switched "review" off. A Legend beside the chart lists
91
+ * the same series in the same order, or passes each `color`.
92
+ *
93
+ * A ZERO PART IS NOT DRAWN, and an empty bucket is a column of no height: the
94
+ * bucket happened and nothing happened in it.
95
+ *
96
+ * THE READING IS PER COLUMN. Pointing at a column, or walking the columns with
97
+ * ←/→ once the plot has focus, opens a tooltip beside it with every part and
98
+ * the total (see `useChartHover`); the tooltip is the live region, so a screen
99
+ * reader hears the same.
100
+ *
101
+ * IT DRAWS ITS OWN LEGEND, from the same list and in the same colours, with
102
+ * the hidden series left out. A legend written beside the chart by its caller
103
+ * was a second copy of `series` that had to be kept in step by hand, and the
104
+ * figure is never meant to be drawn without one; `legend` says only WHERE,
105
+ * under the dates or at the end of the chart's head, top right, as the
106
+ * design's Spend card has it.
107
+ *
108
+ * All of it is HTML positioned by style properties, so it holds a crisp 2px
109
+ * gap and a true 4px corner at any width, which a stretched SVG cannot, and no
110
+ * style element is ever drawn.
111
+ */
112
+ export declare function StackedColumns({ series, buckets, hidden, label, legend, head, height, format, formatTime, summary, className, }: StackedColumnsProps): import("react").JSX.Element;
@@ -61,6 +61,12 @@ export interface TimeSeriesProps {
61
61
  * scale, then the whole of it again. A name is how a graphic carries its
62
62
  * meaning; a second copy in the text is not a fallback, it is a repeat.
63
63
  *
64
+ * A READING, BY POINTER OR BY KEY. Over the plot a crosshair stands on the
65
+ * nearest instant any series has a point at, and a tooltip beside it reads
66
+ * every series at that instant. The plot is one tab stop, and ←/→ walk the
67
+ * same instants (see `useChartHover`), so what a mouse can read a keyboard
68
+ * can too; the tooltip is the live region, so a screen reader hears each one.
69
+ *
64
70
  * The plot is hand drawn rather than taken from a charting library for one
65
71
  * reason that decides it: every mark here reads tokens, in two themes, at the
66
72
  * contrast floors the palette suite measures, and a library's theming surface
@@ -69,8 +75,23 @@ export interface TimeSeriesProps {
69
75
  export declare function TimeSeries({ series, from, to, label, height, format, formatTime, summary, className, }: TimeSeriesProps): import("react").JSX.Element;
70
76
  export interface SparklineProps {
71
77
  values: readonly number[];
72
- /** The line's colour. Defaults to the accent, which is what a trend takes. */
78
+ /**
79
+ * The line's colour. Defaults to the residual neutral, `DATA_COLOR_OTHER`:
80
+ * a shape beside a number is named by that number rather than by a legend,
81
+ * and a series hue is spent only inside a figure that names it.
82
+ */
73
83
  color?: string;
84
+ /**
85
+ * Marks the LAST value as now, with a point in the accent at the line's
86
+ * end: the approved design's "you are here" on a trend. The accent means
87
+ * where the reader is, and on a trend that is the present.
88
+ *
89
+ * The point is cut out of the ground it stands on by a 2px ring of
90
+ * `--crewlet-spark-ground`, the card by default, because a sparkline sits
91
+ * beside a number on a card; one drawn on another rung sets the variable on
92
+ * itself or an ancestor.
93
+ */
94
+ current?: boolean | undefined;
74
95
  /** How tall the shape is, as a CSS length. */
75
96
  height?: string;
76
97
  className?: string;
@@ -86,7 +107,17 @@ export interface SparklineProps {
86
107
  * already say; a shape that genuinely carries a fact on its own is a
87
108
  * TimeSeries, which has a window, a peak and a sentence.
88
109
  *
110
+ * THE LINE IS THE NEUTRAL AND THE PRESENT IS THE ACCENT. With `current` the
111
+ * last value is marked by one accent point, which is the only colour the
112
+ * shape spends: the trend is a quiet mark and "now" is where the eye lands.
113
+ *
114
+ * THE POINT IS NOT PART OF THE PLOT. The plot is stretched to whatever box it
115
+ * is given, so a circle drawn in its viewBox would come out as an ellipse as
116
+ * wide as the box is long; the point is its own element over the plot,
117
+ * placed by the last value's height as a fraction of the box, and stays
118
+ * round at every width.
119
+ *
89
120
  * Fewer than two values draw nothing, and the box keeps its height, so a row
90
121
  * of figures does not jump as one of them gains its second point.
91
122
  */
92
- export declare function Sparkline({ values, color, height, className }: SparklineProps): import("react").JSX.Element;
123
+ export declare function Sparkline({ values, color, current, height, className, }: SparklineProps): import("react").JSX.Element;
@@ -1,20 +1,28 @@
1
1
  /**
2
- * The data ramp: five series and a residual, in a fixed order.
2
+ * The data ramp: four series and a residual, in a fixed order.
3
3
  *
4
- * FIVE, AND THEN EVERYTHING ELSE. The ramp is measured for five hues that a
5
- * reader can tell apart from each other and from the accent under normal,
6
- * protan and deutan vision; a sixth would have to sit between two of them,
7
- * and the honest answer to "what colour is the eleventh series" is that
8
- * eleven series are not a comparison anybody can read. Past the fifth, a
9
- * series takes the residual, which is the neutral that means "the rest".
4
+ * FOUR, AND THEN EVERYTHING ELSE. The ramp is measured for four hues that a
5
+ * reader can tell apart from their neighbours, from the reserved danger red and
6
+ * from the accent, under normal, protan and deutan vision; a fifth would have
7
+ * to sit between two of them, and the honest answer to "what colour is the
8
+ * eleventh series" is that eleven series are not a comparison anybody can
9
+ * read. Past the fourth, a series takes the residual, which is the neutral
10
+ * that means "the rest".
10
11
  *
11
- * A DATA HUE IS ONLY EVER USED INSIDE A CHART THAT CARRIES A LEGEND. It says
12
- * "this series", and a mark with no legend says nothing at all. Status,
13
- * phase and the accent have their own families for exactly that reason: a
14
- * chart colour never means success, and never means "you are here".
12
+ * A DATA HUE IS ONLY EVER USED INSIDE A FIGURE THAT NAMES IT: a legend for two
13
+ * series or more, the label for one. It says "this series", and a mark nothing
14
+ * names says nothing at all. State and the accent have their own families for
15
+ * exactly that reason: a chart colour never means done or stopped, and never
16
+ * means "you are here".
17
+ *
18
+ * A CATEGORY IS A SERIES HERE, and only here. A phase, a unit or a model has no
19
+ * hue of its own anywhere else in the kit, so a figure that draws one per phase
20
+ * takes its series from this ramp in an order the APPLICATION declares, phase
21
+ * to index, and keeps that order across every figure it draws them in; the
22
+ * legend is what says which is which.
15
23
  */
16
- export declare const DATA_COLORS: readonly ["var(--color-data-1)", "var(--color-data-2)", "var(--color-data-3)", "var(--color-data-4)", "var(--color-data-5)"];
17
- /** The neutral for everything past the fifth series. */
24
+ export declare const DATA_COLORS: readonly ["var(--color-data-1)", "var(--color-data-2)", "var(--color-data-3)", "var(--color-data-4)"];
25
+ /** The neutral for everything past the fourth series. */
18
26
  export declare const DATA_COLOR_OTHER = "var(--color-data-other)";
19
- /** The colour of series `index`, with everything past the fifth as the residual. */
27
+ /** The colour of series `index`, with everything past the fourth as the residual. */
20
28
  export declare function dataColor(index: number): string;
@@ -10,3 +10,9 @@ export { ActivityStrip } from './ActivityStrip.js';
10
10
  export type { ActivityBucket, ActivityStripProps } from './ActivityStrip.js';
11
11
  export { TimeSeries, Sparkline } from './TimeSeries.js';
12
12
  export type { Series, SeriesPoint, SparklineProps, TimeSeriesProps } from './TimeSeries.js';
13
+ export { StackedColumns, niceScale } from './StackedColumns.js';
14
+ export type { StackedColumnsBucket, StackedColumnsProps, StackedColumnsSeries } from './StackedColumns.js';
15
+ export { ChartTooltip } from './ChartTooltip.js';
16
+ export type { ChartTooltipProps, ChartTooltipRow } from './ChartTooltip.js';
17
+ export { useChartHover } from './useChartHover.js';
18
+ export type { ChartHover, ChartHoverSource } from './useChartHover.js';
@@ -1,3 +1,3 @@
1
- export { ActivityStrip, BarList, DATA_COLORS, DATA_COLOR_OTHER, Legend, Sparkline, StackedBar, TimeSeries, dataColor } from '../chunk-F4PJZ4ED.js';
1
+ export { ActivityStrip, BarList, ChartTooltip, DATA_COLORS, DATA_COLOR_OTHER, Legend, Sparkline, StackedBar, StackedColumns, TimeSeries, dataColor, niceScale, useChartHover } from '../chunk-RJM4QCGG.js';
2
2
  import '../chunk-BZFWDIV6.js';
3
3
  import '../chunk-ODEQTPFM.js';
@@ -0,0 +1,56 @@
1
+ import type { FocusEvent, KeyboardEvent, PointerEvent } from 'react';
2
+ /** What moved the reading: a pointer over the plot, or a key on the focused plot. */
3
+ export type ChartHoverSource = 'pointer' | 'keyboard';
4
+ export interface ChartHover {
5
+ /**
6
+ * The mark being read, as an index into the chart's own marks, or null when
7
+ * nothing is. Always inside `0..count-1`: a push that shortens the data
8
+ * clamps it to the last mark rather than pointing past the end.
9
+ */
10
+ active: number | null;
11
+ /** What put `active` there, or null when nothing is being read. */
12
+ source: ChartHoverSource | null;
13
+ /**
14
+ * Point at a mark, or at nothing, from a pointer. A chart calls it from its
15
+ * own pointer handler, because only the chart knows which mark lies under a
16
+ * position: a column chart per column, a time series by nearest instant.
17
+ */
18
+ point: (index: number | null) => void;
19
+ /**
20
+ * Spread on the ONE focusable element that holds the plot. It is what takes
21
+ * the keys, and what ends a reading when focus or the pointer leaves it.
22
+ */
23
+ plotProps: {
24
+ tabIndex: 0;
25
+ onKeyDown: (event: KeyboardEvent<HTMLElement>) => void;
26
+ onBlur: (event: FocusEvent<HTMLElement>) => void;
27
+ onPointerLeave: (event: PointerEvent<HTMLElement>) => void;
28
+ };
29
+ }
30
+ /**
31
+ * The reading layer every chart here shares: which mark a reader is on, moved
32
+ * by a pointer or by the keyboard, and dismissed by Escape.
33
+ *
34
+ * THE KEYBOARD IS NOT AN AFTERTHOUGHT OF THE POINTER. A tooltip a mouse alone
35
+ * can open is a figure a keyboard reader cannot read, so the plot is ONE tab
36
+ * stop and ←/→ walk its marks (Home and End jump to the ends). The first key on
37
+ * a plot nobody has read yet opens where that key points: ← and End at the last
38
+ * mark, which is "now" on every chart this kit draws, → and Home at the first.
39
+ * After that a key moves from where the reading stands, and it stops at an end
40
+ * rather than wrapping: a time axis does not come round again.
41
+ *
42
+ * ESCAPE CLOSES THE READING AND ONLY THAT. It stops at the plot when it closed
43
+ * something, so a chart inside a dialog does not take the dialog down with its
44
+ * tooltip; with nothing open it passes through untouched. The place is
45
+ * remembered, so the next arrow reopens where the reader left off rather than
46
+ * throwing them back to an end.
47
+ *
48
+ * A READING ENDS WHERE ITS READER LEFT. Focus leaving the plot ends any
49
+ * reading. The pointer leaving ends a POINTER reading only: a keyboard reader
50
+ * whose mouse happens to drift off the card has not stopped reading.
51
+ *
52
+ * It holds an index and nothing else. What an index MEANS (a column, an
53
+ * instant) and where its tooltip stands are the chart's, so this never
54
+ * measures anything and never draws anything.
55
+ */
56
+ export declare function useChartHover(count: number): ChartHover;