@ahrowe/ui 0.36.0 → 0.38.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 (176) hide show
  1. package/README.md +6 -2
  2. package/dist/cjs-types/common/commandPalette/commandPalette.d.ts +4 -0
  3. package/dist/cjs-types/common/commandPalette/commandPalette.types.d.ts +42 -0
  4. package/dist/cjs-types/common/commandPalette/filterCommands.d.ts +15 -0
  5. package/dist/cjs-types/common/commandPalette/index.d.ts +2 -0
  6. package/dist/cjs-types/common/configProvider/configProvider.types.d.ts +6 -0
  7. package/dist/cjs-types/common/copyButton/copyButton.d.ts +4 -0
  8. package/dist/cjs-types/common/copyButton/copyButton.types.d.ts +36 -0
  9. package/dist/cjs-types/common/copyButton/index.d.ts +2 -0
  10. package/dist/cjs-types/common/errorBoundary/errorBoundary.d.ts +0 -3
  11. package/dist/cjs-types/common/errorBoundary/errorBoundary.types.d.ts +2 -3
  12. package/dist/cjs-types/common/hooks/index.d.ts +15 -0
  13. package/dist/cjs-types/common/hooks/useClipboard.d.ts +16 -0
  14. package/dist/cjs-types/common/hooks/useHotkeys.d.ts +45 -0
  15. package/dist/cjs-types/common/hooks/useSwipeDismiss.d.ts +6 -2
  16. package/dist/cjs-types/common/inputDropdown/inputDropdown.types.d.ts +7 -1
  17. package/dist/cjs-types/common/loading/index.d.ts +0 -1
  18. package/dist/cjs-types/common/menu/index.d.ts +1 -0
  19. package/dist/cjs-types/common/menu/menu.types.d.ts +11 -3
  20. package/dist/cjs-types/common/menu/menuHotkeys.d.ts +20 -0
  21. package/dist/cjs-types/common/popover/usePopoverPosition.d.ts +1 -0
  22. package/dist/cjs-types/common/sticky/sticky.d.ts +1 -1
  23. package/dist/cjs-types/common/sticky/sticky.types.d.ts +15 -0
  24. package/dist/cjs-types/common/sticky/stickyStack.d.ts +5 -0
  25. package/dist/cjs-types/common/themeProvider/themeProvider.d.ts +8 -7
  26. package/dist/cjs-types/common/utils/scrollAncestors.d.ts +10 -0
  27. package/dist/cjs-types/common/virtualList/scroller.d.ts +33 -0
  28. package/dist/cjs-types/common/virtualList/useRowDrag.d.ts +6 -1
  29. package/dist/cjs-types/common/virtualList/useRowNavigation.d.ts +11 -1
  30. package/dist/cjs-types/common/virtualList/useVirtualWindow.d.ts +22 -3
  31. package/dist/cjs-types/common/virtualList/virtualList.d.ts +1 -1
  32. package/dist/cjs-types/common/virtualList/virtualList.types.d.ts +43 -3
  33. package/dist/cjs-types/common/weatherIcon/index.d.ts +3 -0
  34. package/dist/cjs-types/common/weatherIcon/parts.d.ts +26 -0
  35. package/dist/cjs-types/common/weatherIcon/weatherIcon.d.ts +4 -0
  36. package/dist/cjs-types/common/weatherIcon/weatherIcon.types.d.ts +44 -0
  37. package/dist/cjs-types/index.d.ts +7 -0
  38. package/dist/esm/common/buttonGroup/buttonGroup.module.mjs.map +1 -1
  39. package/dist/esm/common/commandPalette/commandPalette.mjs +2 -0
  40. package/dist/esm/common/commandPalette/commandPalette.mjs.map +1 -0
  41. package/dist/esm/common/commandPalette/commandPalette.module.mjs +2 -0
  42. package/dist/esm/common/commandPalette/commandPalette.module.mjs.map +1 -0
  43. package/dist/esm/common/commandPalette/filterCommands.mjs +2 -0
  44. package/dist/esm/common/commandPalette/filterCommands.mjs.map +1 -0
  45. package/dist/esm/common/copyButton/copyButton.mjs +2 -0
  46. package/dist/esm/common/copyButton/copyButton.mjs.map +1 -0
  47. package/dist/esm/common/copyButton/copyButton.module.mjs +2 -0
  48. package/dist/esm/common/copyButton/copyButton.module.mjs.map +1 -0
  49. package/dist/esm/common/dropdown/dropdown.mjs +1 -1
  50. package/dist/esm/common/dropdown/dropdown.module.mjs.map +1 -1
  51. package/dist/esm/common/errorBoundary/errorBoundary.mjs +2 -2
  52. package/dist/esm/common/errorBoundary/errorBoundary.mjs.map +1 -1
  53. package/dist/esm/common/errorBoundary/errorBoundary.module.mjs +1 -1
  54. package/dist/esm/common/errorBoundary/errorBoundary.module.mjs.map +1 -1
  55. package/dist/esm/common/hooks/useClipboard.mjs +2 -0
  56. package/dist/esm/common/hooks/useClipboard.mjs.map +1 -0
  57. package/dist/esm/common/hooks/useHotkeys.mjs +2 -0
  58. package/dist/esm/common/hooks/useHotkeys.mjs.map +1 -0
  59. package/dist/esm/common/hooks/useSwipeDismiss.mjs +1 -1
  60. package/dist/esm/common/hooks/useSwipeDismiss.mjs.map +1 -1
  61. package/dist/esm/common/input/input.mjs +1 -1
  62. package/dist/esm/common/input/input.mjs.map +1 -1
  63. package/dist/esm/common/input/input.module.mjs +1 -1
  64. package/dist/esm/common/input/input.module.mjs.map +1 -1
  65. package/dist/esm/common/inputDropdown/inputDropdown.mjs +1 -1
  66. package/dist/esm/common/inputDropdown/inputDropdown.mjs.map +1 -1
  67. package/dist/esm/common/inputDropdown/inputDropdown.module.mjs +1 -1
  68. package/dist/esm/common/inputDropdown/inputDropdown.module.mjs.map +1 -1
  69. package/dist/esm/common/menu/menu.mjs +1 -1
  70. package/dist/esm/common/menu/menu.mjs.map +1 -1
  71. package/dist/esm/common/menu/menu.types.mjs.map +1 -1
  72. package/dist/esm/common/menu/menuHotkeys.mjs +2 -0
  73. package/dist/esm/common/menu/menuHotkeys.mjs.map +1 -0
  74. package/dist/esm/common/multiSelect/multiSelect.mjs +1 -1
  75. package/dist/esm/common/multiSelect/multiSelect.mjs.map +1 -1
  76. package/dist/esm/common/multiSelect/multiSelect.module.mjs +1 -1
  77. package/dist/esm/common/multiSelect/multiSelect.module.mjs.map +1 -1
  78. package/dist/esm/common/otpInput/otpInput.module.mjs.map +1 -1
  79. package/dist/esm/common/popover/usePopoverPosition.mjs +1 -1
  80. package/dist/esm/common/popover/usePopoverPosition.mjs.map +1 -1
  81. package/dist/esm/common/sticky/sticky.mjs +1 -1
  82. package/dist/esm/common/sticky/sticky.mjs.map +1 -1
  83. package/dist/esm/common/sticky/stickyStack.mjs +1 -1
  84. package/dist/esm/common/sticky/stickyStack.mjs.map +1 -1
  85. package/dist/esm/common/themeProvider/themeProvider.mjs +1 -1
  86. package/dist/esm/common/themeProvider/themeProvider.mjs.map +1 -1
  87. package/dist/esm/common/timer/timer.mjs +1 -1
  88. package/dist/esm/common/timer/timer.mjs.map +1 -1
  89. package/dist/esm/common/utils/scrollAncestors.mjs +1 -1
  90. package/dist/esm/common/utils/scrollAncestors.mjs.map +1 -1
  91. package/dist/esm/common/virtualList/scroller.mjs +2 -0
  92. package/dist/esm/common/virtualList/scroller.mjs.map +1 -0
  93. package/dist/esm/common/virtualList/useRowDrag.mjs +1 -1
  94. package/dist/esm/common/virtualList/useRowDrag.mjs.map +1 -1
  95. package/dist/esm/common/virtualList/useRowNavigation.mjs +1 -1
  96. package/dist/esm/common/virtualList/useRowNavigation.mjs.map +1 -1
  97. package/dist/esm/common/virtualList/useVirtualWindow.mjs +1 -1
  98. package/dist/esm/common/virtualList/useVirtualWindow.mjs.map +1 -1
  99. package/dist/esm/common/virtualList/virtualList.mjs +1 -1
  100. package/dist/esm/common/virtualList/virtualList.mjs.map +1 -1
  101. package/dist/esm/common/virtualList/virtualList.module.mjs +1 -1
  102. package/dist/esm/common/virtualList/virtualList.module.mjs.map +1 -1
  103. package/dist/esm/common/weatherIcon/parts.mjs +2 -0
  104. package/dist/esm/common/weatherIcon/parts.mjs.map +1 -0
  105. package/dist/esm/common/weatherIcon/weatherIcon.mjs +2 -0
  106. package/dist/esm/common/weatherIcon/weatherIcon.mjs.map +1 -0
  107. package/dist/esm/common/weatherIcon/weatherIcon.module.mjs +2 -0
  108. package/dist/esm/common/weatherIcon/weatherIcon.module.mjs.map +1 -0
  109. package/dist/esm/common/weatherIcon/weatherIcon.types.mjs +2 -0
  110. package/dist/esm/common/weatherIcon/weatherIcon.types.mjs.map +1 -0
  111. package/dist/esm/index.mjs +1 -1
  112. package/dist/index.cjs +3 -3
  113. package/dist/index.cjs.map +1 -1
  114. package/dist/style.css +1 -1
  115. package/dist/types/common/commandPalette/commandPalette.d.ts +4 -0
  116. package/dist/types/common/commandPalette/commandPalette.types.d.ts +42 -0
  117. package/dist/types/common/commandPalette/filterCommands.d.ts +15 -0
  118. package/dist/types/common/commandPalette/index.d.ts +2 -0
  119. package/dist/types/common/configProvider/configProvider.types.d.ts +6 -0
  120. package/dist/types/common/copyButton/copyButton.d.ts +4 -0
  121. package/dist/types/common/copyButton/copyButton.types.d.ts +36 -0
  122. package/dist/types/common/copyButton/index.d.ts +2 -0
  123. package/dist/types/common/errorBoundary/errorBoundary.d.ts +0 -3
  124. package/dist/types/common/errorBoundary/errorBoundary.types.d.ts +2 -3
  125. package/dist/types/common/hooks/index.d.ts +15 -0
  126. package/dist/types/common/hooks/useClipboard.d.ts +16 -0
  127. package/dist/types/common/hooks/useHotkeys.d.ts +45 -0
  128. package/dist/types/common/hooks/useSwipeDismiss.d.ts +6 -2
  129. package/dist/types/common/inputDropdown/inputDropdown.types.d.ts +7 -1
  130. package/dist/types/common/loading/index.d.ts +0 -1
  131. package/dist/types/common/menu/index.d.ts +1 -0
  132. package/dist/types/common/menu/menu.types.d.ts +11 -3
  133. package/dist/types/common/menu/menuHotkeys.d.ts +20 -0
  134. package/dist/types/common/popover/usePopoverPosition.d.ts +1 -0
  135. package/dist/types/common/sticky/sticky.d.ts +1 -1
  136. package/dist/types/common/sticky/sticky.types.d.ts +15 -0
  137. package/dist/types/common/sticky/stickyStack.d.ts +5 -0
  138. package/dist/types/common/themeProvider/themeProvider.d.ts +8 -7
  139. package/dist/types/common/utils/scrollAncestors.d.ts +10 -0
  140. package/dist/types/common/virtualList/scroller.d.ts +33 -0
  141. package/dist/types/common/virtualList/useRowDrag.d.ts +6 -1
  142. package/dist/types/common/virtualList/useRowNavigation.d.ts +11 -1
  143. package/dist/types/common/virtualList/useVirtualWindow.d.ts +22 -3
  144. package/dist/types/common/virtualList/virtualList.d.ts +1 -1
  145. package/dist/types/common/virtualList/virtualList.types.d.ts +43 -3
  146. package/dist/types/common/weatherIcon/index.d.ts +3 -0
  147. package/dist/types/common/weatherIcon/parts.d.ts +26 -0
  148. package/dist/types/common/weatherIcon/weatherIcon.d.ts +4 -0
  149. package/dist/types/common/weatherIcon/weatherIcon.types.d.ts +44 -0
  150. package/dist/types/index.d.ts +7 -0
  151. package/docs/ButtonGroup.md +2 -0
  152. package/docs/CLAUDE.md +6 -2
  153. package/docs/CommandPalette.md +84 -0
  154. package/docs/ConfigProvider.md +2 -2
  155. package/docs/CopyButton.md +45 -0
  156. package/docs/ErrorBoundary.md +4 -4
  157. package/docs/Fab.md +1 -2
  158. package/docs/Hooks.md +268 -0
  159. package/docs/InputDropdown.md +9 -4
  160. package/docs/Loading.md +56 -15
  161. package/docs/Menu.md +30 -6
  162. package/docs/Popover.md +2 -0
  163. package/docs/Sticky.md +22 -1
  164. package/docs/VirtualList.md +44 -4
  165. package/docs/WeatherIcon.md +49 -0
  166. package/package.json +1 -2
  167. package/dist/cjs-types/common/loading/iconLoading/iconLoading.d.ts +0 -5
  168. package/dist/cjs-types/common/loading/iconLoading/index.d.ts +0 -2
  169. package/dist/esm/common/loading/iconLoading/iconLoading.mjs +0 -2
  170. package/dist/esm/common/loading/iconLoading/iconLoading.mjs.map +0 -1
  171. package/dist/esm/common/loading/iconLoading/iconLoading.module.mjs +0 -2
  172. package/dist/esm/common/loading/iconLoading/iconLoading.module.mjs.map +0 -1
  173. package/dist/esm/common/loading/iconLoading/index.mjs +0 -2
  174. package/dist/esm/common/loading/iconLoading/index.mjs.map +0 -1
  175. package/dist/types/common/loading/iconLoading/iconLoading.d.ts +0 -5
  176. package/dist/types/common/loading/iconLoading/index.d.ts +0 -2
