@dreamtree-org/twreact-ui 1.3.10 → 2.0.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.
- package/README.md +70 -6
- package/ai-skills/dreamtree-ui.md +58 -15
- package/codemods/v2.cjs +198 -0
- package/dist/ai-schema.json +745 -53
- package/dist/charts/index.js +195 -66
- package/dist/components/blocks/AppShell.d.ts.map +1 -1
- package/dist/components/blocks/BottomActionBar.d.ts +6 -0
- package/dist/components/blocks/BottomActionBar.d.ts.map +1 -0
- package/dist/components/blocks/ConfirmDialog.d.ts.map +1 -1
- package/dist/components/blocks/PageHeader.d.ts.map +1 -1
- package/dist/components/charts/CartesianChart.d.ts.map +1 -1
- package/dist/components/charts/ChartFrame.d.ts.map +1 -1
- package/dist/components/charts/useChartLayout.d.ts +25 -0
- package/dist/components/charts/useChartLayout.d.ts.map +1 -0
- 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/Loader.d.ts.map +1 -1
- package/dist/components/core/LocationPicker.d.ts.map +1 -1
- package/dist/components/core/Popover.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/RoundedTag.d.ts.map +1 -1
- package/dist/components/core/SearchField.d.ts +9 -0
- package/dist/components/core/SearchField.d.ts.map +1 -0
- package/dist/components/core/SegmentedControl.d.ts +8 -0
- package/dist/components/core/SegmentedControl.d.ts.map +1 -0
- 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.map +1 -1
- package/dist/components/core/SpeechToText.d.ts.map +1 -1
- package/dist/components/core/SwipeableListItem.d.ts +4 -0
- package/dist/components/core/SwipeableListItem.d.ts.map +1 -0
- package/dist/components/core/SwipeableListItemGesture.d.ts +58 -0
- package/dist/components/core/SwipeableListItemGesture.d.ts.map +1 -0
- package/dist/components/core/Switch.d.ts.map +1 -1
- package/dist/components/core/Table/ActionMenu.d.ts +10 -3
- package/dist/components/core/Table/ActionMenu.d.ts.map +1 -1
- package/dist/components/core/Table/MobileCard.d.ts +10 -1
- package/dist/components/core/Table/MobileCard.d.ts.map +1 -1
- package/dist/components/core/Table/MobileFilters.d.ts +8 -2
- package/dist/components/core/Table/MobileFilters.d.ts.map +1 -1
- package/dist/components/core/Table/Table.d.ts.map +1 -1
- package/dist/components/core/Table/TableRow.d.ts +2 -1
- package/dist/components/core/Table/TableRow.d.ts.map +1 -1
- package/dist/components/core/Tabs.d.ts +5 -8
- package/dist/components/core/Tabs.d.ts.map +1 -1
- package/dist/components/core/Textarea.d.ts.map +1 -1
- package/dist/components/core/ThreeDotPopover.d.ts +10 -22
- package/dist/components/core/ThreeDotPopover.d.ts.map +1 -1
- package/dist/components/core/Tooltip.d.ts +2 -1
- package/dist/components/core/Tooltip.d.ts.map +1 -1
- package/dist/components/core/internal/Calendar.d.ts +77 -0
- package/dist/components/core/internal/Calendar.d.ts.map +1 -0
- package/dist/components/core/menu/ActionMenuSurface.d.ts +42 -0
- package/dist/components/core/menu/ActionMenuSurface.d.ts.map +1 -0
- package/dist/components/core/menu/ActionSheetMenu.d.ts +17 -0
- package/dist/components/core/menu/ActionSheetMenu.d.ts.map +1 -0
- package/dist/components/core/menu/MenuPopover.d.ts +21 -0
- package/dist/components/core/menu/MenuPopover.d.ts.map +1 -0
- package/dist/components/core/menu/menuItems.d.ts +21 -0
- package/dist/components/core/menu/menuItems.d.ts.map +1 -0
- package/dist/components/core/menu/menuKeyboard.d.ts +16 -0
- package/dist/components/core/menu/menuKeyboard.d.ts.map +1 -0
- package/dist/components/feedback/ActionSheet.d.ts +4 -0
- package/dist/components/feedback/ActionSheet.d.ts.map +1 -0
- package/dist/components/feedback/Alert.d.ts.map +1 -1
- package/dist/components/feedback/Dialog.d.ts.map +1 -1
- package/dist/components/feedback/Drawer.d.ts.map +1 -1
- package/dist/components/feedback/Sheet.d.ts +4 -0
- package/dist/components/feedback/Sheet.d.ts.map +1 -0
- package/dist/components/feedback/Toast.d.ts +4 -3
- package/dist/components/feedback/Toast.d.ts.map +1 -1
- package/dist/components/feedback/ToastItem.d.ts +47 -0
- package/dist/components/feedback/ToastItem.d.ts.map +1 -0
- package/dist/components/feedback/ToastStack.d.ts +20 -0
- package/dist/components/feedback/ToastStack.d.ts.map +1 -0
- package/dist/components/feedback/ToastSwipe.d.ts +22 -0
- package/dist/components/feedback/ToastSwipe.d.ts.map +1 -0
- package/dist/components/feedback/Tour.d.ts.map +1 -1
- package/dist/components/feedback/sheetCore.d.ts +30 -0
- package/dist/components/feedback/sheetCore.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 +6 -0
- package/dist/components/navigation/Sidebar.d.ts.map +1 -1
- package/dist/components/rich-text/RichTextEditor.d.ts.map +1 -1
- package/dist/components/rich-text/RichTextToolbar.d.ts +6 -2
- package/dist/components/rich-text/RichTextToolbar.d.ts.map +1 -1
- package/dist/components/utility/Avatar.d.ts +8 -0
- package/dist/components/utility/Avatar.d.ts.map +1 -1
- package/dist/components/utility/AvatarGroup.d.ts +4 -0
- package/dist/components/utility/AvatarGroup.d.ts.map +1 -0
- package/dist/components/utility/Badge.d.ts.map +1 -1
- package/dist/components/utility/Card.d.ts.map +1 -1
- package/dist/components/utility/Carousel.d.ts.map +1 -1
- package/dist/components/utility/FileUpload.d.ts.map +1 -1
- package/dist/components/utility/Pagination.d.ts.map +1 -1
- package/dist/components/utility/PullToRefresh.d.ts +5 -0
- package/dist/components/utility/PullToRefresh.d.ts.map +1 -0
- package/dist/components/utility/Sortable.d.ts.map +1 -1
- package/dist/components/utility/Stepper.d.ts.map +1 -1
- package/dist/esm/components/blocks/AppShell.js +97 -90
- package/dist/esm/components/blocks/BottomActionBar.js +132 -0
- package/dist/esm/components/blocks/ConfirmDialog.js +40 -4
- package/dist/esm/components/blocks/EmptyState.js +1 -1
- package/dist/esm/components/blocks/ErrorState.js +1 -1
- package/dist/esm/components/blocks/LoadingState.js +4 -4
- package/dist/esm/components/blocks/PageHeader.js +16 -3
- package/dist/esm/components/blocks/StatCard.js +6 -6
- package/dist/esm/components/blocks/StatusPill.js +5 -8
- package/dist/esm/components/charts/CartesianChart.js +85 -62
- package/dist/esm/components/charts/ChartFrame.js +12 -5
- package/dist/esm/components/charts/useChartLayout.js +105 -0
- package/dist/esm/components/core/Button.js +49 -25
- package/dist/esm/components/core/Checkbox.js +72 -57
- package/dist/esm/components/core/ColorPicker.js +31 -42
- package/dist/esm/components/core/DatePicker.js +117 -304
- package/dist/esm/components/core/DateRangePicker.js +260 -308
- package/dist/esm/components/core/Form.js +11 -2
- package/dist/esm/components/core/Input.js +100 -38
- package/dist/esm/components/core/Loader.js +30 -44
- package/dist/esm/components/core/LocationPicker.js +82 -16
- package/dist/esm/components/core/Popover.js +59 -48
- package/dist/esm/components/core/ProgressBar.js +40 -72
- package/dist/esm/components/core/Radio.js +10 -12
- package/dist/esm/components/core/Rate.js +77 -14
- package/dist/esm/components/core/RoundedTag.js +5 -5
- package/dist/esm/components/core/SearchField.js +311 -0
- package/dist/esm/components/core/SegmentedControl.js +189 -0
- package/dist/esm/components/core/Select.js +185 -190
- package/dist/esm/components/core/Skeleton.js +13 -14
- package/dist/esm/components/core/Slider.js +24 -6
- package/dist/esm/components/core/SpeechToText.js +68 -16
- package/dist/esm/components/core/SwipeableListItem.js +286 -0
- package/dist/esm/components/core/SwipeableListItemGesture.js +219 -0
- package/dist/esm/components/core/Switch.js +98 -28
- package/dist/esm/components/core/Table/ActionMenu.js +45 -231
- package/dist/esm/components/core/Table/ColumnMenu.js +1 -1
- package/dist/esm/components/core/Table/MobileCard.js +66 -16
- package/dist/esm/components/core/Table/MobileFilters.js +181 -10
- package/dist/esm/components/core/Table/Table.js +149 -102
- package/dist/esm/components/core/Table/TableRow.js +10 -2
- package/dist/esm/components/core/Tabs.js +186 -39
- package/dist/esm/components/core/Textarea.js +10 -2
- package/dist/esm/components/core/ThreeDotPopover.js +93 -99
- package/dist/esm/components/core/Tooltip.js +138 -145
- package/dist/esm/components/core/internal/Calendar.js +381 -0
- package/dist/esm/components/core/menu/ActionMenuSurface.js +110 -0
- package/dist/esm/components/core/menu/ActionSheetMenu.js +140 -0
- package/dist/esm/components/core/menu/MenuPopover.js +177 -0
- package/dist/esm/components/core/menu/menuItems.js +61 -0
- package/dist/esm/components/core/menu/menuKeyboard.js +54 -0
- package/dist/esm/components/feedback/ActionSheet.js +55 -0
- package/dist/esm/components/feedback/Alert.js +63 -53
- package/dist/esm/components/feedback/Dialog.js +141 -53
- package/dist/esm/components/feedback/Drawer.js +130 -132
- package/dist/esm/components/feedback/Sheet.js +125 -0
- package/dist/esm/components/feedback/Toast.js +21 -291
- package/dist/esm/components/feedback/ToastItem.js +348 -0
- package/dist/esm/components/feedback/ToastStack.js +130 -0
- package/dist/esm/components/feedback/ToastSwipe.js +52 -0
- package/dist/esm/components/feedback/Tour.js +107 -30
- package/dist/esm/components/feedback/sheetCore.js +494 -0
- package/dist/esm/components/navigation/Breadcrumbs.js +97 -35
- package/dist/esm/components/navigation/Dropdown.js +1 -1
- package/dist/esm/components/navigation/FootNav.js +102 -13
- package/dist/esm/components/navigation/Navbar.js +172 -37
- package/dist/esm/components/navigation/Sidebar.js +263 -111
- package/dist/esm/components/rich-text/RichTextEditor.js +9 -3
- package/dist/esm/components/rich-text/RichTextToolbar.js +29 -9
- package/dist/esm/components/utility/Avatar.js +14 -12
- package/dist/esm/components/utility/AvatarGroup.js +56 -0
- package/dist/esm/components/utility/Badge.js +43 -23
- package/dist/esm/components/utility/Card.js +32 -8
- package/dist/esm/components/utility/Carousel.js +139 -29
- package/dist/esm/components/utility/FileUpload.js +106 -31
- package/dist/esm/components/utility/Pagination.js +31 -13
- package/dist/esm/components/utility/Portal.js +31 -0
- package/dist/esm/components/utility/PullToRefresh.js +229 -0
- package/dist/esm/components/utility/Sortable.js +6 -2
- package/dist/esm/components/utility/Stepper.js +110 -47
- package/dist/esm/hooks/useFloatingPosition.js +82 -0
- package/dist/esm/hooks/useHaptics.js +65 -0
- package/dist/esm/hooks/usePresence.js +58 -0
- package/dist/esm/hooks/usePresentation.js +21 -0
- package/dist/esm/hooks/useSheetDrag.js +220 -0
- package/dist/esm/hooks/useSliderValues.js +8 -2
- package/dist/esm/hooks/useSortable.js +107 -5
- package/dist/esm/index.js +14 -2
- package/dist/esm/utils/position.js +10 -63
- package/dist/esm/utils/touchTarget.js +4 -1
- package/dist/hooks/useFloatingPosition.d.ts +8 -4
- package/dist/hooks/useFloatingPosition.d.ts.map +1 -1
- package/dist/hooks/useHaptics.d.ts +19 -0
- package/dist/hooks/useHaptics.d.ts.map +1 -0
- package/dist/hooks/useSheetDrag.d.ts +31 -0
- package/dist/hooks/useSheetDrag.d.ts.map +1 -0
- package/dist/hooks/useSliderValues.d.ts +6 -2
- package/dist/hooks/useSliderValues.d.ts.map +1 -1
- package/dist/hooks/useSortable.d.ts +11 -1
- package/dist/hooks/useSortable.d.ts.map +1 -1
- package/dist/index.css +1 -1
- package/dist/index.d.ts +11 -2
- package/dist/index.esm.css +1 -1
- package/dist/index.esm.js +10645 -3842
- package/dist/index.js +10657 -3845
- package/dist/rich-text/index.js +41 -11
- package/dist/types/blocks.d.ts +32 -2
- package/dist/types/blocks.d.ts.map +1 -1
- package/dist/types/charts.d.ts +3 -1
- package/dist/types/charts.d.ts.map +1 -1
- package/dist/types/index.d.ts +409 -26
- package/dist/types/index.d.ts.map +1 -1
- package/dist/types/rich-text.d.ts +5 -0
- package/dist/types/rich-text.d.ts.map +1 -1
- package/dist/utils/position.d.ts +0 -15
- package/dist/utils/position.d.ts.map +1 -1
- package/doc/README.md +16 -0
- package/mcp/catalog.snapshot.json +1540 -407
- package/package.json +7 -2
- package/dist/esm/hooks/useSwipeToClose.js +0 -66
- package/dist/hooks/useSwipeToClose.d.ts +0 -24
- package/dist/hooks/useSwipeToClose.d.ts.map +0 -1
|
@@ -3,18 +3,75 @@ import { objectWithoutProperties as _objectWithoutProperties, objectSpread2 as _
|
|
|
3
3
|
import { jsx, jsxs } from 'react/jsx-runtime';
|
|
4
4
|
import React from 'react';
|
|
5
5
|
import { cn } from '../../utils/cn.js';
|
|
6
|
+
import { TOUCH_TARGET } from '../../utils/touchTarget.js';
|
|
6
7
|
import { Check } from 'lucide-react';
|
|
7
8
|
|
|
8
9
|
var _excluded = ["steps", "currentStep", "orientation", "variant", "onStepClick", "className"];
|
|
10
|
+
// Layout classes per orientation. "auto" stacks vertically below `sm` and lays
|
|
11
|
+
// out horizontally from `sm` up. Every class is written out literally so
|
|
12
|
+
// Tailwind's content scan picks it up.
|
|
13
|
+
var LAYOUT = {
|
|
14
|
+
horizontal: {
|
|
15
|
+
nav: 'flex-row',
|
|
16
|
+
step: 'flex-col flex-1 min-w-0',
|
|
17
|
+
lastStep: 'flex-none',
|
|
18
|
+
track: 'flex-row items-center',
|
|
19
|
+
// Connectors flex to fill the gap between circles, so steps never overflow.
|
|
20
|
+
line: 'h-0.5 flex-1 min-w-4 mx-2',
|
|
21
|
+
content: 'mt-2 pr-2',
|
|
22
|
+
contentGap: ''
|
|
23
|
+
},
|
|
24
|
+
vertical: {
|
|
25
|
+
nav: 'flex-col',
|
|
26
|
+
step: 'flex-row gap-4',
|
|
27
|
+
lastStep: '',
|
|
28
|
+
track: 'flex-col items-center',
|
|
29
|
+
line: 'w-0.5 flex-1 min-h-8 my-1',
|
|
30
|
+
content: 'pt-1',
|
|
31
|
+
contentGap: 'pb-8'
|
|
32
|
+
},
|
|
33
|
+
auto: {
|
|
34
|
+
nav: 'flex-col sm:flex-row',
|
|
35
|
+
step: 'flex-row gap-4 sm:flex-col sm:gap-0 sm:flex-1 sm:min-w-0',
|
|
36
|
+
lastStep: 'sm:flex-none',
|
|
37
|
+
track: 'flex-col items-center sm:flex-row',
|
|
38
|
+
line: 'w-0.5 flex-1 min-h-8 my-1 sm:h-0.5 sm:w-auto sm:min-h-0 sm:min-w-4 sm:my-0 sm:mx-2',
|
|
39
|
+
content: 'pt-1 sm:pt-0 sm:mt-2 sm:pr-2',
|
|
40
|
+
contentGap: 'pb-8 sm:pb-0'
|
|
41
|
+
}
|
|
42
|
+
};
|
|
43
|
+
var FOCUS_RING = 'outline-none focus-visible:ring-2 focus-visible:ring-primary-500 focus-visible:ring-offset-2 dark:focus-visible:ring-offset-gray-900';
|
|
44
|
+
var statusColors = {
|
|
45
|
+
completed: {
|
|
46
|
+
circle: 'bg-primary-600 text-white',
|
|
47
|
+
line: 'bg-primary-600',
|
|
48
|
+
text: 'text-primary-600 dark:text-primary-400',
|
|
49
|
+
dot: 'w-2 bg-primary-600'
|
|
50
|
+
},
|
|
51
|
+
current: {
|
|
52
|
+
circle: 'bg-primary-600 text-white',
|
|
53
|
+
line: 'bg-gray-300 dark:bg-gray-700',
|
|
54
|
+
text: 'text-primary-600 dark:text-primary-400',
|
|
55
|
+
// The current dot stretches into a pill.
|
|
56
|
+
dot: 'w-6 bg-primary-600'
|
|
57
|
+
},
|
|
58
|
+
upcoming: {
|
|
59
|
+
circle: 'bg-gray-300 text-gray-700 dark:bg-gray-700 dark:text-gray-200',
|
|
60
|
+
line: 'bg-gray-300 dark:bg-gray-700',
|
|
61
|
+
text: 'text-muted',
|
|
62
|
+
dot: 'w-2 bg-gray-300 dark:bg-gray-600'
|
|
63
|
+
}
|
|
64
|
+
};
|
|
9
65
|
var Stepper = /*#__PURE__*/React.forwardRef(function (_ref, ref) {
|
|
10
66
|
var _ref$steps = _ref.steps,
|
|
11
67
|
steps = _ref$steps === void 0 ? [] : _ref$steps,
|
|
12
68
|
_ref$currentStep = _ref.currentStep,
|
|
13
69
|
currentStep = _ref$currentStep === void 0 ? 0 : _ref$currentStep,
|
|
14
70
|
_ref$orientation = _ref.orientation,
|
|
15
|
-
orientation = _ref$orientation === void 0 ? 'horizontal' : _ref$orientation
|
|
16
|
-
_ref.variant
|
|
17
|
-
|
|
71
|
+
orientation = _ref$orientation === void 0 ? 'horizontal' : _ref$orientation,
|
|
72
|
+
_ref$variant = _ref.variant,
|
|
73
|
+
variant = _ref$variant === void 0 ? 'default' : _ref$variant,
|
|
74
|
+
onStepClick = _ref.onStepClick,
|
|
18
75
|
className = _ref.className,
|
|
19
76
|
props = _objectWithoutProperties(_ref, _excluded);
|
|
20
77
|
var getStepStatus = function getStepStatus(stepIndex) {
|
|
@@ -22,73 +79,79 @@ var Stepper = /*#__PURE__*/React.forwardRef(function (_ref, ref) {
|
|
|
22
79
|
if (stepIndex === currentStep) return 'current';
|
|
23
80
|
return 'upcoming';
|
|
24
81
|
};
|
|
25
|
-
var
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
current: {
|
|
32
|
-
circle: 'bg-primary-600 text-white',
|
|
33
|
-
line: 'bg-gray-300',
|
|
34
|
-
text: 'text-primary-600'
|
|
35
|
-
},
|
|
36
|
-
upcoming: {
|
|
37
|
-
circle: 'bg-gray-300 text-gray-700',
|
|
38
|
-
line: 'bg-gray-300',
|
|
39
|
-
text: 'text-muted'
|
|
40
|
-
}
|
|
82
|
+
var stepLabel = function stepLabel(step, stepIndex, status) {
|
|
83
|
+
var _step$title;
|
|
84
|
+
// `label` is accepted as an alias for `title` (the docs used `label`).
|
|
85
|
+
var stepTitle = (_step$title = step.title) !== null && _step$title !== void 0 ? _step$title : step.label;
|
|
86
|
+
// A completed step shows only a check icon, so the button needs a name.
|
|
87
|
+
return "Step ".concat(stepIndex + 1).concat(stepTitle ? ": ".concat(stepTitle) : '').concat(status === 'completed' ? ' (completed)' : '');
|
|
41
88
|
};
|
|
89
|
+
var isClickable = function isClickable(stepIndex) {
|
|
90
|
+
return Boolean(onStepClick) && stepIndex <= currentStep;
|
|
91
|
+
};
|
|
92
|
+
// Compact progress dots: no titles, just one dot per step (current = pill).
|
|
93
|
+
if (variant === 'dots') {
|
|
94
|
+
return jsx("nav", _objectSpread2(_objectSpread2({
|
|
95
|
+
ref: ref,
|
|
96
|
+
className: cn('flex flex-row items-center gap-1', className),
|
|
97
|
+
"aria-label": "Progress",
|
|
98
|
+
"data-variant": "dots"
|
|
99
|
+
}, props), {}, {
|
|
100
|
+
children: steps.map(function (step, stepIndex) {
|
|
101
|
+
var status = getStepStatus(stepIndex);
|
|
102
|
+
return jsx("button", {
|
|
103
|
+
type: "button",
|
|
104
|
+
className: cn('inline-flex items-center justify-center rounded-full p-1', FOCUS_RING, isClickable(stepIndex) ? cn('cursor-pointer', TOUCH_TARGET) : 'cursor-default'),
|
|
105
|
+
onClick: function onClick() {
|
|
106
|
+
return onStepClick === null || onStepClick === void 0 ? void 0 : onStepClick(step, stepIndex);
|
|
107
|
+
},
|
|
108
|
+
disabled: !isClickable(stepIndex),
|
|
109
|
+
"aria-current": status === 'current' ? 'step' : undefined,
|
|
110
|
+
"aria-label": stepLabel(step, stepIndex, status),
|
|
111
|
+
children: jsx("span", {
|
|
112
|
+
"aria-hidden": "true",
|
|
113
|
+
className: cn('block h-2 rounded-full transition-[width,background-color] duration-base ease-standard motion-reduce:transition-none', statusColors[status].dot)
|
|
114
|
+
})
|
|
115
|
+
}, step.id || stepIndex);
|
|
116
|
+
})
|
|
117
|
+
}));
|
|
118
|
+
}
|
|
119
|
+
var layout = LAYOUT[orientation] || LAYOUT.horizontal;
|
|
42
120
|
return jsx("nav", _objectSpread2(_objectSpread2({
|
|
43
121
|
ref: ref,
|
|
44
|
-
className: cn('flex',
|
|
45
|
-
'flex-col': orientation === 'vertical',
|
|
46
|
-
'flex-row': orientation === 'horizontal'
|
|
47
|
-
}, className),
|
|
122
|
+
className: cn('flex', layout.nav, className),
|
|
48
123
|
"aria-label": "Progress"
|
|
49
124
|
}, props), {}, {
|
|
50
125
|
children: steps.map(function (step, stepIndex) {
|
|
51
|
-
var _step$
|
|
126
|
+
var _step$title2;
|
|
52
127
|
var status = getStepStatus(stepIndex);
|
|
53
128
|
var isLast = stepIndex === steps.length - 1;
|
|
54
129
|
var colors = statusColors[status];
|
|
55
|
-
|
|
56
|
-
var stepTitle = (_step$title = step.title) !== null && _step$title !== void 0 ? _step$title : step.label;
|
|
130
|
+
var stepTitle = (_step$title2 = step.title) !== null && _step$title2 !== void 0 ? _step$title2 : step.label;
|
|
57
131
|
return jsxs("div", {
|
|
58
|
-
className: cn('flex
|
|
59
|
-
'flex-col': orientation === 'horizontal',
|
|
60
|
-
'flex-row': orientation === 'vertical',
|
|
61
|
-
'mb-8': orientation === 'vertical' && !isLast,
|
|
62
|
-
'mr-8': orientation === 'horizontal' && !isLast
|
|
63
|
-
}),
|
|
132
|
+
className: cn('flex', layout.step, isLast && layout.lastStep),
|
|
64
133
|
children: [jsxs("div", {
|
|
65
|
-
className:
|
|
134
|
+
className: cn('flex', layout.track),
|
|
66
135
|
children: [jsx("button", {
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
'cursor-default': !onStepClick || stepIndex > currentStep
|
|
70
|
-
}),
|
|
136
|
+
type: "button",
|
|
137
|
+
className: cn('flex h-8 w-8 shrink-0 items-center justify-center rounded-full text-sm font-medium transition-colors duration-fast motion-reduce:transition-none', FOCUS_RING, colors.circle, isClickable(stepIndex) ? cn('cursor-pointer', TOUCH_TARGET) : 'cursor-default'),
|
|
71
138
|
onClick: function onClick() {
|
|
72
139
|
return onStepClick === null || onStepClick === void 0 ? void 0 : onStepClick(step, stepIndex);
|
|
73
140
|
},
|
|
74
|
-
disabled: !
|
|
141
|
+
disabled: !isClickable(stepIndex),
|
|
75
142
|
"aria-current": status === 'current' ? 'step' : undefined,
|
|
76
|
-
"aria-label":
|
|
143
|
+
"aria-label": stepLabel(step, stepIndex, status),
|
|
77
144
|
children: status === 'completed' ? jsx(Check, {
|
|
78
145
|
className: "h-4 w-4",
|
|
79
146
|
"aria-hidden": "true"
|
|
80
147
|
}) : stepIndex + 1
|
|
81
148
|
}), !isLast && jsx("div", {
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
})
|
|
149
|
+
"aria-hidden": "true",
|
|
150
|
+
"data-stepper-connector": "",
|
|
151
|
+
className: cn('transition-colors duration-base motion-reduce:transition-none', layout.line, colors.line)
|
|
86
152
|
})]
|
|
87
153
|
}), jsxs("div", {
|
|
88
|
-
className: cn('flex flex-col',
|
|
89
|
-
'ml-4': orientation === 'vertical',
|
|
90
|
-
'mt-2': orientation === 'horizontal'
|
|
91
|
-
}),
|
|
154
|
+
className: cn('flex min-w-0 flex-col', layout.content, !isLast && layout.contentGap),
|
|
92
155
|
children: [jsx("span", {
|
|
93
156
|
className: cn('text-sm font-medium', colors.text),
|
|
94
157
|
children: stepTitle
|
|
@@ -0,0 +1,82 @@
|
|
|
1
|
+
import { offset, flip, shift, size, useFloating, autoUpdate } from '@floating-ui/react-dom';
|
|
2
|
+
|
|
3
|
+
// Internal (not exported). One positioning engine for every anchored overlay
|
|
4
|
+
// (Popover, Select, Tooltip, Tour, …), replacing the hand-rolled
|
|
5
|
+
// `utils/position.js`.
|
|
6
|
+
var SHIFT_PADDING = 8;
|
|
7
|
+
var MIN_FIT_HEIGHT = 80; // px; never squeeze a capped floating element below this
|
|
8
|
+
/**
|
|
9
|
+
* Positions a floating element next to a reference element.
|
|
10
|
+
*
|
|
11
|
+
* @param {object} [options]
|
|
12
|
+
* @param {import('@floating-ui/react-dom').Placement} [options.placement='bottom-start']
|
|
13
|
+
* @param {number} [options.offset=4] - gap in px between reference and floating.
|
|
14
|
+
* @param {boolean} [options.flip=true] - flip to the opposite side when out of room.
|
|
15
|
+
* @param {boolean} [options.shift=true] - slide along the axis to stay in view (8px padding).
|
|
16
|
+
* @param {boolean|'exact'} [options.matchWidth=false] - `true` sets the floating
|
|
17
|
+
* element's min-width to the reference's width (listboxes, comboboxes);
|
|
18
|
+
* `'exact'` sets its width too.
|
|
19
|
+
* @param {number} [options.maxHeight] - px cap on the floating element's
|
|
20
|
+
* height; it also shrinks to the space left on its side (min 80px).
|
|
21
|
+
* @param {'fixed'|'absolute'} [options.strategy='fixed']
|
|
22
|
+
* @param {boolean} [options.open] - while false, auto-updates are paused.
|
|
23
|
+
* @returns {{ refs: { setReference: Function, setFloating: Function, reference: object, floating: object },
|
|
24
|
+
* floatingStyles: object, placement: string, isPositioned: boolean, update: () => void }}
|
|
25
|
+
*/
|
|
26
|
+
function useFloatingPosition() {
|
|
27
|
+
var _ref = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {},
|
|
28
|
+
_ref$placement = _ref.placement,
|
|
29
|
+
placement = _ref$placement === void 0 ? "bottom-start" : _ref$placement,
|
|
30
|
+
_ref$offset = _ref.offset,
|
|
31
|
+
offset$1 = _ref$offset === void 0 ? 4 : _ref$offset,
|
|
32
|
+
_ref$flip = _ref.flip,
|
|
33
|
+
flip$1 = _ref$flip === void 0 ? true : _ref$flip,
|
|
34
|
+
_ref$shift = _ref.shift,
|
|
35
|
+
shift$1 = _ref$shift === void 0 ? true : _ref$shift,
|
|
36
|
+
_ref$matchWidth = _ref.matchWidth,
|
|
37
|
+
matchWidth = _ref$matchWidth === void 0 ? false : _ref$matchWidth,
|
|
38
|
+
maxHeight = _ref.maxHeight,
|
|
39
|
+
_ref$strategy = _ref.strategy,
|
|
40
|
+
strategy = _ref$strategy === void 0 ? "fixed" : _ref$strategy,
|
|
41
|
+
open = _ref.open;
|
|
42
|
+
var middleware = [offset(offset$1)];
|
|
43
|
+
if (flip$1) middleware.push(flip({
|
|
44
|
+
padding: SHIFT_PADDING
|
|
45
|
+
}));
|
|
46
|
+
if (shift$1) middleware.push(shift({
|
|
47
|
+
padding: SHIFT_PADDING
|
|
48
|
+
}));
|
|
49
|
+
if (matchWidth || maxHeight != null) {
|
|
50
|
+
middleware.push(size({
|
|
51
|
+
padding: SHIFT_PADDING,
|
|
52
|
+
apply: function apply(_ref2) {
|
|
53
|
+
var rects = _ref2.rects,
|
|
54
|
+
elements = _ref2.elements,
|
|
55
|
+
availableHeight = _ref2.availableHeight;
|
|
56
|
+
var style = elements.floating.style;
|
|
57
|
+
if (matchWidth) style.minWidth = "".concat(rects.reference.width, "px");
|
|
58
|
+
if (matchWidth === "exact") style.width = "".concat(rects.reference.width, "px");
|
|
59
|
+
if (maxHeight != null) {
|
|
60
|
+
var room = Math.max(MIN_FIT_HEIGHT, availableHeight);
|
|
61
|
+
style.maxHeight = "".concat(Math.min(maxHeight, room), "px");
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
}));
|
|
65
|
+
}
|
|
66
|
+
var result = useFloating({
|
|
67
|
+
placement: placement,
|
|
68
|
+
strategy: strategy,
|
|
69
|
+
open: open,
|
|
70
|
+
middleware: middleware,
|
|
71
|
+
whileElementsMounted: autoUpdate
|
|
72
|
+
});
|
|
73
|
+
return {
|
|
74
|
+
refs: result.refs,
|
|
75
|
+
floatingStyles: result.floatingStyles,
|
|
76
|
+
placement: result.placement,
|
|
77
|
+
isPositioned: result.isPositioned,
|
|
78
|
+
update: result.update
|
|
79
|
+
};
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
export { useFloatingPosition };
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { useSyncExternalStore, useCallback } from 'react';
|
|
3
|
+
import { useReducedMotion } from './useReducedMotion.js';
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* Named vibration patterns (milliseconds; arrays alternate vibrate / pause).
|
|
7
|
+
* Kept short: haptics confirm an action, they never carry information alone.
|
|
8
|
+
*/
|
|
9
|
+
var HAPTIC_PATTERNS = Object.freeze({
|
|
10
|
+
selection: 10,
|
|
11
|
+
success: [10, 40, 10],
|
|
12
|
+
warning: [20, 60, 20],
|
|
13
|
+
error: [30, 40, 30, 40, 30]
|
|
14
|
+
});
|
|
15
|
+
function canVibrate() {
|
|
16
|
+
return typeof navigator !== "undefined" && typeof navigator.vibrate === "function";
|
|
17
|
+
}
|
|
18
|
+
// Vibration support never changes during a page's life: nothing to subscribe to.
|
|
19
|
+
var subscribeNever = function subscribeNever() {
|
|
20
|
+
return function () {};
|
|
21
|
+
};
|
|
22
|
+
var getServerSupported = function getServerSupported() {
|
|
23
|
+
return false;
|
|
24
|
+
};
|
|
25
|
+
function resolvePattern(pattern) {
|
|
26
|
+
if (typeof pattern === "number") return pattern > 0 ? pattern : null;
|
|
27
|
+
if (Array.isArray(pattern)) return pattern.length > 0 ? pattern : null;
|
|
28
|
+
return Object.prototype.hasOwnProperty.call(HAPTIC_PATTERNS, pattern) ? HAPTIC_PATTERNS[pattern] : null;
|
|
29
|
+
}
|
|
30
|
+
/**
|
|
31
|
+
* Thin, opt-in wrapper around `navigator.vibrate` with named patterns.
|
|
32
|
+
*
|
|
33
|
+
* `trigger` is a no-op (returns `false`) when the Vibration API is missing
|
|
34
|
+
* (iOS Safari, desktop Safari, the server), when the user asks for reduced
|
|
35
|
+
* motion, when `enabled` is `false`, or for an unknown pattern name.
|
|
36
|
+
*
|
|
37
|
+
* @param options - `enabled` (default `true`) gates every trigger.
|
|
38
|
+
* @returns `{ trigger, supported, reducedMotion }`.
|
|
39
|
+
*/
|
|
40
|
+
function useHaptics() {
|
|
41
|
+
var _ref = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {},
|
|
42
|
+
_ref$enabled = _ref.enabled,
|
|
43
|
+
enabled = _ref$enabled === void 0 ? true : _ref$enabled;
|
|
44
|
+
var supported = useSyncExternalStore(subscribeNever, canVibrate, getServerSupported);
|
|
45
|
+
var reducedMotion = useReducedMotion();
|
|
46
|
+
var trigger = useCallback(function () {
|
|
47
|
+
var pattern = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : "selection";
|
|
48
|
+
if (!enabled || reducedMotion || !canVibrate()) return false;
|
|
49
|
+
var resolved = resolvePattern(pattern);
|
|
50
|
+
if (resolved == null) return false;
|
|
51
|
+
try {
|
|
52
|
+
return navigator.vibrate(resolved) !== false;
|
|
53
|
+
} catch (_unused) {
|
|
54
|
+
// Some embedded browsers throw instead of returning false.
|
|
55
|
+
return false;
|
|
56
|
+
}
|
|
57
|
+
}, [enabled, reducedMotion]);
|
|
58
|
+
return {
|
|
59
|
+
trigger: trigger,
|
|
60
|
+
supported: supported,
|
|
61
|
+
reducedMotion: reducedMotion
|
|
62
|
+
};
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
export { HAPTIC_PATTERNS, useHaptics };
|
|
@@ -0,0 +1,58 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { slicedToArray as _slicedToArray } from '../_virtual/_rollupPluginBabelHelpers.js';
|
|
3
|
+
import { useState, useEffect } from 'react';
|
|
4
|
+
import { useReducedMotion } from './useReducedMotion.js';
|
|
5
|
+
|
|
6
|
+
// Internal (not exported). Keeps an overlay mounted through its exit
|
|
7
|
+
// transition so it can animate out before it unmounts.
|
|
8
|
+
/**
|
|
9
|
+
* @param {boolean} open - whether the overlay should be shown.
|
|
10
|
+
* @param {{ duration?: number }} [options] - transition length in ms (default
|
|
11
|
+
* 200). Forced to 0 when the user prefers reduced motion.
|
|
12
|
+
* @returns {{ mounted: boolean, state: 'entering'|'open'|'exiting'|'closed' }}
|
|
13
|
+
* `mounted` stays true through 'exiting' and turns false once `duration`
|
|
14
|
+
* has elapsed after `open` became false.
|
|
15
|
+
*/
|
|
16
|
+
function usePresence(open) {
|
|
17
|
+
var _ref = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {},
|
|
18
|
+
_ref$duration = _ref.duration,
|
|
19
|
+
duration = _ref$duration === void 0 ? 200 : _ref$duration;
|
|
20
|
+
var reducedMotion = useReducedMotion();
|
|
21
|
+
var ms = reducedMotion ? 0 : Math.max(0, Number(duration) || 0);
|
|
22
|
+
var _useState = useState(function () {
|
|
23
|
+
if (!open) return "closed";
|
|
24
|
+
return ms > 0 ? "entering" : "open";
|
|
25
|
+
}),
|
|
26
|
+
_useState2 = _slicedToArray(_useState, 2),
|
|
27
|
+
phase = _useState2[0],
|
|
28
|
+
setPhase = _useState2[1];
|
|
29
|
+
// When `open` flips, start the transition during render (React's "adjust
|
|
30
|
+
// state on prop change" pattern), so the first render after the flip is
|
|
31
|
+
// already 'entering' / 'exiting' and no effect sets state synchronously.
|
|
32
|
+
var _useState3 = useState(open),
|
|
33
|
+
_useState4 = _slicedToArray(_useState3, 2),
|
|
34
|
+
prevOpen = _useState4[0],
|
|
35
|
+
setPrevOpen = _useState4[1];
|
|
36
|
+
if (open !== prevOpen) {
|
|
37
|
+
setPrevOpen(open);
|
|
38
|
+
if (open) setPhase(ms > 0 ? "entering" : "open");else setPhase(ms > 0 ? "exiting" : "closed");
|
|
39
|
+
}
|
|
40
|
+
// Settle on the resting phase once the transition has run.
|
|
41
|
+
useEffect(function () {
|
|
42
|
+
if (phase !== "entering" && phase !== "exiting") return undefined;
|
|
43
|
+
var next = phase === "entering" ? "open" : "closed";
|
|
44
|
+
var timer = setTimeout(function () {
|
|
45
|
+
return setPhase(next);
|
|
46
|
+
}, ms);
|
|
47
|
+
return function () {
|
|
48
|
+
return clearTimeout(timer);
|
|
49
|
+
};
|
|
50
|
+
}, [phase, ms]);
|
|
51
|
+
var state = phase;
|
|
52
|
+
return {
|
|
53
|
+
mounted: state !== "closed",
|
|
54
|
+
state: state
|
|
55
|
+
};
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
export { usePresence };
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import { useMediaQuery } from './useMediaQuery.js';
|
|
2
|
+
|
|
3
|
+
// Internal (not exported). Picks how an overlay presents itself: as a bottom
|
|
4
|
+
// sheet on small touch screens, as an anchored popover everywhere else.
|
|
5
|
+
var SHEET_MEDIA_QUERY = "(pointer: coarse) and (max-width: 639px)";
|
|
6
|
+
/**
|
|
7
|
+
* @param {'auto'|'sheet'|'popover'} [prop='auto'] - an explicit 'sheet' or
|
|
8
|
+
* 'popover' passes through; 'auto' resolves from SHEET_MEDIA_QUERY.
|
|
9
|
+
* @returns {'sheet'|'popover'} - 'popover' on the server and while hydrating.
|
|
10
|
+
*/
|
|
11
|
+
function usePresentation() {
|
|
12
|
+
var prop = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : "auto";
|
|
13
|
+
// Always subscribe (rules of hooks); the result is ignored when explicit.
|
|
14
|
+
var isSheet = useMediaQuery(SHEET_MEDIA_QUERY, {
|
|
15
|
+
defaultValue: false
|
|
16
|
+
});
|
|
17
|
+
if (prop === "sheet" || prop === "popover") return prop;
|
|
18
|
+
return isSheet ? "sheet" : "popover";
|
|
19
|
+
}
|
|
20
|
+
|
|
21
|
+
export { SHEET_MEDIA_QUERY, usePresentation };
|
|
@@ -0,0 +1,220 @@
|
|
|
1
|
+
'use client';
|
|
2
|
+
import { slicedToArray as _slicedToArray, objectSpread2 as _objectSpread2 } from '../_virtual/_rollupPluginBabelHelpers.js';
|
|
3
|
+
import { useState, useRef, useCallback, useEffect } from 'react';
|
|
4
|
+
import { useLatestRef } from './useLatestRef.js';
|
|
5
|
+
|
|
6
|
+
// Internal (not exported). The gesture core behind Sheet: a pointer drag along
|
|
7
|
+
// one axis, measured "toward dismiss" for the edge the sheet is attached to.
|
|
8
|
+
//
|
|
9
|
+
// - `dragProps` go on the grab zone (handle + header). Any drag there moves
|
|
10
|
+
// the sheet.
|
|
11
|
+
// - `bodyDragProps` go on the scrolling body. A drag there only moves the
|
|
12
|
+
// sheet when it heads toward dismiss and the body is already scrolled to
|
|
13
|
+
// that edge (Vaul-style), so it never fights the content's own scroll.
|
|
14
|
+
//
|
|
15
|
+
// The hook only reports `delta` (px toward dismiss; negative = away from the
|
|
16
|
+
// edge) while dragging and calls `onRelease({ delta, velocity })` when the
|
|
17
|
+
// pointer lifts. The caller decides what that means (rubber band, settle on a
|
|
18
|
+
// snap point, dismiss). The pointer is captured only once the drag passes a
|
|
19
|
+
// small slop, so taps and clicks on buttons inside the header still work.
|
|
20
|
+
var FLICK_VELOCITY = 0.5; // px per ms
|
|
21
|
+
var SLOP = 4; // px before a press becomes a drag
|
|
22
|
+
var VELOCITY_WINDOW = 100; // ms of recent samples used for release velocity
|
|
23
|
+
var EDGES = {
|
|
24
|
+
bottom: {
|
|
25
|
+
axis: "y",
|
|
26
|
+
sign: 1
|
|
27
|
+
},
|
|
28
|
+
top: {
|
|
29
|
+
axis: "y",
|
|
30
|
+
sign: -1
|
|
31
|
+
},
|
|
32
|
+
right: {
|
|
33
|
+
axis: "x",
|
|
34
|
+
sign: 1
|
|
35
|
+
},
|
|
36
|
+
left: {
|
|
37
|
+
axis: "x",
|
|
38
|
+
sign: -1
|
|
39
|
+
}
|
|
40
|
+
};
|
|
41
|
+
/**
|
|
42
|
+
* iOS-style rubber band: the further past a limit, the less the sheet follows.
|
|
43
|
+
* Returns a value in [0, dimension) for `distance` >= 0.
|
|
44
|
+
*/
|
|
45
|
+
function rubberBand(distance, dimension) {
|
|
46
|
+
if (distance <= 0 || !dimension) return 0;
|
|
47
|
+
return (1 - 1 / (distance * 0.55 / dimension + 1)) * dimension;
|
|
48
|
+
}
|
|
49
|
+
// Is a scroll container already at the edge a dismiss drag moves away from?
|
|
50
|
+
function atScrollEdge(el, edge) {
|
|
51
|
+
if (!el) return true;
|
|
52
|
+
if (edge === "bottom") return el.scrollTop <= 0;
|
|
53
|
+
if (edge === "top") return Math.ceil(el.scrollTop + el.clientHeight) >= el.scrollHeight;
|
|
54
|
+
return true; // horizontal drags don't compete with vertical scroll
|
|
55
|
+
}
|
|
56
|
+
var now = function now() {
|
|
57
|
+
return Date.now();
|
|
58
|
+
};
|
|
59
|
+
/**
|
|
60
|
+
* @param {{
|
|
61
|
+
* edge?: 'bottom'|'top'|'left'|'right',
|
|
62
|
+
* enabled?: boolean,
|
|
63
|
+
* onRelease?: (r: { delta: number, velocity: number }) => void,
|
|
64
|
+
* bodyEl?: HTMLElement | null,
|
|
65
|
+
* }} options
|
|
66
|
+
* @returns {{ delta: number, dragging: boolean, dragProps: object, bodyDragProps: object }}
|
|
67
|
+
*/
|
|
68
|
+
function useSheetDrag() {
|
|
69
|
+
var _ref = arguments.length > 0 && arguments[0] !== undefined ? arguments[0] : {},
|
|
70
|
+
_ref$edge = _ref.edge,
|
|
71
|
+
edge = _ref$edge === void 0 ? "bottom" : _ref$edge,
|
|
72
|
+
_ref$enabled = _ref.enabled,
|
|
73
|
+
enabled = _ref$enabled === void 0 ? true : _ref$enabled,
|
|
74
|
+
onRelease = _ref.onRelease,
|
|
75
|
+
bodyEl = _ref.bodyEl;
|
|
76
|
+
var _ref2 = EDGES[edge] || EDGES.bottom,
|
|
77
|
+
axis = _ref2.axis,
|
|
78
|
+
sign = _ref2.sign;
|
|
79
|
+
var _useState = useState(0),
|
|
80
|
+
_useState2 = _slicedToArray(_useState, 2),
|
|
81
|
+
delta = _useState2[0],
|
|
82
|
+
setDelta = _useState2[1];
|
|
83
|
+
var _useState3 = useState(false),
|
|
84
|
+
_useState4 = _slicedToArray(_useState3, 2),
|
|
85
|
+
dragging = _useState4[0],
|
|
86
|
+
setDragging = _useState4[1];
|
|
87
|
+
var gesture = useRef(null);
|
|
88
|
+
var onReleaseRef = useLatestRef(onRelease);
|
|
89
|
+
var reset = useCallback(function () {
|
|
90
|
+
gesture.current = null;
|
|
91
|
+
setDragging(false);
|
|
92
|
+
setDelta(0);
|
|
93
|
+
}, []);
|
|
94
|
+
var start = useCallback(function (e, fromBody) {
|
|
95
|
+
if (e.button !== undefined && e.button !== 0) return;
|
|
96
|
+
var t = now();
|
|
97
|
+
gesture.current = {
|
|
98
|
+
x: e.clientX,
|
|
99
|
+
y: e.clientY,
|
|
100
|
+
fromBody: fromBody,
|
|
101
|
+
active: false,
|
|
102
|
+
el: e.currentTarget,
|
|
103
|
+
pointerId: e.pointerId,
|
|
104
|
+
samples: [{
|
|
105
|
+
d: 0,
|
|
106
|
+
t: t
|
|
107
|
+
}]
|
|
108
|
+
};
|
|
109
|
+
}, []);
|
|
110
|
+
var move = useCallback(function (e) {
|
|
111
|
+
var g = gesture.current;
|
|
112
|
+
if (!g) return;
|
|
113
|
+
var dx = e.clientX - g.x;
|
|
114
|
+
var dy = e.clientY - g.y;
|
|
115
|
+
var d = sign * (axis === "y" ? dy : dx);
|
|
116
|
+
if (!g.active) {
|
|
117
|
+
var cross = axis === "y" ? dx : dy;
|
|
118
|
+
if (Math.max(Math.abs(d), Math.abs(cross)) < SLOP) return;
|
|
119
|
+
if (g.fromBody && (d <= 0 || Math.abs(d) < Math.abs(cross) || !atScrollEdge(g.el, edge))) {
|
|
120
|
+
gesture.current = null; // let the body scroll
|
|
121
|
+
return;
|
|
122
|
+
}
|
|
123
|
+
g.active = true;
|
|
124
|
+
setDragging(true);
|
|
125
|
+
try {
|
|
126
|
+
var _g$el, _g$el$setPointerCaptu;
|
|
127
|
+
(_g$el = g.el) === null || _g$el === void 0 || (_g$el$setPointerCaptu = _g$el.setPointerCapture) === null || _g$el$setPointerCaptu === void 0 || _g$el$setPointerCaptu.call(_g$el, g.pointerId);
|
|
128
|
+
} catch (_unused) {
|
|
129
|
+
// The pointer may already be gone (synthetic events, fast lifts).
|
|
130
|
+
}
|
|
131
|
+
}
|
|
132
|
+
var t = now();
|
|
133
|
+
g.samples.push({
|
|
134
|
+
d: d,
|
|
135
|
+
t: t
|
|
136
|
+
});
|
|
137
|
+
while (g.samples.length > 2 && t - g.samples[0].t > VELOCITY_WINDOW) g.samples.shift();
|
|
138
|
+
setDelta(d);
|
|
139
|
+
}, [axis, sign, edge]);
|
|
140
|
+
var end = useCallback(function (e) {
|
|
141
|
+
var _onReleaseRef$current;
|
|
142
|
+
var g = gesture.current;
|
|
143
|
+
if (!g) return;
|
|
144
|
+
if (!g.active) {
|
|
145
|
+
gesture.current = null;
|
|
146
|
+
return;
|
|
147
|
+
}
|
|
148
|
+
var d = sign * (axis === "y" ? e.clientY - g.y : e.clientX - g.x);
|
|
149
|
+
var t = now();
|
|
150
|
+
var first = g.samples[0];
|
|
151
|
+
var velocity = (d - first.d) / Math.max(1, t - first.t);
|
|
152
|
+
reset();
|
|
153
|
+
(_onReleaseRef$current = onReleaseRef.current) === null || _onReleaseRef$current === void 0 || _onReleaseRef$current.call(onReleaseRef, {
|
|
154
|
+
delta: d,
|
|
155
|
+
velocity: velocity
|
|
156
|
+
});
|
|
157
|
+
}, [axis, sign, reset, onReleaseRef]);
|
|
158
|
+
// iOS/Android start a native pan on the body before pointer events can
|
|
159
|
+
// claim it. While the body sits at its scroll edge, cancel touchmoves that
|
|
160
|
+
// head toward dismiss so the pointer drag above keeps receiving events.
|
|
161
|
+
useEffect(function () {
|
|
162
|
+
var el = bodyEl;
|
|
163
|
+
if (!enabled || !el || typeof el.addEventListener !== "function") return undefined;
|
|
164
|
+
var startPos = null;
|
|
165
|
+
var onStart = function onStart(e) {
|
|
166
|
+
var _e$touches;
|
|
167
|
+
var p = (_e$touches = e.touches) === null || _e$touches === void 0 ? void 0 : _e$touches[0];
|
|
168
|
+
startPos = p ? {
|
|
169
|
+
x: p.clientX,
|
|
170
|
+
y: p.clientY
|
|
171
|
+
} : null;
|
|
172
|
+
};
|
|
173
|
+
var onMove = function onMove(e) {
|
|
174
|
+
var _e$touches2, _gesture$current;
|
|
175
|
+
var p = (_e$touches2 = e.touches) === null || _e$touches2 === void 0 ? void 0 : _e$touches2[0];
|
|
176
|
+
if (!startPos || !p) return;
|
|
177
|
+
var d = sign * (axis === "y" ? p.clientY - startPos.y : p.clientX - startPos.x);
|
|
178
|
+
if (d > 0 && atScrollEdge(el, edge) || (_gesture$current = gesture.current) !== null && _gesture$current !== void 0 && _gesture$current.active) {
|
|
179
|
+
if (e.cancelable) e.preventDefault();
|
|
180
|
+
}
|
|
181
|
+
};
|
|
182
|
+
el.addEventListener("touchstart", onStart, {
|
|
183
|
+
passive: true
|
|
184
|
+
});
|
|
185
|
+
el.addEventListener("touchmove", onMove, {
|
|
186
|
+
passive: false
|
|
187
|
+
});
|
|
188
|
+
return function () {
|
|
189
|
+
el.removeEventListener("touchstart", onStart);
|
|
190
|
+
el.removeEventListener("touchmove", onMove);
|
|
191
|
+
};
|
|
192
|
+
}, [enabled, bodyEl, axis, sign, edge]);
|
|
193
|
+
if (!enabled) return {
|
|
194
|
+
delta: 0,
|
|
195
|
+
dragging: false,
|
|
196
|
+
dragProps: {},
|
|
197
|
+
bodyDragProps: {}
|
|
198
|
+
};
|
|
199
|
+
var common = {
|
|
200
|
+
onPointerMove: move,
|
|
201
|
+
onPointerUp: end,
|
|
202
|
+
onPointerCancel: reset
|
|
203
|
+
};
|
|
204
|
+
return {
|
|
205
|
+
delta: delta,
|
|
206
|
+
dragging: dragging,
|
|
207
|
+
dragProps: _objectSpread2(_objectSpread2({}, common), {}, {
|
|
208
|
+
onPointerDown: function onPointerDown(e) {
|
|
209
|
+
return start(e, false);
|
|
210
|
+
}
|
|
211
|
+
}),
|
|
212
|
+
bodyDragProps: _objectSpread2(_objectSpread2({}, common), {}, {
|
|
213
|
+
onPointerDown: function onPointerDown(e) {
|
|
214
|
+
return start(e, true);
|
|
215
|
+
}
|
|
216
|
+
})
|
|
217
|
+
};
|
|
218
|
+
}
|
|
219
|
+
|
|
220
|
+
export { FLICK_VELOCITY, rubberBand, useSheetDrag };
|