@primitiv-ui/react 0.1.0 → 0.1.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.
Files changed (207) hide show
  1. package/LICENSE +21 -0
  2. package/package.json +2 -1
  3. package/src/AccessibleIcon/AccessibleIcon.tsx +6 -2
  4. package/src/AccessibleIcon/__tests__/AccessibleIcon.test.tsx +1 -1
  5. package/src/AccessibleIcon/types.ts +4 -0
  6. package/src/Accordion/Accordion.tsx +34 -12
  7. package/src/Accordion/AccordionContext.ts +1 -1
  8. package/src/Accordion/__tests__/Accordion.reading-direction.test.tsx +1 -1
  9. package/src/Accordion/hooks/useAccordionItem.ts +1 -1
  10. package/src/Accordion/hooks/useAccordionRoot.ts +1 -1
  11. package/src/Accordion/hooks/useAccordionTrigger.ts +2 -2
  12. package/src/Accordion/index.ts +2 -1
  13. package/src/Accordion/types.ts +55 -13
  14. package/src/Alert/Alert.tsx +9 -2
  15. package/src/Alert/__tests__/Alert.test.tsx +1 -1
  16. package/src/Alert/types.ts +1 -0
  17. package/src/Avatar/Avatar.tsx +20 -7
  18. package/src/Avatar/AvatarContext.ts +12 -6
  19. package/src/Breadcrumb/Breadcrumb.tsx +32 -10
  20. package/src/Button/Button.tsx +5 -2
  21. package/src/Button/types.ts +4 -0
  22. package/src/Carousel/Carousel.tsx +30 -14
  23. package/src/Carousel/CarouselContext.ts +7 -3
  24. package/src/Carousel/__tests__/Carousel.asChild.test.tsx +1 -1
  25. package/src/Carousel/__tests__/Carousel.auto-play.test.tsx +1 -1
  26. package/src/Carousel/__tests__/Carousel.basic-rendering.test.tsx +1 -1
  27. package/src/Carousel/__tests__/Carousel.controlled-state.test.tsx +1 -1
  28. package/src/Carousel/__tests__/Carousel.error-handling.test.tsx +1 -1
  29. package/src/Carousel/__tests__/Carousel.ids.test.tsx +1 -1
  30. package/src/Carousel/__tests__/Carousel.imperative-api.test.tsx +2 -2
  31. package/src/Carousel/__tests__/Carousel.indicators.test.tsx +1 -1
  32. package/src/Carousel/__tests__/Carousel.intersection-observer.test.tsx +2 -2
  33. package/src/Carousel/__tests__/Carousel.keyboard-navigation.test.tsx +1 -1
  34. package/src/Carousel/__tests__/Carousel.play-pause.test.tsx +1 -1
  35. package/src/Carousel/__tests__/Carousel.prev-next.test.tsx +1 -1
  36. package/src/Carousel/__tests__/Carousel.reduced-motion.test.tsx +1 -1
  37. package/src/Carousel/__tests__/Carousel.refresh-progress.test.tsx +2 -2
  38. package/src/Carousel/__tests__/Carousel.scroll-snap-change.test.tsx +1 -1
  39. package/src/Carousel/__tests__/Carousel.scroll-sync.test.tsx +1 -1
  40. package/src/Carousel/__tests__/Carousel.slides-per-move.test.tsx +1 -1
  41. package/src/Carousel/__tests__/Carousel.slides-per-page.test.tsx +1 -1
  42. package/src/Carousel/__tests__/Carousel.touch-interaction.test.tsx +1 -1
  43. package/src/Carousel/__tests__/Carousel.transition-modes.test.tsx +1 -1
  44. package/src/Carousel/__tests__/Carousel.translations.test.tsx +1 -1
  45. package/src/Carousel/__tests__/Carousel.uncontrolled-state.test.tsx +1 -1
  46. package/src/Carousel/types.ts +8 -0
  47. package/src/Checkbox/Checkbox.tsx +11 -6
  48. package/src/Checkbox/CheckboxContext.ts +1 -1
  49. package/src/Checkbox/hooks/useCheckboxRoot.ts +1 -1
  50. package/src/Checkbox/index.ts +1 -0
  51. package/src/Checkbox/types.ts +30 -3
  52. package/src/CheckboxCard/CheckboxCard.tsx +13 -11
  53. package/src/CheckboxCard/CheckboxCardContext.ts +19 -6
  54. package/src/CheckboxCard/hooks/useCheckboxCardRoot.ts +2 -2
  55. package/src/CheckboxCard/types.ts +21 -5
  56. package/src/Collapsible/Collapsible.tsx +37 -21
  57. package/src/Collapsible/CollapsibleContext.ts +1 -1
  58. package/src/Collapsible/hooks/useCollapsibleRoot.ts +1 -1
  59. package/src/Collapsible/hooks/useCollapsibleTrigger.ts +1 -1
  60. package/src/Collapsible/index.ts +1 -0
  61. package/src/Collapsible/types.ts +45 -12
  62. package/src/ContextMenu/ContextMenu.tsx +60 -34
  63. package/src/ContextMenu/ContextMenuContext.ts +2 -2
  64. package/src/ContextMenu/ContextMenuSubContext.ts +1 -1
  65. package/src/ContextMenu/__tests__/ContextMenu.reading-direction.test.tsx +1 -1
  66. package/src/ContextMenu/index.ts +2 -1
  67. package/src/ContextMenu/types.ts +160 -17
  68. package/src/DirectionProvider/DirectionProvider.tsx +7 -1
  69. package/src/DirectionProvider/__tests__/DirectionProvider.test.tsx +1 -1
  70. package/src/DirectionProvider/types.ts +1 -0
  71. package/src/Divider/Divider.tsx +4 -1
  72. package/src/Divider/__tests__/Divider.test.tsx +1 -1
  73. package/src/Divider/index.ts +2 -1
  74. package/src/Divider/types.ts +5 -0
  75. package/src/Dropdown/Dropdown.tsx +60 -34
  76. package/src/Dropdown/DropdownContext.ts +2 -2
  77. package/src/Dropdown/DropdownSubContext.ts +1 -1
  78. package/src/Dropdown/__tests__/Dropdown.reading-direction.test.tsx +1 -1
  79. package/src/Dropdown/hooks/useDropdownContent.ts +1 -1
  80. package/src/Dropdown/hooks/useDropdownItem.ts +1 -1
  81. package/src/Dropdown/hooks/useDropdownRoot.ts +2 -2
  82. package/src/Dropdown/hooks/useDropdownTrigger.ts +1 -1
  83. package/src/Dropdown/index.ts +2 -1
  84. package/src/Dropdown/types.ts +153 -25
  85. package/src/EmptyState/EmptyState.tsx +34 -20
  86. package/src/EmptyState/__tests__/EmptyState.Actions.test.tsx +1 -1
  87. package/src/EmptyState/__tests__/EmptyState.Description.test.tsx +1 -1
  88. package/src/EmptyState/__tests__/EmptyState.Media.test.tsx +1 -1
  89. package/src/EmptyState/__tests__/EmptyState.Root.test.tsx +1 -1
  90. package/src/EmptyState/__tests__/EmptyState.Title.test.tsx +1 -1
  91. package/src/EmptyState/types.ts +2 -1
  92. package/src/Field/Field.tsx +24 -10
  93. package/src/Field/FieldContext.ts +1 -1
  94. package/src/Field/types.ts +4 -0
  95. package/src/Fieldset/Fieldset.tsx +26 -10
  96. package/src/Fieldset/types.ts +2 -0
  97. package/src/Input/Input.tsx +6 -3
  98. package/src/Input/__tests__/Input.field-integration.test.tsx +1 -1
  99. package/src/Input/types.ts +4 -0
  100. package/src/InputGroup/InputGroup.tsx +15 -8
  101. package/src/InputGroup/types.ts +9 -0
  102. package/src/MillerColumns/MillerColumns.tsx +28 -8
  103. package/src/MillerColumns/MillerColumnsContext.ts +1 -1
  104. package/src/MillerColumns/hooks/useMillerColumnsItem.ts +2 -2
  105. package/src/MillerColumns/hooks/useMillerColumnsRoot.ts +0 -0
  106. package/src/MillerColumns/index.ts +1 -1
  107. package/src/MillerColumns/types.ts +67 -14
  108. package/src/MillerColumns/useMillerColumnsSelection.ts +1 -1
  109. package/src/Modal/Modal.tsx +25 -11
  110. package/src/Modal/ModalContext.ts +14 -7
  111. package/src/Modal/hooks/useModalRoot.ts +1 -1
  112. package/src/Modal/hooks/useModalTrigger.ts +2 -2
  113. package/src/Modal/types.ts +51 -2
  114. package/src/Portal/Portal.tsx +3 -1
  115. package/src/Portal/types.ts +4 -0
  116. package/src/Progress/Progress.tsx +12 -7
  117. package/src/Progress/ProgressContext.ts +18 -6
  118. package/src/RadioCard/RadioCard.tsx +17 -11
  119. package/src/RadioCard/RadioCardContext.ts +17 -5
  120. package/src/RadioCard/RadioCardItemContext.ts +18 -5
  121. package/src/RadioCard/__tests__/RadioCard.reading-direction.test.tsx +1 -1
  122. package/src/RadioCard/hooks/useRadioCardRoot.ts +1 -1
  123. package/src/RadioCard/types.ts +24 -3
  124. package/src/RadioGroup/RadioGroup.tsx +17 -11
  125. package/src/RadioGroup/RadioGroupContext.ts +1 -1
  126. package/src/RadioGroup/RadioGroupItemContext.ts +1 -1
  127. package/src/RadioGroup/__tests__/RadioGroup.reading-direction.test.tsx +1 -1
  128. package/src/RadioGroup/hooks/useRadioGroupRoot.ts +1 -1
  129. package/src/RadioGroup/index.ts +1 -0
  130. package/src/RadioGroup/types.ts +34 -3
  131. package/src/Select/Select.tsx +23 -8
  132. package/src/Select/__tests__/Select.field-integration.test.tsx +1 -1
  133. package/src/Select/index.ts +1 -1
  134. package/src/Select/types.ts +18 -3
  135. package/src/SkipNav/SkipNav.tsx +7 -2
  136. package/src/SkipNav/__tests__/SkipNav.ids.test.tsx +1 -1
  137. package/src/Slider/Slider.tsx +26 -11
  138. package/src/Slider/SliderContext.ts +13 -6
  139. package/src/Slider/__tests__/Slider.reading-direction.test.tsx +1 -1
  140. package/src/Slider/hooks/useSliderRoot.ts +1 -1
  141. package/src/Slider/types.ts +12 -3
  142. package/src/Status/Status.tsx +9 -2
  143. package/src/Status/__tests__/Status.test.tsx +1 -1
  144. package/src/Status/types.ts +4 -0
  145. package/src/Switch/Switch.tsx +16 -6
  146. package/src/Switch/SwitchContext.ts +13 -5
  147. package/src/Switch/hooks/useSwitchRoot.ts +1 -1
  148. package/src/Switch/types.ts +24 -3
  149. package/src/Table/Table.tsx +51 -25
  150. package/src/Table/__tests__/Table.Body.test.tsx +1 -1
  151. package/src/Table/__tests__/Table.Caption.test.tsx +1 -1
  152. package/src/Table/__tests__/Table.Cell.test.tsx +1 -1
  153. package/src/Table/__tests__/Table.Footer.test.tsx +1 -1
  154. package/src/Table/__tests__/Table.Head.test.tsx +1 -1
  155. package/src/Table/__tests__/Table.Header.test.tsx +1 -1
  156. package/src/Table/__tests__/Table.Root.test.tsx +1 -1
  157. package/src/Table/__tests__/Table.Row.test.tsx +1 -1
  158. package/src/Table/__tests__/Table.ScrollArea.test.tsx +1 -1
  159. package/src/Table/index.ts +2 -1
  160. package/src/Tabs/Tabs.tsx +30 -10
  161. package/src/Tabs/TabsContext.ts +15 -7
  162. package/src/Tabs/__tests__/Tabs.asChild.test.tsx +1 -1
  163. package/src/Tabs/__tests__/Tabs.basic-rendering.test.tsx +1 -1
  164. package/src/Tabs/__tests__/Tabs.change-event-callbacks.test.tsx +1 -1
  165. package/src/Tabs/__tests__/Tabs.controlled-state.test.tsx +1 -1
  166. package/src/Tabs/__tests__/Tabs.error-handling.test.tsx +1 -1
  167. package/src/Tabs/__tests__/Tabs.imperative-api.test.tsx +1 -1
  168. package/src/Tabs/__tests__/Tabs.keyboard-interaction.test.tsx +1 -1
  169. package/src/Tabs/__tests__/Tabs.lazy-mount.test.tsx +1 -1
  170. package/src/Tabs/__tests__/Tabs.mouse-interaction.test.tsx +1 -1
  171. package/src/Tabs/__tests__/Tabs.reading-direction.test.tsx +1 -1
  172. package/src/Tabs/__tests__/Tabs.uncontrolled-state.test.tsx +1 -1
  173. package/src/Tabs/hooks/useTabsContent.ts +1 -1
  174. package/src/Tabs/hooks/useTabsRoot.ts +1 -1
  175. package/src/Tabs/hooks/useTabsTrigger.ts +1 -1
  176. package/src/Tabs/types.ts +35 -1
  177. package/src/Tabs/utils.ts +1 -1
  178. package/src/Textarea/Textarea.tsx +6 -3
  179. package/src/Textarea/__tests__/Textarea.field-integration.test.tsx +1 -1
  180. package/src/Textarea/types.ts +4 -0
  181. package/src/Toggle/Toggle.tsx +11 -4
  182. package/src/Toggle/types.ts +7 -3
  183. package/src/ToggleGroup/ToggleGroup.tsx +23 -13
  184. package/src/ToggleGroup/ToggleGroupContext.ts +1 -1
  185. package/src/ToggleGroup/__tests__/ToggleGroup.reading-direction.test.tsx +1 -1
  186. package/src/ToggleGroup/hooks/useToggleGroupRoot.ts +1 -1
  187. package/src/ToggleGroup/types.ts +45 -5
  188. package/src/Tooltip/Tooltip.tsx +46 -15
  189. package/src/Tooltip/TooltipContext.ts +1 -1
  190. package/src/Tooltip/hooks/useTooltipContent.ts +1 -1
  191. package/src/Tooltip/hooks/useTooltipRoot.ts +1 -1
  192. package/src/Tooltip/hooks/useTooltipTrigger.ts +1 -1
  193. package/src/Tooltip/index.ts +1 -0
  194. package/src/Tooltip/types.ts +50 -2
  195. package/src/Tree/Tree.tsx +58 -12
  196. package/src/Tree/TreeContext.ts +1 -1
  197. package/src/Tree/__tests__/Tree.selection-path.test.tsx +2 -2
  198. package/src/Tree/hooks/useTreeItemKeyboard.ts +1 -1
  199. package/src/Tree/hooks/useTreeRoot.ts +1 -1
  200. package/src/Tree/index.ts +1 -1
  201. package/src/Tree/types.ts +39 -7
  202. package/src/VisuallyHidden/VisuallyHidden.tsx +4 -2
  203. package/src/VisuallyHidden/__tests__/VisuallyHidden.test.tsx +1 -1
  204. package/src/VisuallyHidden/types.ts +4 -0
  205. package/src/index.ts +39 -38
  206. package/src/types.ts +1 -0
  207. package/src/utils/createStrictContext.ts +9 -5