@@ -0,0 +1,4 @@
1
+ import { ReactElement } from 'react';
2
+ import { CommandPaletteProps } from './commandPalette.types.js';
3
+ declare function CommandPalette(props: CommandPaletteProps): ReactElement;
4
+ export default CommandPalette;
@@ -0,0 +1,42 @@
1
+ import { CSSProperties } from 'react';
2
+ import { MenuEntry } from '../menu/menu.types.js';
3
+ import { Presentation } from '../configProvider/presentation.types.js';
4
+ import { SlotClassNames, SlotStyles, HtmlProps } from '../types/slots.types.js';
5
+ export type CommandPaletteSlots = 'root' | 'search' | 'input' | 'list' | 'item' | 'itemIcon' | 'itemLabel' | 'itemShortcut' | 'heading' | 'separator' | 'empty';
6
+ export interface CommandPaletteLabels {
7
+ /** Accessible name of the dialog and the search field. Default: "Search commands". */
8
+ label?: string;
9
+ /** Placeholder in the search field. Default: "Type a command or search…". */
10
+ placeholder?: string;
11
+ /** Shown when nothing matches. Default: "No results". */
12
+ empty?: string;
13
+ /** Shown while `isLoading` and nothing matches yet. Default: "Searching…". */
14
+ loading?: string;
15
+ /** Announced to screen readers as the matches change. */
16
+ results?: (count: number) => string;
17
+ }
18
+ export interface CommandPaletteProps extends HtmlProps<HTMLDivElement> {
19
+ /** The commands, in the same shape `Menu` takes. Headings group them; separators split groups. */
20
+ items: MenuEntry[];
21
+ isOpen: boolean;
22
+ onClose: () => void;
23
+ /** Called with the id of the command that was run, after its own `onClick`. */
24
+ onAction?: (id: string) => void;
25
+ /** Called on every keystroke, and with `''` each time the palette opens. */
26
+ onQueryChange?: (query: string) => void;
27
+ /**
28
+ * Filter `items` by the query. Default `true`. Set `false` when `items` are already the results,
29
+ * e.g. fetched from a server in `onQueryChange`.
30
+ */
31
+ filter?: boolean;
32
+ /** Shows the `loading` label instead of `empty` while nothing matches. */
33
+ isLoading?: boolean;
34
+ /** Centred dialog, bottom sheet, or a sheet only on a small touch screen. */
35
+ presentation?: Presentation;
36
+ /** Text this component renders of its own. */
37
+ labels?: CommandPaletteLabels;
38
+ className?: string;
39
+ style?: CSSProperties;
40
+ classNames?: SlotClassNames<CommandPaletteSlots>;
41
+ styles?: SlotStyles<CommandPaletteSlots>;
42
+ }
@@ -0,0 +1,15 @@
1
+ import { ReactNode } from 'react';
2
+ import { MenuAction, MenuEntry } from '../menu/menu.types.js';
3
+ export interface CommandGroup {
4
+ heading?: ReactNode;
5
+ /** Whether a separator started this group, so the divider can be drawn above it. */
6
+ separated: boolean;
7
+ actions: MenuAction[];
8
+ }
9
+ /** Splits entries into groups at each heading and separator, keeping their order. */
10
+ export declare function groupCommands(items: MenuEntry[]): CommandGroup[];
11
+ /**
12
+ * The groups with only the actions matching `query`, best matches first within each group, and
13
+ * the group holding the best match first. A heading moves with its group, never away from it.
14
+ */
15
+ export declare function filterCommands(groups: CommandGroup[], query: string): CommandGroup[];
@@ -0,0 +1,2 @@
1
+ export { default } from './commandPalette.js';
2
+ export * from './commandPalette.types.js';
@@ -15,6 +15,9 @@ import { SearchInputLabels } from '../searchInput/searchInput.types.js';
15
15
  import { TooltipLabels } from '../tooltip/tooltip.types.js';
