@blakesteve/roster 5.10.0 → 5.12.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.
Files changed (55) hide show
  1. package/README.md +202 -11
  2. package/dist/components/atoms/Chip/chip-variants.cjs +1 -1
  3. package/dist/components/atoms/Chip/chip-variants.js +8 -2
  4. package/dist/components/atoms/Combobox/Combobox.cjs +1 -1
  5. package/dist/components/atoms/Combobox/Combobox.js +20 -18
  6. package/dist/components/atoms/MultiSelect/MultiSelect.cjs +1 -1
  7. package/dist/components/atoms/MultiSelect/MultiSelect.js +22 -20
  8. package/dist/components/atoms/PasswordInput/PasswordInput.cjs +1 -1
  9. package/dist/components/atoms/PasswordInput/PasswordInput.js +5 -5
  10. package/dist/components/atoms/Select/Select.cjs +1 -1
  11. package/dist/components/atoms/Select/Select.js +19 -17
  12. package/dist/components/atoms/Select/select-variants.cjs +1 -1
  13. package/dist/components/atoms/Select/select-variants.js +11 -2
  14. package/dist/components/molecules/Carousel/Carousel.cjs +1 -1
  15. package/dist/components/molecules/Carousel/Carousel.js +31 -29
  16. package/dist/components/molecules/FileUpload/FileUpload.cjs +1 -1
  17. package/dist/components/molecules/FileUpload/FileUpload.js +21 -19
  18. package/dist/components/molecules/LiquidTabs/LiquidTabs.cjs +1 -1
  19. package/dist/components/molecules/LiquidTabs/LiquidTabs.js +22 -20
  20. package/dist/components/molecules/Menu/Menu.cjs +1 -1
  21. package/dist/components/molecules/Menu/Menu.js +133 -124
  22. package/dist/components/molecules/RadioGroup/RadioGroup.cjs +1 -1
  23. package/dist/components/molecules/RadioGroup/RadioGroup.js +23 -21
  24. package/dist/components/molecules/RangeSlider/RangeSlider.cjs +1 -0
  25. package/dist/components/molecules/RangeSlider/RangeSlider.d.ts +79 -0
  26. package/dist/components/molecules/RangeSlider/RangeSlider.js +166 -0
  27. package/dist/components/molecules/Slider/Slider.cjs +1 -0
  28. package/dist/components/molecules/Slider/Slider.d.ts +91 -0
  29. package/dist/components/molecules/Slider/Slider.js +130 -0
  30. package/dist/components/molecules/Slider/track-parts.cjs +1 -0
  31. package/dist/components/molecules/Slider/track-parts.d.ts +65 -0
  32. package/dist/components/molecules/Slider/track-parts.js +121 -0
  33. package/dist/components/molecules/Slider/track.cjs +1 -0
  34. package/dist/components/molecules/Slider/track.d.ts +115 -0
  35. package/dist/components/molecules/Slider/track.js +152 -0
  36. package/dist/components/organisms/Dialog/Dialog.cjs +1 -1
  37. package/dist/components/organisms/Dialog/Dialog.js +19 -17
  38. package/dist/components/organisms/ModerationQueue/ModerationQueue.cjs +1 -1
  39. package/dist/components/organisms/ModerationQueue/ModerationQueue.js +45 -43
  40. package/dist/components/organisms/Navbar/Navbar.cjs +1 -1
  41. package/dist/components/organisms/Navbar/Navbar.js +24 -22
  42. package/dist/components/organisms/Sheet/Sheet.cjs +1 -1
  43. package/dist/components/organisms/Sheet/Sheet.js +25 -23
  44. package/dist/index.d.ts +2 -0
  45. package/dist/internal/key-focus.cjs +1 -0
  46. package/dist/internal/key-focus.d.ts +7 -0
  47. package/dist/internal/key-focus.js +60 -0
  48. package/dist/internal/popup.cjs +1 -1
  49. package/dist/internal/popup.d.ts +15 -1
  50. package/dist/internal/popup.js +17 -12
  51. package/dist/meta.json +3 -3
  52. package/dist/roster.cjs +1 -1
  53. package/dist/roster.css +1 -1
  54. package/dist/roster.js +67 -63
  55. package/package.json +1 -1
package/README.md CHANGED
@@ -543,6 +543,39 @@ The band matters more than it looks. Without it the ring sits directly on the
543
543
  fill, and a `primary-500` ring on a `primary-600` button is 1.37:1 — which is
544
544
  why the ring and its offset are a pair rather than two independent knobs.
545
545
 
546
+ **A row in a popup marks focus with the ring too.** The focused row in `Menu`,
547
+ `Select`, `Combobox` and `MultiSelect` keeps its soft primary tint and adds a
548
+ 2px inset ring in `--roster-ring`. The tint alone was the indicator until
549
+ 5.11.0, and it measured 1.17:1 against the panel in light and 1.03:1 in dark
550
+ on Roster's own defaults: a keyboard user couldn't see where they were. The
551
+ ring follows the token you already set against your own surfaces, so it holds
552
+ wherever the panel is: 6.37:1 and 5.61:1 on the defaults. If you set
553
+ `--roster-popover-bg` to a surface `--roster-ring` doesn't contrast with, set
554
+ the ring with it. In `Menu` the ring shows for keyboard focus only, because the
555
+ pointer moves focus there too. Headless UI's popups mark the keys' row and the
556
+ pointer's alike, so in theirs it shows on hover as well.
557
+
558
+ **Keyboard focus shows in Safari too.** Every ring is drawn on Roster's
559
+ `focus-visible` variant, which matches the engine's own `:focus-visible` or an
560
+ element marked `data-key-focus`. WebKit doesn't match `:focus-visible` on an
561
+ element a script focuses in answer to a key once the page has been clicked.
562
+ Escape handing focus back to a menu's or a select's trigger, or to a dialog's
563
+ opener, and a radio group's or tabs' arrows all drew no ring in Safari after
564
+ a click. A small internal tracker marks those elements: keyboard mode starts on a navigation key (Tab, Option+Tab, the
565
+ arrows, Escape, Enter, Space, Home, End, PageUp, PageDown) and ends on pointer
566
+ input, and it marks only what Chromium's own `:focus-visible` already matches,
567
+ so Chromium's rings are unchanged. It runs while a component that moves focus
568
+ is mounted (Menu, the select family, Dialog, Sheet, RadioGroup, LiquidTabs,
569
+ Slider and the rest), on one set of document listeners.
570
+
571
+ Your own components' rings come from your Tailwind, not Roster's, so they
572
+ don't follow the mark on their own. To have them do the same, redefine the
573
+ variant in your stylesheet as Roster does:
574
+
575
+ ```css
576
+ @custom-variant focus-visible (&:is(:focus-visible, [data-key-focus]));
577
+ ```
578
+
546
579
  ### Motion
547
580
 
548
581
  Two hand-rolled utilities, both of which stop for `prefers-reduced-motion`.
@@ -732,11 +765,10 @@ opens are also legitimately different surfaces in plenty of palettes.
732
765
  **Set these at `:root`, not on a container.** The menu and the tooltip bubble
733
766
  are portaled to `<body>`, so they are not descendants of whatever you rendered
734
767
  the component inside: properties set on a wrapper reach the trigger and stop
735
- there. Any ancestor of `<body>` works — `:root` is simply the one that always
736
- is, which is also why the `.dark` block below reaches a menu whose `.dark`
737
- scope `Select` copies across the portal. The result is a themed trigger opening an unthemed panel, which is the
738
- exact problem this family exists to fix. Set them in both scopes too, for the
739
- same reason the control family needs both.
768
+ there, and the result is a themed trigger opening an unthemed panel, which is
769
+ the exact problem this family exists to fix. Any ancestor of `<body>` works:
770
+ `:root`, `html.dark`, or inline on `<html>` all reach every panel. Set them in
771
+ both scopes too, for the same reason the control family needs both.
740
772
 
741
773
  Where each component takes them, and why not everywhere:
742
774
 
@@ -773,6 +805,8 @@ Every field therefore has a second prop, **named for the element it reaches**:
773
805
  | `Combobox` | `className` | `inputClassName` | `optionsClassName` |
774
806
  | `CheckboxGroup`| `className` | — | `optionsClassName` |
775
807
  | `RadioGroup` | `className` | `radioClassName` | `optionsClassName`, `optionClassName`, `labelClassName`, `optionLabelClassName`, `descriptionClassName`, `messageClassName` |
808
+ | `Slider` | `className` | `trackClassName` | `thumbClassName`, `chipClassName`, `labelClassName`, `messageClassName` |
809
+ | `RangeSlider` | `className` | `thumbClassName` | `trackClassName`, `chipClassName`, `labelClassName`, `messageClassName` |
776
810
 
777
811
  `CheckboxGroup` and `RadioGroup` have no single "control" to reach, since they
