@dreamtree-org/twreact-ui 1.2.1 → 1.3.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.
- package/DESIGN.md +118 -0
- package/README.md +231 -44
- package/ai-skills/dreamtree-ui.md +98 -12
- package/dist/ai-schema.json +452 -17
- package/dist/components/blocks/AppShell.d.ts +4 -0
- package/dist/components/blocks/AppShell.d.ts.map +1 -0
- package/dist/components/blocks/ConfirmDialog.d.ts +4 -0
- package/dist/components/blocks/ConfirmDialog.d.ts.map +1 -0
- package/dist/components/blocks/EmptyState.d.ts +4 -0
- package/dist/components/blocks/EmptyState.d.ts.map +1 -0
- package/dist/components/blocks/ErrorState.d.ts +4 -0
- package/dist/components/blocks/ErrorState.d.ts.map +1 -0
- package/dist/components/blocks/LoadingState.d.ts +9 -0
- package/dist/components/blocks/LoadingState.d.ts.map +1 -0
- package/dist/components/blocks/PageHeader.d.ts +4 -0
- package/dist/components/blocks/PageHeader.d.ts.map +1 -0
- package/dist/components/blocks/StatCard.d.ts +4 -0
- package/dist/components/blocks/StatCard.d.ts.map +1 -0
- package/dist/components/blocks/StatusPill.d.ts +5 -0
- package/dist/components/blocks/StatusPill.d.ts.map +1 -0
- package/dist/components/core/Accordion.d.ts.map +1 -1
- package/dist/components/core/Button.d.ts.map +1 -1
- package/dist/components/core/Checkbox.d.ts.map +1 -1
- package/dist/components/core/ColorPicker.d.ts.map +1 -1
- package/dist/components/core/DatePicker.d.ts.map +1 -1
- package/dist/components/core/DateRangePicker.d.ts.map +1 -1
- package/dist/components/core/Form.d.ts.map +1 -1
- package/dist/components/core/Input.d.ts.map +1 -1
- package/dist/components/core/LocationPicker.d.ts.map +1 -1
- package/dist/components/core/Popover.d.ts +4 -0
- package/dist/components/core/Popover.d.ts.map +1 -0
- package/dist/components/core/PriceRangePicker.d.ts.map +1 -1
- package/dist/components/core/ProgressBar.d.ts.map +1 -1
- package/dist/components/core/Radio.d.ts.map +1 -1
- package/dist/components/core/Rate.d.ts.map +1 -1
- package/dist/components/core/Select.d.ts.map +1 -1
- package/dist/components/core/Skeleton.d.ts.map +1 -1
- package/dist/components/core/Slider.d.ts +4 -0
- package/dist/components/core/Slider.d.ts.map +1 -0
- package/dist/components/core/SpeechToText.d.ts.map +1 -1
- package/dist/components/core/Switch.d.ts.map +1 -1
- package/dist/components/core/Table/ActionMenu.d.ts.map +1 -1
- package/dist/components/core/Table/ColumnMenu.d.ts +2 -1
- package/dist/components/core/Table/ColumnMenu.d.ts.map +1 -1
- package/dist/components/core/Table/MobileCard.d.ts +2 -2
- package/dist/components/core/Table/MobileCard.d.ts.map +1 -1
- package/dist/components/core/Table/Table.d.ts.map +1 -1
- package/dist/components/core/Table/TableRow.d.ts +4 -2
- package/dist/components/core/Table/TableRow.d.ts.map +1 -1
- package/dist/components/core/Tabs.d.ts.map +1 -1
- package/dist/components/core/Textarea.d.ts +4 -0
- package/dist/components/core/Textarea.d.ts.map +1 -0
- package/dist/components/core/ThreeDotPopover.d.ts.map +1 -1
- package/dist/components/core/Tooltip.d.ts.map +1 -1
- package/dist/components/feedback/Dialog.d.ts.map +1 -1
- package/dist/components/feedback/Drawer.d.ts +4 -0
- package/dist/components/feedback/Drawer.d.ts.map +1 -0
- package/dist/components/feedback/Toast.d.ts +14 -5
- package/dist/components/feedback/Toast.d.ts.map +1 -1
- package/dist/components/feedback/Tour.d.ts +4 -0
- package/dist/components/feedback/Tour.d.ts.map +1 -0
- package/dist/components/feedback/TourSpotlight.d.ts +9 -0
- package/dist/components/feedback/TourSpotlight.d.ts.map +1 -0
- package/dist/components/navigation/Breadcrumbs.d.ts.map +1 -1
- package/dist/components/navigation/FootNav.d.ts.map +1 -1
- package/dist/components/navigation/Navbar.d.ts.map +1 -1
- package/dist/components/navigation/Sidebar.d.ts +8 -2
- package/dist/components/navigation/Sidebar.d.ts.map +1 -1
- package/dist/components/utility/Badge.d.ts.map +1 -1
- package/dist/components/utility/FileUpload.d.ts.map +1 -1
- package/dist/components/utility/Sortable.d.ts +4 -0
- package/dist/components/utility/Sortable.d.ts.map +1 -0
- package/dist/esm/_vendor/object-assign/index.js +99 -0
- package/dist/esm/_vendor/prop-types/_vendor/react-is/cjs/react-is.development.js +190 -0
- package/dist/esm/_vendor/prop-types/_vendor/react-is/cjs/react-is.production.min.js +26 -0
- package/dist/esm/_vendor/prop-types/_vendor/react-is/index.js +19 -0
- package/dist/esm/_vendor/prop-types/checkPropTypes.js +115 -0
- package/dist/esm/_vendor/prop-types/factoryWithThrowingShims.js +74 -0
- package/dist/esm/_vendor/prop-types/factoryWithTypeCheckers.js +625 -0
- package/dist/esm/_vendor/prop-types/index.js +30 -0
- package/dist/esm/_vendor/prop-types/lib/ReactPropTypesSecret.js +21 -0
- package/dist/esm/_vendor/prop-types/lib/has.js +11 -0
- package/dist/esm/_virtual/_commonjsHelpers.js +5 -0
- package/dist/esm/_virtual/_rollupPluginBabelHelpers.js +329 -0
- package/dist/esm/_virtual/index.js +3 -0
- package/dist/esm/_virtual/index2.js +3 -0
- package/dist/esm/_virtual/react-is.development.js +3 -0
- package/dist/esm/_virtual/react-is.production.min.js +3 -0
- package/dist/esm/components/blocks/AppShell.js +205 -0
- package/dist/esm/components/blocks/ConfirmDialog.js +57 -0
- package/dist/esm/components/blocks/EmptyState.js +44 -0
- package/dist/esm/components/blocks/ErrorState.js +53 -0
- package/dist/esm/components/blocks/LoadingState.js +134 -0
- package/dist/esm/components/blocks/PageHeader.js +51 -0
- package/dist/esm/components/blocks/StatCard.js +79 -0
- package/dist/esm/components/blocks/StatusPill.js +55 -0
- package/dist/esm/components/core/Accordion.js +260 -0
- package/dist/esm/components/core/Button.js +59 -0
- package/dist/esm/components/core/Checkbox.js +188 -0
- package/dist/esm/components/core/ColorPicker.js +348 -0
- package/dist/esm/components/core/DatePicker.js +436 -0
- package/dist/esm/components/core/DateRangePicker.js +494 -0
- package/dist/esm/components/core/Form.js +522 -0
- package/dist/esm/components/core/Input.js +179 -0
- package/dist/esm/components/core/Loader.js +141 -0
- package/dist/esm/components/core/LocationPicker.js +161 -0
- package/dist/esm/components/core/Popover.js +171 -0
- package/dist/esm/components/core/PriceRangePicker.js +376 -0
- package/dist/esm/components/core/ProgressBar.js +152 -0
- package/dist/esm/components/core/Radio.js +156 -0
- package/dist/esm/components/core/Rate.js +197 -0
- package/dist/esm/components/core/RoundedTag.js +118 -0
- package/dist/esm/components/core/Select.js +857 -0
- package/dist/esm/components/core/Skeleton.js +100 -0
- package/dist/esm/components/core/Slider.js +134 -0
- package/dist/esm/components/core/SpeechToText.js +226 -0
- package/dist/esm/components/core/Switch.js +207 -0
- package/dist/esm/components/core/Table/ActionMenu.js +251 -0
- package/dist/esm/components/core/Table/ColumnMenu.js +55 -0
- package/dist/esm/components/core/Table/FieldInput.js +157 -0
- package/dist/esm/components/core/Table/MobileCard.js +187 -0
- package/dist/esm/components/core/Table/MobileFilters.js +72 -0
- package/dist/esm/components/core/Table/Pagination.js +157 -0
- package/dist/esm/components/core/Table/Table.js +1533 -0
- package/dist/esm/components/core/Table/TableRow.js +254 -0
- package/dist/esm/components/core/Table/constants.js +35 -0
- package/dist/esm/components/core/Table/helpers.js +124 -0
- package/dist/esm/components/core/Table/useClickOutside.js +26 -0
- package/dist/esm/components/core/Tabs.js +289 -0
- package/dist/esm/components/core/TextToSpeech.js +52 -0
- package/dist/esm/components/core/Textarea.js +125 -0
- package/dist/esm/components/core/ThreeDotPopover.js +160 -0
- package/dist/esm/components/core/Tooltip.js +372 -0
- package/dist/esm/components/feedback/Alert.js +96 -0
- package/dist/esm/components/feedback/Dialog.js +200 -0
- package/dist/esm/components/feedback/Drawer.js +171 -0
- package/dist/esm/components/feedback/Toast.js +362 -0
- package/dist/esm/components/feedback/Tour.js +214 -0
- package/dist/esm/components/feedback/TourSpotlight.js +71 -0
- package/dist/esm/components/navigation/Breadcrumbs.js +75 -0
- package/dist/esm/components/navigation/Dropdown.js +53 -0
- package/dist/esm/components/navigation/FootNav.js +51 -0
- package/dist/esm/components/navigation/Navbar.js +437 -0
- package/dist/esm/components/navigation/Sidebar.js +567 -0
- package/dist/esm/components/utility/Avatar.js +89 -0
- package/dist/esm/components/utility/Badge.js +47 -0
- package/dist/esm/components/utility/Card.js +85 -0
- package/dist/esm/components/utility/Carousel.js +97 -0
- package/dist/esm/components/utility/Condition.js +9 -0
- package/dist/esm/components/utility/FileUpload.js +177 -0
- package/dist/esm/components/utility/Pagination.js +111 -0
- package/dist/esm/components/utility/Sortable.js +190 -0
- package/dist/esm/components/utility/Stepper.js +101 -0
- package/dist/esm/hooks/useApi.js +169 -0
- package/dist/esm/hooks/useControllableState.js +32 -0
- package/dist/esm/hooks/useFocusTrap.js +85 -0
- package/dist/esm/hooks/useLatestRef.js +20 -0
- package/dist/esm/hooks/useMixins.js +100 -0
- package/dist/esm/hooks/useScrollLock.js +26 -0
- package/dist/esm/hooks/useSliderValues.js +135 -0
- package/dist/esm/hooks/useSortable.js +188 -0
- package/dist/esm/hooks/useTheme.js +53 -0
- package/dist/esm/hooks/useTourTarget.js +92 -0
- package/dist/esm/index.js +65 -0
- package/dist/esm/store/index.js +26 -0
- package/dist/esm/store/store.js +107 -0
- package/dist/esm/store/storeSlice.js +45 -0
- package/dist/esm/utils/cn.js +11 -0
- package/dist/esm/utils/emitter.js +169 -0
- package/dist/esm/utils/helpers.js +161 -0
- package/dist/esm/utils/position.js +134 -0
- package/dist/hooks/useApi.d.ts +2 -1
- package/dist/hooks/useApi.d.ts.map +1 -1
- package/dist/hooks/useControllableState.d.ts +11 -0
- package/dist/hooks/useControllableState.d.ts.map +1 -0
- package/dist/hooks/useFocusTrap.d.ts +15 -0
- package/dist/hooks/useFocusTrap.d.ts.map +1 -0
- package/dist/hooks/useLatestRef.d.ts +8 -0
- package/dist/hooks/useLatestRef.d.ts.map +1 -0
- package/dist/hooks/useMixins.d.ts.map +1 -1
- package/dist/hooks/useScrollLock.d.ts +2 -0
- package/dist/hooks/useScrollLock.d.ts.map +1 -0
- package/dist/hooks/useSliderValues.d.ts +43 -0
- package/dist/hooks/useSliderValues.d.ts.map +1 -0
- package/dist/hooks/useSortable.d.ts +32 -0
- package/dist/hooks/useSortable.d.ts.map +1 -0
- package/dist/hooks/useTheme.d.ts.map +1 -1
- package/dist/hooks/useTourTarget.d.ts +15 -0
- package/dist/hooks/useTourTarget.d.ts.map +1 -0
- package/dist/index.css +1 -1
- package/dist/index.d.ts +55 -39
- package/dist/index.esm.css +1 -1
- package/dist/index.esm.js +7937 -4659
- package/dist/index.js +7950 -4657
- package/dist/tokens/brands/default.css +1 -0
- package/dist/tokens/brands/default.json +5 -0
- package/dist/tokens/brands/practicepro.css +17 -0
- package/dist/tokens/brands/practicepro.json +27 -0
- package/dist/tokens/tailwind3-preset.cjs +214 -0
- package/dist/tokens/theme.css +193 -0
- package/dist/tokens/tokens.json +373 -0
- package/dist/tokens/vars.css +98 -0
- package/dist/types/blocks.d.ts +109 -0
- package/dist/types/blocks.d.ts.map +1 -0
- package/dist/types/index.d.ts +194 -5
- package/dist/types/index.d.ts.map +1 -1
- package/dist/utils/position.d.ts +30 -0
- package/dist/utils/position.d.ts.map +1 -0
- package/doc/README.md +26 -1
- package/mcp/catalog.snapshot.json +1643 -549
- package/package.json +24 -6
- package/tokens/brands/default.json +5 -0
- package/tokens/brands/practicepro.json +27 -0
- package/tokens/lib.cjs +128 -0
- package/tokens/tokens.json +133 -0
|
@@ -0,0 +1,376 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { objectWithoutProperties as _objectWithoutProperties, typeof as _typeof, slicedToArray as _slicedToArray, objectSpread2 as _objectSpread2 } from '../../_virtual/_rollupPluginBabelHelpers.js';
|
|
3
|
+
import { jsxs, jsx, Fragment } from 'react/jsx-runtime';
|
|
4
|
+
import { forwardRef, useState, useEffect, useMemo } from 'react';
|
|
5
|
+
import { cn } from '../../utils/cn.js';
|
|
6
|
+
|
|
7
|
+
var _excluded = ["min", "max", "step", "minGap", "value", "defaultValue", "onChange", "onFinalChange", "showInputs", "showTooltips", "disabled", "presets", "formatValue", "className", "size", "colorClass", "ariaLabel"];
|
|
8
|
+
/**
|
|
9
|
+
* PriceRangeSlider - UI library component (Tailwind)
|
|
10
|
+
*
|
|
11
|
+
* Props
|
|
12
|
+
* - min: number (default 0)
|
|
13
|
+
* - max: number (default 1000)
|
|
14
|
+
* - step: number (default 1)
|
|
15
|
+
* - minGap: number (minimum distance between thumbs, default 5)
|
|
16
|
+
* - value: { min: number, max: number } | null (controlled)
|
|
17
|
+
* - defaultValue: { min: number, max: number } (uncontrolled initial)
|
|
18
|
+
* - onChange: (value) => void
|
|
19
|
+
* - onFinalChange: (value) => void // called on mouseup/touchend or Enter in inputs
|
|
20
|
+
* - showInputs: boolean (default true)
|
|
21
|
+
* - showTooltips: boolean (default true)
|
|
22
|
+
* - disabled: boolean
|
|
23
|
+
* - presets: Array<{ id: string|number, label: string, value: {min:number,max:number} }>
|
|
24
|
+
* - formatValue: (n) => string (formatting callback, default: n => n)
|
|
25
|
+
* - className: string (container custom classes)
|
|
26
|
+
* - size: 'sm' | 'md' | 'lg' (affects thumb size & spacing)
|
|
27
|
+
* - colorClass: Tailwind class for active track/thumb, default 'bg-pink-500'
|
|
28
|
+
* - ariaLabel: string
|
|
29
|
+
*
|
|
30
|
+
* Usage notes
|
|
31
|
+
* - Controlled mode: pass `value` and handle updates via onChange.
|
|
32
|
+
* - Uncontrolled mode: omit `value` and use `defaultValue`.
|
|
33
|
+
*
|
|
34
|
+
* Accessibility
|
|
35
|
+
* - Inputs are labelled and thumbs are keyboard-focusable
|
|
36
|
+
*/
|
|
37
|
+
var PriceRangePicker = /*#__PURE__*/forwardRef(function PriceRangePicker(_ref, ref) {
|
|
38
|
+
var _ref$min = _ref.min,
|
|
39
|
+
min = _ref$min === void 0 ? 0 : _ref$min,
|
|
40
|
+
_ref$max = _ref.max,
|
|
41
|
+
max = _ref$max === void 0 ? 1000 : _ref$max,
|
|
42
|
+
_ref$step = _ref.step,
|
|
43
|
+
step = _ref$step === void 0 ? 1 : _ref$step,
|
|
44
|
+
_ref$minGap = _ref.minGap,
|
|
45
|
+
minGap = _ref$minGap === void 0 ? 5 : _ref$minGap,
|
|
46
|
+
_ref$value = _ref.value,
|
|
47
|
+
value = _ref$value === void 0 ? null : _ref$value,
|
|
48
|
+
_ref$defaultValue = _ref.defaultValue,
|
|
49
|
+
defaultValue = _ref$defaultValue === void 0 ? {
|
|
50
|
+
min: 0,
|
|
51
|
+
max: 1000
|
|
52
|
+
} : _ref$defaultValue,
|
|
53
|
+
_ref$onChange = _ref.onChange,
|
|
54
|
+
onChange = _ref$onChange === void 0 ? function () {} : _ref$onChange,
|
|
55
|
+
_ref$onFinalChange = _ref.onFinalChange,
|
|
56
|
+
onFinalChange = _ref$onFinalChange === void 0 ? function () {} : _ref$onFinalChange,
|
|
57
|
+
_ref$showInputs = _ref.showInputs,
|
|
58
|
+
showInputs = _ref$showInputs === void 0 ? true : _ref$showInputs,
|
|
59
|
+
_ref$showTooltips = _ref.showTooltips,
|
|
60
|
+
showTooltips = _ref$showTooltips === void 0 ? true : _ref$showTooltips,
|
|
61
|
+
_ref$disabled = _ref.disabled,
|
|
62
|
+
disabled = _ref$disabled === void 0 ? false : _ref$disabled,
|
|
63
|
+
_ref$presets = _ref.presets,
|
|
64
|
+
presets = _ref$presets === void 0 ? [] : _ref$presets,
|
|
65
|
+
_ref$formatValue = _ref.formatValue,
|
|
66
|
+
formatValue = _ref$formatValue === void 0 ? function (n) {
|
|
67
|
+
return String(n);
|
|
68
|
+
} : _ref$formatValue,
|
|
69
|
+
_ref$className = _ref.className,
|
|
70
|
+
className = _ref$className === void 0 ? "" : _ref$className,
|
|
71
|
+
_ref$size = _ref.size,
|
|
72
|
+
size = _ref$size === void 0 ? "md" : _ref$size,
|
|
73
|
+
_ref$colorClass = _ref.colorClass,
|
|
74
|
+
colorClass = _ref$colorClass === void 0 ? "bg-pink-500" : _ref$colorClass,
|
|
75
|
+
_ref$ariaLabel = _ref.ariaLabel,
|
|
76
|
+
ariaLabel = _ref$ariaLabel === void 0 ? "Price range" : _ref$ariaLabel,
|
|
77
|
+
rest = _objectWithoutProperties(_ref, _excluded);
|
|
78
|
+
var isControlled = value && _typeof(value) === "object";
|
|
79
|
+
var _useState = useState(isControlled ? value.min : defaultValue.min),
|
|
80
|
+
_useState2 = _slicedToArray(_useState, 2),
|
|
81
|
+
internalMin = _useState2[0],
|
|
82
|
+
setInternalMin = _useState2[1];
|
|
83
|
+
var _useState3 = useState(isControlled ? value.max : defaultValue.max),
|
|
84
|
+
_useState4 = _slicedToArray(_useState3, 2),
|
|
85
|
+
internalMax = _useState4[0],
|
|
86
|
+
setInternalMax = _useState4[1];
|
|
87
|
+
// Inputs mirror state so editing doesn't immediately break constraints
|
|
88
|
+
var _useState5 = useState(internalMin),
|
|
89
|
+
_useState6 = _slicedToArray(_useState5, 2),
|
|
90
|
+
minInput = _useState6[0],
|
|
91
|
+
setMinInput = _useState6[1];
|
|
92
|
+
var _useState7 = useState(internalMax),
|
|
93
|
+
_useState8 = _slicedToArray(_useState7, 2),
|
|
94
|
+
maxInput = _useState8[0],
|
|
95
|
+
setMaxInput = _useState8[1];
|
|
96
|
+
// dragging state
|
|
97
|
+
var _useState9 = useState(false),
|
|
98
|
+
_useState0 = _slicedToArray(_useState9, 2),
|
|
99
|
+
isDragging = _useState0[0],
|
|
100
|
+
setIsDragging = _useState0[1];
|
|
101
|
+
useEffect(function () {
|
|
102
|
+
if (isControlled) {
|
|
103
|
+
setInternalMin(value.min);
|
|
104
|
+
setInternalMax(value.max);
|
|
105
|
+
setMinInput(value.min);
|
|
106
|
+
setMaxInput(value.max);
|
|
107
|
+
}
|
|
108
|
+
}, [value, isControlled]);
|
|
109
|
+
// Update inputs when internal changes (uncontrolled)
|
|
110
|
+
useEffect(function () {
|
|
111
|
+
if (!isControlled) {
|
|
112
|
+
setMinInput(internalMin);
|
|
113
|
+
setMaxInput(internalMax);
|
|
114
|
+
}
|
|
115
|
+
}, [internalMin, internalMax, isControlled]);
|
|
116
|
+
var clamp = function clamp(v) {
|
|
117
|
+
return Math.min(max, Math.max(min, v));
|
|
118
|
+
};
|
|
119
|
+
var setValues = function setValues(next) {
|
|
120
|
+
// next: {min, max}
|
|
121
|
+
// enforce gap and clamp
|
|
122
|
+
var a = clamp(Math.round(next.min / step) * step);
|
|
123
|
+
var b = clamp(Math.round(next.max / step) * step);
|
|
124
|
+
if (b - a < minGap) {
|
|
125
|
+
// push them apart (prefer keeping changed thumb)
|
|
126
|
+
if (next._active === "min") {
|
|
127
|
+
a = clamp(b - minGap);
|
|
128
|
+
} else if (next._active === "max") {
|
|
129
|
+
b = clamp(a + minGap);
|
|
130
|
+
} else {
|
|
131
|
+
// equal distribution
|
|
132
|
+
if (a + minGap <= max) b = a + minGap;else a = b - minGap;
|
|
133
|
+
}
|
|
134
|
+
}
|
|
135
|
+
if (isControlled) {
|
|
136
|
+
onChange({
|
|
137
|
+
min: a,
|
|
138
|
+
max: b
|
|
139
|
+
});
|
|
140
|
+
} else {
|
|
141
|
+
setInternalMin(a);
|
|
142
|
+
setInternalMax(b);
|
|
143
|
+
onChange({
|
|
144
|
+
min: a,
|
|
145
|
+
max: b
|
|
146
|
+
});
|
|
147
|
+
}
|
|
148
|
+
};
|
|
149
|
+
var handleFinal = function handleFinal(next) {
|
|
150
|
+
onFinalChange({
|
|
151
|
+
min: next.min,
|
|
152
|
+
max: next.max
|
|
153
|
+
});
|
|
154
|
+
};
|
|
155
|
+
// Handlers for range inputs
|
|
156
|
+
var handleMinRange = function handleMinRange(e) {
|
|
157
|
+
if (disabled) return;
|
|
158
|
+
var v = parseInt(e.target.value, 10);
|
|
159
|
+
setValues({
|
|
160
|
+
min: v,
|
|
161
|
+
max: isControlled ? value.max : internalMax,
|
|
162
|
+
_active: "min"
|
|
163
|
+
});
|
|
164
|
+
};
|
|
165
|
+
var handleMaxRange = function handleMaxRange(e) {
|
|
166
|
+
if (disabled) return;
|
|
167
|
+
var v = parseInt(e.target.value, 10);
|
|
168
|
+
setValues({
|
|
169
|
+
min: isControlled ? value.min : internalMin,
|
|
170
|
+
max: v,
|
|
171
|
+
_active: "max"
|
|
172
|
+
});
|
|
173
|
+
};
|
|
174
|
+
// Inputs change handlers (number boxes)
|
|
175
|
+
var handleMinInputChange = function handleMinInputChange(e) {
|
|
176
|
+
var raw = e.target.value;
|
|
177
|
+
var parsed = raw === "" ? "" : parseInt(raw, 10);
|
|
178
|
+
setMinInput(parsed);
|
|
179
|
+
};
|
|
180
|
+
var handleMaxInputChange = function handleMaxInputChange(e) {
|
|
181
|
+
var raw = e.target.value;
|
|
182
|
+
var parsed = raw === "" ? "" : parseInt(raw, 10);
|
|
183
|
+
setMaxInput(parsed);
|
|
184
|
+
};
|
|
185
|
+
var commitMinInput = function commitMinInput() {
|
|
186
|
+
var v = minInput === "" ? min : parseInt(minInput, 10);
|
|
187
|
+
v = clamp(v);
|
|
188
|
+
setValues({
|
|
189
|
+
min: v,
|
|
190
|
+
max: isControlled ? value.max : internalMax,
|
|
191
|
+
_active: "min"
|
|
192
|
+
});
|
|
193
|
+
handleFinal({
|
|
194
|
+
min: v,
|
|
195
|
+
max: isControlled ? value.max : internalMax
|
|
196
|
+
});
|
|
197
|
+
};
|
|
198
|
+
var commitMaxInput = function commitMaxInput() {
|
|
199
|
+
var v = maxInput === "" ? max : parseInt(maxInput, 10);
|
|
200
|
+
v = clamp(v);
|
|
201
|
+
setValues({
|
|
202
|
+
min: isControlled ? value.min : internalMin,
|
|
203
|
+
max: v,
|
|
204
|
+
_active: "max"
|
|
205
|
+
});
|
|
206
|
+
handleFinal({
|
|
207
|
+
min: isControlled ? value.min : internalMin,
|
|
208
|
+
max: v
|
|
209
|
+
});
|
|
210
|
+
};
|
|
211
|
+
// Keyboard handling for inputs
|
|
212
|
+
var handleMinInputKey = function handleMinInputKey(e) {
|
|
213
|
+
if (e.key === "Enter") commitMinInput();
|
|
214
|
+
};
|
|
215
|
+
var handleMaxInputKey = function handleMaxInputKey(e) {
|
|
216
|
+
if (e.key === "Enter") commitMaxInput();
|
|
217
|
+
};
|
|
218
|
+
// Dragging helpers
|
|
219
|
+
var startDrag = function startDrag() {
|
|
220
|
+
return setIsDragging(true);
|
|
221
|
+
};
|
|
222
|
+
var stopDrag = function stopDrag() {
|
|
223
|
+
setIsDragging(false);
|
|
224
|
+
handleFinal({
|
|
225
|
+
min: isControlled ? value.min : internalMin,
|
|
226
|
+
max: isControlled ? value.max : internalMax
|
|
227
|
+
});
|
|
228
|
+
};
|
|
229
|
+
var minPercent = useMemo(function () {
|
|
230
|
+
return ((isControlled ? value.min : internalMin) - min) / (max - min) * 100;
|
|
231
|
+
}, [value, internalMin, min, max, isControlled]);
|
|
232
|
+
var maxPercent = useMemo(function () {
|
|
233
|
+
return ((isControlled ? value.max : internalMax) - min) / (max - min) * 100;
|
|
234
|
+
}, [value, internalMax, min, max, isControlled]);
|
|
235
|
+
var thumbSize = size === "sm" ? 16 : size === "lg" ? 28 : 22;
|
|
236
|
+
var inputWidth = size === "sm" ? "w-12" : size === "lg" ? "w-20" : "w-14";
|
|
237
|
+
var trackHeight = size === "sm" ? "h-1" : size === "lg" ? "h-2" : "h-1.5";
|
|
238
|
+
// Preset helper
|
|
239
|
+
var applyPreset = function applyPreset(p) {
|
|
240
|
+
if (!p || !p.value) return;
|
|
241
|
+
var _p$value = p.value,
|
|
242
|
+
pmin = _p$value.min,
|
|
243
|
+
pmax = _p$value.max;
|
|
244
|
+
setValues({
|
|
245
|
+
min: pmin,
|
|
246
|
+
max: pmax
|
|
247
|
+
});
|
|
248
|
+
handleFinal({
|
|
249
|
+
min: pmin,
|
|
250
|
+
max: pmax
|
|
251
|
+
});
|
|
252
|
+
};
|
|
253
|
+
return jsxs("div", _objectSpread2(_objectSpread2({
|
|
254
|
+
ref: ref,
|
|
255
|
+
className: cn("bg-white rounded-lg p-4 w-full max-w-lg", className)
|
|
256
|
+
}, rest), {}, {
|
|
257
|
+
children: [jsxs("div", {
|
|
258
|
+
className: "flex items-center justify-between",
|
|
259
|
+
children: [showInputs ? jsxs("div", {
|
|
260
|
+
className: "flex items-center gap-2 w-full",
|
|
261
|
+
children: [jsx("div", {
|
|
262
|
+
className: "flex-1",
|
|
263
|
+
children: jsx("input", {
|
|
264
|
+
type: "number",
|
|
265
|
+
"aria-label": "Minimum",
|
|
266
|
+
value: minInput,
|
|
267
|
+
onChange: handleMinInputChange,
|
|
268
|
+
onBlur: commitMinInput,
|
|
269
|
+
onKeyDown: handleMinInputKey,
|
|
270
|
+
className: "".concat(inputWidth, " py-2 border border-gray-300 rounded-md text-center text-sm disabled:opacity-50"),
|
|
271
|
+
min: min,
|
|
272
|
+
max: max,
|
|
273
|
+
disabled: disabled
|
|
274
|
+
})
|
|
275
|
+
}), jsx("div", {
|
|
276
|
+
className: "text-xs text-primary-500",
|
|
277
|
+
children: "\u2014"
|
|
278
|
+
}), jsx("div", {
|
|
279
|
+
className: "flex-1 flex justify-end",
|
|
280
|
+
children: jsx("input", {
|
|
281
|
+
type: "number",
|
|
282
|
+
"aria-label": "Maximum",
|
|
283
|
+
value: maxInput,
|
|
284
|
+
onChange: handleMaxInputChange,
|
|
285
|
+
onBlur: commitMaxInput,
|
|
286
|
+
onKeyDown: handleMaxInputKey,
|
|
287
|
+
className: "".concat(inputWidth, " py-2 border border-gray-300 rounded-md text-center text-sm disabled:opacity-50"),
|
|
288
|
+
min: min,
|
|
289
|
+
max: max,
|
|
290
|
+
disabled: disabled
|
|
291
|
+
})
|
|
292
|
+
})]
|
|
293
|
+
}) : jsxs("div", {
|
|
294
|
+
className: "text-sm",
|
|
295
|
+
children: [formatValue(isControlled ? value.min : internalMin), " - ", formatValue(isControlled ? value.max : internalMax)]
|
|
296
|
+
}), presets && presets.length > 0 && jsx("div", {
|
|
297
|
+
className: "ml-4 flex gap-2",
|
|
298
|
+
children: presets.map(function (p) {
|
|
299
|
+
return jsx("button", {
|
|
300
|
+
type: "button",
|
|
301
|
+
onClick: function onClick() {
|
|
302
|
+
return applyPreset(p);
|
|
303
|
+
},
|
|
304
|
+
className: "text-xs px-2 py-1 border rounded-md hover:bg-gray-50 disabled:opacity-50",
|
|
305
|
+
disabled: disabled,
|
|
306
|
+
children: p.label
|
|
307
|
+
}, p.id);
|
|
308
|
+
})
|
|
309
|
+
})]
|
|
310
|
+
}), jsxs("div", {
|
|
311
|
+
className: "relative w-full mt-4 ".concat(trackHeight, " bg-gray-300 rounded-full"),
|
|
312
|
+
children: [jsx("div", {
|
|
313
|
+
className: "absolute ".concat(trackHeight, " rounded-full ").concat(colorClass),
|
|
314
|
+
style: {
|
|
315
|
+
left: "".concat(minPercent, "%"),
|
|
316
|
+
right: "".concat(100 - maxPercent, "%")
|
|
317
|
+
}
|
|
318
|
+
}), jsx("input", {
|
|
319
|
+
type: "range",
|
|
320
|
+
min: min,
|
|
321
|
+
max: max,
|
|
322
|
+
step: step,
|
|
323
|
+
value: isControlled ? value.min : internalMin,
|
|
324
|
+
onChange: handleMinRange,
|
|
325
|
+
onMouseDown: startDrag,
|
|
326
|
+
onMouseUp: stopDrag,
|
|
327
|
+
onTouchStart: startDrag,
|
|
328
|
+
onTouchEnd: stopDrag,
|
|
329
|
+
disabled: disabled,
|
|
330
|
+
"aria-label": "".concat(ariaLabel, " - min"),
|
|
331
|
+
className: "absolute inset-0 w-full appearance-none bg-transparent pointer-events-auto",
|
|
332
|
+
style: {
|
|
333
|
+
zIndex: 20
|
|
334
|
+
}
|
|
335
|
+
}), jsx("input", {
|
|
336
|
+
type: "range",
|
|
337
|
+
min: min,
|
|
338
|
+
max: max,
|
|
339
|
+
step: step,
|
|
340
|
+
value: isControlled ? value.max : internalMax,
|
|
341
|
+
onChange: handleMaxRange,
|
|
342
|
+
onMouseDown: startDrag,
|
|
343
|
+
onMouseUp: stopDrag,
|
|
344
|
+
onTouchStart: startDrag,
|
|
345
|
+
onTouchEnd: stopDrag,
|
|
346
|
+
disabled: disabled,
|
|
347
|
+
"aria-label": "".concat(ariaLabel, " - max"),
|
|
348
|
+
className: "absolute inset-0 w-full appearance-none bg-transparent pointer-events-auto",
|
|
349
|
+
style: {
|
|
350
|
+
zIndex: 10
|
|
351
|
+
}
|
|
352
|
+
}), showTooltips && isDragging && jsxs(Fragment, {
|
|
353
|
+
children: [jsx("div", {
|
|
354
|
+
className: "absolute -top-9 text-xs bg-white px-2 py-1 rounded-md shadow-sm border",
|
|
355
|
+
style: {
|
|
356
|
+
left: "".concat(minPercent, "%"),
|
|
357
|
+
transform: "translateX(-50%)"
|
|
358
|
+
},
|
|
359
|
+
children: formatValue(isControlled ? value.min : internalMin)
|
|
360
|
+
}), jsx("div", {
|
|
361
|
+
className: "absolute -top-9 text-xs bg-white px-2 py-1 rounded-md shadow-sm border",
|
|
362
|
+
style: {
|
|
363
|
+
left: "".concat(maxPercent, "%"),
|
|
364
|
+
transform: "translateX(-50%)"
|
|
365
|
+
},
|
|
366
|
+
children: formatValue(isControlled ? value.max : internalMax)
|
|
367
|
+
})]
|
|
368
|
+
})]
|
|
369
|
+
}), jsx("style", {
|
|
370
|
+
children: "\n input[type=range] { -webkit-appearance: none; appearance: none; background: transparent; }\n input[type=range]::-webkit-slider-runnable-track { height: 6px; background: transparent; }\n input[type=range]::-moz-range-track { height: 6px; background: transparent; }\n\n input[type=range]::-webkit-slider-thumb {\n -webkit-appearance: none;\n appearance: none;\n height: ".concat(thumbSize, "px;\n width: ").concat(thumbSize, "px;\n border-radius: 9999px;\n border: 3px solid #ffffff;\n background: #ff6b6b;\n box-shadow: 0 2px 8px rgba(0,0,0,0.12);\n cursor: pointer;\n margin-top: -").concat(Math.round(thumbSize / 2 - 6), "px; /* vertical centering tweak */\n position: relative;\n }\n\n input[type=range]::-moz-range-thumb {\n height: ").concat(thumbSize, "px;\n width: ").concat(thumbSize, "px;\n border-radius: 9999px;\n border: 3px solid #ffffff;\n background: #ff6b6b;\n box-shadow: 0 2px 8px rgba(0,0,0,0.12);\n cursor: pointer;\n position: relative;\n }\n\n /* Make the track invisible so our styled track shows through */\n input[type=range]::-webkit-slider-runnable-track { background: transparent; }\n input[type=range]::-moz-range-track { background: transparent; }\n\n ")
|
|
371
|
+
})]
|
|
372
|
+
}));
|
|
373
|
+
});
|
|
374
|
+
PriceRangePicker.displayName = "PriceRangePicker";
|
|
375
|
+
|
|
376
|
+
export { PriceRangePicker as default };
|
|
@@ -0,0 +1,152 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { objectWithoutProperties as _objectWithoutProperties, objectSpread2 as _objectSpread2 } from '../../_virtual/_rollupPluginBabelHelpers.js';
|
|
3
|
+
import { jsxs, jsx } from 'react/jsx-runtime';
|
|
4
|
+
import { forwardRef } from 'react';
|
|
5
|
+
import { cn } from '../../utils/cn.js';
|
|
6
|
+
|
|
7
|
+
var _excluded = ["value", "max", "size", "showValue", "rounded", "color", "bgColor", "valueColor", "striped", "animated", "label", "ariaLabel", "className", "style"];
|
|
8
|
+
// ProgressBar. Without colour props it uses the primary token classes, so it follows the brand (STUDIO-59).
|
|
9
|
+
// color, bgColor and valueColor still accept HEX for backwards compatibility (deprecated).
|
|
10
|
+
var SIZE_MAP = {
|
|
11
|
+
xs: "h-1",
|
|
12
|
+
sm: "h-2",
|
|
13
|
+
md: "h-3",
|
|
14
|
+
lg: "h-5"
|
|
15
|
+
};
|
|
16
|
+
function isHexColor(str) {
|
|
17
|
+
return typeof str === "string" && /^#([0-9A-F]{3}){1,2}$/i.test(str);
|
|
18
|
+
}
|
|
19
|
+
function hexToRgb(hex) {
|
|
20
|
+
if (!isHexColor(hex)) return null;
|
|
21
|
+
var h = hex.replace('#', '');
|
|
22
|
+
if (h.length === 3) h = h.split('').map(function (ch) {
|
|
23
|
+
return ch + ch;
|
|
24
|
+
}).join('');
|
|
25
|
+
var bigint = parseInt(h, 16);
|
|
26
|
+
return {
|
|
27
|
+
r: bigint >> 16 & 255,
|
|
28
|
+
g: bigint >> 8 & 255,
|
|
29
|
+
b: bigint & 255
|
|
30
|
+
};
|
|
31
|
+
}
|
|
32
|
+
function luminance(hex) {
|
|
33
|
+
var rgb = hexToRgb(hex);
|
|
34
|
+
if (!rgb) return 0;
|
|
35
|
+
// relative luminance
|
|
36
|
+
var srgb = [rgb.r, rgb.g, rgb.b].map(function (v) {
|
|
37
|
+
var s = v / 255;
|
|
38
|
+
return s <= 0.03928 ? s / 12.92 : Math.pow((s + 0.055) / 1.055, 2.4);
|
|
39
|
+
});
|
|
40
|
+
return 0.2126 * srgb[0] + 0.7152 * srgb[1] + 0.0722 * srgb[2];
|
|
41
|
+
}
|
|
42
|
+
function readableTextColor(bgHex, preferred) {
|
|
43
|
+
// If preferred is provided and valid, use it; otherwise pick black/white based on contrast
|
|
44
|
+
if (isHexColor(preferred)) return preferred;
|
|
45
|
+
var L = luminance(bgHex);
|
|
46
|
+
// WCAG suggests threshold around 0.179 for black/white contrast — we'll use 0.179
|
|
47
|
+
return L > 0.179 ? '#000000' : '#ffffff';
|
|
48
|
+
}
|
|
49
|
+
var ProgressBar = /*#__PURE__*/forwardRef(function ProgressBar(_ref, ref) {
|
|
50
|
+
var _SIZE_MAP$size;
|
|
51
|
+
var _ref$value = _ref.value,
|
|
52
|
+
value = _ref$value === void 0 ? 0 : _ref$value,
|
|
53
|
+
_ref$max = _ref.max,
|
|
54
|
+
max = _ref$max === void 0 ? 100 : _ref$max,
|
|
55
|
+
_ref$size = _ref.size,
|
|
56
|
+
size = _ref$size === void 0 ? 'md' : _ref$size,
|
|
57
|
+
_ref$showValue = _ref.showValue,
|
|
58
|
+
showValue = _ref$showValue === void 0 ? false : _ref$showValue,
|
|
59
|
+
_ref$rounded = _ref.rounded,
|
|
60
|
+
rounded = _ref$rounded === void 0 ? true : _ref$rounded,
|
|
61
|
+
_ref$color = _ref.color,
|
|
62
|
+
color = _ref$color === void 0 ? undefined : _ref$color,
|
|
63
|
+
_ref$bgColor = _ref.bgColor,
|
|
64
|
+
bgColor = _ref$bgColor === void 0 ? undefined : _ref$bgColor,
|
|
65
|
+
_ref$valueColor = _ref.valueColor,
|
|
66
|
+
valueColor = _ref$valueColor === void 0 ? undefined : _ref$valueColor,
|
|
67
|
+
_ref$striped = _ref.striped,
|
|
68
|
+
striped = _ref$striped === void 0 ? false : _ref$striped,
|
|
69
|
+
_ref$animated = _ref.animated,
|
|
70
|
+
animated = _ref$animated === void 0 ? false : _ref$animated,
|
|
71
|
+
_ref$label = _ref.label,
|
|
72
|
+
label = _ref$label === void 0 ? '' : _ref$label,
|
|
73
|
+
_ref$ariaLabel = _ref.ariaLabel,
|
|
74
|
+
ariaLabel = _ref$ariaLabel === void 0 ? 'Progress' : _ref$ariaLabel,
|
|
75
|
+
_ref$className = _ref.className,
|
|
76
|
+
className = _ref$className === void 0 ? '' : _ref$className,
|
|
77
|
+
_ref$style = _ref.style,
|
|
78
|
+
style = _ref$style === void 0 ? {} : _ref$style,
|
|
79
|
+
rest = _objectWithoutProperties(_ref, _excluded);
|
|
80
|
+
var safeMax = typeof max === 'number' && max > 0 ? max : 100;
|
|
81
|
+
var safeValue = typeof value === 'number' ? value : 0;
|
|
82
|
+
var clamped = Math.max(0, Math.min(safeValue, safeMax));
|
|
83
|
+
var percent = safeMax === 0 ? 0 : clamped / safeMax * 100;
|
|
84
|
+
// A valid HEX override is applied inline; anything else falls back to the token classes.
|
|
85
|
+
var fillHex = isHexColor(color) ? color : null;
|
|
86
|
+
var trackHex = isHexColor(bgColor) ? bgColor : null;
|
|
87
|
+
var textHex = isHexColor(valueColor) ? valueColor : fillHex ? readableTextColor(fillHex, undefined) : null;
|
|
88
|
+
var fillClass = fillHex ? '' : 'bg-primary-600';
|
|
89
|
+
var trackClass = trackHex ? '' : 'bg-primary-100';
|
|
90
|
+
var textClass = textHex ? '' : 'text-white';
|
|
91
|
+
// height class or inline style
|
|
92
|
+
var heightClass = typeof size === 'number' ? '' : (_SIZE_MAP$size = SIZE_MAP[size]) !== null && _SIZE_MAP$size !== void 0 ? _SIZE_MAP$size : SIZE_MAP['md'];
|
|
93
|
+
var heightStyle = typeof size === 'number' ? {
|
|
94
|
+
height: "".concat(size, "px")
|
|
95
|
+
} : {};
|
|
96
|
+
var radiusClass = rounded ? 'rounded-full' : 'rounded-sm';
|
|
97
|
+
var trackRadiusClass = rounded ? 'rounded-full' : 'rounded-sm';
|
|
98
|
+
// stripe background
|
|
99
|
+
var stripeStyle = striped ? {
|
|
100
|
+
backgroundImage: "repeating-linear-gradient(45deg, rgba(255,255,255,0.12) 0, rgba(255,255,255,0.12) 10px, transparent 10px, transparent 20px)",
|
|
101
|
+
backgroundSize: '20px 20px',
|
|
102
|
+
overflow: 'hidden'
|
|
103
|
+
} : {};
|
|
104
|
+
var animatedStyle = animated ? {
|
|
105
|
+
animation: 'stripeShift 1s linear infinite'
|
|
106
|
+
} : {};
|
|
107
|
+
var finalFillStyle = _objectSpread2(_objectSpread2(_objectSpread2(_objectSpread2(_objectSpread2({
|
|
108
|
+
width: "".concat(percent, "%")
|
|
109
|
+
}, fillHex ? {
|
|
110
|
+
backgroundColor: fillHex
|
|
111
|
+
} : {}), textHex ? {
|
|
112
|
+
color: textHex
|
|
113
|
+
} : {}), stripeStyle), animatedStyle), {}, {
|
|
114
|
+
transition: 'width 300ms ease-out'
|
|
115
|
+
});
|
|
116
|
+
return jsxs("div", _objectSpread2(_objectSpread2({
|
|
117
|
+
ref: ref,
|
|
118
|
+
className: cn("w-full", className),
|
|
119
|
+
style: style
|
|
120
|
+
}, rest), {}, {
|
|
121
|
+
children: [jsx("style", {
|
|
122
|
+
children: "@keyframes stripeShift { 0% { background-position: 0 0; } 100% { background-position: 40px 0; } }"
|
|
123
|
+
}), label ? jsx("div", {
|
|
124
|
+
className: "mb-2 text-sm font-medium",
|
|
125
|
+
children: label
|
|
126
|
+
}) : null, jsx("div", {
|
|
127
|
+
className: cn('w-full relative overflow-hidden', trackRadiusClass, trackClass),
|
|
128
|
+
style: _objectSpread2(_objectSpread2({}, trackHex ? {
|
|
129
|
+
backgroundColor: trackHex
|
|
130
|
+
} : {}), heightStyle),
|
|
131
|
+
role: "progressbar",
|
|
132
|
+
"aria-label": ariaLabel,
|
|
133
|
+
"aria-valuemin": 0,
|
|
134
|
+
"aria-valuemax": safeMax,
|
|
135
|
+
"aria-valuenow": clamped,
|
|
136
|
+
children: jsx("div", {
|
|
137
|
+
className: cn(radiusClass, heightClass, fillClass, textClass, 'flex items-center justify-center text-sm font-medium'),
|
|
138
|
+
style: finalFillStyle,
|
|
139
|
+
children: showValue ? jsxs("div", {
|
|
140
|
+
className: "px-2 whitespace-nowrap truncate",
|
|
141
|
+
style: textHex ? {
|
|
142
|
+
color: textHex
|
|
143
|
+
} : undefined,
|
|
144
|
+
children: [Math.round(percent), "%"]
|
|
145
|
+
}) : null
|
|
146
|
+
})
|
|
147
|
+
})]
|
|
148
|
+
}));
|
|
149
|
+
});
|
|
150
|
+
ProgressBar.displayName = "ProgressBar";
|
|
151
|
+
|
|
152
|
+
export { ProgressBar as default };
|
|
@@ -0,0 +1,156 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { objectWithoutProperties as _objectWithoutProperties, slicedToArray as _slicedToArray, objectSpread2 as _objectSpread2 } from '../../_virtual/_rollupPluginBabelHelpers.js';
|
|
3
|
+
import { jsxs, jsx } from 'react/jsx-runtime';
|
|
4
|
+
import { forwardRef, useId, useState } from 'react';
|
|
5
|
+
import PropTypes from '../../_vendor/prop-types/index.js';
|
|
6
|
+
|
|
7
|
+
var _excluded = ["id", "name", "value", "checked", "defaultChecked", "onChange", "disabled", "required", "label", "size", "labelPosition", "radioColor", "className", "ariaLabel"];
|
|
8
|
+
var cn = function cn() {
|
|
9
|
+
for (var _len = arguments.length, vals = new Array(_len), _key = 0; _key < _len; _key++) {
|
|
10
|
+
vals[_key] = arguments[_key];
|
|
11
|
+
}
|
|
12
|
+
return vals.filter(Boolean).join(" ");
|
|
13
|
+
};
|
|
14
|
+
var SIZE_MAP = {
|
|
15
|
+
sm: {
|
|
16
|
+
outer: "h-4 w-4",
|
|
17
|
+
dot: "w-2.5 h-2.5",
|
|
18
|
+
label: "text-sm"
|
|
19
|
+
},
|
|
20
|
+
md: {
|
|
21
|
+
outer: "h-5 w-5",
|
|
22
|
+
dot: "w-3 h-3",
|
|
23
|
+
label: "text-base"
|
|
24
|
+
},
|
|
25
|
+
lg: {
|
|
26
|
+
outer: "h-6 w-6",
|
|
27
|
+
dot: "w-3.5 h-3.5",
|
|
28
|
+
label: "text-base"
|
|
29
|
+
}
|
|
30
|
+
};
|
|
31
|
+
var Radio = /*#__PURE__*/forwardRef(function Radio(_ref, ref) {
|
|
32
|
+
var id = _ref.id,
|
|
33
|
+
name = _ref.name,
|
|
34
|
+
value = _ref.value,
|
|
35
|
+
checked = _ref.checked,
|
|
36
|
+
defaultChecked = _ref.defaultChecked,
|
|
37
|
+
onChange = _ref.onChange,
|
|
38
|
+
_ref$disabled = _ref.disabled,
|
|
39
|
+
disabled = _ref$disabled === void 0 ? false : _ref$disabled,
|
|
40
|
+
_ref$required = _ref.required,
|
|
41
|
+
required = _ref$required === void 0 ? false : _ref$required,
|
|
42
|
+
label = _ref.label,
|
|
43
|
+
_ref$size = _ref.size,
|
|
44
|
+
size = _ref$size === void 0 ? "md" : _ref$size,
|
|
45
|
+
_ref$labelPosition = _ref.labelPosition,
|
|
46
|
+
labelPosition = _ref$labelPosition === void 0 ? "right" : _ref$labelPosition,
|
|
47
|
+
radioColor = _ref.radioColor,
|
|
48
|
+
_ref$className = _ref.className,
|
|
49
|
+
className = _ref$className === void 0 ? "" : _ref$className,
|
|
50
|
+
ariaLabel = _ref.ariaLabel,
|
|
51
|
+
props = _objectWithoutProperties(_ref, _excluded);
|
|
52
|
+
var autoId = useId();
|
|
53
|
+
var inputId = id || "".concat(autoId, "-radio");
|
|
54
|
+
var accentColor = radioColor || "blue";
|
|
55
|
+
var _useState = useState(!!defaultChecked),
|
|
56
|
+
_useState2 = _slicedToArray(_useState, 2),
|
|
57
|
+
internalChecked = _useState2[0],
|
|
58
|
+
setInternalChecked = _useState2[1];
|
|
59
|
+
// Reset to `defaultChecked` when it (or controlled-ness) changes
|
|
60
|
+
// (adjust-during-render pattern).
|
|
61
|
+
var _useState3 = useState({
|
|
62
|
+
defaultChecked: defaultChecked,
|
|
63
|
+
checked: checked
|
|
64
|
+
}),
|
|
65
|
+
_useState4 = _slicedToArray(_useState3, 2),
|
|
66
|
+
prevProps = _useState4[0],
|
|
67
|
+
setPrevProps = _useState4[1];
|
|
68
|
+
if (prevProps.defaultChecked !== defaultChecked || prevProps.checked !== checked) {
|
|
69
|
+
setPrevProps({
|
|
70
|
+
defaultChecked: defaultChecked,
|
|
71
|
+
checked: checked
|
|
72
|
+
});
|
|
73
|
+
if (checked === undefined) setInternalChecked(!!defaultChecked);
|
|
74
|
+
}
|
|
75
|
+
var isChecked = checked !== undefined ? checked : internalChecked;
|
|
76
|
+
function handleChange(e) {
|
|
77
|
+
if (checked === undefined) setInternalChecked(e.target.checked);
|
|
78
|
+
if (typeof onChange === "function") onChange(e);
|
|
79
|
+
}
|
|
80
|
+
var sizeClasses = SIZE_MAP[size] || SIZE_MAP.md;
|
|
81
|
+
var showLabelLeft = label && labelPosition === "left";
|
|
82
|
+
return jsxs("label", {
|
|
83
|
+
htmlFor: inputId,
|
|
84
|
+
className: cn("relative inline-flex items-center select-none gap-2", disabled ? "opacity-50 cursor-not-allowed" : "cursor-pointer", className),
|
|
85
|
+
"aria-disabled": disabled ? "true" : undefined,
|
|
86
|
+
children: [showLabelLeft && jsxs("span", {
|
|
87
|
+
className: cn(sizeClasses.label, "leading-none", disabled && "text-primary-400"),
|
|
88
|
+
children: [label, required ? jsx("span", {
|
|
89
|
+
"aria-hidden": "true",
|
|
90
|
+
children: " *"
|
|
91
|
+
}) : null]
|
|
92
|
+
}), jsx("input", _objectSpread2({
|
|
93
|
+
ref: ref,
|
|
94
|
+
id: inputId,
|
|
95
|
+
type: "radio",
|
|
96
|
+
name: name,
|
|
97
|
+
value: value,
|
|
98
|
+
checked: checked,
|
|
99
|
+
defaultChecked: defaultChecked,
|
|
100
|
+
onChange: handleChange,
|
|
101
|
+
disabled: disabled,
|
|
102
|
+
required: required,
|
|
103
|
+
"aria-label": ariaLabel,
|
|
104
|
+
className: "absolute inset-0 w-full h-full opacity-0 appearance-none m-0 z-10 cursor-pointer"
|
|
105
|
+
}, props)), jsx("span", {
|
|
106
|
+
"aria-hidden": true,
|
|
107
|
+
className: cn("inline-flex items-center justify-center rounded-full transition-all"),
|
|
108
|
+
style: {
|
|
109
|
+
"--radio-accent": accentColor
|
|
110
|
+
},
|
|
111
|
+
children: jsx("span", {
|
|
112
|
+
className: cn("flex items-center justify-center rounded-full border transition-colors duration-150 ease-in-out border-slate-300", sizeClasses.outer, disabled ? "bg-slate-100" : "bg-white", isChecked ? "shadow-inner" : ""),
|
|
113
|
+
children: jsx("span", {
|
|
114
|
+
"aria-hidden": true,
|
|
115
|
+
className: cn("rounded-full transform transition-all duration-200 ease-out", sizeClasses.dot),
|
|
116
|
+
style: {
|
|
117
|
+
backgroundColor: isChecked ? accentColor : "transparent",
|
|
118
|
+
opacity: isChecked ? 1 : 0,
|
|
119
|
+
transform: isChecked ? "scale(1)" : "scale(0.7)"
|
|
120
|
+
}
|
|
121
|
+
})
|
|
122
|
+
})
|
|
123
|
+
}), !showLabelLeft && label && jsxs("span", {
|
|
124
|
+
className: cn(sizeClasses.label, "leading-none", disabled && "text-primary-400"),
|
|
125
|
+
children: [label, required ? jsx("span", {
|
|
126
|
+
"aria-hidden": "true",
|
|
127
|
+
children: " *"
|
|
128
|
+
}) : null]
|
|
129
|
+
})]
|
|
130
|
+
});
|
|
131
|
+
});
|
|
132
|
+
Radio.propTypes = {
|
|
133
|
+
id: PropTypes.string,
|
|
134
|
+
name: PropTypes.string,
|
|
135
|
+
value: PropTypes.oneOfType([PropTypes.string, PropTypes.number]),
|
|
136
|
+
checked: PropTypes.bool,
|
|
137
|
+
defaultChecked: PropTypes.bool,
|
|
138
|
+
onChange: PropTypes.func,
|
|
139
|
+
disabled: PropTypes.bool,
|
|
140
|
+
required: PropTypes.bool,
|
|
141
|
+
label: PropTypes.node,
|
|
142
|
+
size: PropTypes.oneOf(["sm", "md", "lg"]),
|
|
143
|
+
labelPosition: PropTypes.oneOf(["left", "right"]),
|
|
144
|
+
radioColor: PropTypes.string,
|
|
145
|
+
backgroundColor: PropTypes.string,
|
|
146
|
+
className: PropTypes.string,
|
|
147
|
+
ariaLabel: PropTypes.string
|
|
148
|
+
};
|
|
149
|
+
Radio.defaultProps = {
|
|
150
|
+
size: "md",
|
|
151
|
+
labelPosition: "right",
|
|
152
|
+
disabled: false,
|
|
153
|
+
required: false
|
|
154
|
+
};
|
|
155
|
+
|
|
156
|
+
export { Radio as default };
|