16
16
  import { VirtualListLabels } from '../virtualList/virtualList.types.js';
17
17
  import { ButtonProps } from '../button/button.types.js';
18
+ import { CopyButtonProps } from '../copyButton/copyButton.types.js';
19
+ import { CommandPaletteProps } from '../commandPalette/commandPalette.types.js';
20
+ import { WeatherIconProps } from '../weatherIcon/weatherIcon.types.js';
18
21
  import { ActionButtonsProps } from '../actionButtons/actionButtons.types.js';
19
22
  import { ConfirmModalProps } from '../confirmModal/confirmModal.types.js';
20
23
  import { BadgeProps } from '../badge/badge.types.js';
@@ -91,6 +94,7 @@ export interface ComponentDefaults {
91
94
  RadioGroup?: Partial<RadioGroupProps>;
92
95
  DatePicker?: Partial<DatePickerProps>;
93
96
  Button?: Partial<ButtonProps>;
97
+ CopyButton?: Partial<CopyButtonProps>;
94
98
  ActionButtons?: Partial<ActionButtonsProps>;
95
99
  ConfirmModal?: Partial<ConfirmModalProps>;
96
100
  Badge?: Partial<BadgeProps>;
@@ -118,6 +122,8 @@ export interface ComponentDefaults {
118
122
  RoomViewer?: Partial<RoomViewerProps>;
119
123
  Popover?: Partial<PopoverProps>;
120
124
  Modal?: Partial<ModalProps>;
125
+ CommandPalette?: Partial<CommandPaletteProps>;
126
+ WeatherIcon?: Partial<WeatherIconProps>;
121
127
  }
122
128
  export interface ConfigProviderProps {
123
129
  children: React.ReactNode;
@@ -0,0 +1,4 @@
1
+ import { ReactElement } from 'react';
2
+ import { CopyButtonProps } from './copyButton.types.js';
3
+ declare function CopyButton(props: CopyButtonProps): ReactElement;
4
+ export default CopyButton;
@@ -0,0 +1,36 @@
1
+ import { CSSProperties, MouseEvent, Ref } from 'react';
2
+ import { IconContent } from '../types/icon.types.js';
3
+ import { SlotClassNames, SlotStyles, HtmlProps } from '../types/slots.types.js';
4
+ export type CopyButtonSlots = 'root' | 'icon';
5
+ export interface CopyButtonLabels {
6
+ /** Accessible name and tooltip before copying. Default: "Copy". */
7
+ copy?: string;
8
+ /** Accessible name and tooltip after a successful copy, also announced. Default: "Copied". */
9
+ copied?: string;
10
+ /** Announced when the copy fails. Default: "Could not copy". */
11
+ failed?: string;
12
+ }
13
+ export interface CopyButtonProps extends Omit<HtmlProps<HTMLDivElement>, 'onCopy' | 'onError'> {
14
+ /** Text written to the clipboard on click. */
15
+ value: string;
16
+ /** How long the copied state shows, in ms. Default: 2000. */
17
+ timeout?: number;
18
+ /** Icon before copying. Default: `faCopy`. */
19
+ icon?: IconContent;
20
+ /** Icon while the copied state shows. Default: `faCheck`. */
21
+ copiedIcon?: IconContent;
22
+ /** Called after a successful copy. */
23
+ onCopy?: (value: string) => void;
24
+ /** Called when the clipboard refuses the write, e.g. outside a secure context. */
25
+ onError?: () => void;
26
+ /** Called on every click, before the copy. */
27
+ onClick?: (event: MouseEvent<HTMLDivElement>) => void;
28
+ /** Text this component renders of its own. */
29
+ labels?: CopyButtonLabels;
30
+ /** Ref to the root element. */
31
+ ref?: Ref<HTMLDivElement>;
32
+ className?: string;
33
+ style?: CSSProperties;
34
+ classNames?: SlotClassNames<CopyButtonSlots>;
35
+ styles?: SlotStyles<CopyButtonSlots>;
36
+ }
@@ -0,0 +1,2 @@
1
+ export { default } from './copyButton.js';
2
+ export * from './copyButton.types.js';
@@ -2,13 +2,10 @@ import { default as React } from 'react';
2
2
  import { ErrorBoundaryProps, ErrorBoundaryState } from './errorBoundary.types.js';
3
3
  declare class ErrorBoundary extends React.Component<ErrorBoundaryProps, ErrorBoundaryState> {
4
4
  state: ErrorBoundaryState;
5
- private copyResetTimeout;
6
5
  static getDerivedStateFromError(error: Error): Partial<ErrorBoundaryState>;
7
6
  componentDidCatch(error: Error, errorInfo: React.ErrorInfo): void;
8
7
  componentDidUpdate(prevProps: ErrorBoundaryProps): void;
9
- componentWillUnmount(): void;
10
8
  private reset;
11
- private copyStackTrace;
12
9
  render(): React.ReactNode;
13
10
  }
14
11
  export default ErrorBoundary;
@@ -13,9 +13,9 @@ export interface ErrorBoundaryFallbackProps {
13
13
  export interface ErrorBoundaryLabels {
14
14
  /** Accordion header for the stack trace section. Default: "Stack trace". */
15
15
  stackTrace?: string;
16
- /** Copy button label before copying. Default: "Copy". */
16
+ /** Copy button's tooltip and accessible name before copying. Default: "Copy". */
17
17
  copy?: string;
18
- /** Copy button label right after a successful copy. Default: "Copied". */
18
+ /** Copy button's tooltip and accessible name right after a successful copy. Default: "Copied". */
19
19
  copied?: string;
20
20
  /** Reset button label. Default: "Try again". */
21
21
  reset?: string;
@@ -53,5 +53,4 @@ export interface ErrorBoundaryProps extends Omit<HtmlProps, 'title' | 'onError'>
53
53
  export interface ErrorBoundaryState {
54
54
  error: Error | null;
55
55
  errorInfo: ErrorInfo | null;
56
- copied: boolean;
57
56
  }
@@ -0,0 +1,15 @@
1
+ export { useHotkeys, formatHotkey } from './useHotkeys.js';
2
+ export type { HotkeyHandler, HotkeyMap, UseHotkeysOptions } from './useHotkeys.js';
3
+ export { useMediaQuery } from './useMediaQuery.js';
4
+ export { useCoarsePointer } from './useCoarsePointer.js';
5
+ export { useVisualViewportSize } from './useVisualViewportSize.js';
6
+ export type { VisualViewportSize } from './useVisualViewportSize.js';
7
+ export { useScrollEdges } from './useScrollEdges.js';
8
+ export type { ScrollEdges, ScrollEdgesOptions } from './useScrollEdges.js';
9
+ export { useSwipeDismiss } from './useSwipeDismiss.js';
10
+ export type { UseSwipeDismissOptions, UseSwipeDismissResult } from './useSwipeDismiss.js';
11
+ export { useOverlay } from './useOverlay.js';
12
+ export type { UseOverlayArgs } from './useOverlay.js';
13
+ export { tabbablesIn } from './useFocusBoundary.js';
14
+ export { useClipboard } from './useClipboard.js';
15
+ export type { UseClipboardOptions, UseClipboardResult } from './useClipboard.js';
@@ -0,0 +1,16 @@
1
+ export interface UseClipboardOptions {
2
+ /** How long `copied` stays `true` after a successful copy, in ms. Default: 2000. */
3
+ timeout?: number;
4
+ }
5
+ export interface UseClipboardResult {
6
+ /** Writes `text` to the clipboard. Resolves `true` on success, `false` on failure. */
7
+ copy: (text: string) => Promise<boolean>;
8
+ /** `true` for `timeout` ms after a successful copy. */
9
+ copied: boolean;
10
+ /** Why the last copy failed, until the next attempt. */
11
+ error: Error | null;
12
+ /** Clears `copied` and `error` early. */
13
+ reset: () => void;
14
+ }
15
+ export declare function useClipboard({ timeout }?: UseClipboardOptions): UseClipboardResult;
16
+ export default useClipboard;
@@ -0,0 +1,45 @@
1
+ import { RefObject } from 'react';
2
+ export type HotkeyHandler = (event: KeyboardEvent) => void;
3
+ /** Combo → handler, e.g. `{ 'mod+k': open, Escape: close }`. */
4
+ export type HotkeyMap = Record<string, HotkeyHandler>;
5
+ export interface UseHotkeysOptions {
6
+ /** Attach the listener at all. Default `true`; pass `false` to suspend every combo at once. */
7
+ enabled?: boolean;
8
+ /** Scope the shortcuts to one element instead of the whole window. */
9
+ target?: RefObject<HTMLElement | null>;
10
+ /**
11
+ * Let plain-key combos fire while a text field or `contenteditable` has focus. Default `false`,
12
+ * so `'n'` does not fire for every `n` typed into an input. Combos carrying Ctrl, Cmd or Alt
13
+ * are never suppressed — they cannot be confused with typing.
14
+ */
15
+ enableInFields?: boolean;
16
+ /**
17
+ * Call `preventDefault()` on a match, so `mod+s` does not also open the browser's save dialog.
18
+ * Default `true`.
19
+ */
20
+ preventDefault?: boolean;
21
+ }
22
+ /**
23
+ * A combo written for the reader: `'mod+shift+k'` reads `⇧⌘K` on an Apple platform and
24
+ * `Ctrl+Shift+K` everywhere else.
25
+ *
26
+ * So a shortcut is written once, in one spelling, and the hint beside it cannot contradict what
27
+ * the binding actually listens for. Hand-written `'⌘K'` hints are wrong on every other platform,
28
+ * silently, because nothing compares the label to the binding.
29
+ *
30
+ * Resolved from the platform at call time, so a server-rendered page renders the non-Apple form.
31
+ */
32
+ export declare function formatHotkey(combo: string): string;
33
+ /**
34
+ * Keyboard shortcuts, for a whole app or for one element.
35
+ *
36
+ * ```tsx
37
+ * useHotkeys({ 'mod+k': () => setPaletteOpen(true), '?': () => setHelpOpen(true) });
38
+ * ```
39
+ *
40
+ * The map is read through a ref at event time, so an inline object literal is fine and no handler
41
+ * needs memoising. Shortcuts keep firing while a Modal or Drawer is open — pass `enabled` for the
42
+ * ones that should not.
43
+ */
44
+ export declare function useHotkeys(hotkeys: HotkeyMap, options?: UseHotkeysOptions): void;
45
+ export default useHotkeys;
@@ -19,8 +19,12 @@ export interface UseSwipeDismissOptions {
19
19
  }
20
20
  export interface UseSwipeDismissResult<T extends HTMLElement> {
21
21
  /** Attach to the element that should become draggable. The hook wires up its own pointer
22
- * listeners on this node directly (no handlers to spread), so this is the only thing to attach. */
23
- ref: React.RefObject<T | null>;
22
+ * listeners on this node directly (no handlers to spread), so this is the only thing to attach.
23
+ *
24
+ * A callback ref rather than an object one, because the hook has to know when the node changes:
25
+ * an element that is unmounted and rendered again is a *different* node, and a ref object cannot
26
+ * say so. To keep a ref of your own on the element, call both from one callback. */
27
+ ref: React.RefCallback<T>;
24
28
  /** True for the duration of an active drag — e.g. use it to pause an auto-dismiss timer. */
25
29
  isDragging: boolean;
26
30
  }
@@ -1,7 +1,11 @@
1
1
  import { default as React } from 'react';
2
2
  import { SlotClassNames, SlotStyles, HtmlProps } from '../types/slots.types.js';
3
3
  import { FormValidator } from '../../services/formValidation/index.js';
4
- export type InputDropdownSlots = 'root' | 'dropdown' | 'item';
4
+ export type InputDropdownSlots = 'root' | 'dropdown' | 'item' | 'empty';
5
+ export interface InputDropdownLabels {
6
+ /** Shown when nothing matches the typed text and `allowCustomValue` is off (default `No matches`). */
7
+ empty?: string;
8
+ }
5
9
  export interface InputDropdownItem {
6
10
  label?: string;
7
11
  value: string;
@@ -29,6 +33,8 @@ export interface InputDropdownProps extends Omit<HtmlProps, 'onSelect'> {
29
33
  onChange?: (value: unknown) => void;
30
34
  placeholder?: string;
31
35
  readOnly?: boolean;
36
+ /** Overrides the text InputDropdown renders of its own. Merged per key. */
37
+ labels?: InputDropdownLabels;
32
38
  className?: string;
33
39
  style?: React.CSSProperties;
34
40
  classNames?: SlotClassNames<InputDropdownSlots>;
@@ -1,2 +1 @@
1
- export { default as IconLoading } from './iconLoading/index.js';
2
1
  export { default as SpinnerLoading } from './spinnerLoading/index.js';
@@ -1,2 +1,3 @@
1
1
  export { default } from './menu.js';
2
+ export { menuHotkeys } from './menuHotkeys.js';
2
3
  export * from './menu.types.js';
@@ -10,10 +10,18 @@ export interface MenuAction {
10
10
  label: ReactNode;
11
11
  icon?: IconContent;
12
12
  /**
13
- * Keyboard hint on the trailing edge, e.g. `⌘K`. Display only: binding the
14
- * shortcut is yours, since only you know what else is listening.
13
+ * A keyboard shortcut for this action, in `useHotkeys` spelling: `'mod+k'`,
14
+ * `'shift+f2'`, `'delete'`. Shown on the trailing edge written for the
15
+ * platform: `⌘K` on an Apple one, `Ctrl+K` elsewhere.
16
+ *
17
+ * The menu draws it and nothing more. Binding is yours, because only the app
18
+ * knows what else is listening and whether the shortcut should work at all
19
+ * times or only while the menu is open. `menuHotkeys` turns these entries
20
+ * into a `useHotkeys` map, so the one spelling covers both ends.
15
21
  */
16
- shortcut?: ReactNode;
22
+ shortcut?: string;
23
+ /** Extra search terms for `CommandPalette`, which also matches a string `label`. `Menu` ignores them. */
24
+ keywords?: string[];
17
25
  disabled?: boolean;
18
26
  /** Renders in the destructive colour. For deleting, discarding, revoking. */
19
27
  danger?: boolean;
@@ -0,0 +1,20 @@
1
+ import { HotkeyMap } from '../hooks/useHotkeys.js';
2
+ import { MenuEntry } from './menu.types.js';
3
+ /**
4
+ * The bindings for a menu's `shortcut` entries, to hand to `useHotkeys` yourself.
5
+ *
6
+ * The menu draws a shortcut but never listens for one, because only the app knows what else is
7
+ * listening: binding it here as well as in an app's own keymap would run the action twice, and
8
+ * whether a shortcut should work at all times or only while the menu is open is the app's
9
+ * question, not the menu's. Calling this keeps the answer in one spelling, so the hint the menu
10
+ * draws cannot drift from what actually fires.
11
+ *
12
+ * ```tsx
13
+ * useHotkeys(menuHotkeys(items, run)); // whenever the page is up
14
+ * useHotkeys(menuHotkeys(items, run), { enabled: isOpen }); // only while the menu is open
15
+ * ```
16
+ *
17
+ * Runs each entry the way clicking it does: its own `onClick`, then `onAction`. A `disabled`
18
+ * entry, and an entry with no `shortcut`, is left out.
19
+ */
20
+ export declare function menuHotkeys(items: MenuEntry[], onAction?: (id: string) => void): HotkeyMap;
@@ -1,5 +1,6 @@
1
1
  import { RefObject } from 'react';
2
2
  import { PopoverPlacement, PopoverAlign } from './popover.types.js';
3
+ export declare function supportsAnchoring(): boolean;
3
4
  export interface UsePopoverPositionArgs {
4
5
  isOpen: boolean;
5
6
  placement: PopoverPlacement;
@@ -1,3 +1,3 @@
1
1
  import { default as React } from 'react';
2
2
  import { StickyProps } from './sticky.types.js';
3
- export default function Sticky({ children, offsetTop, offsetElement, stickToScrollParent, zIndex, disabled, onStuckChange, className, style, classNames, styles: slotStyles, ...rest }: StickyProps): React.JSX.Element;
3
+ export default function Sticky({ children, offsetTop, offsetElement, stickToScrollParent, boundary, boundaryInset, zIndex, disabled, onStuckChange, className, style, classNames, styles: slotStyles, ...rest }: StickyProps): React.JSX.Element;
@@ -9,6 +9,21 @@ export interface StickyProps extends HtmlProps {
9
9
  offsetElement?: React.RefObject<HTMLElement | null>;
10
10
  /** Stick to the top of the nearest scrollable ancestor instead of the browser viewport. Falls back to the viewport if no scrollable ancestor is found. */
11
11
  stickToScrollParent?: boolean;
12
+ /**
13
+ * Element the content is confined to, normally the one it labels. Once that
14
+ * element's bottom edge reaches the pinned content, the content is pushed up
15
+ * with it and scrolls away, instead of staying pinned over whatever follows.
16
+ * Without it the content pins for as long as the page scrolls.
17
+ */
18
+ boundary?: React.RefObject<HTMLElement | null>;
19
+ /**
20
+ * How much of the boundary's lower end stays uncovered as the content leaves,
21
+ * in px. At 0 the content rests on the very bottom edge, which means the last
22
+ * stretch of the boundary, as tall as the pinned content, spends the whole
23
+ * exit hidden underneath it. Set it to how much you want to stay in sight:
24
+ * for a table header, a few rows. Default 0. Ignored without `boundary`.
25
+ */
26
+ boundaryInset?: number;
12
27
  /** z-index applied to the content while stuck. Default 20. */
13
28
  zIndex?: number;
14
29
  /** Disable sticking entirely — content stays in normal flow. */
@@ -15,6 +15,11 @@ export interface StickyStackMetrics {
15
15
  * in unrelated scroll panels should never push each other down just because they happen to
16
16
  * share horizontal DOM coordinates. */
17
17
  container: HTMLElement | null;
18
+ /** The element the entry is confined to, or null when nothing confines it.
19
+ * Entries sharing one leave together. */
20
+ boundary: HTMLElement | null;
21
+ /** Bottom edge of that element (less its inset), in the same coordinate space as `top`. */
22
+ boundaryBottom: number | null;
18
23
  }
19
24
  export interface StickyStackEntry {
20
25
  node: HTMLElement;
@@ -9,6 +9,11 @@ interface State {
9
9
  resolvedVariables: Record<string, string>;
10
10
  colorFadeActive: boolean;
11
11
  currentThemeColor: string | null;
12
+ /** What `resolvedVariables` was resolved from, to tell a theme change from any other render. */
13
+ resolvedFrom: {
14
+ themes: Theme[] | undefined;
15
+ currentThemeId: string | undefined;
16
+ };
12
17
  }
13
18
  declare class ThemeProvider extends Component<Props, State> {
14
19
  state: State;
@@ -16,6 +21,7 @@ declare class ThemeProvider extends Component<Props, State> {
16
21
  private wrapperRef;
17
22
  private themeColorMeta;
18
23
  private createdThemeColorMeta;
24
+ static getDerivedStateFromProps(props: Props, state: State): Partial<State> | null;
19
25
  componentDidMount(): void;
20
26
  componentDidUpdate(prevProps: Props, prevState: State): void;
21
27
  componentWillUnmount(): void;
@@ -26,13 +32,8 @@ declare class ThemeProvider extends Component<Props, State> {
26
32
  * (and removes it again on unmount).
27
33
  */
28
34
  private syncThemeColorMeta;
29
- /**
30
- * Resolves the full variable set for a given theme ID by walking up the
31
- * baseThemeId chain. Returns variables ordered from deepest ancestor to
32
- * the requested theme so callers can merge in order (later entries win).
33
- */
34
- private resolveChain;
35
- private applyTheme;
35
+ /** `--primary-color` as the browser resolved it, which may be a `var()` of another variable. */
36
+ private readThemeColor;
36
37
  render(): React.JSX.Element;
37
38
  }
38
39
  export default ThemeProvider;
@@ -1,2 +1,12 @@
1
1
  export declare function getScrollableAncestors(el: HTMLElement): HTMLElement[];
2
2
  export declare function isHiddenByAnyAncestor(rect: DOMRect, ancestors: HTMLElement[]): boolean;
3
+ /**
4
+ * The ancestor whose scrollbar carries `el`, or null when that is the page.
5
+ * `Sticky` pins against it and `VirtualList` virtualizes against it, and the two
6
+ * have to agree or a sticky header and the rows under it come apart.
7
+ *
8
+ * Narrower than `getScrollableAncestors` above, which is about who *clips* and so
9
+ * counts `hidden` too: a `hidden` box never scrolls, so pinning to it would pin
10
+ * to something that never moves.
11
+ */
12
+ export declare function getScrollParent(el: HTMLElement | null): HTMLElement | null;
@@ -0,0 +1,33 @@
1
+ import { VirtualListScrollParent } from './virtualList.types.js';
2
+ /**
3
+ * Whatever carries the list's scroll, and how the list is measured against it.
4
+ *
5
+ * Everything here works in *list space*: offset 0 is the top of the first row,
6
+ * which is the root's `scrollTop` when the list scrolls itself and its distance
7
+ * above the scrollport's top edge when it doesn't. One coordinate system, so the
8
+ * windowing, anchoring and jump math never branch.
9
+ */
10
+ export type Scroller = HTMLElement | Window;
11
+ export declare function isWindowScroller(scroller: Scroller): scroller is Window;
12
+ /** `'nearest'` is resolved by the caller, which caches the ancestor walk. */
13
+ export declare function resolveScroller(scrollParent: Exclude<VirtualListScrollParent, 'nearest'> | undefined): Scroller | null;
14
+ /** In viewport coordinates, which is what the rects below are compared against. */
15
+ export declare function scrollportBounds(scroller: Scroller): {
16
+ top: number;
17
+ height: number;
18
+ };
19
+ export interface Viewport {
20
+ /** List-space scroll position, unclamped: negative while the list starts below
21
+ * the scrollport, which is what makes a target reachable from either side. */
22
+ rel: number;
23
+ /** The slice of the scrollport the list occupies now. */
24
+ visibleHeight: number;
25
+ /** The whole scrollport, which is what a scroll target is aimed within. */
26
+ viewportHeight: number;
27
+ /** From the list's last row to the end of the scrollport. The browser clamps
28
+ * `scrollTop`, so a list that scrolls itself never reports this negative;
29
+ * riding a scrollport, it does, for the whole rest of the page. */
30
+ distanceToEnd: number;
31
+ width: number;
32
+ }
33
+ export declare function measureViewport(root: HTMLElement, scroller: Scroller | null): Viewport;
@@ -1,5 +1,6 @@
1
1
  import { default as React } from 'react';
2
2
  import { TreeDropPosition, TreeDropTarget } from './virtualList.types.js';
3
+ import { ListViewportRect } from './useVirtualWindow.js';
3
4
  interface UseRowDragArgs {
4
5
  reorderable: boolean;
5
6
  treeReorder: boolean;
@@ -15,6 +16,10 @@ interface UseRowDragArgs {
15
16
  rootRef: React.RefObject<HTMLDivElement | null>;
16
17
  /** Latest keys for async (touch / rAF) consumers — owned by useVirtualWindow. */
17
18
  keysRef: React.RefObject<(string | number)[]>;
19
+ /** Where the list is on screen, which is not its own box once it rides a
20
+ * scrollport — owned by useVirtualWindow, as is `scrollBy`. */
21
+ getVisibleRect: () => ListViewportRect | null;
22
+ scrollBy: (dy: number) => void;
18
23
  }
19
24
  /** The drag-related props the parent spreads onto a given row. */
20
25
  export interface RowDragProps {
@@ -54,5 +59,5 @@ interface UseRowDragResult {
54
59
  * Touch uses a long-press → lifted-clone → pointer-move path with edge
55
60
  * auto-scroll. `dragHandle` restricts initiation to `[data-drag-handle]`.
56
61
  */
57
- export declare function useRowDrag({ reorderable, treeReorder, onReorder, onTreeDrop, longPressDelay, dragHandle, treeIndentPx, keys, depths, isGroupAt, rootRef, keysRef, }: UseRowDragArgs): UseRowDragResult;
62
+ export declare function useRowDrag({ reorderable, treeReorder, onReorder, onTreeDrop, longPressDelay, dragHandle, treeIndentPx, keys, depths, isGroupAt, rootRef, keysRef, getVisibleRect, scrollBy, }: UseRowDragArgs): UseRowDragResult;
58
63
  export {};
@@ -1,12 +1,18 @@
1
1
  import { default as React } from 'react';
2
2
  import { VirtualListScrollOptions } from './virtualList.types.js';
3
+ import { VisibleSlice } from './useVirtualWindow.js';
3
4
  interface UseRowNavigationArgs {
4
5
  enabled: boolean;
6
+ tabAcrossRows: boolean;
5
7
  rowCount: number;
6
8
  /** Row tops, from the windowing engine, used for paging and visibility. */
7
9
  offsets: number[];
8
10
  rootRef: React.RefObject<HTMLDivElement | null>;
9
11
  headerRef: React.RefObject<HTMLDivElement | null>;
12
+ /** Read live: a held arrow key moves the slice faster than the state commits. */
13
+ getVisibleSlice: () => VisibleSlice;
14
+ /** The whole scrollport, which is what one PageDown covers. */
15
+ viewportHeight: number;
10
16
  scrollToIndex: (index: number, options?: VirtualListScrollOptions) => void;
11
17
  /** Row index the active row starts on, normally the selected one. */
12
18
  initialIndex: number;
@@ -45,6 +51,10 @@ interface UseRowNavigationResult {
45
51
  * hold an input, a dropdown or a button, and every one of them wants the arrows,
46
52
  * Enter and Space for itself. `F2` steps into such a row and `Escape` steps back
47
53
  * out, which is the one pair of keys that does work from inside a cell.
54
+ *
55
+ * `tabAcrossRows` adds the second pair, Tab and Shift+Tab, which the browser
56
+ * cannot carry across a row boundary itself: the next row may not be in the DOM
57
+ * when it looks for the next stop.
48
58
  */
49
- export declare function useRowNavigation({ enabled, rowCount, offsets, rootRef, headerRef, scrollToIndex, initialIndex, multiSelect, onActivate, onToggleSelect, }: UseRowNavigationArgs): UseRowNavigationResult;
59
+ export declare function useRowNavigation({ enabled, tabAcrossRows, rowCount, offsets, rootRef, headerRef, getVisibleSlice, viewportHeight, scrollToIndex, initialIndex, multiSelect, onActivate, onToggleSelect, }: UseRowNavigationArgs): UseRowNavigationResult;
50
60
  export {};
@@ -1,5 +1,5 @@
1
1
  import { default as React } from 'react';
2
- import { VirtualListHandle } from './virtualList.types.js';
2
+ import { VirtualListHandle, VirtualListScrollParent } from './virtualList.types.js';
3
3
  interface UseVirtualWindowArgs<T> {
4
4
  items: T[];
5
5
  /** Stable key per row (already derived by the caller). */
@@ -12,6 +12,19 @@ interface UseVirtualWindowArgs<T> {
12
12
  loadMoreThreshold: number;
13
13
  /** Initial/filter load in progress — the body is replaced by a spinner. */
14
14
  isLoading: boolean;
15
+ scrollParent?: VirtualListScrollParent;
16
+ }
17
+ /** Where the list is on screen, which is not its own box once it rides a scrollport. */
18
+ export interface ListViewportRect {
19
+ top: number;
20
+ bottom: number;
21
+ left: number;
22
+ right: number;
23
+ }
24
+ /** The list-space slice currently on screen, read live for keyboard navigation. */
25
+ export interface VisibleSlice {
26
+ top: number;
27
+ height: number;
15
28
  }
16
29
  interface UseVirtualWindowResult {
17
30
  rootRef: React.RefObject<HTMLDivElement | null>;
@@ -22,15 +35,21 @@ interface UseVirtualWindowResult {
22
35
  keysRef: React.RefObject<(string | number)[]>;
23
36
  offsets: number[];
24
37
  totalHeight: number;
38
+ /** The list's visible slice, which is what decides which rows are rendered. */
25
39
  containerHeight: number;
40
+ /** The whole scrollport, which is what a scroll target is aimed within. */
41
+ viewportHeight: number;
26
42
  containerWidth: number;
27
43
  startIndex: number;
28
44
  endIndex: number;
29
- handleScroll: (e: React.UIEvent<HTMLDivElement>) => void;
30
45
  showLoadMoreSpinner: boolean;
46
+ isWindowed: boolean;
47
+ getVisibleSlice: () => VisibleSlice;
48
+ getVisibleRect: () => ListViewportRect | null;
49
+ scrollBy: (dy: number) => void;
31
50
  /** The scroll-related imperative methods, for the component to compose into
32
51
  * the forwarded handle alongside column controls. */
33
52
  scrollApi: Omit<VirtualListHandle, 'recalculateColumns' | 'resetColumnWidths'>;
34
53
  }
35
- export declare function useVirtualWindow<T>({ items, keys, getItemKey, estimatedRowHeight, rowGap, overscan, onLoadMore, loadMoreThreshold, isLoading, }: UseVirtualWindowArgs<T>): UseVirtualWindowResult;
54
+ export declare function useVirtualWindow<T>({ items, keys, getItemKey, estimatedRowHeight, rowGap, overscan, onLoadMore, loadMoreThreshold, isLoading, scrollParent, }: UseVirtualWindowArgs<T>): UseVirtualWindowResult;
36
55
  export {};
@@ -1,5 +1,5 @@
1
1
  import { default as React } from 'react';
2
2
  import { VirtualListProps } from './virtualList.types.js';
3
3
  export { buildOffsets, findStartIndex, getVisibleRange, resolveReorderTarget, resolveTreeDropTarget, lastDescendantIndex, buildColumnTemplate, compareSortValues, isColumnSortable, isEmptySortValue, nextSort, sortItems, } from './virtualList.utils.js';
4
- declare function VirtualList<T>({ ref, items, renderRow, ariaRoles, columns, height, estimatedRowHeight, overscan, rowGap, rowPadding, selectedKey, getItemKey, onRowClick, keyboardNavigation, visibleColumnKeys, onVisibleColumnsChange, persistColumnsKey, resizableColumns, columnWidths, onColumnWidthsChange, labels, sort, defaultSort, onSortChange, showColumnToggle, onLoadMore, loadMoreThreshold, isLoading, multiSelect, selectedKeys, onSelectionChange, reorderable, onReorder, longPressDelay, treeReorder, getItemDepth, isGroup, onTreeDrop, treeIndentPx, dragHandle, showDivider, rowHover, className, style, classNames, styles: slotStyles, ...rest }: VirtualListProps<T>): React.JSX.Element;
4
+ declare function VirtualList<T>(props: VirtualListProps<T>): React.JSX.Element;
5
5
  export default VirtualList;