@salemcobalt/ui 0.2.0-rc.0 → 0.2.0-rc.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +56 -13
- package/dist/index.d.ts +988 -16
- package/dist/index.js +738 -0
- package/dist/index.js.map +1 -1
- package/dist/styles.css +1181 -3
- package/package.json +4 -4
package/README.md
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
# @salemcobalt/ui
|
|
2
2
|
|
|
3
|
-
React 19 components for the Salem Cobalt design system: `Button`, `IconButton`, `Icon` and a shipped icon set, `Badge`, `Card`, `Stack`, `Inline`, `Kbd`, `Dialog`, `Tooltip`, `Menu`. Requires `@salemcobalt/tokens`.
|
|
3
|
+
React 19 components for the Salem Cobalt design system: `Button`, `IconButton`, `Icon` and a shipped icon set, `Badge`, `Card`, `Stack`, `Inline`, `Heading`, `Text`, `Kbd`, `Dialog`, `Tooltip`, `Menu`, `Toolbar`, `Banner`, `Spinner`, `Progress`, `Tabs`, `Input`, `Textarea`, `Select`, `Checkbox`, `Switch`, `Table`, `Stat`. Requires `@salemcobalt/tokens`.
|
|
4
4
|
|
|
5
5
|
```ts
|
|
6
6
|
import '@salemcobalt/tokens/css'; // custom properties, light + dark
|
|
@@ -23,18 +23,24 @@ import {
|
|
|
23
23
|
|
|
24
24
|
Styles ship as one stylesheet inside `@layer sc`, so an app's unlayered CSS always wins. Every value in it is a token custom property; theme with `data-theme="light|dark"` on `<html>` and density with `data-density="compact"` on any ancestor. Interactive behaviour (Dialog, Tooltip and Menu focus and keyboard handling, `render` composition) comes from Base UI; see `docs/adr/0001-headless-primitives.md`.
|
|
25
25
|
|
|
26
|
-
| Component
|
|
27
|
-
|
|
|
28
|
-
| `Button`
|
|
29
|
-
| `IconButton`
|
|
30
|
-
| `Icon`, `*Icon`
|
|
31
|
-
| `Badge`
|
|
32
|
-
| `Card`
|
|
33
|
-
| `Stack`, `Inline`
|
|
34
|
-
| `Kbd`
|
|
35
|
-
| `Dialog`
|
|
36
|
-
| `
|
|
37
|
-
| `
|
|
26
|
+
| Component | Notes |
|
|
27
|
+
| -------------------- | ---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
|
28
|
+
| `Button` | `variant` primary · secondary · ghost · danger; `size` sm · md · lg; `iconStart`/`iconEnd`; `loading` (keeps width, `aria-busy`); `fullWidth`. |
|
|
29
|
+
| `IconButton` | Square Button for one icon. Required `label` (the accessible name); `variant` ghost (default) · secondary · primary · danger; `size`; `tooltip` (`true` shows `label`, or a string); `tooltipSide`; `round`; `loading`. |
|
|
30
|
+
| `Icon`, `*Icon` | 49 outline icons on a 16px grid in `currentColor`, one component each (`PlayIcon`, `ChevronDownIcon` …, listed in `iconNames`); `size` xs 12 · sm 14 · md 16 · lg 20 · xl 24 · em; decorative unless `title` is given. `Icon` wraps your own paths. |
|
|
31
|
+
| `Badge` | `tone` neutral · accent · success · warning · danger · info; `variant` soft · solid · outline; `size` sm · md; `dot`. Text only. |
|
|
32
|
+
| `Card` | `variant` outlined · elevated · filled; `padding` none · sm · md · lg; `interactive`; `selected`; `as` or `render` to make it an `a`/`button`/`li`. |
|
|
33
|
+
| `Stack`, `Inline` | `gap` from the spacing scale (`none` … `4xl`); `align`; `justify`; `as`. `Inline` wraps unless `wrap={false}`. |
|
|
34
|
+
| `Kbd` | One key per `Kbd`; `Kbd.Group label="Command K"` groups a shortcut with a `+` (or `separator="space"`). |
|
|
35
|
+
| `Dialog` | `Root` (`open`, `defaultOpen`, `onOpenChange`, `dismissible`), `Trigger`, `Content` (`size` sm · md · lg), `Title`, `Description`, `Body`, `Actions`, `Close`. |
|
|
36
|
+
| `Toolbar` | `Root` (required `aria-label`, `wrap`, `gap`), `Group` (`aria-label`, `gap`), `Separator`, `Spacer`, `Button` (`render={<IconButton … />}` or `render={<Menu.Trigger render={…} />}` so the control joins the roving focus: Tab enters, arrows move, Tab leaves). |
|
|
37
|
+
| `Banner` | `tone` info (default) · success · warning · danger · neutral; `icon` (or `false`); `action` slot; `dismissible` + `onDismiss` (`open` to control); warning and danger are `role="alert"`, the rest `role="status"`. |
|
|
38
|
+
| `Tabs` | `Root` (`value`, `defaultValue`, `onValueChange`), `List` (required `aria-label`, `fill`), `Tab` (`value`, `icon`, `count`, `disabled`), `Panel` (`value`, `keepMounted`). Arrow keys move, Enter/Space activates. |
|
|
39
|
+
| `Input`, `Textarea` | Labelled native controls on Base UI's Field: required `label` (`hideLabel` keeps it for assistive tech), `description`, `error` (sets invalid and announces), `invalid`, `required`, `disabled`, `name`, `size` sm · md · lg (Input), `iconStart`/`iconEnd` (Input), `rows`/`resize` (Textarea), `onValueChange(string)` beside native `onChange`. |
|
|
40
|
+
| `Select` | Same field props; `options` as `{ value, label, disabled? }` or `{ label, options }` groups; `value`/`defaultValue`/`onValueChange` (`null` for none); `placeholder`; `fullWidth`. Submits through `name` like a native select. |
|
|
41
|
+
| `Checkbox`, `Switch` | Required `label`, `description`, `checked`/`defaultChecked`/`onCheckedChange(boolean)`, `name`/`value`, `disabled`, `required`; Checkbox adds `indeterminate`; Switch adds `labelPosition` start · end. |
|
|
42
|
+
| `Tooltip` | `content`; `children` is the trigger (an `IconButton`, `Button` or focusable `Badge`); `side` top · bottom · left · right; `align`; `delay` (300ms); `open`/`onOpenChange`; `disabled`. `Tooltip.Provider` around a row skips the delay between siblings. |
|
|
43
|
+
| `Menu` | `Root` (`open`, `onOpenChange`, `modal`), `Trigger` (secondary Button with a chevron, or `render={<IconButton label="More" />}`), `Content` (`side`, `align`), `Item` (`icon`, `trailing`, `tone="danger"`, `disabled`), `LinkItem` (`href`), `CheckboxItem` (`checked`, `onCheckedChange`), `RadioGroup` (`value`, `onValueChange`, `label`) + `RadioItem`, `Group` (`label`), `Separator`. Arrow keys, Home/End, type-ahead, Esc and focus return come from Base UI. |
|
|
38
44
|
|
|
39
45
|
```tsx
|
|
40
46
|
<Dialog.Root>
|
|
@@ -78,6 +84,43 @@ Styles ship as one stylesheet inside `@layer sc`, so an app's unlayered CSS alwa
|
|
|
78
84
|
</Tooltip.Provider>
|
|
79
85
|
```
|
|
80
86
|
|
|
87
|
+
```tsx
|
|
88
|
+
<Toolbar.Root aria-label="Inbox actions">
|
|
89
|
+
<Toolbar.Group aria-label="Sweeps">
|
|
90
|
+
<Toolbar.Button render={<IconButton label="Pause my sweeps" tooltip />}>
|
|
91
|
+
<PauseIcon />
|
|
92
|
+
</Toolbar.Button>
|
|
93
|
+
</Toolbar.Group>
|
|
94
|
+
<Toolbar.Separator />
|
|
95
|
+
<Toolbar.Spacer />
|
|
96
|
+
<Toolbar.Button render={<Button size="sm" />}>Add job</Toolbar.Button>
|
|
97
|
+
</Toolbar.Root>
|
|
98
|
+
|
|
99
|
+
<Banner tone="warning" action={<Button variant="ghost" size="sm">Resume</Button>}>Your sweeps are paused.</Banner>
|
|
100
|
+
|
|
101
|
+
<Progress label="Verifying" value={460} max={859} valueText="460 of 859 · 3 min elapsed" />
|
|
102
|
+
<Progress variant="inline" label="Queued" />
|
|
103
|
+
|
|
104
|
+
<Tabs.Root defaultValue="inbox">
|
|
105
|
+
<Tabs.List aria-label="Inbox sections">
|
|
106
|
+
<Tabs.Tab value="inbox" count={12}>Inbox</Tabs.Tab>
|
|
107
|
+
<Tabs.Tab value="applied">Applied</Tabs.Tab>
|
|
108
|
+
</Tabs.List>
|
|
109
|
+
<Tabs.Panel value="inbox">…</Tabs.Panel>
|
|
110
|
+
<Tabs.Panel value="applied">…</Tabs.Panel>
|
|
111
|
+
</Tabs.Root>
|
|
112
|
+
|
|
113
|
+
<form action={save}>
|
|
114
|
+
<Stack gap="md">
|
|
115
|
+
<Input label="Posting URL" name="url" type="url" required description="Paste the job page." />
|
|
116
|
+
<Select label="Status" name="status" options={[{ value: 'new', label: 'New' }, { value: 'replied', label: 'Replied' }]} />
|
|
117
|
+
<Textarea label="Notes" name="notes" />
|
|
118
|
+
<Checkbox label="Remote only" name="remote" />
|
|
119
|
+
<Switch label="Pause my sweeps" name="paused" labelPosition="start" />
|
|
120
|
+
</Stack>
|
|
121
|
+
</form>
|
|
122
|
+
```
|
|
123
|
+
|
|
81
124
|
Icons are generated from `src/icons/svg/*.svg` by `scripts/build-icons.mjs` (run by `pnpm build`): the folder is the manifest, every fill and stroke must be `currentColor` or `none`, and the output is committed. The package has no side effects besides CSS, so a bundler keeps only the icons an app imports.
|
|
82
125
|
|
|
83
126
|
Accessibility baseline: native elements, one focus ring on `:focus-visible`, WCAG AA text on every fill in both themes, 44px touch targets on coarse pointers, `prefers-reduced-motion` honoured, logical properties throughout, Dialog traps focus, closes on Esc and returns focus to its trigger, Menu is fully keyboard operable, and every IconButton is named. Tooltips are hints only: they never open on touch and the trigger must already carry its own name.
|