package/src/Tabs/types.ts CHANGED
@@ -1,9 +1,16 @@
1
1
  import { ComponentProps, Ref } from "react";
2
2
 
3
+ /** Layout axis of the tab list. `"horizontal"` arranges triggers in a row and
4
+ * binds ArrowLeft/ArrowRight; `"vertical"` stacks them and binds
5
+ * ArrowUp/ArrowDown. */
3
6
  export type TabsOrientation = "horizontal" | "vertical";
4
7
 
8
+ /** Reading direction of the tab list. In `"rtl"` the horizontal arrow keys are
9
+ * mirrored so navigation follows the visual order. */
5
10
  export type TabsReadingDirection = "ltr" | "rtl";
6
11
 
12
+ /** When a focused trigger becomes active. `"automatic"` activates a tab as soon
13
+ * as it receives focus via the arrow keys; `"manual"` requires Enter/Space. */
7
14
  export type TabsActivationMode = "automatic" | "manual";
8
15
 
9
16
  /**
@@ -17,22 +24,34 @@ export type TabsActivationMode = "automatic" | "manual";
17
24
  */
18
25
  export type TabMetadata = { index: number; name: string };
19
26
 
27
+ /** Props common to both controlled and uncontrolled `Tabs.Root` usage. */
20
28
  export type BaseTabsRootProps = {
29
+ /** Fired on every user-driven activation with the activated tab's metadata. */
21
30
  onChange?: ({ index, name }: TabMetadata) => void;
22
31
  };