778
812
  hold one per option, so `RadioGroup`'s `radioClassName` lands on every radio
@@ -925,9 +959,16 @@ look like oversights until you know why:
925
959
  variable that inline rule reads:
926
960
  `optionsClassName="rst:[--anchor-max-height:20rem]"`.
927
961
  - **The panel is portaled to `<body>`**, so a `.dark` scoped to part of your
928
- page does not reach it. All three components copy the nearest `.dark` onto
929
- the panel to fix that. Custom properties are not carried the same way — set
930
- `--roster-popover-*` at `:root`.
962
+ page does not reach it. The panel carries `.dark` itself in that case, and
963
+ only then: when `.dark` is on `<html>` or `<body>` the panel is already
964
+ inside it, and carrying the class would re-declare Roster's palette on the
965
+ panel over your own. Every portaled surface does the same (`Menu`, `Sheet`
966
+ and the toasts too). Custom properties are not carried: set
967
+ `--roster-popover-*` on an ancestor of `<body>`.
968
+ - **A row is a click target, and focus is a ring.** Every option row shows
969
+ the pointer cursor, as `Menu`'s items do (a disabled one, `not-allowed`).
970
+ A focused row keeps its tint and adds an inset `--roster-ring`, which is
971
+ what reaches 3:1 against the panel ([Focus](#focus)).
931
972
  - **`Menu` shares the panel, not the anchoring.** Its panel takes the same
932
973
  surface, tokens and dark carry, but `Menu` places itself (see
933
974
  [Menu](#menu)), writing its own inline `max-height`. It reads the same
@@ -1584,8 +1625,10 @@ import { Menu, MenuButton, MenuItems, MenuItem, MenuSeparator } from "@blakestev
1584
1625
  - **Styling.** `className` on `MenuItems` and on each item merges last, so a
1585
1626
  fill such as `bg-gray-100` takes; the scroll shadows are drawn over it. Its
1586
1627
  ring and separators follow `--roster-border-width`. Items show the pointer
1587
- cursor, a disabled one `not-allowed`. In forced colors the focused item gets
1588
- an outline, since its fill is dropped.
1628
+ cursor, a disabled one `not-allowed`. Keyboard focus adds an inset ring in
1629
+ `--roster-ring` to the item's tint, which alone doesn't reach 3:1 against
1630
+ the panel ([Focus](#focus)). In forced colors the focused item gets an
1631
+ outline, since its fill and ring are dropped.
1589
1632
  - **Targets.** Every item is at least 44px tall, and `MenuButton` at least 44
1590
1633
  by 44 whatever its size. `MenuButton plain` renders a bare `<button>` for a
1591
1634
  trigger drawn its own way; keep its target at least 44 by 44 with a hit
@@ -1599,6 +1642,126 @@ that its rows are 44px tall rather than 36, and that with neither an inbox nor
1599
1642
  a theme row it no longer draws an empty band and rule at the top. It keeps its
1600
1643
  own white fill, whatever `--roster-popover-bg` says.
1601
1644
 
1645
+ ### Slider
1646
+
1647
+ A value picked along a track: tapped, dragged, stepped with the keys, or set
1648
+ from a named snap point.
1649
+
1650
+ ```tsx
1651
+ import { Slider } from "@blakesteve/roster";
1652
+
1653
+ <Slider
1654
+ label="How sure are you?"
1655
+ value={sure}
1656
+ onChange={setSure}
1657
+ snapPoints={[{ value: 100, label: "Certain" }, { value: 75, label: "Likely" }, { value: 50, label: "Toss-up" }]}
1658
+ formatValue={(v) => `${v}%`}
1659
+ />;
1660
+ ```
1661
+
1662
+ - **It starts with a thumb**, in the middle of the range by default.
1663
+ `startValue` moves where it starts, and `defaultValue` sets it outright:
1664
+ `defaultValue={0}` starts it at the low end.
1665
+ - **Not set** is opt-in: `defaultValue={null}`, or `value={null}` when
1666
+ controlled, leaves the track empty with no thumb until the first input. A
1667
+ form takes it as a valid answer: under `name` it submits an empty string.
1668
+ Controlled, `value` can go back to `null`, which is how a consumer offers a
1669
+ clear.
1670
+ - **Snap points** are named stops, any values and labels: a selectable
1671
+ `Chip` under the track for each, in the track's order, moves the thumb
1672
+ there, and a bead on the rail shows where. They're shortcuts, so dragging
1673
+ still lands anywhere between them. A chip shows as pressed (solid rather
1674
+ than outline) while the value is exactly its value, and pressing it again
1675
+ leaves it there. A point outside `min` to `max` is left out.
1676
+ - **The label** is a string or a node, so it can carry markup; the slider is
1677
+ named by reference to it, so what's read is its text. A consumer's own
1678
+ `aria-labelledby` names it instead, as when the visible label is shared and
1679
+ each slider needs its own name.
1680
+ - **The number** shows beside the label (`formatValue` writes it). A screen
1681
+ reader hears it with the nearest snap point's name, "72%, Likely", and
1682
+ "Not set" while there's no value, never a number. Every string is in
1683
+ `labels`.
1684
+ - **In range.** A value outside `min` to `max` shows, and is said, at the
1685
+ end it's past. A controlled owner that turns a change down (a clamp, say)
1686
+ leaves the next key stepping from the value it kept.
1687
+ - **Pointer.** A tap on the track sets the value there; a press on the thumb
1688
+ takes it without a jump, and commits only if the drag moved it. On touch
1689
+ the track waits to see which way a finger goes: across is a drag, down the
1690
+ page scrolls it and sets nothing (and takes no focus), and a tap sets on
1691
+ lift. A pointermove with no press, which WebKit sends when content scrolls
1692
+ under a resting pointer, sets nothing. A second finger is left alone.
1693
+ - **Keys.** The arrows step by `step`, PageUp and PageDown by `pageStep` (a
1694
+ tenth of the range by default), Home and End go to the ends. **On an empty
1695
+ slider an arrow or Page key places the thumb at `startValue`, the middle
1696
+ by default**; it doesn't step from anywhere. A key at an end does nothing.
1697
+ From a value between steps, a key goes to the next step that way. Keys
1698
+ always step from the value last set, never from where the thumb is drawn
1699
+ while it eases there, so a burst of presses counts every one. A key the
1700
+ consumer's own `onKeyDown` handled (`preventDefault`) is left to it.
1701
+ - **Focus.** By keyboard, the ring is round the thumb; an empty slider rings
1702
+ the track. A disabled slider takes no focus at all.
1703
+ - **Form.** Under `name` it submits its value, or an empty string while not
1704
+ set; disabled, nothing, as a disabled input submits nothing. A form's
1705
+ reset puts an uncontrolled slider back where it started.
1706
+ - **Targets.** The track is 44px tall and its rail stops 22px short of each
1707
+ end, so the thumb's 44 by 44 target stays on it at every value. Each chip
1708
+ has Chip's 44px-tall target and is at least 44 wide, and the chip row sits
1709
+ 8px under the track so its targets never take the thumb's. Under reduced
1710
+ motion the thumb moves without easing. Under `dir="rtl"` the track runs
1711
+ from the right.
1712
+ - **Look.** The rail is a light surface edged in `--roster-control-border`,
1713
+ which carries a control edge's 3:1 when there's no thumb to show the
1714
+ slider. Snap points are beads set in the rail, the edge's color on the bare
1715
+ rail and the page's on the fill.
1716
+
1717
+ One thumb. Two, for a range, is [RangeSlider](#rangeslider), on the same
1718
+ track, so `value` here stays a number.
1719
+
1720
+ ### RangeSlider
1721
+
1722
+ A low and a high along one track: `Slider`'s track, with two thumbs.
1723
+
1724
+ ```tsx
1725
+ import { RangeSlider } from "@blakesteve/roster";
1726
+
1727
+ <RangeSlider
1728
+ label="Price"
1729
+ min={0}
1730
+ max={500}
1731
+ step={5}
1732
+ value={price}
1733
+ onChange={setPrice}
1734
+ formatValue={(v) => `$${v}`}
1735
+ />;
1736
+ ```
1737
+
1738
+ - **It starts at the whole range**, `[min, max]`, unless `defaultValue`
1739
+ says otherwise. `value` is `[low, high]`, always low first: a pair given
1740
+ the wrong way round is shown the right way. There's no not-set state; the
1741
+ whole range is what "any" looks like.
1742
+ - **Each thumb is a slider** to the keyboard and a screen reader: its own
1743
+ tab stop, named for the slider and its end ("Price Minimum", "Price
1744
+ Maximum", both in `labels`), whose `aria-valuemin` and `aria-valuemax`
1745
+ run to the other thumb. The thumbs meet and never cross: End on the low
1746
+ thumb takes it to the high one. The whole is a group named by the label.
1747
+ - **Pointer.** A press takes the nearer thumb: a tap on the track moves it
1748
+ there, a drag carries it. Two thumbs on one spot part by the way the drag
1749
+ first moves, up the range taking the high one. Touch, the resting
1750
+ pointer, the second finger and the keys work as `Slider`'s do.
1751
+ - **Snap points** put a bead on the rail and a `Chip` under it, which does
1752
+ what a tap on its mark does: moves the nearer thumb there (halfway, the
1753
+ low one). A chip shows as pressed while either thumb is on it.
1754
+ - **The label** takes a node too, and names the group and each thumb by
1755
+ reference; a consumer's `aria-labelledby` names them instead.
1756
+ - **The number** beside the label shows both, "$120 – $340"
1757
+ (`labels.range`). Each thumb says its own value with the nearest snap
1758
+ point's name.
1759
+ - **Form.** Under `name` both values are submitted, low then high, as a
1760
+ multiple select's are: read them with `formData.getAll(name)`.
1761
+ - **Focus, targets, motion, RTL and look** as `Slider`'s: the ring is round
1762
+ the focused thumb, each thumb's 44 by 44 target stays on the track at
1763
+ every value.
1764
+
1602
1765
  ### Pagination
1603
1766
 
1604
1767
  Moves through pages of a list, built for a long list browsed on a phone.
@@ -1886,6 +2049,8 @@ function App() {
1886
2049
  | `StepProgress` | Named steps: a stepper with markers and connectors, or a compact segmented "Step x of y" |
1887
2050
  | `Pullquote` | A line lifted out of prose, as `<figure>` + `<blockquote>` + `<figcaption>` |
1888
2051
  | `RadioGroup` | Radio set reporting one `string`; descriptions, error, 44px targets |
2052
+ | `Slider` | A value along a track, starting in the middle or not set on request; named snap-point chips, a visible number, the full keyboard, 44px targets (see [Slider](#slider)) |
2053
+ | `RangeSlider` | A low and a high on one track: two thumbs that meet and never cross, each its own slider to the keyboard (see [RangeSlider](#rangeslider)) |
1889
2054
  | `Toast` | Transient floating notice; `Toaster` + the imperative `toast` handle |
1890
2055
 
1891
2056
  ### Organisms
@@ -1997,6 +2162,32 @@ such as `AvatarStrip`'s `ringClass`, stays exactly as they wrote it.
1997
2162
 
1998
2163
  `npm run build` fails if any unprefixed class reaches `dist/roster.css`.
1999
2164
 
2165
+ ## Authoring components: cursors
2166
+
2167
+ **If it's clickable, it's the pointer.** Every element that does something
2168
+ when it's clicked shows `cursor: pointer`, and says so in its classes. A
2169
+ browser gives a button the arrow; Tailwind v3's preflight gave it the pointer
2170
+ and v4's doesn't, so a `<button>` with no cursor class shows the arrow. Until 5.11.0 the option rows
2171
+ in `Select`, `Combobox` and `MultiSelect` showed the arrow while `Menu`'s
2172
+ showed the pointer, and `PasswordInput`'s reveal button showed the arrow too.
2173
+
2174
+ - A disabled control shows `not-allowed`.
2175
+ - A busy one may say so: `Button`'s `loading` shows `progress`.
2176
+ - A text field's label keeps the arrow, as a native one does: clicking it puts
2177
+ the caret in the field rather than doing something.
2178
+
2179
+ Three things keep another cursor, because they aren't click targets:
2180
+
2181
+ - **`Breadcrumbs`' current crumb** is the page you're on, not a link:
2182
+ `default`.
2183
+ - **`Tooltip`'s trigger wrapper** isn't necessarily clickable: `default`. A
2184
+ control inside it brings its own pointer.
2185
+ - **A drag surface** says what it does: `Carousel`'s track and `Sheet`'s drag
2186
+ handle show `grab`, then `grabbing`.
2187
+
2188
+ `src/internal/popups.checks.stories.tsx` reads the computed cursor on a row in
2189
+ each popup, with a disabled row as its twin.
2190
+
2000
2191
  ## Development
2001
2192
 
2002
2193
  Storybook is the component playground. Each component has dedicated stories covering all variants, props, and light/dark mode.
@@ -2128,7 +2319,7 @@ like a file count but counts `describe` blocks — 166 against 92 real files.
2128
2319
  Pull requests are welcome. Please:
2129
2320
 
2130
2321
  1. Open an issue or discussion first for significant changes
2131
- 2. Follow the existing code style (CVA variants, forwardRef, Storybook stories, unit tests)
2322
+ 2. Follow the existing code style (CVA variants, forwardRef, Storybook stories, unit tests) and the authoring rules above: the `rst:` prefix and cursors
2132
2323
  3. Fill out the pull request template checklist before requesting review
2133
2324
 
2134
2325
  ## License
@@ -1 +1 @@
1
- "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const r=require("../../../node_modules/class-variance-authority/dist/index.cjs"),t=r.cva("rst:font-ui rst:inline-flex rst:items-center rst:rounded-full rst:font-medium rst:whitespace-nowrap rst:align-middle rst:transition-colors",{variants:{colorScheme:{primary:"",success:"",error:"",amber:"",info:"",neutral:""},variant:{soft:"",outline:"rst:bg-transparent rst:border",solid:""},size:{sm:"rst:text-xs rst:px-2.5 rst:py-0.5 rst:gap-1.5",md:"rst:text-sm rst:px-3 rst:py-1 rst:gap-2"},disabled:{true:"rst:opacity-50 rst:cursor-not-allowed",false:""}},compoundVariants:[{variant:"soft",colorScheme:"primary",className:"rst:bg-primary-50 rst:text-primary-700 rst:dark:bg-primary-500/15 rst:dark:text-primary-300"},{variant:"soft",colorScheme:"success",className:"rst:bg-success-50 rst:text-success-700 rst:dark:bg-success-500/15 rst:dark:text-success-300"},{variant:"soft",colorScheme:"error",className:"rst:bg-error-50 rst:text-error-700 rst:dark:bg-error-500/15 rst:dark:text-error-300"},{variant:"soft",colorScheme:"amber",className:"rst:bg-amber-50 rst:text-amber-800 rst:dark:bg-amber-500/15 rst:dark:text-amber-300"},{variant:"soft",colorScheme:"info",className:"rst:bg-info-50 rst:text-info-700 rst:dark:bg-info-500/15 rst:dark:text-info-300"},{variant:"soft",colorScheme:"neutral",className:"rst:bg-gray-100 rst:text-gray-700 rst:dark:bg-gray-500/15 rst:dark:text-gray-300"},{variant:"outline",colorScheme:"primary",className:"rst:border-primary-600 rst:text-primary-700 rst:dark:border-primary-400 rst:dark:text-primary-300"},{variant:"outline",colorScheme:"success",className:"rst:border-success-600 rst:text-success-700 rst:dark:border-success-400 rst:dark:text-success-300"},{variant:"outline",colorScheme:"error",className:"rst:border-error-600 rst:text-error-700 rst:dark:border-error-400 rst:dark:text-error-300"},{variant:"outline",colorScheme:"amber",className:"rst:border-amber-600 rst:text-amber-800 rst:dark:border-amber-400 rst:dark:text-amber-300"},{variant:"outline",colorScheme:"info",className:"rst:border-info-600 rst:text-info-700 rst:dark:border-info-400 rst:dark:text-info-300"},{variant:"outline",colorScheme:"neutral",className:"rst:border-gray-600 rst:text-gray-700 rst:dark:border-gray-400 rst:dark:text-gray-300"},{variant:"solid",colorScheme:"primary",className:"rst:bg-primary-500 rst:text-primary-500-ink"},{variant:"solid",colorScheme:"success",className:"rst:bg-success-500 rst:text-success-500-ink"},{variant:"solid",colorScheme:"error",className:"rst:bg-error-500 rst:text-error-500-ink"},{variant:"solid",colorScheme:"amber",className:"rst:bg-amber-500 rst:text-amber-500-ink"},{variant:"solid",colorScheme:"info",className:"rst:bg-info-500 rst:text-info-500-ink"},{variant:"solid",colorScheme:"neutral",className:"rst:bg-gray-600 rst:dark:bg-gray-500 rst:text-gray-600-ink rst:dark:text-gray-500-ink"}],defaultVariants:{colorScheme:"neutral",variant:"soft",size:"md",disabled:!1}});exports.chipVariants=t;
1
+ "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const r=require("../../../node_modules/class-variance-authority/dist/index.cjs"),t=r.cva("rst:font-ui rst:inline-flex rst:items-center rst:rounded-full rst:border rst:border-transparent rst:font-medium rst:whitespace-nowrap rst:align-middle rst:transition-colors",{variants:{colorScheme:{primary:"",success:"",error:"",amber:"",info:"",neutral:""},variant:{soft:"",outline:"rst:bg-transparent",solid:""},size:{sm:"rst:text-xs rst:px-2.5 rst:py-0.5 rst:gap-1.5",md:"rst:text-sm rst:px-3 rst:py-1 rst:gap-2"},disabled:{true:"rst:opacity-50 rst:cursor-not-allowed",false:""}},compoundVariants:[{variant:"soft",colorScheme:"primary",className:"rst:bg-primary-50 rst:text-primary-700 rst:dark:bg-primary-500/15 rst:dark:text-primary-300"},{variant:"soft",colorScheme:"success",className:"rst:bg-success-50 rst:text-success-700 rst:dark:bg-success-500/15 rst:dark:text-success-300"},{variant:"soft",colorScheme:"error",className:"rst:bg-error-50 rst:text-error-700 rst:dark:bg-error-500/15 rst:dark:text-error-300"},{variant:"soft",colorScheme:"amber",className:"rst:bg-amber-50 rst:text-amber-800 rst:dark:bg-amber-500/15 rst:dark:text-amber-300"},{variant:"soft",colorScheme:"info",className:"rst:bg-info-50 rst:text-info-700 rst:dark:bg-info-500/15 rst:dark:text-info-300"},{variant:"soft",colorScheme:"neutral",className:"rst:bg-gray-100 rst:text-gray-700 rst:dark:bg-gray-500/15 rst:dark:text-gray-300"},{variant:"outline",colorScheme:"primary",className:"rst:border-primary-600 rst:text-primary-700 rst:dark:border-primary-400 rst:dark:text-primary-300"},{variant:"outline",colorScheme:"success",className:"rst:border-success-600 rst:text-success-700 rst:dark:border-success-400 rst:dark:text-success-300"},{variant:"outline",colorScheme:"error",className:"rst:border-error-600 rst:text-error-700 rst:dark:border-error-400 rst:dark:text-error-300"},{variant:"outline",colorScheme:"amber",className:"rst:border-amber-600 rst:text-amber-800 rst:dark:border-amber-400 rst:dark:text-amber-300"},{variant:"outline",colorScheme:"info",className:"rst:border-info-600 rst:text-info-700 rst:dark:border-info-400 rst:dark:text-info-300"},{variant:"outline",colorScheme:"neutral",className:"rst:border-gray-600 rst:text-gray-700 rst:dark:border-gray-400 rst:dark:text-gray-300"},{variant:"solid",colorScheme:"primary",className:"rst:bg-primary-500 rst:text-primary-500-ink"},{variant:"solid",colorScheme:"success",className:"rst:bg-success-500 rst:text-success-500-ink"},{variant:"solid",colorScheme:"error",className:"rst:bg-error-500 rst:text-error-500-ink"},{variant:"solid",colorScheme:"amber",className:"rst:bg-amber-500 rst:text-amber-500-ink"},{variant:"solid",colorScheme:"info",className:"rst:bg-info-500 rst:text-info-500-ink"},{variant:"solid",colorScheme:"neutral",className:"rst:bg-gray-600 rst:dark:bg-gray-500 rst:text-gray-600-ink rst:dark:text-gray-500-ink"}],defaultVariants:{colorScheme:"neutral",variant:"soft",size:"md",disabled:!1}});exports.chipVariants=t;
@@ -1,6 +1,12 @@
1
1
  import { cva as r } from "../../../node_modules/class-variance-authority/dist/index.js";
2
2
  const s = /* @__PURE__ */ r(
3
- "rst:font-ui rst:inline-flex rst:items-center rst:rounded-full rst:font-medium rst:whitespace-nowrap rst:align-middle rst:transition-colors",
3
+ /* A border on every variant, transparent where the variant draws none, so
4
+ every variant is one size. Only `outline` had one, so a chip that swaps
5
+ `outline` for `solid` when selected, as a filter row and a slider's snap
6
+ chips do, lost the border's width on both sides at the press and the row
7
+ jumped. A transparent border costs nothing to see: the fill paints under
8
+ it. Its width is `--roster-border-width`, like every edge. */
9
+ "rst:font-ui rst:inline-flex rst:items-center rst:rounded-full rst:border rst:border-transparent rst:font-medium rst:whitespace-nowrap rst:align-middle rst:transition-colors",
4
10
  {
5
11
  variants: {
6
12
  colorScheme: {
@@ -13,7 +19,7 @@ const s = /* @__PURE__ */ r(
13
19
  },
14
20
  variant: {
15
21
  soft: "",
16
- outline: "rst:bg-transparent rst:border",
22
+ outline: "rst:bg-transparent",
17
23
  solid: ""
18
24
  },
19
25
  size: {
@@ -1 +1 @@
1
- "use client";"use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("react/jsx-runtime"),y=require("react"),a=require("../../../node_modules/@headlessui/react/dist/components/combobox/combobox.cjs"),F=require("../../../node_modules/@headlessui/react/dist/components/description/description.cjs"),L=require("../../../node_modules/@headlessui/react/dist/components/field/field.cjs"),R=require("../../../node_modules/@headlessui/react/dist/components/label/label.cjs"),T=require("../../../node_modules/@headlessui/react/dist/components/transition/transition.cjs"),U=require("../../../node_modules/@fortawesome/react-fontawesome/dist/index.cjs"),A=require("../../../node_modules/@fortawesome/free-solid-svg-icons/index.cjs"),i=require("../../../lib/utils.cjs"),j=require("../../../internal/field-invalid.cjs"),V=require("../Input/input-variants.cjs"),E=require("../../../internal/PopupOption.cjs"),l=require("../../../internal/popup.cjs");function H(t){const s=Object.create(null,{[Symbol.toStringTag]:{value:"Module"}});if(t){for(const r in t)if(r!=="default"){const o=Object.getOwnPropertyDescriptor(t,r);Object.defineProperty(s,r,o.get?o:{enumerable:!0,get:()=>t[r]})}}return s.default=t,Object.freeze(s)}const B=H(y),Q=(t,s)=>{const r=s.trim().toLowerCase();return r?t.filter(o=>o.label.toLowerCase().includes(r)):t},W=({options:t,value:s,onChange:r,placeholder:o="Search...",disabled:x=!1,variant:m,size:c,error:P,label:p,helperText:b,errorMessage:u,className:q,inputClassName:O,optionsClassName:g,emptyMessage:N="No matches",filter:C=Q,...f})=>{const[k,v]=B.useState(""),{ref:w,inDarkScope:D}=l.useDarkScope(),d=!!u||P,I=j.isFieldInvalid(d,f),S=j.withoutInvalidProps(f),h=C(t,k),_=t.find(n=>n.value===s)??null;return e.jsxs(L.Field,{disabled:x,className:i.cn("rst:flex rst:flex-col rst:gap-1.5",q),...S,children:[p&&e.jsx(R.Label,{className:"rst:block rst:text-sm rst:font-medium rst:text-[var(--roster-control-text)] rst:text-left",children:p}),e.jsx(a.Combobox,{value:s??null,onChange:r,disabled:x,children:e.jsxs("div",{ref:w,className:"rst:relative",children:[e.jsx(a.ComboboxInput,{"aria-invalid":I||void 0,className:i.cn(V.inputVariants({variant:m,size:c,error:d}),O,"rst:pr-9"),placeholder:o,displayValue:()=>_?.label??"",onChange:n=>v(n.target.value)}),e.jsx(a.ComboboxButton,{className:i.cn("rst:absolute rst:inset-y-0 rst:right-0 rst:flex rst:w-11 rst:cursor-pointer rst:items-center rst:justify-end",c==="sm"?"rst:pr-2.5":"rst:pr-3"),children:e.jsx(U.FontAwesomeIcon,{icon:A.faChevronDown,className:"rst:h-3.5 rst:w-3.5 rst:text-gray-400 rst:dark:text-gray-500","aria-hidden":"true"})}),e.jsx(T.Transition,{as:y.Fragment,leave:"rst:transition rst:ease-in rst:duration-100",leaveFrom:"rst:opacity-100",leaveTo:"rst:opacity-0",afterLeave:()=>v(""),children:e.jsx(a.ComboboxOptions,{anchor:l.POPUP_ANCHOR,className:i.cn(l.popupInDarkPalette(D,m)&&"dark",l.POPUP_PANEL,l.POPUP_WIDTH_OF_INPUT,g),children:h.length===0?e.jsx(a.ComboboxOption,{value:"",disabled:!0,className:i.cn("rst:px-4 rst:py-2.5 rst:text-sm rst:opacity-70",c==="sm"&&"rst:px-3 rst:py-2"),children:N}):h.map(n=>e.jsx(E.PopupOption,{as:a.ComboboxOption,value:n.value,disabled:n.disabled,size:c,children:n.label},n.value))})})]})}),(b||u)&&e.jsx(F.Description,{className:i.cn("rst:text-xs rst:text-left",d?"rst:text-error-600 rst:dark:text-error-400 rst:font-medium":"rst:text-gray-500 rst:dark:text-gray-400"),children:u||b})]})};exports.Combobox=W;
1
+ "use client";"use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("react/jsx-runtime"),j=require("react"),a=require("../../../node_modules/@headlessui/react/dist/components/combobox/combobox.cjs"),_=require("../../../node_modules/@headlessui/react/dist/components/description/description.cjs"),L=require("../../../node_modules/@headlessui/react/dist/components/field/field.cjs"),R=require("../../../node_modules/@headlessui/react/dist/components/label/label.cjs"),T=require("../../../node_modules/@headlessui/react/dist/components/transition/transition.cjs"),U=require("../../../node_modules/@fortawesome/react-fontawesome/dist/index.cjs"),A=require("../../../node_modules/@fortawesome/free-solid-svg-icons/index.cjs"),i=require("../../../lib/utils.cjs"),h=require("../../../internal/field-invalid.cjs"),V=require("../Input/input-variants.cjs"),E=require("../../../internal/PopupOption.cjs"),c=require("../../../internal/popup.cjs"),H=require("../../../internal/key-focus.cjs");function B(t){const s=Object.create(null,{[Symbol.toStringTag]:{value:"Module"}});if(t){for(const r in t)if(r!=="default"){const n=Object.getOwnPropertyDescriptor(t,r);Object.defineProperty(s,r,n.get?n:{enumerable:!0,get:()=>t[r]})}}return s.default=t,Object.freeze(s)}const K=B(j),Q=(t,s)=>{const r=s.trim().toLowerCase();return r?t.filter(n=>n.label.toLowerCase().includes(r)):t},W=({options:t,value:s,onChange:r,placeholder:n="Search...",disabled:x=!1,variant:m,size:l,error:P,label:p,helperText:b,errorMessage:u,className:q,inputClassName:O,optionsClassName:g,emptyMessage:N="No matches",filter:C=Q,...f})=>{H.useKeyFocus();const[k,v]=K.useState(""),{ref:F,inDarkScope:w}=c.useDarkScope(),d=!!u||P,D=h.isFieldInvalid(d,f),I=h.withoutInvalidProps(f),y=C(t,k),S=t.find(o=>o.value===s)??null;return e.jsxs(L.Field,{disabled:x,className:i.cn("rst:flex rst:flex-col rst:gap-1.5",q),...I,children:[p&&e.jsx(R.Label,{className:"rst:block rst:text-sm rst:font-medium rst:text-[var(--roster-control-text)] rst:text-left",children:p}),e.jsx(a.Combobox,{value:s??null,onChange:r,disabled:x,children:e.jsxs("div",{ref:F,className:"rst:relative",children:[e.jsx(a.ComboboxInput,{"aria-invalid":D||void 0,className:i.cn(V.inputVariants({variant:m,size:l,error:d}),O,"rst:pr-9"),placeholder:n,displayValue:()=>S?.label??"",onChange:o=>v(o.target.value)}),e.jsx(a.ComboboxButton,{className:i.cn("rst:absolute rst:inset-y-0 rst:right-0 rst:flex rst:w-11 rst:cursor-pointer rst:items-center rst:justify-end",l==="sm"?"rst:pr-2.5":"rst:pr-3"),children:e.jsx(U.FontAwesomeIcon,{icon:A.faChevronDown,className:"rst:h-3.5 rst:w-3.5 rst:text-gray-400 rst:dark:text-gray-500","aria-hidden":"true"})}),e.jsx(T.Transition,{as:j.Fragment,leave:"rst:transition rst:ease-in rst:duration-100",leaveFrom:"rst:opacity-100",leaveTo:"rst:opacity-0",afterLeave:()=>v(""),children:e.jsx(a.ComboboxOptions,{anchor:c.POPUP_ANCHOR,className:i.cn(c.popupInDarkPalette(w,m)&&"dark",c.POPUP_PANEL,c.POPUP_WIDTH_OF_INPUT,g),children:y.length===0?e.jsx(a.ComboboxOption,{value:"",disabled:!0,className:i.cn("rst:px-4 rst:py-2.5 rst:text-sm rst:opacity-70",l==="sm"&&"rst:px-3 rst:py-2"),children:N}):y.map(o=>e.jsx(E.PopupOption,{as:a.ComboboxOption,value:o.value,disabled:o.disabled,size:l,children:o.label},o.value))})})]})}),(b||u)&&e.jsx(_.Description,{className:i.cn("rst:text-xs rst:text-left",d?"rst:text-error-600 rst:dark:text-error-400 rst:font-medium":"rst:text-gray-500 rst:dark:text-gray-400"),children:u||b})]})};exports.Combobox=W;
@@ -8,16 +8,17 @@ import { Field as T } from "../../../node_modules/@headlessui/react/dist/compone
8
8
  import { Label as q } from "../../../node_modules/@headlessui/react/dist/components/label/label.js";
9
9
  import { Transition as B } from "../../../node_modules/@headlessui/react/dist/components/transition/transition.js";
10
10
  import { FontAwesomeIcon as E } from "../../../node_modules/@fortawesome/react-fontawesome/dist/index.js";
11
- import { faChevronDown as V } from "../../../node_modules/@fortawesome/free-solid-svg-icons/index.js";
11
+ import { faChevronDown as K } from "../../../node_modules/@fortawesome/free-solid-svg-icons/index.js";
12
12
  import { cn as e } from "../../../lib/utils.js";
13
- import { isFieldInvalid as W, withoutInvalidProps as K } from "../../../internal/field-invalid.js";
13
+ import { isFieldInvalid as V, withoutInvalidProps as W } from "../../../internal/field-invalid.js";
14
14
  import { inputVariants as Q } from "../Input/input-variants.js";
15
15
  import { PopupOption as Z } from "../../../internal/PopupOption.js";
16
16
  import { useDarkScope as G, POPUP_ANCHOR as J, POPUP_WIDTH_OF_INPUT as X, POPUP_PANEL as Y, popupInDarkPalette as $ } from "../../../internal/popup.js";
17
- const M = (s, o) => {
17
+ import { useKeyFocus as M } from "../../../internal/key-focus.js";
18
+ const z = (s, o) => {
18
19
  const a = o.trim().toLowerCase();
19
20
  return a ? s.filter((l) => l.label.toLowerCase().includes(a)) : s;
20
- }, ft = ({
21
+ }, xt = ({
21
22
  options: s,
22
23
  value: o,
23
24
  onChange: a,
@@ -25,23 +26,24 @@ const M = (s, o) => {
25
26
  disabled: c = !1,
26
27
  variant: d,
27
28
  size: i,
28
- error: P,
29
+ error: y,
29
30
  label: p,
30
31
  helperText: f,
31
- errorMessage: n,
32
- className: y,
32
+ errorMessage: m,
33
+ className: P,
33
34
  inputClassName: N,
34
35
  optionsClassName: C,
35
36
  emptyMessage: k = "No matches",
36
- filter: g = M,
37
+ filter: g = z,
37
38
  ...u
38
39
  }) => {
39
- const [O, x] = U.useState(""), { ref: w, inDarkScope: F } = G(), m = !!n || P, I = W(m, u), D = K(u), h = g(s, O), L = s.find((r) => r.value === o) ?? null;
40
+ M();
41
+ const [F, x] = U.useState(""), { ref: O, inDarkScope: w } = G(), n = !!m || y, I = V(n, u), D = W(u), h = g(s, F), L = s.find((r) => r.value === o) ?? null;
40
42
  return /* @__PURE__ */ b(
41
43
  T,
42
44
  {
43
45
  disabled: c,
44
- className: e("rst:flex rst:flex-col rst:gap-1.5", y),
46
+ className: e("rst:flex rst:flex-col rst:gap-1.5", P),
45
47
  ...D,
46
48
  children: [
47
49
  p && /* @__PURE__ */ t(q, { className: "rst:block rst:text-sm rst:font-medium rst:text-[var(--roster-control-text)] rst:text-left", children: p }),
@@ -51,13 +53,13 @@ const M = (s, o) => {
51
53
  value: o ?? null,
52
54
  onChange: a,
53
55
  disabled: c,
54
- children: /* @__PURE__ */ b("div", { ref: w, className: "rst:relative", children: [
56
+ children: /* @__PURE__ */ b("div", { ref: O, className: "rst:relative", children: [
55
57
  /* @__PURE__ */ t(
56
58
  S,
57
59
  {
58
60
  "aria-invalid": I || void 0,
59
61
  className: e(
60
- Q({ variant: d, size: i, error: m }),
62
+ Q({ variant: d, size: i, error: n }),
61
63
  N,
62
64
  "rst:pr-9"
63
65
  ),
@@ -76,7 +78,7 @@ const M = (s, o) => {
76
78
  children: /* @__PURE__ */ t(
77
79
  E,
78
80
  {
79
- icon: V,
81
+ icon: K,
80
82
  className: "rst:h-3.5 rst:w-3.5 rst:text-gray-400 rst:dark:text-gray-500",
81
83
  "aria-hidden": "true"
82
84
  }
@@ -96,7 +98,7 @@ const M = (s, o) => {
96
98
  {
97
99
  anchor: J,
98
100
  className: e(
99
- $(F, d) && "dark",
101
+ $(w, d) && "dark",
100
102
  Y,
101
103
  /* `--input-width`, not `--button-width`: the button here is
102
104
  the chevron, so matching it renders a 20px sliver. */
@@ -132,14 +134,14 @@ const M = (s, o) => {
132
134
  ] })
133
135
  }
134
136
  ),
135
- (f || n) && /* @__PURE__ */ t(
137
+ (f || m) && /* @__PURE__ */ t(
136
138
  R,
137
139
  {
138
140
  className: e(
139
141
  "rst:text-xs rst:text-left",
140
- m ? "rst:text-error-600 rst:dark:text-error-400 rst:font-medium" : "rst:text-gray-500 rst:dark:text-gray-400"
142
+ n ? "rst:text-error-600 rst:dark:text-error-400 rst:font-medium" : "rst:text-gray-500 rst:dark:text-gray-400"
141
143
  ),
142
- children: n || f
144
+ children: m || f
143
145
  }
144
146
  )
145
147
  ]
@@ -147,5 +149,5 @@ const M = (s, o) => {
147
149
  );
148
150
  };
149
151
  export {
150
- ft as Combobox
152
+ xt as Combobox
151
153
  };
@@ -1 +1 @@
1
- "use client";"use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const t=require("react/jsx-runtime"),T=require("react"),W=require("../../../node_modules/@headlessui/react/dist/components/description/description.cjs"),X=require("../../../node_modules/@headlessui/react/dist/components/field/field.cjs"),G=require("../../../node_modules/@headlessui/react/dist/components/label/label.cjs"),h=require("../../../node_modules/@headlessui/react/dist/components/listbox/listbox.cjs"),J=require("../../../node_modules/@headlessui/react/dist/components/transition/transition.cjs"),F=require("../../../node_modules/@fortawesome/react-fontawesome/dist/index.cjs"),R=require("../../../node_modules/@fortawesome/free-solid-svg-icons/index.cjs"),n=require("../../../lib/utils.cjs"),_=require("../../../internal/field-invalid.cjs"),K=require("../Select/select-variants.cjs"),D=require("../Chip/Chip.cjs"),Q=require("../../../internal/PopupOption.cjs"),c=require("../../../internal/popup.cjs"),Z=({options:x,value:i,onChange:m,placeholder:v="Select options",disabled:l=!1,variant:f,size:o,error:L,className:A,triggerClassName:E,optionsClassName:U,helperText:b,errorMessage:p,label:g,display:u="chips",maxChips:N,clearable:j=!1,chipColorScheme:w="neutral",chipVariant:k="outline",clearLabel:$="Clear selection",removeLabel:C=e=>`Remove ${e}`,countLabel:I=e=>`${e} selected`,...P})=>{const e=!!p||L,V=_.isFieldInvalid(e,P),B=_.withoutInvalidProps(P),a=i.length>0,y=new Map(x.map((r,s)=>[r.value,s])),d=i.map(r=>({value:r,label:x.find(s=>s.value===r)?.label??String(r)})).sort((r,s)=>(y.get(r.value)??Number.POSITIVE_INFINITY)-(y.get(s.value)??Number.POSITIVE_INFINITY)),q=N===void 0?d:d.slice(0,N),O=d.length-q.length,{ref:H,inDarkScope:M}=c.useDarkScope(),S=T.useRef(null);return t.jsxs(X.Field,{disabled:l,className:n.cn("rst:flex rst:flex-col rst:gap-1.5",A),...B,children:[g&&t.jsx(G.Label,{className:"rst:block rst:text-sm rst:font-medium rst:text-[var(--roster-control-text)] rst:text-left",children:g}),t.jsx(h.Listbox,{value:i,onChange:m,disabled:l,multiple:!0,children:t.jsxs("div",{ref:H,className:"rst:relative",children:[t.jsxs("div",{className:n.cn(K.selectTriggerVariants({variant:f,size:o,error:e}),"rst:h-auto rst:flex-wrap rst:items-center rst:gap-1.5 rst:py-1.5",o==="sm"?"rst:min-h-9":o==="lg"?"rst:min-h-11":"rst:min-h-10",j&&a&&"rst:pr-16","rst:focus-within:ring-[length:calc(var(--roster-border-width,1px)+1px)] rst:focus-within:ring-ring",l&&"rst:opacity-50 rst:cursor-not-allowed",E),children:[t.jsx(h.ListboxButton,{ref:S,"aria-invalid":V||void 0,className:"rst:absolute rst:inset-0 rst:h-full rst:w-full rst:cursor-pointer rst:rounded-md rst:focus:outline-hidden rst:disabled:cursor-not-allowed",children:t.jsx("span",{className:"rst:sr-only",children:a?u==="count"?I(i.length):d.map(r=>r.label).join(", "):v})}),!a&&t.jsx("span",{"aria-hidden":"true",className:"rst:pointer-events-none rst:relative rst:block rst:truncate rst:text-gray-500 rst:dark:text-gray-400",children:v}),a&&u==="count"&&t.jsx("span",{"aria-hidden":"true",className:"rst:pointer-events-none rst:relative rst:block rst:truncate",children:I(i.length)}),a&&u==="chips"&&q.map((r,s)=>t.jsx(D.Chip,{size:"sm",variant:k,colorScheme:w,disabled:l,onRemove:()=>m(i.filter(Y=>Y!==r.value)),removeLabel:C(r.label),className:n.cn("rst:relative rst:max-w-[12rem] rst:pointer-events-none","rst:[&_button]:pointer-events-auto","rst:text-inherit rst:border-current/70 rst:dark:text-inherit rst:dark:border-current/70"),children:t.jsx("span",{className:"rst:block rst:truncate",children:r.label})},`${s}-${String(r.value)}`)),O>0&&u==="chips"&&t.jsxs(D.Chip,{size:"sm",variant:k,colorScheme:w,"aria-hidden":"true",className:"rst:pointer-events-none rst:relative rst:text-inherit rst:border-current/70 rst:dark:text-inherit rst:dark:border-current/70",children:["+",O]}),t.jsx("span",{className:n.cn("rst:pointer-events-none rst:absolute rst:inset-y-0 rst:right-0 rst:flex rst:items-center",o==="sm"?"rst:pr-2.5":"rst:pr-3"),children:t.jsx(F.FontAwesomeIcon,{icon:R.faChevronDown,className:"rst:h-3.5 rst:w-3.5 rst:text-gray-400 rst:dark:text-gray-500","aria-hidden":"true"})}),j&&a&&t.jsx("button",{type:"button",disabled:l,onClick:()=>{m([]),S.current?.focus()},"aria-label":$,className:n.cn("rst:absolute rst:inset-y-0 rst:flex rst:w-6 rst:items-center rst:justify-center","rst:cursor-pointer rst:disabled:cursor-not-allowed","rst:text-current rst:opacity-70 rst:hover:opacity-100 rst:disabled:opacity-40","rst:focus:outline-hidden rst:focus-visible:ring-2 rst:focus-visible:ring-ring rst:rounded-sm",o==="sm"?"rst:right-7":"rst:right-8"),children:t.jsx(F.FontAwesomeIcon,{icon:R.faXmark,className:"rst:h-3.5 rst:w-3.5","aria-hidden":"true"})})]}),t.jsx(J.Transition,{as:T.Fragment,leave:"rst:transition rst:ease-in rst:duration-100",leaveFrom:"rst:opacity-100",leaveTo:"rst:opacity-0",children:t.jsx(h.ListboxOptions,{anchor:c.POPUP_ANCHOR,className:n.cn(c.popupInDarkPalette(M,f)&&"dark",c.POPUP_PANEL,c.POPUP_WIDTH_OF_BUTTON,U),children:x.map(r=>t.jsx(Q.PopupOption,{as:h.ListboxOption,value:r.value,disabled:r.disabled,size:o,children:r.label},r.value))})})]})}),(b||p)&&t.jsx(W.Description,{className:n.cn("rst:text-xs rst:text-left",e?"rst:text-error-600 rst:dark:text-error-400 rst:font-medium":"rst:text-gray-500 rst:dark:text-gray-400"),children:p||b})]})};exports.MultiSelect=Z;
1
+ "use client";"use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const t=require("react/jsx-runtime"),F=require("react"),K=require("../../../node_modules/@headlessui/react/dist/components/description/description.cjs"),W=require("../../../node_modules/@headlessui/react/dist/components/field/field.cjs"),X=require("../../../node_modules/@headlessui/react/dist/components/label/label.cjs"),h=require("../../../node_modules/@headlessui/react/dist/components/listbox/listbox.cjs"),G=require("../../../node_modules/@headlessui/react/dist/components/transition/transition.cjs"),T=require("../../../node_modules/@fortawesome/react-fontawesome/dist/index.cjs"),R=require("../../../node_modules/@fortawesome/free-solid-svg-icons/index.cjs"),n=require("../../../lib/utils.cjs"),_=require("../../../internal/field-invalid.cjs"),J=require("../Select/select-variants.cjs"),D=require("../Chip/Chip.cjs"),Q=require("../../../internal/PopupOption.cjs"),c=require("../../../internal/popup.cjs"),Z=require("../../../internal/key-focus.cjs"),z=({options:x,value:i,onChange:m,placeholder:v="Select options",disabled:l=!1,variant:f,size:o,error:L,className:A,triggerClassName:E,optionsClassName:U,helperText:b,errorMessage:p,label:g,display:u="chips",maxChips:N,clearable:j=!1,chipColorScheme:k="neutral",chipVariant:w="outline",clearLabel:$="Clear selection",removeLabel:C=e=>`Remove ${e}`,countLabel:y=e=>`${e} selected`,...I})=>{Z.useKeyFocus();const e=!!p||L,V=_.isFieldInvalid(e,I),B=_.withoutInvalidProps(I),a=i.length>0,P=new Map(x.map((r,s)=>[r.value,s])),d=i.map(r=>({value:r,label:x.find(s=>s.value===r)?.label??String(r)})).sort((r,s)=>(P.get(r.value)??Number.POSITIVE_INFINITY)-(P.get(s.value)??Number.POSITIVE_INFINITY)),q=N===void 0?d:d.slice(0,N),O=d.length-q.length,{ref:H,inDarkScope:M}=c.useDarkScope(),S=F.useRef(null);return t.jsxs(W.Field,{disabled:l,className:n.cn("rst:flex rst:flex-col rst:gap-1.5",A),...B,children:[g&&t.jsx(X.Label,{className:"rst:block rst:text-sm rst:font-medium rst:text-[var(--roster-control-text)] rst:text-left",children:g}),t.jsx(h.Listbox,{value:i,onChange:m,disabled:l,multiple:!0,children:t.jsxs("div",{ref:H,className:"rst:relative",children:[t.jsxs("div",{className:n.cn(J.selectTriggerVariants({variant:f,size:o,error:e}),"rst:h-auto rst:flex-wrap rst:items-center rst:gap-1.5 rst:py-1.5",o==="sm"?"rst:min-h-9":o==="lg"?"rst:min-h-11":"rst:min-h-10",j&&a&&"rst:pr-16","rst:focus-within:ring-[length:calc(var(--roster-border-width,1px)+1px)] rst:focus-within:ring-ring",l&&"rst:opacity-50 rst:cursor-not-allowed",E),children:[t.jsx(h.ListboxButton,{ref:S,"aria-invalid":V||void 0,className:"rst:absolute rst:inset-0 rst:h-full rst:w-full rst:cursor-pointer rst:rounded-md rst:focus:outline-hidden rst:disabled:cursor-not-allowed",children:t.jsx("span",{className:"rst:sr-only",children:a?u==="count"?y(i.length):d.map(r=>r.label).join(", "):v})}),!a&&t.jsx("span",{"aria-hidden":"true",className:"rst:pointer-events-none rst:relative rst:block rst:truncate rst:text-gray-500 rst:dark:text-gray-400",children:v}),a&&u==="count"&&t.jsx("span",{"aria-hidden":"true",className:"rst:pointer-events-none rst:relative rst:block rst:truncate",children:y(i.length)}),a&&u==="chips"&&q.map((r,s)=>t.jsx(D.Chip,{size:"sm",variant:w,colorScheme:k,disabled:l,onRemove:()=>m(i.filter(Y=>Y!==r.value)),removeLabel:C(r.label),className:n.cn("rst:relative rst:max-w-[12rem] rst:pointer-events-none","rst:[&_button]:pointer-events-auto","rst:text-inherit rst:border-current/70 rst:dark:text-inherit rst:dark:border-current/70"),children:t.jsx("span",{className:"rst:block rst:truncate",children:r.label})},`${s}-${String(r.value)}`)),O>0&&u==="chips"&&t.jsxs(D.Chip,{size:"sm",variant:w,colorScheme:k,"aria-hidden":"true",className:"rst:pointer-events-none rst:relative rst:text-inherit rst:border-current/70 rst:dark:text-inherit rst:dark:border-current/70",children:["+",O]}),t.jsx("span",{className:n.cn("rst:pointer-events-none rst:absolute rst:inset-y-0 rst:right-0 rst:flex rst:items-center",o==="sm"?"rst:pr-2.5":"rst:pr-3"),children:t.jsx(T.FontAwesomeIcon,{icon:R.faChevronDown,className:"rst:h-3.5 rst:w-3.5 rst:text-gray-400 rst:dark:text-gray-500","aria-hidden":"true"})}),j&&a&&t.jsx("button",{type:"button",disabled:l,onClick:()=>{m([]),S.current?.focus()},"aria-label":$,className:n.cn("rst:absolute rst:inset-y-0 rst:flex rst:w-6 rst:items-center rst:justify-center","rst:cursor-pointer rst:disabled:cursor-not-allowed","rst:text-current rst:opacity-70 rst:hover:opacity-100 rst:disabled:opacity-40","rst:focus:outline-hidden rst:focus-visible:ring-2 rst:focus-visible:ring-ring rst:rounded-sm",o==="sm"?"rst:right-7":"rst:right-8"),children:t.jsx(T.FontAwesomeIcon,{icon:R.faXmark,className:"rst:h-3.5 rst:w-3.5","aria-hidden":"true"})})]}),t.jsx(G.Transition,{as:F.Fragment,leave:"rst:transition rst:ease-in rst:duration-100",leaveFrom:"rst:opacity-100",leaveTo:"rst:opacity-0",children:t.jsx(h.ListboxOptions,{anchor:c.POPUP_ANCHOR,className:n.cn(c.popupInDarkPalette(M,f)&&"dark",c.POPUP_PANEL,c.POPUP_WIDTH_OF_BUTTON,U),children:x.map(r=>t.jsx(Q.PopupOption,{as:h.ListboxOption,value:r.value,disabled:r.disabled,size:o,children:r.label},r.value))})})]})}),(b||p)&&t.jsx(K.Description,{className:n.cn("rst:text-xs rst:text-left",e?"rst:text-error-600 rst:dark:text-error-400 rst:font-medium":"rst:text-gray-500 rst:dark:text-gray-400"),children:p||b})]})};exports.MultiSelect=z;
@@ -1,20 +1,21 @@
1
1
  "use client";
2
2
  import { jsxs as d, jsx as r } from "react/jsx-runtime";
3
- import V, { Fragment as W } from "react";
4
- import { Description as Y } from "../../../node_modules/@headlessui/react/dist/components/description/description.js";
5
- import { Field as C } from "../../../node_modules/@headlessui/react/dist/components/field/field.js";
6
- import { Label as K } from "../../../node_modules/@headlessui/react/dist/components/label/label.js";
3
+ import K, { Fragment as V } from "react";
4
+ import { Description as W } from "../../../node_modules/@headlessui/react/dist/components/description/description.js";
5
+ import { Field as Y } from "../../../node_modules/@headlessui/react/dist/components/field/field.js";
6
+ import { Label as C } from "../../../node_modules/@headlessui/react/dist/components/label/label.js";
7
7
  import { Listbox as X, ListboxButton as Z, ListboxOptions as q, ListboxOption as G } from "../../../node_modules/@headlessui/react/dist/components/listbox/listbox.js";
8
8
  import { Transition as J } from "../../../node_modules/@headlessui/react/dist/components/transition/transition.js";
9
- import { FontAwesomeIcon as T } from "../../../node_modules/@fortawesome/react-fontawesome/dist/index.js";
9
+ import { FontAwesomeIcon as F } from "../../../node_modules/@fortawesome/react-fontawesome/dist/index.js";
10
10
  import { faChevronDown as Q, faXmark as z } from "../../../node_modules/@fortawesome/free-solid-svg-icons/index.js";
11
11
  import { cn as n } from "../../../lib/utils.js";
12
12
  import { isFieldInvalid as tt, withoutInvalidProps as rt } from "../../../internal/field-invalid.js";
13
13
  import { selectTriggerVariants as et } from "../Select/select-variants.js";
14
- import { Chip as F } from "../Chip/Chip.js";
14
+ import { Chip as T } from "../Chip/Chip.js";
15
15
  import { PopupOption as st } from "../../../internal/PopupOption.js";
16
16
  import { useDarkScope as nt, POPUP_ANCHOR as ot, POPUP_WIDTH_OF_BUTTON as it, POPUP_PANEL as at, popupInDarkPalette as lt } from "../../../internal/popup.js";
17
- const Pt = ({
17
+ import { useKeyFocus as ct } from "../../../internal/key-focus.js";
18
+ const Ot = ({
18
19
  options: u,
19
20
  value: o,
20
21
  onChange: p,
@@ -37,22 +38,23 @@ const Pt = ({
37
38
  clearLabel: E = "Clear selection",
38
39
  removeLabel: U = (e) => `Remove ${e}`,
39
40
  countLabel: I = (e) => `${e} selected`,
40
- ...P
41
+ ...y
41
42
  }) => {
42
- const e = !!h || R, $ = tt(e, P), A = rt(P), a = o.length > 0, y = new Map(u.map((t, s) => [t.value, s])), m = o.map((t) => ({
43
+ ct();
44
+ const e = !!h || R, $ = tt(e, y), A = rt(y), a = o.length > 0, P = new Map(u.map((t, s) => [t.value, s])), m = o.map((t) => ({
43
45
  value: t,
44
46
  label: u.find((s) => s.value === t)?.label ?? String(t)
45
47
  })).sort(
46
- (t, s) => (y.get(t.value) ?? Number.POSITIVE_INFINITY) - (y.get(s.value) ?? Number.POSITIVE_INFINITY)
47
- ), O = g === void 0 ? m : m.slice(0, g), S = m.length - O.length, { ref: B, inDarkScope: M } = nt(), _ = V.useRef(null);
48
+ (t, s) => (P.get(t.value) ?? Number.POSITIVE_INFINITY) - (P.get(s.value) ?? Number.POSITIVE_INFINITY)
49
+ ), O = g === void 0 ? m : m.slice(0, g), S = m.length - O.length, { ref: B, inDarkScope: M } = nt(), _ = K.useRef(null);
48
50
  return /* @__PURE__ */ d(
49
- C,
51
+ Y,
50
52
  {
51
53
  disabled: l,
52
54
  className: n("rst:flex rst:flex-col rst:gap-1.5", D),
53
55
  ...A,
54
56
  children: [
55
- b && /* @__PURE__ */ r(K, { className: "rst:block rst:text-sm rst:font-medium rst:text-[var(--roster-control-text)] rst:text-left", children: b }),
57
+ b && /* @__PURE__ */ r(C, { className: "rst:block rst:text-sm rst:font-medium rst:text-[var(--roster-control-text)] rst:text-left", children: b }),
56
58
  /* @__PURE__ */ r(X, { value: o, onChange: p, disabled: l, multiple: !0, children: /* @__PURE__ */ d("div", { ref: B, className: "rst:relative", children: [
57
59
  /* @__PURE__ */ d(
58
60
  "div",
@@ -98,7 +100,7 @@ const Pt = ({
98
100
  }
99
101
  ),
100
102
  a && c === "chips" && O.map((t, s) => /* @__PURE__ */ r(
101
- F,
103
+ T,
102
104
  {
103
105
  size: "sm",
104
106
  variant: w,
@@ -116,7 +118,7 @@ const Pt = ({
116
118
  `${s}-${String(t.value)}`
117
119
  )),
118
120
  S > 0 && c === "chips" && /* @__PURE__ */ d(
119
- F,
121
+ T,
120
122
  {
121
123
  size: "sm",
122
124
  variant: w,
@@ -137,7 +139,7 @@ const Pt = ({
137
139
  i === "sm" ? "rst:pr-2.5" : "rst:pr-3"
138
140
  ),
139
141
  children: /* @__PURE__ */ r(
140
- T,
142
+ F,
141
143
  {
142
144
  icon: Q,
143
145
  className: "rst:h-3.5 rst:w-3.5 rst:text-gray-400 rst:dark:text-gray-500",
@@ -167,7 +169,7 @@ const Pt = ({
167
169
  i === "sm" ? "rst:right-7" : "rst:right-8"
168
170
  ),
169
171
  children: /* @__PURE__ */ r(
170
- T,
172
+ F,
171
173
  {
172
174
  icon: z,
173
175
  className: "rst:h-3.5 rst:w-3.5",
@@ -182,7 +184,7 @@ const Pt = ({
182
184
  /* @__PURE__ */ r(
183
185
  J,
184
186
  {
185
- as: W,
187
+ as: V,
186
188
  leave: "rst:transition rst:ease-in rst:duration-100",
187
189
  leaveFrom: "rst:opacity-100",
188
190
  leaveTo: "rst:opacity-0",
@@ -213,7 +215,7 @@ const Pt = ({
213
215
  )
214
216
  ] }) }),
215
217
  (x || h) && /* @__PURE__ */ r(
216
- Y,
218
+ W,
217
219
  {
218
220
  className: n(
219
221
  "rst:text-xs rst:text-left",
@@ -227,5 +229,5 @@ const Pt = ({
227
229
  );
228
230
  };
229
231
  export {
230
- Pt as MultiSelect
232
+ Ot as MultiSelect
231
233
  };
@@ -1 +1 @@
1
- "use client";"use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const s=require("react/jsx-runtime"),i=require("react"),j=require("../../../node_modules/@fortawesome/react-fontawesome/dist/index.cjs"),c=require("../../../node_modules/@fortawesome/free-solid-svg-icons/index.cjs"),a=require("../../../lib/utils.cjs"),S=require("../Input/Input.cjs"),u=i.forwardRef(({revealable:l=!0,defaultRevealed:d=!1,revealed:r,onRevealChange:p,showLabel:y="Show password",hideLabel:f="Hide password",disabled:e,variant:m,error:w,errorMessage:h,className:v,...x},g)=>{const[I,q]=i.useState(d),o=r!==void 0,t=o?r:I,b=()=>{const n=!t;o||q(n),p?.(n)};return s.jsx(S.Input,{ref:g,type:t?"text":"password",disabled:e,variant:m,error:w,errorMessage:h,className:a.cn("rst:[&_input::-ms-reveal]:hidden",v),endIcon:l?s.jsx("button",{type:"button",onClick:b,disabled:e,"aria-label":t?f:y,"aria-pressed":t,className:a.cn("rst:-m-1 rst:flex rst:items-center rst:rounded-sm rst:p-1 rst:transition-opacity","rst:opacity-70 rst:hover:opacity-100","rst:focus:outline-hidden rst:focus-visible:ring-2 rst:focus-visible:ring-ring",e&&"rst:cursor-not-allowed rst:opacity-40 rst:hover:opacity-40"),children:s.jsx(j.FontAwesomeIcon,{icon:t?c.faEyeSlash:c.faEye,className:"rst:h-4 rst:w-4","aria-hidden":"true"})}):void 0,...x})});u.displayName="PasswordInput";exports.PasswordInput=u;
1
+ "use client";"use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("react/jsx-runtime"),i=require("react"),j=require("../../../node_modules/@fortawesome/react-fontawesome/dist/index.cjs"),c=require("../../../node_modules/@fortawesome/free-solid-svg-icons/index.cjs"),a=require("../../../lib/utils.cjs"),S=require("../Input/Input.cjs"),u=i.forwardRef(({revealable:l=!0,defaultRevealed:d=!1,revealed:r,onRevealChange:p,showLabel:y="Show password",hideLabel:f="Hide password",disabled:s,variant:m,error:w,errorMessage:h,className:v,...x},g)=>{const[I,q]=i.useState(d),o=r!==void 0,t=o?r:I,b=()=>{const n=!t;o||q(n),p?.(n)};return e.jsx(S.Input,{ref:g,type:t?"text":"password",disabled:s,variant:m,error:w,errorMessage:h,className:a.cn("rst:[&_input::-ms-reveal]:hidden",v),endIcon:l?e.jsx("button",{type:"button",onClick:b,disabled:s,"aria-label":t?f:y,"aria-pressed":t,className:a.cn("rst:-m-1 rst:flex rst:items-center rst:rounded-sm rst:p-1 rst:transition-opacity","rst:opacity-70 rst:hover:opacity-100","rst:focus:outline-hidden rst:focus-visible:ring-2 rst:focus-visible:ring-ring",s?"rst:cursor-not-allowed rst:opacity-40 rst:hover:opacity-40":"rst:cursor-pointer"),children:e.jsx(j.FontAwesomeIcon,{icon:t?c.faEyeSlash:c.faEye,className:"rst:h-4 rst:w-4","aria-hidden":"true"})}):void 0,...x})});u.displayName="PasswordInput";exports.PasswordInput=u;