@tangible/ui 0.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (212) hide show
  1. package/README.md +100 -0
  2. package/components/Accordion/Accordion.d.ts +22 -0
  3. package/components/Accordion/Accordion.js +192 -0
  4. package/components/Accordion/AccordionContext.d.ts +5 -0
  5. package/components/Accordion/AccordionContext.js +23 -0
  6. package/components/Accordion/index.d.ts +2 -0
  7. package/components/Accordion/index.js +1 -0
  8. package/components/Accordion/types.d.ts +61 -0
  9. package/components/Accordion/types.js +1 -0
  10. package/components/Avatar/Avatar.d.ts +11 -0
  11. package/components/Avatar/Avatar.js +67 -0
  12. package/components/Avatar/AvatarGroup.d.ts +11 -0
  13. package/components/Avatar/AvatarGroup.js +45 -0
  14. package/components/Avatar/index.d.ts +9 -0
  15. package/components/Avatar/index.js +7 -0
  16. package/components/Avatar/types.d.ts +44 -0
  17. package/components/Avatar/types.js +12 -0
  18. package/components/Button/Button.d.ts +4 -0
  19. package/components/Button/Button.js +33 -0
  20. package/components/Button/index.d.ts +2 -0
  21. package/components/Button/index.js +1 -0
  22. package/components/Button/types.d.ts +127 -0
  23. package/components/Button/types.js +1 -0
  24. package/components/Card/Card.d.ts +29 -0
  25. package/components/Card/Card.js +47 -0
  26. package/components/Card/index.d.ts +2 -0
  27. package/components/Card/index.js +1 -0
  28. package/components/Chip/Chip.d.ts +24 -0
  29. package/components/Chip/Chip.js +37 -0
  30. package/components/Chip/index.d.ts +2 -0
  31. package/components/Chip/index.js +1 -0
  32. package/components/Chips/Chips.d.ts +31 -0
  33. package/components/Chips/Chips.js +21 -0
  34. package/components/Chips/index.d.ts +2 -0
  35. package/components/Chips/index.js +1 -0
  36. package/components/ContentIndicator/ContentIndicator.d.ts +2 -0
  37. package/components/ContentIndicator/ContentIndicator.js +21 -0
  38. package/components/ContentIndicator/index.d.ts +2 -0
  39. package/components/ContentIndicator/index.js +1 -0
  40. package/components/ContentIndicator/types.d.ts +57 -0
  41. package/components/ContentIndicator/types.js +1 -0
  42. package/components/Dropdown/Dropdown.d.ts +31 -0
  43. package/components/Dropdown/Dropdown.js +219 -0
  44. package/components/Dropdown/DropdownContext.d.ts +3 -0
  45. package/components/Dropdown/DropdownContext.js +9 -0
  46. package/components/Dropdown/index.d.ts +2 -0
  47. package/components/Dropdown/index.js +1 -0
  48. package/components/Dropdown/types.d.ts +102 -0
  49. package/components/Dropdown/types.js +8 -0
  50. package/components/Icon/Icon.d.ts +22 -0
  51. package/components/Icon/Icon.js +24 -0
  52. package/components/Icon/index.d.ts +2 -0
  53. package/components/Icon/index.js +1 -0
  54. package/components/IconButton/IconButton.d.ts +2 -0
  55. package/components/IconButton/IconButton.js +50 -0
  56. package/components/IconButton/index.d.ts +2 -0
  57. package/components/IconButton/index.js +1 -0
  58. package/components/IconButton/types.d.ts +79 -0
  59. package/components/IconButton/types.js +1 -0
  60. package/components/Modal/Modal.d.ts +52 -0
  61. package/components/Modal/Modal.js +133 -0
  62. package/components/Modal/context.d.ts +6 -0
  63. package/components/Modal/context.js +9 -0
  64. package/components/Modal/index.d.ts +2 -0
  65. package/components/Modal/index.js +1 -0
  66. package/components/Notice/Notice.d.ts +93 -0
  67. package/components/Notice/Notice.js +144 -0
  68. package/components/Notice/index.d.ts +2 -0
  69. package/components/Notice/index.js +1 -0
  70. package/components/OverlapStack/OverlapStack.d.ts +44 -0
  71. package/components/OverlapStack/OverlapStack.js +41 -0
  72. package/components/OverlapStack/index.d.ts +2 -0
  73. package/components/OverlapStack/index.js +1 -0
  74. package/components/Pager/Pager.d.ts +26 -0
  75. package/components/Pager/Pager.js +151 -0
  76. package/components/Pager/index.d.ts +2 -0
  77. package/components/Pager/index.js +1 -0
  78. package/components/Progress/Progress.d.ts +2 -0
  79. package/components/Progress/Progress.js +100 -0
  80. package/components/Progress/index.d.ts +4 -0
  81. package/components/Progress/index.js +2 -0
  82. package/components/Progress/types.d.ts +251 -0
  83. package/components/Progress/types.js +1 -0
  84. package/components/Progress/useProgressSegments.d.ts +40 -0
  85. package/components/Progress/useProgressSegments.js +42 -0
  86. package/components/Rating/Rating.d.ts +32 -0
  87. package/components/Rating/Rating.js +74 -0
  88. package/components/Rating/index.d.ts +2 -0
  89. package/components/Rating/index.js +1 -0
  90. package/components/SegmentedControl/SegmentedControl.d.ts +10 -0
  91. package/components/SegmentedControl/SegmentedControl.js +183 -0
  92. package/components/SegmentedControl/SegmentedControlContext.d.ts +3 -0
  93. package/components/SegmentedControl/SegmentedControlContext.js +9 -0
  94. package/components/SegmentedControl/index.d.ts +2 -0
  95. package/components/SegmentedControl/index.js +1 -0
  96. package/components/SegmentedControl/types.d.ts +63 -0
  97. package/components/SegmentedControl/types.js +1 -0
  98. package/components/Sidebar/Sidebar.d.ts +17 -0
  99. package/components/Sidebar/Sidebar.js +107 -0
  100. package/components/Sidebar/index.d.ts +2 -0
  101. package/components/Sidebar/index.js +1 -0
  102. package/components/Sidebar/types.d.ts +65 -0
  103. package/components/Sidebar/types.js +4 -0
  104. package/components/StepIndicator/StepIndicator.d.ts +2 -0
  105. package/components/StepIndicator/StepIndicator.js +64 -0
  106. package/components/StepIndicator/index.d.ts +2 -0
  107. package/components/StepIndicator/index.js +1 -0
  108. package/components/StepIndicator/types.d.ts +68 -0
  109. package/components/StepIndicator/types.js +1 -0
  110. package/components/StepList/StepList.d.ts +12 -0
  111. package/components/StepList/StepList.js +59 -0
  112. package/components/StepList/StepListContext.d.ts +3 -0
  113. package/components/StepList/StepListContext.js +9 -0
  114. package/components/StepList/index.d.ts +2 -0
  115. package/components/StepList/index.js +1 -0
  116. package/components/StepList/types.d.ts +91 -0
  117. package/components/StepList/types.js +4 -0
  118. package/components/Table/BulkActionsBar.d.ts +12 -0
  119. package/components/Table/BulkActionsBar.js +9 -0
  120. package/components/Table/DataTable.d.ts +35 -0
  121. package/components/Table/DataTable.js +184 -0
  122. package/components/Table/Pagination.d.ts +13 -0
  123. package/components/Table/Pagination.js +13 -0
  124. package/components/Table/index.d.ts +2 -0
  125. package/components/Table/index.js +1 -0
  126. package/components/Tabs/Tabs.d.ts +23 -0
  127. package/components/Tabs/Tabs.js +309 -0
  128. package/components/Tabs/TabsContext.d.ts +3 -0
  129. package/components/Tabs/TabsContext.js +12 -0
  130. package/components/Tabs/index.d.ts +2 -0
  131. package/components/Tabs/index.js +1 -0
  132. package/components/Tabs/types.d.ts +75 -0
  133. package/components/Tabs/types.js +1 -0
  134. package/components/Toolbar/Toolbar.d.ts +18 -0
  135. package/components/Toolbar/Toolbar.js +241 -0
  136. package/components/Toolbar/index.d.ts +2 -0
  137. package/components/Toolbar/index.js +1 -0
  138. package/components/Toolbar/types.d.ts +28 -0
  139. package/components/Toolbar/types.js +1 -0
  140. package/components/Tooltip/Tooltip.d.ts +15 -0
  141. package/components/Tooltip/Tooltip.js +166 -0
  142. package/components/Tooltip/TooltipContext.d.ts +15 -0
  143. package/components/Tooltip/TooltipContext.js +25 -0
  144. package/components/Tooltip/index.d.ts +2 -0
  145. package/components/Tooltip/index.js +1 -0
  146. package/components/Tooltip/types.d.ts +85 -0
  147. package/components/Tooltip/types.js +8 -0
  148. package/components/index.d.ts +52 -0
  149. package/components/index.js +26 -0
  150. package/constants.d.ts +16 -0
  151. package/constants.js +16 -0
  152. package/icons/cred/index.d.ts +31 -0
  153. package/icons/cred/index.js +136 -0
  154. package/icons/icons.svg +155 -0
  155. package/icons/lms/index.d.ts +21 -0
  156. package/icons/lms/index.js +81 -0
  157. package/icons/manifest.json +1226 -0
  158. package/icons/player/index.d.ts +55 -0
  159. package/icons/player/index.js +268 -0
  160. package/icons/reaction/index.d.ts +79 -0
  161. package/icons/reaction/index.js +400 -0
  162. package/icons/registry.d.ts +316 -0
  163. package/icons/registry.js +163 -0
  164. package/icons/system/index.d.ts +155 -0
  165. package/icons/system/index.js +818 -0
  166. package/package.json +121 -0
  167. package/styles/all.css +1 -0
  168. package/styles/all.expanded.css +4137 -0
  169. package/styles/all.expanded.unlayered.css +4137 -0
  170. package/styles/all.unlayered.css +1 -0
  171. package/styles/components/_bundle.scss +51 -0
  172. package/styles/components/index.scss +1 -0
  173. package/styles/components/input/index.scss +248 -0
  174. package/styles/index.scss +71 -0
  175. package/styles/system/_constants.scss +12 -0
  176. package/styles/system/_motion.scss +47 -0
  177. package/styles/system/_palette-fns.scss +10 -0
  178. package/styles/system/_palettes.scss +80 -0
  179. package/styles/system/_tokens.scss +249 -0
  180. package/styles/system/index.scss +4 -0
  181. package/styles/utilities/_index.scss +373 -0
  182. package/tui-manifest.json +1858 -0
  183. package/types/index.d.ts +2 -0
  184. package/types/index.js +1 -0
  185. package/types/index.ts +2 -0
  186. package/types/sizes.d.ts +17 -0
  187. package/types/sizes.js +10 -0
  188. package/types/sizes.ts +21 -0
  189. package/types/svg.d.ts +5 -0
  190. package/types/themes.d.ts +14 -0
  191. package/types/themes.js +9 -0
  192. package/types/themes.ts +17 -0
  193. package/utils/color/contrast.d.ts +33 -0
  194. package/utils/color/contrast.js +88 -0
  195. package/utils/color-scheme.d.ts +25 -0
  196. package/utils/color-scheme.js +55 -0
  197. package/utils/compose-refs.d.ts +17 -0
  198. package/utils/compose-refs.js +38 -0
  199. package/utils/cx.d.ts +12 -0
  200. package/utils/cx.js +14 -0
  201. package/utils/focus-trap.d.ts +40 -0
  202. package/utils/focus-trap.js +93 -0
  203. package/utils/index.d.ts +10 -0
  204. package/utils/index.js +16 -0
  205. package/utils/math.d.ts +4 -0
  206. package/utils/math.js +19 -0
  207. package/utils/merge-props.d.ts +25 -0
  208. package/utils/merge-props.js +60 -0
  209. package/utils/polymorphic.d.ts +28 -0
  210. package/utils/polymorphic.js +44 -0
  211. package/utils/portal.d.ts +11 -0
  212. package/utils/portal.js +105 -0