23
32
 
33
+ /** Uncontrolled `Tabs.Root` props: the component owns the active tab, seeded by
34
+ * an optional `defaultValue`. Mutually exclusive with the controlled props. */
24
35
  export type UncontrolledTabsRootProps = {
36
+ /** Value of the tab active on first render. */
25
37
  defaultValue?: string;
26
38
  value?: never;
27
39
  onValueChange?: never;
28
40
  };
29
41
 
30
- type ControlledTabsRootProps = {
42
+ /** Controlled `Tabs.Root` props: the caller owns the active tab via `value` and
43
+ * is notified of activation requests through `onValueChange`. */
44
+ export type ControlledTabsRootProps = {
45
+ /** Value of the currently active tab. */
31
46
  value: string;
47
+ /** Called with the requested value when the user activates a tab. */
32
48
  onValueChange: (value: string) => void;
33
49
  defaultValue?: never;
34
50
  };
35
51
 
52
+ /** Props for `Tabs.Root` — the state owner and context provider. Extends the
53
+ * native `<div>` props (minus `onChange`) and resolves to either the
54
+ * controlled or uncontrolled prop shape. */
36
55
  export type TabsRootProps = Omit<ComponentProps<"div">, "onChange"> & {
37
56
  orientation?: TabsOrientation;
38
57
  dir?: TabsReadingDirection;
@@ -46,6 +65,9 @@ export type TabsRootProps = Omit<ComponentProps<"div">, "onChange"> & {
46
65
  } & BaseTabsRootProps &
47
66
  (UncontrolledTabsRootProps | ControlledTabsRootProps);
48
67
 
68
+ /** The value shared by `Tabs.Root` with its descendants through context:
69
+ * resolved configuration, the active tab and its setter, and the registry of
70
+ * triggers used for roving focus and keyboard navigation. */
49
71
  export type TabsContextValue = {
50
72
  orientation: TabsOrientation;
51
73
  dir: TabsReadingDirection;
@@ -67,6 +89,9 @@ export type TabsContextValue = {
67
89
  focusTrigger: (value: string) => void;
68
90
  };
69
91
 
92
+ /** Props for `Tabs.List` — the `role="tablist"` container. Requires exactly one
93
+ * accessible name source: either an inline `label` or an `ariaLabelledBy` id
94
+ * referencing existing label text. */
70
95
  export type TabsListProps = Omit<
71
96
  ComponentProps<"div">,
72
97
  "label" | "aria-labelledby"
@@ -75,6 +100,10 @@ export type TabsListProps = Omit<
75
100
  | { label: string; ariaLabelledBy?: never }
76
101
  | { label?: never; ariaLabelledBy: string }
77
102
  );
103
+ /** Props for `Tabs.Trigger` — an individual `role="tab"` button. Identified by
104
+ * its required `value`, which links it to the `Tabs.Content` of the same value.
105
+ * The element type defaults to `HTMLButtonElement` and can be overridden via
106
+ * `asChild` and the `ref` type parameter. */
78
107
  export type TabsTriggerProps<T extends HTMLElement = HTMLButtonElement> = Omit<
79
108
  ComponentProps<"button">,
80
109
  "ref"
@@ -90,10 +119,15 @@ export type TabsTriggerProps<T extends HTMLElement = HTMLButtonElement> = Omit<
90
119
  ref?: Ref<T>;
91
120
  };
92
121
 
122
+ /** Props for `Tabs.Content` — a `role="tabpanel"`. Its required `value` links
123
+ * it to the `Tabs.Trigger` of the same value. */
93
124
  export type TabsContentProps = ComponentProps<"div"> & {
125
+ /** Value of the trigger this panel belongs to. */
94
126
  value: string;
95
127
  };
96
128
 
129
+ /** Imperative handle exposed on the `Tabs.Root` ref for programmatic control. */
97
130
  export type TabsImperativeApi = {
131
+ /** Activate the tab with the given value. */
98
132
  setActiveTab: (value: string) => void;
99
133
  };
package/src/Tabs/utils.ts CHANGED
@@ -1,4 +1,4 @@
1
- import { deriveId } from "../utils";
1
+ import { deriveId } from "../utils/index.ts";
2
2
 
3
3
  export function getTriggerAndPanelIds(tabsId: string, value: string) {
4
4
  return {
@@ -1,5 +1,7 @@
1
- import { useFieldProps } from "../Field/hooks";
2
- import { Slot } from "../Slot";
1
+ import type { ReactElement } from "react";
2
+
3
+ import { useFieldProps } from "../Field/hooks/index.ts";
4
+ import { Slot } from "../Slot/index.ts";
3
5
  import { TextareaProps } from "./types";
4
6
 
5
7
  /**
@@ -74,7 +76,7 @@ export function Textarea({
74
76
  children,
75
77
  ref,
76
78
  ...consumer
77
- }: TextareaProps) {
79
+ }: TextareaProps): ReactElement {
78
80
  const merged = useFieldProps(consumer);
79
81
 
80
82
  const rootProps = {
@@ -90,4 +92,5 @@ export function Textarea({
90
92
  return <textarea {...rootProps} />;
91
93
  }
92
94
 
95
+ /** @internal */
93
96
  Textarea.displayName = "Textarea";
@@ -1,6 +1,6 @@
1
1
  import { render, screen } from "@testing-library/react";
2
2
 
3
- import { Field } from "../../Field";
3
+ import { Field } from "../../Field/index.ts";
4
4
  import { Textarea } from "../Textarea";
5
5
 
6
6
  describe("Textarea — Field integration", () => {
@@ -1,5 +1,9 @@
1
1
  import { ComponentProps, ReactNode, Ref } from "react";
2
2
 
3
+ /**
4
+ * Props for {@link Textarea} — all native `<textarea>` attributes plus the
5
+ * `asChild` escape hatch and a typed `ref`.
6
+ */
3
7
  export type TextareaProps = ComponentProps<"textarea"> & {
4
8
  asChild?: boolean;
5
9
  ref?: Ref<HTMLTextAreaElement>;
@@ -1,5 +1,7 @@
1
- import { useControllableState } from "../hooks";
2
- import { Slot, composeEventHandlers } from "../Slot";
1
+ import type { ReactElement } from "react";
2
+
3
+ import { useControllableState } from "../hooks/index.ts";
4
+ import { Slot, composeEventHandlers } from "../Slot/index.ts";
3
5
 
4
6
  import { ToggleProps } from "./types";
5
7
 
@@ -50,7 +52,7 @@ function Toggle({
50
52
  children,
51
53
  ref,
52
54
  ...rest
53
- }: ToggleProps) {
55
+ }: ToggleProps): ReactElement {
54
56
  const [pressed, setPressed] = useControllableState<boolean>(
55
57
  controlledPressed,
56
58
  defaultPressed ?? false,
@@ -73,9 +75,14 @@ function Toggle({
73
75
  };
74
76
 
75
77
  if (asChild) return <Slot {...toggleProps}>{children}</Slot>;
76
- return <button type="button" {...toggleProps}>{children}</button>;
78
+ return (
79
+ <button type="button" {...toggleProps}>
80
+ {children}
81
+ </button>
82
+ );
77
83
  }
78
84
 
85
+ /** @internal */
79
86
  Toggle.displayName = "Toggle";
80
87
 
81
88
  export { Toggle };
@@ -1,23 +1,27 @@
1
1
  import { ButtonHTMLAttributes, ReactNode, Ref } from "react";
2
2
 
3
- type UncontrolledToggleProps = {
3
+ /** Uncontrolled `Toggle` props: seed with `defaultPressed`; `pressed`/`onPressedChange` are disallowed. */
4
+ export type UncontrolledToggleProps = {
4
5
  defaultPressed?: boolean;
5
6
  pressed?: never;
6
7
  onPressedChange?: never;
7
8
  };
8
9
 
9
- type ControlledToggleProps = {
10
+ /** Controlled `Toggle` props: drive with `pressed` and `onPressedChange`; `defaultPressed` is disallowed. */
11
+ export type ControlledToggleProps = {
10
12
  pressed: boolean;
11
13
  onPressedChange: (pressed: boolean) => void;
12
14
  defaultPressed?: never;
13
15
  };
14
16
 
15
- type ToggleBaseProps = {
17
+ /** Props common to both `Toggle` modes: `disabled`, `asChild`, `children`, `ref`, and the native `<button>` attributes (minus `type`). */
18
+ export type ToggleBaseProps = {
16
19
  disabled?: boolean;
17
20
  asChild?: boolean;
18
21
  children?: ReactNode;
19
22
  ref?: Ref<HTMLButtonElement>;
20
23
  } & Omit<ButtonHTMLAttributes<HTMLButtonElement>, "type">;
21
24
 
25
+ /** Props for the `Toggle` button — base props combined with the controlled/uncontrolled discriminated union. */
22
26
  export type ToggleProps = ToggleBaseProps &
23
27
  (UncontrolledToggleProps | ControlledToggleProps);
@@ -1,11 +1,12 @@
1
1
  import { useEffect, useMemo, useRef } from "react";
2
+ import type { ReactElement } from "react";
2
3
 
3
- import { useDirection } from "../DirectionProvider";
4
- import { useRovingTabindex } from "../hooks";
5
- import { Slot, composeEventHandlers, composeRefs } from "../Slot";
4
+ import { useDirection } from "../DirectionProvider/index.ts";
5
+ import { useRovingTabindex } from "../hooks/index.ts";
6
+ import { Slot, composeEventHandlers, composeRefs } from "../Slot/index.ts";
6
7
 
7
8
  import { ToggleGroupContext } from "./ToggleGroupContext";
8
- import { useToggleGroupRoot, useToggleGroupContext } from "./hooks";
9
+ import { useToggleGroupRoot, useToggleGroupContext } from "./hooks/index.ts";
9
10
  import { ToggleGroupItemProps, ToggleGroupRootProps } from "./types";
10
11
 
11
12
  /**
@@ -62,7 +63,7 @@ import { ToggleGroupItemProps, ToggleGroupRootProps } from "./types";
62
63
  * </ToggleGroup.Root>
63
64
  * ```
64
65
  */
65
- function ToggleGroupRoot({
66
+ export function ToggleGroupRoot({
66
67
  type,
67
68
  defaultValue,
68
69
  value: controlledValue,
@@ -73,7 +74,7 @@ function ToggleGroupRoot({
73
74
  children,
74
75
  ref,
75
76
  ...rest
76
- }: ToggleGroupRootProps) {
77
+ }: ToggleGroupRootProps): ReactElement {
77
78
  const resolvedDir = dir ?? useDirection();
78
79
  const {
79
80
  value,
@@ -138,6 +139,7 @@ function ToggleGroupRoot({
138
139
  );
139
140
  }
140
141
 
142
+ /** @internal */
141
143
  ToggleGroupRoot.displayName = "ToggleGroupRoot";
142
144
 
143
145
  /**
@@ -167,7 +169,7 @@ ToggleGroupRoot.displayName = "ToggleGroupRoot";
167
169
  *
168
170
  * @throws if rendered outside a `ToggleGroup.Root`.
169
171
  */
170
- function ToggleGroupItem({
172
+ export function ToggleGroupItem({
171
173
  value,
172
174
  disabled,
173
175
  asChild = false,
@@ -177,7 +179,7 @@ function ToggleGroupItem({
177
179
  children,
178
180
  ref,
179
181
  ...rest
180
- }: ToggleGroupItemProps) {
182
+ }: ToggleGroupItemProps): ReactElement {
181
183
  const {
182
184
  value: groupValue,
183
185
  toggle,
@@ -250,9 +252,14 @@ function ToggleGroupItem({
250
252
  );
251
253
  }
252
254
 
255
+ /** @internal */
253
256
  ToggleGroupItem.displayName = "ToggleGroupItem";
254
257
 
255
- type TToggleGroupCompound = typeof ToggleGroupRoot & {
258
+ /**
259
+ * The shape of the exported `ToggleGroup` value — callable as
260
+ * `ToggleGroup.Root` and carrying `Root` and `Item` as static properties.
261
+ */
262
+ export type TToggleGroupCompound = typeof ToggleGroupRoot & {
256
263
  Root: typeof ToggleGroupRoot;
257
264
  Item: typeof ToggleGroupItem;
258
265
  };
@@ -288,10 +295,13 @@ type TToggleGroupCompound = typeof ToggleGroupRoot & {
288
295
  * @see {@link ToggleGroupRoot} for type modes, state, and ARIA.
289
296
  * @see {@link ToggleGroupItem} for selection, roving tabindex, and keyboard navigation.
290
297
  */
291
- const ToggleGroupCompound: TToggleGroupCompound = Object.assign(ToggleGroupRoot, {
292
- Root: ToggleGroupRoot,
293
- Item: ToggleGroupItem,
294
- });
298
+ const ToggleGroupCompound: TToggleGroupCompound = Object.assign(
299
+ ToggleGroupRoot,
300
+ {
301
+ Root: ToggleGroupRoot,
302
+ Item: ToggleGroupItem,
303
+ },
304
+ );
295
305
 
296
306
  ToggleGroupCompound.displayName = "ToggleGroup";
297
307
 
@@ -1,4 +1,4 @@
1
- import { createStrictContext } from "../utils";
1
+ import { createStrictContext } from "../utils/index.ts";
2
2
 
3
3
  import { ToggleGroupContextValue } from "./types";
4
4
 
@@ -1,7 +1,7 @@
1
1
  import { render, screen } from "@testing-library/react";
2
2
  import userEvent from "@testing-library/user-event";
3
3
 
4
- import { DirectionProvider } from "../../DirectionProvider";
4
+ import { DirectionProvider } from "../../DirectionProvider/index.ts";
5
5
  import { ToggleGroup } from "../ToggleGroup";
6
6
 
7
7
  describe("ToggleGroup reading direction", () => {
@@ -1,6 +1,6 @@
1
1
  import { useCallback, useMemo, useState } from "react";
2
2
 
3
- import { useCollection, useControllableState } from "../../hooks";
3
+ import { useCollection, useControllableState } from "../../hooks/index.ts";
4
4
 
5
5
  type ItemMeta = { element: HTMLButtonElement; disabled: boolean };
6
6
 
@@ -1,6 +1,14 @@
1
1
  import { HTMLAttributes, ButtonHTMLAttributes, ReactNode, Ref } from "react";
2
2
 
3
- type ToggleGroupRootBaseProps = Omit<HTMLAttributes<HTMLDivElement>, "dir"> & {
3
+ /**
4
+ * Mode-independent props shared by every `ToggleGroup.Root` variant —
5
+ * orientation, direction, `asChild`, children, and the ref. Combined with
6
+ * a mode-specific arm to form {@link ToggleGroupRootProps}.
7
+ */
8
+ export type ToggleGroupRootBaseProps = Omit<
9
+ HTMLAttributes<HTMLDivElement>,
10
+ "dir"
11
+ > & {
4
12
  orientation?: "horizontal" | "vertical";
5
13
  dir?: "ltr" | "rtl";
6
14
  asChild?: boolean;
@@ -8,34 +16,56 @@ type ToggleGroupRootBaseProps = Omit<HTMLAttributes<HTMLDivElement>, "dir"> & {
8
16
  ref?: Ref<HTMLDivElement>;
9
17
  };
10
18
 
11
- type SingleUncontrolledProps = {
19
+ /**
20
+ * Single-selection mode, uncontrolled — at most one item pressed, with the
21
+ * initial value supplied via `defaultValue`.
22
+ */
23
+ export type SingleUncontrolledProps = {
12
24
  type: "single";
13
25
  defaultValue?: string;
14
26
  value?: never;
15
27
  onValueChange?: never;
16
28
  };
17
29
 
18
- type SingleControlledProps = {
30
+ /**
31
+ * Single-selection mode, controlled — the pressed value is owned by the
32
+ * caller via `value` / `onValueChange`.
33
+ */
34
+ export type SingleControlledProps = {
19
35
  type: "single";
20
36
  value: string | undefined;
21
37
  onValueChange: (value: string | undefined) => void;
22
38
  defaultValue?: never;
23
39
  };
24
40
 
25
- type MultipleUncontrolledProps = {
41
+ /**
42
+ * Multiple-selection mode, uncontrolled — items toggle independently, with
43
+ * the initial set supplied via `defaultValue`.
44
+ */
45
+ export type MultipleUncontrolledProps = {
26
46
  type: "multiple";
27
47
  defaultValue?: string[];
28
48
  value?: never;
29
49
  onValueChange?: never;
30
50
  };
31
51
 
32
- type MultipleControlledProps = {
52
+ /**
53
+ * Multiple-selection mode, controlled — the set of pressed values is owned
54
+ * by the caller via `value` / `onValueChange`.
55
+ */
56
+ export type MultipleControlledProps = {
33
57
  type: "multiple";
34
58
  value: string[];
35
59
  onValueChange: (value: string[]) => void;
36
60
  defaultValue?: never;
37
61
  };
38
62
 
63
+ /**
64
+ * Props for `ToggleGroup.Root`. Combines the shared
65
+ * {@link ToggleGroupRootBaseProps} with one mode-specific arm — single or
66
+ * multiple, controlled or uncontrolled — so the `value` / `defaultValue` /
67
+ * `onValueChange` shape is enforced per `type`.
68
+ */
39
69
  export type ToggleGroupRootProps = ToggleGroupRootBaseProps &
40
70
  (
41
71
  | SingleUncontrolledProps
@@ -44,6 +74,11 @@ export type ToggleGroupRootProps = ToggleGroupRootBaseProps &
44
74
  | MultipleControlledProps
45
75
  );
46
76
 
77
+ /**
78
+ * Props for `ToggleGroup.Item` — a pressable toggle button. `value`
79
+ * identifies the item within the group; `asChild` merges the behaviour
80
+ * onto a custom child element.
81
+ */
47
82
  export type ToggleGroupItemProps = Omit<
48
83
  ButtonHTMLAttributes<HTMLButtonElement>,
49
84
  "type"
@@ -54,6 +89,11 @@ export type ToggleGroupItemProps = Omit<
54
89
  ref?: Ref<HTMLButtonElement>;
55
90
  };
56
91
 
92
+ /**
93
+ * Context shared from `ToggleGroup.Root` to its items — the pressed
94
+ * values, the toggle action, item registration for roving tabindex, and
95
+ * the resolved orientation / direction.
96
+ */
57
97
  export type ToggleGroupContextValue = {
58
98
  value: string[];
59
99
  toggle: (itemValue: string) => void;
@@ -1,5 +1,7 @@
1
- import { Portal } from "../Portal";
2
- import { Slot, composeRefs } from "../Slot";
1
+ import type { ReactElement } from "react";
2
+
3
+ import { Portal } from "../Portal/index.ts";
4
+ import { Slot, composeRefs } from "../Slot/index.ts";
3
5
 
4
6
  import {
5
7
  TooltipProvider,
@@ -11,7 +13,7 @@ import {
11
13
  useTooltipProvider,
12
14
  useTooltipRoot,
13
15
  useTooltipTrigger,
14
- } from "./hooks";
16
+ } from "./hooks/index.ts";
15
17
  import type {
16
18
  TooltipArrowProps,
17
19
  TooltipContentProps,
@@ -33,12 +35,15 @@ import type {
33
35
  * </Tooltip.Provider>
34
36
  * ```
35
37
  */
36
- function TooltipProviderComponent({
38
+ export function TooltipProviderComponent({
37
39
  children,
38
40
  delayDuration = 700,
39
41
  skipDelayDuration = 300,
40
- }: TooltipProviderProps) {
41
- const { contextValue } = useTooltipProvider({ delayDuration, skipDelayDuration });
42
+ }: TooltipProviderProps): ReactElement {
43
+ const { contextValue } = useTooltipProvider({
44
+ delayDuration,
45
+ skipDelayDuration,
46
+ });
42
47
  return (
43
48
  <TooltipProviderProvider value={contextValue}>
44
49
  {children}
@@ -46,6 +51,7 @@ function TooltipProviderComponent({
46
51
  );
47
52
  }
48
53
 
54
+ /** @internal */
49
55
  TooltipProviderComponent.displayName = "TooltipProvider";
50
56
 
51
57
  /**
@@ -65,14 +71,14 @@ TooltipProviderComponent.displayName = "TooltipProvider";
65
71
  * </Tooltip.Root>
66
72
  * ```
67
73
  */
68
- function TooltipRoot({
74
+ export function TooltipRoot({
69
75
  children,
70
76
  defaultOpen,
71
77
  open,
72
78
  onOpenChange,
73
79
  delayDuration,
74
80
  disableHoverableContent,
75
- }: TooltipRootProps) {
81
+ }: TooltipRootProps): ReactElement {
76
82
  const { contextValue } = useTooltipRoot({
77
83
  defaultOpen,
78
84
  open,
@@ -84,6 +90,7 @@ function TooltipRoot({
84
90
  return <TooltipProvider value={contextValue}>{children}</TooltipProvider>;
85
91
  }
86
92
 
93
+ /** @internal */
87
94
  TooltipRoot.displayName = "TooltipRoot";
88
95
 
89
96
  /**
@@ -104,7 +111,7 @@ TooltipRoot.displayName = "TooltipRoot";
104
111
  * </Tooltip.Trigger>
105
112
  * ```
106
113
  */
107
- function TooltipTrigger({
114
+ export function TooltipTrigger({
108
115
  ref,
109
116
  asChild = false,
110
117
  onPointerEnter,
@@ -114,7 +121,7 @@ function TooltipTrigger({
114
121
  onKeyDown,
115
122
  type,
116
123
  ...rest
117
- }: TooltipTriggerProps) {
124
+ }: TooltipTriggerProps): ReactElement {
118
125
  const { getTriggerProps } = useTooltipTrigger({
119
126
  onPointerEnter,
120
127
  onPointerLeave,
@@ -131,6 +138,7 @@ function TooltipTrigger({
131
138
  return <button ref={ref} type={type ?? "button"} {...getTriggerProps()} />;
132
139
  }
133
140
 
141
+ /** @internal */
134
142
  TooltipTrigger.displayName = "TooltipTrigger";
135
143
 
136
144
  /**
@@ -149,7 +157,11 @@ TooltipTrigger.displayName = "TooltipTrigger";
149
157
  * </Tooltip.Portal>
150
158
  * ```
151
159
  */
152
- function TooltipPortal({ children, container, forceMount }: TooltipPortalProps) {
160
+ export function TooltipPortal({
161
+ children,
162
+ container,
163
+ forceMount,
164
+ }: TooltipPortalProps): ReactElement | null {
153
165
  const { open } = useTooltipContext();
154
166
 
155
167
  if (!open && !forceMount) return null;
@@ -157,6 +169,7 @@ function TooltipPortal({ children, container, forceMount }: TooltipPortalProps)
157
169
  return <Portal container={container}>{children}</Portal>;
158
170
  }
159
171
 
172
+ /** @internal */
160
173
  TooltipPortal.displayName = "TooltipPortal";
161
174
 
162
175
  /**
@@ -187,7 +200,7 @@ TooltipPortal.displayName = "TooltipPortal";
187
200
  * </Tooltip.Content>
188
201
  * ```
189
202
  */
190
- function TooltipContent({
203
+ export function TooltipContent({
191
204
  ref,
192
205
  forceMount,
193
206
  onEscapeKeyDown,
@@ -195,7 +208,7 @@ function TooltipContent({
195
208
  onPointerEnter,
196
209
  onPointerLeave,
197
210
  ...rest
198
- }: TooltipContentProps) {
211
+ }: TooltipContentProps): ReactElement | null {
199
212
  const { open } = useTooltipContext();
200
213
  const { getContentProps, internalRef } = useTooltipContent({
201
214
  onEscapeKeyDown,
@@ -210,6 +223,7 @@ function TooltipContent({
210
223
  return <div ref={composeRefs(internalRef, ref)} {...getContentProps()} />;
211
224
  }
212
225
 
226
+ /** @internal */
213
227
  TooltipContent.displayName = "TooltipContent";
214
228
 
215
229
  /**
@@ -227,7 +241,11 @@ TooltipContent.displayName = "TooltipContent";
227
241
  * </Tooltip.Content>
228
242
  * ```
229
243
  */
230
- function TooltipArrow({ ref, asChild = false, ...rest }: TooltipArrowProps) {
244
+ export function TooltipArrow({
245
+ ref,
246
+ asChild = false,
247
+ ...rest
248
+ }: TooltipArrowProps): ReactElement {
231
249
  if (asChild) {
232
250
  return <Slot ref={ref} {...rest} />;
233
251
  }
@@ -235,9 +253,11 @@ function TooltipArrow({ ref, asChild = false, ...rest }: TooltipArrowProps) {
235
253
  return <span ref={ref} {...rest} />;
236
254
  }
237
255
 
256
+ /** @internal */
238
257
  TooltipArrow.displayName = "TooltipArrow";
239
258
 
240
- type TooltipCompound = typeof TooltipRoot & {
259
+ /** Type of the {@link Tooltip} compound: the root callable plus its attached sub-components. */
260
+ export type TooltipCompound = typeof TooltipRoot & {
241
261
  Provider: typeof TooltipProviderComponent;
242
262
  Root: typeof TooltipRoot;
243
263
  Trigger: typeof TooltipTrigger;
@@ -246,6 +266,16 @@ type TooltipCompound = typeof TooltipRoot & {
246
266
  Arrow: typeof TooltipArrow;
247
267
  };
248
268
 
269
+ /**
270
+ * Headless, accessible **Tooltip** — a compound component implementing the
271
+ * [WAI-ARIA tooltip pattern](https://www.w3.org/WAI/ARIA/apg/patterns/tooltip/):
272
+ * a deferred, hoverable label anchored to a trigger, with a shared
273
+ * {@link Tooltip.Provider} governing open / skip delays across a group. Zero
274
+ * styles ship.
275
+ *
276
+ * The default export is the `Root`; sub-components are attached as static
277
+ * properties (`Tooltip.Provider`, `Tooltip.Trigger`, `Tooltip.Content`, …).
278
+ */
249
279
  const TooltipCompound: TooltipCompound = Object.assign(TooltipRoot, {
250
280
  Provider: TooltipProviderComponent,
251
281
  Root: TooltipRoot,
@@ -255,6 +285,7 @@ const TooltipCompound: TooltipCompound = Object.assign(TooltipRoot, {
255
285
  Arrow: TooltipArrow,
256
286
  });
257
287
 
288
+ /** @internal */
258
289
  TooltipCompound.displayName = "Tooltip";
259
290
 
260
291
  export { TooltipCompound as Tooltip };
@@ -1,4 +1,4 @@
1
- import { createStrictContext } from "../utils";
1
+ import { createStrictContext } from "../utils/index.ts";
2
2
 
3
3
  import type { TooltipContextValue, TooltipProviderContextValue } from "./types";
4
4
 
@@ -1,6 +1,6 @@
1
1
  import { useEffect, useRef } from "react";
2
2
 
3
- import { composeEventHandlers } from "../../Slot";
3
+ import { composeEventHandlers } from "../../Slot/index.ts";
4
4
  import { useTooltipContext } from "../TooltipContext";
5
5
  import type { TooltipContentProps } from "../types";
6
6
 
@@ -1,6 +1,6 @@
1
1
  import { useCallback, useId, useMemo, useRef } from "react";
2
2
 
3
- import { useControllableState } from "../../hooks";
3
+ import { useControllableState } from "../../hooks/index.ts";
4
4
  import { useTooltipProviderContext } from "../TooltipContext";
5
5
  import type { TooltipContextValue, TooltipRootProps } from "../types";
6
6
 
@@ -1,6 +1,6 @@
1
1
  import { KeyboardEvent } from "react";
2
2
 
3
- import { composeEventHandlers } from "../../Slot";
3
+ import { composeEventHandlers } from "../../Slot/index.ts";
4
4
  import { useTooltipContext } from "../TooltipContext";
5
5
  import type { TooltipTriggerProps } from "../types";
6
6
 
@@ -1 +1,2 @@
1
1
  export * from "./Tooltip";
2
+ export * from "./types";