@@ -0,0 +1,33 @@
1
+ import { jsx as _jsx, Fragment as _Fragment, jsxs as _jsxs } from "react/jsx-runtime";
2
+ import React, { forwardRef } from 'react';
3
+ import { cx } from '../../utils/cx.js';
4
+ import { Icon } from '../Icon/index.js';
5
+ import { getSafeRel } from '../../utils/polymorphic.js';
6
+ export const Button = forwardRef(({ label, children, size = 'md', theme = 'primary', variant = 'solid', fullWidth, disabled = false, loading = false, leftIconName, rightIconName, leftIcon, rightIcon, iconSize = 'sm', className, target, rel, onClick, style, ...rest }, ref) => {
7
+ const isLink = typeof rest.href === 'string';
8
+ const isDisabled = disabled || loading;
9
+ // Normalize destructive → danger for CSS class
10
+ const themeClass = theme === 'destructive' ? 'danger' : theme;
11
+ const classes = cx('tui-button', `is-size-${size}`, `is-theme-${themeClass}`, variant !== 'solid' && `is-style-${variant}`, fullWidth && 'is-width-full', isDisabled && 'is-disabled', className);
12
+ // Icon size: pass string sizes to Icon component
13
+ const iconSizeForIcon = typeof iconSize === 'string' ? iconSize : undefined;
14
+ const Left = leftIcon ?? (leftIconName ? _jsx(Icon, { name: leftIconName, size: iconSizeForIcon }) : null);
15
+ const Right = rightIcon ?? (rightIconName ? _jsx(Icon, { name: rightIconName, size: iconSizeForIcon }) : null);
16
+ const content = label != null ? (_jsxs(_Fragment, { children: [Left, _jsx("span", { children: label }), Right] })) : (_jsxs(_Fragment, { children: [Left, children, Right] }));
17
+ if (isLink) {
18
+ const { href, tabIndex, ...anchorRest } = rest;
19
+ const safeRel = getSafeRel(target, rel);
20
+ const handleClick = (e) => {
21
+ if (isDisabled) {
22
+ e.preventDefault();
23
+ e.stopPropagation();
24
+ return;
25
+ }
26
+ onClick?.(e);
27
+ };
28
+ return (_jsx("a", { ref: ref, href: isDisabled ? undefined : href, className: classes, "aria-disabled": isDisabled || undefined, "aria-busy": loading || undefined, tabIndex: isDisabled ? -1 : tabIndex, onClick: handleClick, "data-loading": loading || undefined, target: target, rel: safeRel, style: style, ...anchorRest, children: content }));
29
+ }
30
+ const buttonRest = rest;
31
+ return (_jsx("button", { ref: ref, type: buttonRest.type ?? 'button', className: classes, disabled: isDisabled, "aria-disabled": isDisabled || undefined, "aria-busy": loading || undefined, onClick: onClick, "data-loading": loading || undefined, style: style, ...buttonRest, children: content }));
32
+ });
33
+ Button.displayName = 'Button';
@@ -0,0 +1,2 @@
1
+ export { Button } from './Button';
2
+ export type { ButtonProps } from './Button';
@@ -0,0 +1 @@
1
+ export { Button } from './Button.js';
@@ -0,0 +1,127 @@
1
+ import type { IconName } from '../../icons/registry';
2
+ import type { Size, ThemeIntent } from '../../types';
3
+ export type { Size };
4
+ /**
5
+ * Semantic color themes.
6
+ * - `'primary'`: Primary action (default)
7
+ * - `'secondary'`: Secondary/neutral action
8
+ * - `'danger'`: Destructive action
9
+ * - `'destructive'`: Alias for danger
10
+ */
11
+ export type Theme = ThemeIntent | 'destructive';
12
+ /**
13
+ * Visual style variants.
14
+ * - `'solid'`: Filled background (default)
15
+ * - `'outline'`: Border only, transparent background
16
+ * - `'ghost'`: Transparent, shows background on hover
17
+ * - `'link'`: Text-link styling, no background
18
+ */
19
+ export type Variant = 'solid' | 'outline' | 'ghost' | 'link';
20
+ type CommonProps = {
21
+ /**
22
+ * Button label text. If provided, renders as the button content.
23
+ * Use this for simple text buttons.
24
+ */
25
+ label?: React.ReactNode;
26
+ /**
27
+ * Rich content for the button. Used when label is not provided.
28
+ * Use this for buttons with custom markup.
29
+ */
30
+ children?: React.ReactNode;
31
+ /**
32
+ * Size of the button.
33
+ * @default 'md'
34
+ */
35
+ size?: Size;
36
+ /**
37
+ * Semantic color theme.
38
+ * Note: Defaults to 'primary' (unlike IconButton which defaults to 'secondary')
39
+ * because Buttons are typically primary CTAs.
40
+ * @default 'primary'
41
+ */
42
+ theme?: Theme;
43
+ /**
44
+ * Visual style variant.
45
+ * @default 'solid'
46
+ */
47
+ variant?: Variant;
48
+ /**
49
+ * Make button full width of container.
50
+ * @default false
51
+ */
52
+ fullWidth?: boolean;
53
+ /**
54
+ * Disabled state. Prevents interaction.
55
+ * @default false
56
+ */
57
+ disabled?: boolean;
58
+ /**
59
+ * Loading state. Shows spinner and prevents interaction.
60
+ * @default false
61
+ */
62
+ loading?: boolean;
63
+ /**
64
+ * Link target (for anchor variant).
65
+ */
66
+ target?: React.HTMLAttributeAnchorTarget;
67
+ /**
68
+ * Link rel attribute (for anchor variant).
69
+ */
70
+ rel?: string;
71
+ /**
72
+ * Click handler. Works for both button and anchor variants.
73
+ */
74
+ onClick?: React.MouseEventHandler<HTMLButtonElement | HTMLAnchorElement>;
75
+ /**
76
+ * Icon to display before the label.
77
+ * Use icon registry paths like "system/check".
78
+ * @example leftIconName="system/check"
79
+ */
80
+ leftIconName?: IconName;
81
+ /**
82
+ * Icon to display after the label.
83
+ * Use icon registry paths like "system/chevron-right".
84
+ * @example rightIconName="system/chevron-right"
85
+ */
86
+ rightIconName?: IconName;
87
+ /**
88
+ * Custom left icon element. Overrides leftIconName.
89
+ */
90
+ leftIcon?: React.ReactNode;
91
+ /**
92
+ * Custom right icon element. Overrides rightIconName.
93
+ */
94
+ rightIcon?: React.ReactNode;
95
+ /**
96
+ * Size of icons.
97
+ * @default 'sm'
98
+ */
99
+ iconSize?: Size;
100
+ /**
101
+ * Additional CSS class names.
102
+ * Note: Use sparingly. Prefer component API tokens for customization.
103
+ */
104
+ className?: string;
105
+ /**
106
+ * Inline styles.
107
+ */
108
+ style?: React.CSSProperties;
109
+ };
110
+ /**
111
+ * Props when Button renders as a <button> element.
112
+ */
113
+ export type ButtonAsButton = CommonProps & Omit<React.ButtonHTMLAttributes<HTMLButtonElement>, 'disabled' | 'children'> & {
114
+ href?: undefined;
115
+ };
116
+ /**
117
+ * Props when Button renders as an <a> element.
118
+ */
119
+ export type ButtonAsAnchor = CommonProps & Omit<React.AnchorHTMLAttributes<HTMLAnchorElement>, 'children'> & {
120
+ /** URL for the link. When provided, Button renders as <a>. */
121
+ href: string;
122
+ };
123
+ /**
124
+ * Button component props.
125
+ * Renders as <button> by default, or <a> when href is provided.
126
+ */
127
+ export type ButtonProps = ButtonAsButton | ButtonAsAnchor;
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,29 @@
1
+ import React from 'react';
2
+ import type { JSX } from 'react';
3
+ type RootAs = 'article' | 'section' | 'div';
4
+ type CommonProps = {
5
+ inline?: boolean;
6
+ elevated?: boolean;
7
+ interactive?: boolean;
8
+ disabled?: boolean;
9
+ className?: string;
10
+ style?: React.CSSProperties;
11
+ };
12
+ export type CardRootProps<TAs extends RootAs = 'article'> = CommonProps & {
13
+ as?: TAs;
14
+ onClick?: React.MouseEventHandler<HTMLElement>;
15
+ children?: React.ReactNode;
16
+ };
17
+ type SlotProps = React.HTMLAttributes<HTMLDivElement> & {
18
+ className?: string;
19
+ children?: React.ReactNode;
20
+ };
21
+ type CardCompound = {
22
+ <TAs extends RootAs = 'article'>(props: CardRootProps<TAs> & Omit<React.ComponentPropsWithoutRef<TAs>, keyof CardRootProps>): JSX.Element;
23
+ Head: React.FC<SlotProps>;
24
+ Body: React.FC<SlotProps>;
25
+ Foot: React.FC<SlotProps>;
26
+ Link: React.FC<React.AnchorHTMLAttributes<HTMLAnchorElement>>;
27
+ };
28
+ export declare const Card: CardCompound;
29
+ export {};
@@ -0,0 +1,47 @@
1
+ import { jsx as _jsx } from "react/jsx-runtime";
2
+ import React, { forwardRef, useCallback } from 'react';
3
+ import { cx } from '../../utils/cx.js';
4
+ export const Card = forwardRef(function Card({ as = 'article', inline, elevated, interactive, disabled, className, style, onClick, children, ...rest }, ref) {
5
+ const Tag = as;
6
+ // Determine if this card is clickable (needs button semantics)
7
+ const isClickable = (interactive || onClick) && !disabled;
8
+ // Keyboard handler for interactive cards
9
+ const handleKeyDown = useCallback((e) => {
10
+ if (!isClickable || !onClick)
11
+ return;
12
+ if (e.key === 'Enter' || e.key === ' ') {
13
+ e.preventDefault();
14
+ onClick(e);
15
+ }
16
+ }, [isClickable, onClick]);
17
+ const classes = cx('tui-card', inline && 'is-layout-inline', elevated && 'is-style-elevated', interactive && 'has-interaction', className);
18
+ // Button semantics for clickable cards
19
+ const buttonProps = isClickable
20
+ ? {
21
+ role: 'button',
22
+ tabIndex: 0,
23
+ onKeyDown: handleKeyDown,
24
+ }
25
+ : {};
26
+ return (_jsx(Tag, { ref: ref, className: classes, style: style, "aria-disabled": disabled || undefined, onClick: disabled ? undefined : onClick, ...buttonProps, ...rest, children: _jsx("div", { className: "tui-card__inner", children: children }) }));
27
+ });
28
+ function CardHead({ className, children, ...rest }) {
29
+ return (_jsx("div", { className: cx('tui-card__head', className), ...rest, children: children }));
30
+ }
31
+ CardHead.displayName = 'Card.Head';
32
+ function CardBody({ className, children, ...rest }) {
33
+ return (_jsx("div", { className: cx('tui-card__body', className), ...rest, children: children }));
34
+ }
35
+ CardBody.displayName = 'Card.Body';
36
+ function CardFoot({ className, children, ...rest }) {
37
+ return (_jsx("div", { className: cx('tui-card__foot', className), ...rest, children: children }));
38
+ }
39
+ CardFoot.displayName = 'Card.Foot';
40
+ function CardLink({ className, children, rel, target, ...rest }) {
41
+ return (_jsx("a", { className: cx('tui-stretched-link', className), rel: target === '_blank' ? ['noopener', 'noreferrer', rel].filter(Boolean).join(' ') : rel, target: target, ...rest, children: children }));
42
+ }
43
+ CardLink.displayName = 'Card.Link';
44
+ Card.Head = CardHead;
45
+ Card.Body = CardBody;
46
+ Card.Foot = CardFoot;
47
+ Card.Link = CardLink;
@@ -0,0 +1,2 @@
1
+ export { Card } from './Card';
2
+ export type { CardRootProps } from './Card';
@@ -0,0 +1 @@
1
+ export { Card } from './Card.js';
@@ -0,0 +1,24 @@
1
+ import * as React from 'react';
2
+ import type { SizeCompact, Theme as ThemeFull } from '../../types';
3
+ type Size = SizeCompact;
4
+ type Theme = ThemeFull;
5
+ type Variant = 'default' | 'outline' | 'ghost' | 'solid' | 'flush';
6
+ export type ChipProps = {
7
+ as?: 'span' | 'div' | 'a';
8
+ href?: string;
9
+ target?: React.HTMLAttributeAnchorTarget;
10
+ rel?: string;
11
+ children: React.ReactNode;
12
+ size?: Size;
13
+ theme?: Theme;
14
+ variant?: Variant;
15
+ selected?: boolean;
16
+ disabled?: boolean;
17
+ interactive?: boolean;
18
+ className?: string;
19
+ leftIcon?: React.ReactNode;
20
+ rightIcon?: React.ReactNode;
21
+ onClick?: React.MouseEventHandler<HTMLElement>;
22
+ } & Omit<React.HTMLAttributes<HTMLSpanElement>, 'onClick'>;
23
+ export declare function Chip({ as, href, target, rel, children, size, theme, variant, selected, disabled, interactive, className, leftIcon, rightIcon, onClick, ...rest }: ChipProps): import("react/jsx-runtime").JSX.Element;
24
+ export {};
@@ -0,0 +1,37 @@
1
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ import * as React from 'react';
3
+ import { useCallback } from 'react';
4
+ import { cx } from '../../utils/cx.js';
5
+ export function Chip({ as = 'span', href, target, rel, children, size = 'md', theme = 'secondary', variant = 'default', selected, disabled, interactive, className, leftIcon, rightIcon, onClick, ...rest }) {
6
+ const Tag = (as === 'a' ? 'a' : as);
7
+ // Determine if this chip is clickable (needs button semantics)
8
+ const isClickable = (interactive || onClick) && !disabled;
9
+ // Keyboard handler for interactive chips
10
+ const handleKeyDown = useCallback((e) => {
11
+ if (!isClickable || !onClick)
12
+ return;
13
+ if (e.key === 'Enter' || e.key === ' ') {
14
+ e.preventDefault();
15
+ onClick(e);
16
+ }
17
+ }, [isClickable, onClick]);
18
+ const classes = cx('tui-chip', size && `is-size-${size}`, theme && `is-theme-${theme}`, variant !== 'default' && `is-style-${variant}`, selected && 'is-selected', interactive && 'is-interactive', className);
19
+ const anchorProps = as === 'a'
20
+ ? {
21
+ href: disabled ? undefined : href ?? '#',
22
+ target,
23
+ rel,
24
+ 'aria-disabled': disabled || undefined,
25
+ tabIndex: disabled ? -1 : undefined,
26
+ }
27
+ : { 'aria-disabled': disabled || undefined };
28
+ // Button semantics for non-anchor clickable chips
29
+ const buttonProps = as !== 'a' && isClickable
30
+ ? {
31
+ role: 'button',
32
+ tabIndex: 0,
33
+ onKeyDown: handleKeyDown,
34
+ }
35
+ : {};
36
+ return (_jsxs(Tag, { className: classes, ...anchorProps, ...buttonProps, onClick: disabled ? undefined : onClick, ...rest, children: [leftIcon && leftIcon, _jsx("span", { className: "tui-chip__text", children: children }), rightIcon && rightIcon] }));
37
+ }
@@ -0,0 +1,2 @@
1
+ export { Chip } from './Chip';
2
+ export type { ChipProps } from './Chip';
@@ -0,0 +1 @@
1
+ export { Chip } from './Chip.js';
@@ -0,0 +1,31 @@
1
+ import React from 'react';
2
+ import type { SizeCompact, Theme as ThemeFull } from '../../types';
3
+ type Size = SizeCompact;
4
+ type Theme = ThemeFull;
5
+ type Variant = 'default' | 'outline' | 'ghost' | 'solid' | 'flush';
6
+ export type ChipOption = {
7
+ label: React.ReactNode;
8
+ as?: 'a' | 'span' | 'div';
9
+ href?: string;
10
+ target?: React.HTMLAttributeAnchorTarget;
11
+ rel?: string;
12
+ size?: Size;
13
+ theme?: Theme;
14
+ variant?: Variant;
15
+ disabled?: boolean;
16
+ className?: string;
17
+ leftIcon?: React.ReactNode;
18
+ rightIcon?: React.ReactNode;
19
+ };
20
+ export type ChipsProps = {
21
+ name?: string;
22
+ options: ChipOption[];
23
+ /** Gap between chips */
24
+ density?: 'xs' | 'sm' | 'md';
25
+ direction?: 'inline' | 'stack';
26
+ alignment?: 'start' | 'center' | 'end';
27
+ className?: string;
28
+ role?: React.AriaRole;
29
+ };
30
+ export declare function Chips({ name, options, density, direction, alignment, className, role }: ChipsProps): import("react/jsx-runtime").JSX.Element;
31
+ export {};
@@ -0,0 +1,21 @@
1
+ import { jsx as _jsx } from "react/jsx-runtime";
2
+ import React from 'react';
3
+ import { Chip } from '../Chip/index.js';
4
+ const DENSITY_MAP = {
5
+ xs: 'var(--tui-spacing-xs)',
6
+ sm: 'var(--tui-spacing-sm)',
7
+ md: 'var(--tui-spacing-md)',
8
+ };
9
+ export function Chips({ name, options, density = 'sm', direction = 'inline', alignment, className, role = 'group' }) {
10
+ const isInline = direction === 'inline';
11
+ const style = {
12
+ display: 'flex',
13
+ flexDirection: isInline ? 'row' : 'column',
14
+ flexWrap: isInline ? 'wrap' : undefined,
15
+ gap: DENSITY_MAP[density],
16
+ justifyContent: isInline && alignment ? alignment : undefined,
17
+ alignItems: !isInline && alignment ? alignment : undefined,
18
+ marginBlockEnd: 'var(--tui-spacing-sm)',
19
+ };
20
+ return (_jsx("div", { role: role, className: className, "data-chips-name": name, style: style, children: options.map((o) => (_jsx(Chip, { as: o.as ?? (o.href ? 'a' : 'span'), href: o.href, target: o.target, rel: o.rel, size: o.size, theme: o.theme, variant: o.variant, disabled: o.disabled, className: o.className, leftIcon: o.leftIcon, rightIcon: o.rightIcon, children: o.label }))) }));
21
+ }
@@ -0,0 +1,2 @@
1
+ export { Chips } from './Chips';
2
+ export type { ChipsProps, ChipOption } from './Chips';
@@ -0,0 +1 @@
1
+ export { Chips } from './Chips.js';
@@ -0,0 +1,2 @@
1
+ import type { ContentIndicatorProps } from './types';
2
+ export declare function ContentIndicator(props: ContentIndicatorProps): import("react/jsx-runtime").JSX.Element;
@@ -0,0 +1,21 @@
1
+ import { jsx as _jsx } from "react/jsx-runtime";
2
+ import { Icon } from '../Icon/index.js';
3
+ // =============================================================================
4
+ // Component
5
+ // =============================================================================
6
+ export function ContentIndicator(props) {
7
+ const { icon, size = 'sm', theme = 'default', variant = 'ring', label, className, } = props;
8
+ // Build class names
9
+ const rootClassName = [
10
+ 'tui-content-indicator',
11
+ `is-size-${size}`,
12
+ `is-theme-${theme}`,
13
+ `is-variant-${variant}`,
14
+ className,
15
+ ]
16
+ .filter(Boolean)
17
+ .join(' ');
18
+ // If no label, the icon is decorative and the whole element is presentational
19
+ const isDecorative = !label;
20
+ return (_jsx("div", { className: rootClassName, role: isDecorative ? 'presentation' : 'img', "aria-label": label, "aria-hidden": isDecorative || undefined, children: _jsx("div", { className: "tui-content-indicator__circle", children: _jsx(Icon, { name: icon }) }) }));
21
+ }
@@ -0,0 +1,2 @@
1
+ export { ContentIndicator } from './ContentIndicator';
2
+ export type { ContentIndicatorProps, Size as ContentIndicatorSize, Theme as ContentIndicatorTheme, Variant as ContentIndicatorVariant, } from './types';
@@ -0,0 +1 @@
1
+ export { ContentIndicator } from './ContentIndicator.js';
@@ -0,0 +1,57 @@
1
+ import type { IconName } from '../../icons/registry';
2
+ import type { Size } from '../../types';
3
+ export type { Size };
4
+ /**
5
+ * Visual theme for the indicator.
6
+ * - `default`: Uses border color (neutral)
7
+ * - `info`: Blue theme
8
+ * - `success`: Green theme
9
+ * - `warning`: Amber theme
10
+ * - `danger`: Red theme
11
+ */
12
+ export type Theme = 'default' | 'info' | 'success' | 'warning' | 'danger';
13
+ /**
14
+ * Visual variant.
15
+ * - `ring`: Hollow circle with border (default)
16
+ * - `solid`: Filled circle
17
+ */
18
+ export type Variant = 'ring' | 'solid';
19
+ export type ContentIndicatorProps = {
20
+ /**
21
+ * Icon to display in the center.
22
+ * Uses the icon registry path format: "category/name"
23
+ * @example "lms/question-mark"
24
+ */
25
+ icon: IconName;
26
+ /**
27
+ * Size of the indicator.
28
+ * - `'xs'`: 16px circle
29
+ * - `'sm'`: 24px circle (default)
30
+ * - `'md'`: 32px circle
31
+ * - `'lg'`: 40px circle
32
+ * @default 'sm'
33
+ */
34
+ size?: Size;
35
+ /**
36
+ * Color theme for the indicator.
37
+ * @default 'default'
38
+ */
39
+ theme?: Theme;
40
+ /**
41
+ * Visual variant.
42
+ * - `'ring'`: Hollow circle with border (default)
43
+ * - `'solid'`: Filled circle with icon in contrasting color
44
+ * @default 'ring'
45
+ */
46
+ variant?: Variant;
47
+ /**
48
+ * Accessible label for the indicator.
49
+ * Required for meaningful icons. Omit only if the icon is purely decorative
50
+ * and context is provided by surrounding content.
51
+ */
52
+ label?: string;
53
+ /**
54
+ * Additional CSS class names.
55
+ */
56
+ className?: string;
57
+ };
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,31 @@
1
+ import type { DropdownProps, DropdownTriggerProps, DropdownContentProps, DropdownItemProps } from './types';
2
+ declare function DropdownRoot({ open: controlledOpen, onOpenChange, defaultOpen, children, }: DropdownProps): import("react/jsx-runtime").JSX.Element;
3
+ declare namespace DropdownRoot {
4
+ var displayName: string;
5
+ }
6
+ declare function DropdownTriggerComponent({ asChild, children }: DropdownTriggerProps): import("react/jsx-runtime").JSX.Element;
7
+ declare namespace DropdownTriggerComponent {
8
+ var displayName: string;
9
+ }
10
+ declare function DropdownContentComponent({ side, align, sideOffset, className, style, children, }: DropdownContentProps): import("react/jsx-runtime").JSX.Element | null;
11
+ declare namespace DropdownContentComponent {
12
+ var displayName: string;
13
+ }
14
+ /**
15
+ * Dropdown menu item. Renders a Button internally with ghost variant.
16
+ * When href is provided, renders as an anchor.
17
+ */
18
+ declare function DropdownItemComponent({ onSelect, href, target, disabled, keepOpen, className, children, ...props }: DropdownItemProps & Record<string, unknown>): import("react/jsx-runtime").JSX.Element;
19
+ declare namespace DropdownItemComponent {
20
+ var displayName: string;
21
+ }
22
+ type DropdownCompound = typeof DropdownRoot & {
23
+ Trigger: typeof DropdownTriggerComponent;
24
+ Content: typeof DropdownContentComponent;
25
+ Item: typeof DropdownItemComponent;
26
+ };
27
+ export declare const Dropdown: DropdownCompound;
28
+ export declare const DropdownTrigger: typeof DropdownTriggerComponent;
29
+ export declare const DropdownContent: typeof DropdownContentComponent;
30
+ export declare const DropdownItem: typeof DropdownItemComponent;
31
+ export { useDropdownContext as useDropdown } from './DropdownContext';