@rio-cloud/rio-uikit 2.0.0 → 2.1.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/components/actionBarItem/ActionBarItem.d.ts +2 -2
- package/components/actionBarItem/ActionBarItem.js.map +1 -1
- package/components/applicationHeader/ApplicationHeader.d.ts +6 -7
- package/components/applicationHeader/ApplicationHeader.js.map +1 -1
- package/components/applicationLayout/SubNavigation.d.ts +7 -0
- package/components/applicationLayout/SubNavigation.js.map +1 -1
- package/components/assetTree/AssetTree.d.ts +7 -0
- package/components/assetTree/AssetTree.js.map +1 -1
- package/components/assetTree/Tree.d.ts +15 -0
- package/components/assetTree/Tree.js.map +1 -1
- package/components/assetTree/TreeIcon.d.ts +30 -0
- package/components/assetTree/TreeIcon.js +16 -0
- package/components/assetTree/TreeIcon.js.map +1 -0
- package/components/assetTree/TreeLeaf.js +22 -22
- package/components/assetTree/TreeLeaf.js.map +1 -1
- package/components/assetTree/TreeNode.js +25 -25
- package/components/assetTree/TreeNode.js.map +1 -1
- package/components/assetTree/TreeSearch.d.ts +2 -0
- package/components/assetTree/TreeSearch.js.map +1 -1
- package/components/barList/BarList.d.ts +26 -0
- package/components/barList/BarList.js.map +1 -1
- package/components/bottomSheet/BottomSheet.d.ts +17 -3
- package/components/bottomSheet/BottomSheet.js.map +1 -1
- package/components/bottomSheet/TimedBottomSheet.d.ts +10 -0
- package/components/bottomSheet/TimedBottomSheet.js.map +1 -1
- package/components/calendarStripe/CalendarStripe.d.ts +1 -1
- package/components/calendarStripe/CalendarStripe.js +34 -36
- package/components/calendarStripe/CalendarStripe.js.map +1 -1
- package/components/charts/Area.d.ts +2 -2
- package/components/charts/Area.js.map +1 -1
- package/components/charts/Line.d.ts +2 -2
- package/components/charts/Line.js.map +1 -1
- package/components/checkbox/Checkbox.d.ts +0 -3
- package/components/checkbox/Checkbox.js.map +1 -1
- package/components/clearableInput/ClearableInput.d.ts +21 -20
- package/components/clearableInput/ClearableInput.js.map +1 -1
- package/components/collapse/Collapse.d.ts +3 -0
- package/components/collapse/Collapse.js +12 -12
- package/components/collapse/Collapse.js.map +1 -1
- package/components/contentLoader/ContentLoader.d.ts +10 -2
- package/components/contentLoader/ContentLoader.js.map +1 -1
- package/components/dataTabs/DataTabs.d.ts +6 -0
- package/components/dataTabs/DataTabs.js.map +1 -1
- package/components/datepicker/DatePicker.d.ts +2 -2
- package/components/datepicker/DatePicker.js +31 -31
- package/components/datepicker/DatePicker.js.map +1 -1
- package/components/dialog/ConfirmationDialog.d.ts +22 -0
- package/components/dialog/ConfirmationDialog.js.map +1 -1
- package/components/dialog/Dialog.d.ts +13 -1
- package/components/dialog/Dialog.js.map +1 -1
- package/components/dialog/ReleaseNotesDialog.d.ts +3 -3
- package/components/dialog/ReleaseNotesDialog.js.map +1 -1
- package/components/dropdown/ButtonDropdown.d.ts +4 -0
- package/components/dropdown/ButtonDropdown.js +51 -51
- package/components/dropdown/ButtonDropdown.js.map +1 -1
- package/components/dropdown/DropdownSubmenu.d.ts +4 -0
- package/components/dropdown/DropdownSubmenu.js.map +1 -1
- package/components/editableContent/EditableContent.d.ts +6 -0
- package/components/editableContent/EditableContent.js.map +1 -1
- package/components/expander/ExpanderList.d.ts +3 -0
- package/components/expander/ExpanderList.js.map +1 -1
- package/components/expander/ExpanderPanel.d.ts +14 -4
- package/components/expander/ExpanderPanel.js.map +1 -1
- package/components/fade/Fade.d.ts +1 -1
- package/components/fade/Fade.js.map +1 -1
- package/components/filepicker/FilePicker.d.ts +0 -2
- package/components/filepicker/FilePicker.js.map +1 -1
- package/components/groupedItemList/GroupedItemList.d.ts +10 -7
- package/components/groupedItemList/GroupedItemList.js.map +1 -1
- package/components/listMenu/ListMenu.js.map +1 -1
- package/components/listMenu/ListMenuGroup.d.ts +2 -1
- package/components/listMenu/ListMenuGroup.js.map +1 -1
- package/components/map/components/Map.js.map +1 -1
- package/components/map/components/constants.js.map +1 -1
- package/components/map/components/features/ContextMenuItem.d.ts +1 -1
- package/components/map/components/features/ContextMenuItem.js +2 -17
- package/components/map/components/features/ContextMenuItem.js.map +1 -1
- package/components/map/components/features/basics/Polyline.d.ts +4 -1
- package/components/map/components/features/basics/Polyline.js +1 -1
- package/components/map/components/features/basics/Polyline.js.map +1 -1
- package/components/map/components/features/layers/MarkerLayer.d.ts +3 -1
- package/components/map/components/features/layers/MarkerLayer.js.map +1 -1
- package/components/map/components/features/layers/clustering/ClusterLayer.js +1 -1
- package/components/map/components/features/layers/clustering/ClusterLayer.js.map +1 -1
- package/components/map/components/features/layers/clustering/SimpleClusterLayer.d.ts +3 -2
- package/components/map/components/features/layers/clustering/SimpleClusterLayer.js.map +1 -1
- package/components/map/components/features/layers/overlayLayers/RoadRestrictionLayer.js +7 -7
- package/components/map/components/features/layers/overlayLayers/RoadRestrictionLayer.js.map +1 -1
- package/components/map/components/features/layers/overlayLayers/TrafficLayer.js +4 -4
- package/components/map/components/features/layers/overlayLayers/TrafficLayer.js.map +1 -1
- package/components/map/utils/clustering.d.ts +6 -1
- package/components/map/utils/clustering.js +25 -19
- package/components/map/utils/clustering.js.map +1 -1
- package/components/map/utils/rendering.d.ts +1 -1
- package/components/map/utils/rendering.js +23 -23
- package/components/map/utils/rendering.js.map +1 -1
- package/components/menuItems/MenuItem.d.ts +23 -0
- package/components/menuItems/MenuItem.js.map +1 -1
- package/components/notification/Notification.js +4 -4
- package/components/notification/Notification.js.map +1 -1
- package/components/onboarding/OnboardingTip.d.ts +18 -12
- package/components/onboarding/OnboardingTip.js.map +1 -1
- package/components/overlay/OverlayTrigger.d.ts +43 -1
- package/components/overlay/OverlayTrigger.js.map +1 -1
- package/components/pager/Pager.d.ts +3 -0
- package/components/pager/Pager.js.map +1 -1
- package/components/popover/Popover.d.ts +1 -0
- package/components/popover/Popover.js.map +1 -1
- package/components/preloader/ImagePreloader.d.ts +1 -1
- package/components/preloader/ImagePreloader.js.map +1 -1
- package/components/radiobutton/RadioButton.d.ts +9 -5
- package/components/radiobutton/RadioButton.js.map +1 -1
- package/components/releaseNotes/ReleaseNotes.d.ts +0 -3
- package/components/releaseNotes/ReleaseNotes.js.map +1 -1
- package/components/resizer/Resizer.d.ts +17 -3
- package/components/resizer/Resizer.js.map +1 -1
- package/components/rioglyph/Rioglyph.d.ts +20 -8
- package/components/rioglyph/Rioglyph.js.map +1 -1
- package/components/rules/RulesWrapper.js +1 -1
- package/components/rules/RulesWrapper.js.map +1 -1
- package/components/saveableInput/SaveableDateInput.d.ts +20 -2
- package/components/saveableInput/SaveableDateInput.js.map +1 -1
- package/components/saveableInput/SaveableInput.d.ts +10 -2
- package/components/saveableInput/SaveableInput.js.map +1 -1
- package/components/selects/BaseSelectDropdown.js +90 -79
- package/components/selects/BaseSelectDropdown.js.map +1 -1
- package/components/selects/Select.d.ts +5 -0
- package/components/selects/Select.js +94 -94
- package/components/selects/Select.js.map +1 -1
- package/components/sidebars/Sidebar.d.ts +19 -3
- package/components/sidebars/Sidebar.js.map +1 -1
- package/components/slider/RangeSlider.d.ts +15 -0
- package/components/slider/RangeSlider.js.map +1 -1
- package/components/slider/Slider.d.ts +9 -0
- package/components/slider/Slider.js.map +1 -1
- package/components/smoothScrollbars/SmoothScrollbars.d.ts +44 -0
- package/components/smoothScrollbars/SmoothScrollbars.js.map +1 -1
- package/components/spinner/Spinner.d.ts +3 -3
- package/components/spinner/Spinner.js.map +1 -1
- package/components/states/BaseStateProps.d.ts +6 -2
- package/components/states/StateIcon.d.ts +14 -1
- package/components/states/StateIcon.js.map +1 -1
- package/components/statsWidget/StatsWidget.d.ts +2 -0
- package/components/statsWidget/StatsWidget.js.map +1 -1
- package/components/statsWidget/StatsWidgetBody.d.ts +1 -0
- package/components/statsWidget/StatsWidgetBody.js.map +1 -1
- package/components/statsWidget/StatsWidgetNumber.d.ts +2 -0
- package/components/statsWidget/StatsWidgetNumber.js.map +1 -1
- package/components/statusBar/StatusBar.d.ts +2 -31
- package/components/statusBar/StatusBar.js.map +1 -1
- package/components/statusBar/StatusBarIcon.d.ts +2 -2
- package/components/statusBar/StatusBarIcon.js.map +1 -1
- package/components/statusBar/StatusBarLabel.d.ts +2 -2
- package/components/statusBar/StatusBarLabel.js.map +1 -1
- package/components/statusBar/StatusBarProgressBar.d.ts +1 -1
- package/components/statusBar/StatusBarProgressBar.js.map +1 -1
- package/components/statusBar/{StatusBar.types.d.ts → StatusBarProps.d.ts} +44 -2
- package/components/steppedProgressBar/SteppedProgressBar.d.ts +1 -1
- package/components/steppedProgressBar/SteppedProgressBar.js.map +1 -1
- package/components/switch/Switch.d.ts +13 -1
- package/components/switch/Switch.js.map +1 -1
- package/components/table/SortArrowDown.d.ts +1 -1
- package/components/table/SortArrowDown.js.map +1 -1
- package/components/table/SortArrowUp.d.ts +1 -1
- package/components/table/SortArrowUp.js.map +1 -1
- package/components/table/TableSettingsDialog.d.ts +5 -0
- package/components/table/TableSettingsDialog.js +119 -109
- package/components/table/TableSettingsDialog.js.map +1 -1
- package/components/table/TableSettingsDialogFooter.js +9 -9
- package/components/table/TableSettingsDialogFooter.js.map +1 -1
- package/components/table/TableViewToggles.d.ts +21 -1
- package/components/table/TableViewToggles.js.map +1 -1
- package/components/tag/Tag.d.ts +7 -2
- package/components/tag/Tag.js.map +1 -1
- package/components/tagManager/TagManager.d.ts +15 -0
- package/components/tagManager/TagManager.js.map +1 -1
- package/components/tagManager/TagManagerTag.d.ts +9 -0
- package/components/teaser/Teaser.d.ts +57 -55
- package/components/teaser/Teaser.js.map +1 -1
- package/components/teaser/TeaserContainer.d.ts +1 -1
- package/components/teaser/TeaserContainer.js.map +1 -1
- package/components/tooltip/SimpleTooltip.d.ts +22 -4
- package/components/tooltip/SimpleTooltip.js.map +1 -1
- package/components/tooltip/Tooltip.d.ts +22 -2
- package/components/tooltip/Tooltip.js.map +1 -1
- package/components/video/ResponsiveVideo.d.ts +8 -3
- package/components/video/ResponsiveVideo.js.map +1 -1
- package/hooks/useKey.d.ts +1 -1
- package/hooks/useKey.js.map +1 -1
- package/hooks/useOnboarding.d.ts +86 -80
- package/hooks/useOnboarding.js.map +1 -1
- package/hooks/useTableExport.js.map +1 -1
- package/hooks/useUncontrollable.d.ts +1 -1
- package/hooks/useUncontrollable.js.map +1 -1
- package/package.json +12 -14
- package/utils/colorScheme.js +14 -13
- package/utils/colorScheme.js.map +1 -1
- package/utils/cssuseragent.js.map +1 -1
- package/utils/scrollItemIntoView.js +12 -11
- package/utils/scrollItemIntoView.js.map +1 -1
- package/utils/urlFeatureToggles.js +19 -20
- package/utils/urlFeatureToggles.js.map +1 -1
- package/version.d.ts +1 -1
- package/version.js +1 -1
- package/version.js.map +1 -1
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"BarList.js","sources":["../../../src/components/barList/BarList.tsx"],"sourcesContent":["import React, { useMemo } from 'react';\nimport classNames from 'classnames';\nimport { motion, type Variants } from 'motion/react';\n\nimport { SortDirection, type SortDirectionType } from '../../utils/SortUtils';\nimport { useSortedBars } from './useSortedBars';\n\nexport type BarListRow<T> = T & {\n key?: string;\n href?: string;\n value: number;\n name: string;\n color?: string; // individual progress color override\n barColor?: string; // individual bar color override\n background?: string; // individual background override\n};\n\n/**\n * Props for the BarList component.\n *\n * @template T - The type of the custom data associated with each bar row.\n */\ntype BarListProps<T = unknown> = React.HTMLAttributes<HTMLDivElement> & {\n /**\n * Array of bar row data to be rendered.\n */\n data: BarListRow<T>[];\n\n /**\n * Optional function to format the numeric value displayed on the right side of each bar.\n * Can return a string or a React element.\n *\n * @example\n * valueFormatter={(value) => `${value}%`}\n */\n valueFormatter?: (value: number) => string | React.ReactElement;\n\n /**\n * A reference value used to calculate relative widths.\n * If not provided, the maximum value in `data` will be used.\n *\n * @default max(data.value)\n */\n referenceValue?: number;\n\n /**\n * Whether to animate the bar width transitions using Framer Motion.\n *\n * @default false\n */\n showAnimation?: boolean;\n\n /**\n * Callback fired when a bar is clicked.\n *\n * @param payload - The full data object of the clicked bar.\n */\n onSelectRow?: (payload: BarListRow<T>) => void;\n\n /**\n * The sort order for the bars. Options are 'asc', 'desc', or 'none'.\n *\n * @default 'none'\n */\n sortOrder?: SortDirectionType | 'none';\n\n /**\n * Height of each bar row in pixels.\n *\n * @default 32\n */\n rowHeight?: number;\n\n /**\n * Opacity applied to non-hovered bars (between 0 and 1).\n *\n * @default 0.5\n */\n opacity?: number;\n\n /**\n * CSS color string used for the active/progress portion of each bar.\n *\n * @default 'bg-highlight-light'\n */\n barColor?: string;\n\n /**\n * CSS color string used for the text labels.\n *\n * @default 'text-color-darker'\n */\n labelColor?: string;\n\n /**\n * CSS color string used for the bar background.\n *\n * @default 'bg-transparent'\n */\n background?: string;\n\n /**\n * Additional className added to the wrapper element.\n */\n className?: string;\n};\n\n// Animation variants\nconst containerVariants: Variants = {\n animate: {\n transition: {\n staggerChildren: 0.1,\n },\n },\n};\n\nconst barVariants: Variants = {\n initial: { width: 0 },\n animate: (width: number) => ({\n width: `${width}%`,\n transition: { duration: 0.8, ease: 'easeOut' },\n }),\n};\n\nconst DEFAULT_ROW_HEIGHT = 25;\nconst DEFAULT_OPACITY = 0.5;\n\nconst BarListInner = <T,>(props: BarListProps<T>, forwardedRef: React.ForwardedRef<HTMLDivElement>) => {\n const {\n data = [],\n valueFormatter = value => value.toString(),\n showAnimation = false,\n onSelectRow,\n referenceValue,\n sortOrder = SortDirection.DESCENDING,\n barColor = 'bg-highlight-light',\n labelColor = 'text-color-darker',\n background = 'bg-transparent',\n rowHeight = DEFAULT_ROW_HEIGHT,\n opacity = DEFAULT_OPACITY,\n className = '',\n ...remainingProps\n } = props;\n\n const sortedData = useSortedBars(data, sortOrder, item => item.value);\n\n const [hoveredIndex, setHoveredIndex] = React.useState<number | null>(null);\n\n const widths = useMemo(() => {\n const base = referenceValue ?? Math.max(...sortedData.map(item => item.value), 0);\n return sortedData.map(item => (base === 0 || item.value === 0 ? 0 : Math.max((item.value / base) * 100, 2)));\n }, [sortedData, referenceValue]);\n\n return (\n <div\n {...remainingProps}\n ref={forwardedRef}\n className={classNames('display-flex justify-content-between gap-15', className)}\n >\n <motion.div\n variants={showAnimation ? containerVariants : undefined}\n initial='initial'\n animate='animate'\n className='width-100pct space-y-5'\n >\n {sortedData.map((item, index) => {\n const width = widths[index];\n\n const itemLabelColor = item.color ?? labelColor;\n const itemBarColor = item.barColor ?? barColor;\n const itemBackground = item.background ?? background;\n\n return (\n <div\n key={item.key ?? item.name}\n onMouseEnter={() => setHoveredIndex(index)}\n onMouseLeave={() => setHoveredIndex(null)}\n onClick={() => onSelectRow?.(item)}\n className={classNames(\n 'position-relative width-100pct rounded-small',\n 'transition-all transition-ease-in-out transition-duration-01',\n itemBackground,\n onSelectRow && 'cursor-pointer',\n hoveredIndex === index && 'bg-lightest'\n )}\n >\n {/* Animated Progress Bar */}\n <motion.div\n custom={width}\n variants={showAnimation ? barVariants : undefined}\n className={classNames(\n 'display-flex align-items-center rounded-small',\n 'transition-all transition-ease-in-out transition-duration-01',\n itemBarColor\n )}\n style={{ height: `${rowHeight}px`, opacity: hoveredIndex === index ? 1 : opacity }}\n role='presentation'\n />\n\n {/* Label */}\n <div className='position-absolute left-0 top-50pct translate-y-50pct display-flex width-100pct padding-left-10'>\n {item.href ? (\n <a\n href={item.href}\n className={itemLabelColor}\n target='_blank'\n rel='noreferrer'\n onClick={event => event.stopPropagation()}\n >\n {item.name}\n </a>\n ) : (\n <div className={itemLabelColor}>{item.name}</div>\n )}\n </div>\n </div>\n );\n })}\n </motion.div>\n\n {/* legend */}\n <div className='space-y-5'>\n {sortedData.map(item => (\n <div\n key={item.key ?? item.name}\n className={classNames('display-flex align-items-center justify-content-end')}\n style={{ height: `${rowHeight}px` }}\n >\n <div className='text-color-darkest'>{valueFormatter(item.value)}</div>\n </div>\n ))}\n </div>\n </div>\n );\n};\n\nBarListInner.displayName = 'BarList';\n\nconst BarList = React.forwardRef(BarListInner) as <T>(\n props: BarListProps<T> & { ref?: React.ForwardedRef<HTMLDivElement> }\n) => ReturnType<typeof BarListInner>;\n\nexport default BarList;\n"],"names":["containerVariants","barVariants","width","DEFAULT_ROW_HEIGHT","DEFAULT_OPACITY","BarListInner","props","forwardedRef","data","valueFormatter","value","showAnimation","onSelectRow","referenceValue","sortOrder","SortDirection","barColor","labelColor","background","rowHeight","opacity","className","remainingProps","sortedData","useSortedBars","item","hoveredIndex","setHoveredIndex","React","widths","useMemo","base","jsxs","classNames","jsx","motion","index","itemLabelColor","itemBarColor","itemBackground","event","BarList"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"BarList.js","sources":["../../../src/components/barList/BarList.tsx"],"sourcesContent":["import React, { useMemo } from 'react';\nimport classNames from 'classnames';\nimport { motion, type Variants } from 'motion/react';\n\nimport { SortDirection, type SortDirectionType } from '../../utils/SortUtils';\nimport { useSortedBars } from './useSortedBars';\n\n/**\n * A single entry in the BarList.\n *\n * @template T Custom payload merged into the row data.\n */\nexport type BarListRow<T> = T & {\n /**\n * Optional unique identifier. Falls back to `name` when not provided.\n */\n key?: string;\n\n /**\n * Optional URL. When provided, the label renders as a link.\n */\n href?: string;\n\n /**\n * Numeric value used for sorting and bar width calculations.\n */\n value: number;\n\n /**\n * Label shown for the bar.\n */\n name: string;\n\n /**\n * Text color override for this specific row.\n */\n color?: string;\n\n /**\n * Progress color override for this specific row.\n */\n barColor?: string;\n\n /**\n * Background color override for this specific row.\n */\n background?: string;\n};\n\n/**\n * Props for the BarList component.\n *\n * @template T - The type of the custom data associated with each bar row.\n */\ntype BarListProps<T = unknown> = React.HTMLAttributes<HTMLDivElement> & {\n /**\n * Array of bar row data to be rendered.\n */\n data: BarListRow<T>[];\n\n /**\n * Optional function to format the numeric value displayed on the right side of each bar.\n * Can return a string or a React element.\n *\n * @example\n * valueFormatter={(value) => `${value}%`}\n */\n valueFormatter?: (value: number) => string | React.ReactElement;\n\n /**\n * A reference value used to calculate relative widths.\n * If not provided, the maximum value in `data` will be used.\n *\n * @default max(data.value)\n */\n referenceValue?: number;\n\n /**\n * Whether to animate the bar width transitions using Framer Motion.\n *\n * @default false\n */\n showAnimation?: boolean;\n\n /**\n * Callback fired when a bar is clicked.\n *\n * @param payload - The full data object of the clicked bar.\n */\n onSelectRow?: (payload: BarListRow<T>) => void;\n\n /**\n * The sort order for the bars. Options are 'asc', 'desc', or 'none'.\n *\n * @default 'none'\n */\n sortOrder?: SortDirectionType | 'none';\n\n /**\n * Height of each bar row in pixels.\n *\n * @default 32\n */\n rowHeight?: number;\n\n /**\n * Opacity applied to non-hovered bars (between 0 and 1).\n *\n * @default 0.5\n */\n opacity?: number;\n\n /**\n * CSS color string used for the active/progress portion of each bar.\n *\n * @default 'bg-highlight-light'\n */\n barColor?: string;\n\n /**\n * CSS color string used for the text labels.\n *\n * @default 'text-color-darker'\n */\n labelColor?: string;\n\n /**\n * CSS color string used for the bar background.\n *\n * @default 'bg-transparent'\n */\n background?: string;\n\n /**\n * Additional className added to the wrapper element.\n */\n className?: string;\n};\n\n// Animation variants\nconst containerVariants: Variants = {\n animate: {\n transition: {\n staggerChildren: 0.1,\n },\n },\n};\n\nconst barVariants: Variants = {\n initial: { width: 0 },\n animate: (width: number) => ({\n width: `${width}%`,\n transition: { duration: 0.8, ease: 'easeOut' },\n }),\n};\n\nconst DEFAULT_ROW_HEIGHT = 25;\nconst DEFAULT_OPACITY = 0.5;\n\nconst BarListInner = <T,>(props: BarListProps<T>, forwardedRef: React.ForwardedRef<HTMLDivElement>) => {\n const {\n data = [],\n valueFormatter = value => value.toString(),\n showAnimation = false,\n onSelectRow,\n referenceValue,\n sortOrder = SortDirection.DESCENDING,\n barColor = 'bg-highlight-light',\n labelColor = 'text-color-darker',\n background = 'bg-transparent',\n rowHeight = DEFAULT_ROW_HEIGHT,\n opacity = DEFAULT_OPACITY,\n className = '',\n ...remainingProps\n } = props;\n\n const sortedData = useSortedBars(data, sortOrder, item => item.value);\n\n const [hoveredIndex, setHoveredIndex] = React.useState<number | null>(null);\n\n const widths = useMemo(() => {\n const base = referenceValue ?? Math.max(...sortedData.map(item => item.value), 0);\n return sortedData.map(item => (base === 0 || item.value === 0 ? 0 : Math.max((item.value / base) * 100, 2)));\n }, [sortedData, referenceValue]);\n\n return (\n <div\n {...remainingProps}\n ref={forwardedRef}\n className={classNames('display-flex justify-content-between gap-15', className)}\n >\n <motion.div\n variants={showAnimation ? containerVariants : undefined}\n initial='initial'\n animate='animate'\n className='width-100pct space-y-5'\n >\n {sortedData.map((item, index) => {\n const width = widths[index];\n\n const itemLabelColor = item.color ?? labelColor;\n const itemBarColor = item.barColor ?? barColor;\n const itemBackground = item.background ?? background;\n\n return (\n <div\n key={item.key ?? item.name}\n onMouseEnter={() => setHoveredIndex(index)}\n onMouseLeave={() => setHoveredIndex(null)}\n onClick={() => onSelectRow?.(item)}\n className={classNames(\n 'position-relative width-100pct rounded-small',\n 'transition-all transition-ease-in-out transition-duration-01',\n itemBackground,\n onSelectRow && 'cursor-pointer',\n hoveredIndex === index && 'bg-lightest'\n )}\n >\n {/* Animated Progress Bar */}\n <motion.div\n custom={width}\n variants={showAnimation ? barVariants : undefined}\n className={classNames(\n 'display-flex align-items-center rounded-small',\n 'transition-all transition-ease-in-out transition-duration-01',\n itemBarColor\n )}\n style={{ height: `${rowHeight}px`, opacity: hoveredIndex === index ? 1 : opacity }}\n role='presentation'\n />\n\n {/* Label */}\n <div className='position-absolute left-0 top-50pct translate-y-50pct display-flex width-100pct padding-left-10'>\n {item.href ? (\n <a\n href={item.href}\n className={itemLabelColor}\n target='_blank'\n rel='noreferrer'\n onClick={event => event.stopPropagation()}\n >\n {item.name}\n </a>\n ) : (\n <div className={itemLabelColor}>{item.name}</div>\n )}\n </div>\n </div>\n );\n })}\n </motion.div>\n\n {/* legend */}\n <div className='space-y-5'>\n {sortedData.map(item => (\n <div\n key={item.key ?? item.name}\n className={classNames('display-flex align-items-center justify-content-end')}\n style={{ height: `${rowHeight}px` }}\n >\n <div className='text-color-darkest'>{valueFormatter(item.value)}</div>\n </div>\n ))}\n </div>\n </div>\n );\n};\n\nBarListInner.displayName = 'BarList';\n\nconst BarList = React.forwardRef(BarListInner) as <T>(\n props: BarListProps<T> & { ref?: React.ForwardedRef<HTMLDivElement> }\n) => ReturnType<typeof BarListInner>;\n\nexport default BarList;\n"],"names":["containerVariants","barVariants","width","DEFAULT_ROW_HEIGHT","DEFAULT_OPACITY","BarListInner","props","forwardedRef","data","valueFormatter","value","showAnimation","onSelectRow","referenceValue","sortOrder","SortDirection","barColor","labelColor","background","rowHeight","opacity","className","remainingProps","sortedData","useSortedBars","item","hoveredIndex","setHoveredIndex","React","widths","useMemo","base","jsxs","classNames","jsx","motion","index","itemLabelColor","itemBarColor","itemBackground","event","BarList"],"mappings":"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"}
|
|
@@ -2,6 +2,7 @@ import { MutableRefObject, PropsWithChildren, ReactElement, ReactNode } from 're
|
|
|
2
2
|
export type BottomSheetProps = {
|
|
3
3
|
/**
|
|
4
4
|
* Set the visibility of the bottom sheet. The component is already mounted and just moved offscreen.
|
|
5
|
+
*
|
|
5
6
|
* @default false
|
|
6
7
|
*/
|
|
7
8
|
show: boolean;
|
|
@@ -36,32 +37,45 @@ export type BottomSheetProps = {
|
|
|
36
37
|
showMaximizeButton?: boolean;
|
|
37
38
|
/**
|
|
38
39
|
* The callback function triggered when the maximize button is clicked and the height changes.
|
|
40
|
+
*
|
|
41
|
+
* @default () => {}
|
|
39
42
|
*/
|
|
40
43
|
onHeightChange?: VoidFunction;
|
|
41
44
|
/**
|
|
42
45
|
* Set to `true` to detach the bottom sheet from the left side and the bottom and create a little offset.
|
|
46
|
+
*
|
|
43
47
|
* @default false
|
|
44
48
|
*/
|
|
45
49
|
detach?: boolean;
|
|
46
50
|
/**
|
|
47
51
|
* Defines the amount of pixels for the sheet.
|
|
52
|
+
*
|
|
48
53
|
* @default 15
|
|
49
54
|
*/
|
|
50
55
|
detachOffset?: number;
|
|
51
56
|
/**
|
|
52
57
|
* Set to `true` to render a modal like backdrop to emphasize the bottom sheet.
|
|
58
|
+
*
|
|
53
59
|
* @default false
|
|
54
60
|
*/
|
|
55
61
|
hasBackdrop?: boolean;
|
|
56
62
|
/**
|
|
57
63
|
* Callback function triggered when the backdrop is clicked. Usually used to close the bottom sheet.
|
|
64
|
+
*
|
|
65
|
+
* @default () => {}
|
|
58
66
|
*/
|
|
59
67
|
onBackdropClick?: VoidFunction;
|
|
60
|
-
/**
|
|
68
|
+
/**
|
|
69
|
+
* A react ref added to the bottom sheet body.
|
|
70
|
+
*/
|
|
61
71
|
bodyRef?: MutableRefObject<HTMLDivElement | null>;
|
|
62
|
-
/**
|
|
72
|
+
/**
|
|
73
|
+
* Additional classes to be set on the body element.
|
|
74
|
+
*/
|
|
63
75
|
bodyClassName?: string;
|
|
64
|
-
/**
|
|
76
|
+
/**
|
|
77
|
+
* Additional classes to be set on the wrapping element.
|
|
78
|
+
*/
|
|
65
79
|
className?: string;
|
|
66
80
|
};
|
|
67
81
|
declare const BottomSheet: (props: BottomSheetProps & PropsWithChildren) => ReactElement;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"BottomSheet.js","sources":["../../../src/components/bottomSheet/BottomSheet.tsx"],"sourcesContent":["import {\n type MutableRefObject,\n type PropsWithChildren,\n type ReactElement,\n type ReactNode,\n useEffect,\n useState,\n} from 'react';\nimport { createPortal } from 'react-dom';\nimport classNames from 'classnames';\nimport { motion } from 'motion/react';\nimport { isFunction } from 'es-toolkit/predicate';\n\nimport { getOrCreatePortalRoot } from '../../utils/portalRoot';\n\nconst OFFSET_POSITION = -1000;\nconst DEFAULT_OFFSET_PX = 15;\n\nexport type BottomSheetProps = {\n /**\n * Set the visibility of the bottom sheet. The component is already mounted and just moved offscreen.\n * @default false\n */\n show: boolean;\n\n /**\n * Callback for when the sheet closes.\n */\n onClose?: (isShown: boolean) => void;\n\n /**\n * The width of the bottom sheet. This is useful for desktop when not using the entire screen width.\n * When no width is given it will take the width of the content and maximum `100%` of the screen.\n * So it this case you might want to apply a `max-width-xxx` via `className` to control it better.\n */\n width?: number | string;\n\n /**\n * The height of the bottom sheet. If no height is given, the height is automatically\n * calculated from the content.\n */\n height?: number | string;\n\n /**\n * The title content shown in the header. If no title is given, the bottom sheet header is not shown.\n */\n title?: string | ReactNode;\n\n /**\n * Defines whether or not the close button is shown.\n * @default true\n */\n showCloseButton?: boolean;\n\n /**\n * Defines whether or not the maximize button in the header is shown.\n * @default false\n */\n showMaximizeButton?: boolean;\n\n /**\n * The callback function triggered when the maximize button is clicked and the height changes.\n */\n onHeightChange?: VoidFunction;\n\n /**\n * Set to `true` to detach the bottom sheet from the left side and the bottom and create a little offset.\n * @default false\n */\n detach?: boolean;\n\n /**\n * Defines the amount of pixels for the sheet.\n * @default 15\n */\n detachOffset?: number;\n\n /**\n * Set to `true` to render a modal like backdrop to emphasize the bottom sheet.\n * @default false\n */\n hasBackdrop?: boolean;\n\n /**\n * Callback function triggered when the backdrop is clicked. Usually used to close the bottom sheet.\n */\n onBackdropClick?: VoidFunction;\n\n /** A react ref added to the bottom sheet body. */\n bodyRef?: MutableRefObject<HTMLDivElement | null>;\n\n /** Additional classes to be set on the body element. */\n bodyClassName?: string;\n\n /** Additional classes to be set on the wrapping element. */\n className?: string;\n};\n\nconst BottomSheet = (props: BottomSheetProps & PropsWithChildren) => {\n const {\n show = false,\n onClose,\n width,\n height,\n title,\n detach = false,\n detachOffset = DEFAULT_OFFSET_PX,\n hasBackdrop = false,\n showCloseButton = true,\n showMaximizeButton = false,\n onHeightChange = () => {},\n bodyRef,\n bodyClassName,\n className,\n children,\n onBackdropClick = () => {},\n ...remainingProps\n } = props;\n\n const [isShown, setIsShown] = useState(show);\n const [isMaxHeight, setIsMaxHeight] = useState(false);\n\n useEffect(() => setIsShown(show), [show]);\n\n const modalRoot = getOrCreatePortalRoot();\n\n const handleToggle = () => {\n const newValue = !isShown;\n if (isFunction(onClose)) {\n onClose(newValue);\n } else {\n setIsShown(newValue);\n }\n };\n\n const handleBackdropClick = () => {\n onBackdropClick();\n handleToggle();\n };\n\n const handleMaximize = () => {\n const newValue = !isMaxHeight;\n setIsMaxHeight(newValue);\n onHeightChange();\n };\n\n const sheetClasses = classNames(\n 'bottom-sheet',\n 'position-fixed left-0',\n !height && !isMaxHeight && 'height-auto',\n 'bg-white',\n 'shadow-hard',\n detach ? 'rounded' : 'rounded-top-left rounded-top-right',\n className && className\n );\n\n const sheetBodyClasses = classNames('bottom-sheet-body', 'height-100pct', bodyClassName && bodyClassName);\n\n const sheetHeight = isMaxHeight ? window.innerHeight : height;\n\n // Note: we always have to kep the body element in the DOM as there might be a ref assigned to it.\n // Unmounting it will lead to losing the reference and breaking the functionality that is implemented on that ref.\n // That is the reason why there is no \"AnimatePresence\" with an \"exit\" animation here.\n // Instead, we change the \"animate\" values.\n\n return createPortal(\n <>\n <motion.div\n {...remainingProps}\n className={sheetClasses}\n style={{\n width,\n maxWidth: detach ? `calc(100% - ${DEFAULT_OFFSET_PX * 2}px)` : '100%',\n margin: detach ? `${DEFAULT_OFFSET_PX}px` : 0,\n }}\n initial={{ opacity: 0 }}\n animate={{\n opacity: isShown ? 1 : 0,\n y: 0,\n bottom: isShown ? 0 : OFFSET_POSITION,\n height: isShown ? sheetHeight : 0,\n }}\n >\n <div className='bottom-sheet-header'>\n {title && (\n <div\n className={\n 'bottom-sheet-title display-flex justify-content-between padding-15 ' +\n 'border border-top-none border-left-none border-right-none border-color-lighter'\n }\n >\n <div className='text-size-18'>{title}</div>\n </div>\n )}\n {showCloseButton && (\n <div className='bottom-sheet-close position-absolute top-10 right-10'>\n <button type='button' className='btn btn-muted btn-sm btn-icon-only' onClick={handleToggle}>\n <span className='rioglyph rioglyph-remove' />\n </button>\n </div>\n )}\n {showMaximizeButton && (\n <div\n className={\n 'bottom-sheet-maximize height-30 ' +\n 'position-absolute top-5 left-50pct translate-x-50 cursor-pointer'\n }\n onClick={handleMaximize}\n >\n <div className='height-5 width-40 rounded bg-lighter' />\n </div>\n )}\n </div>\n <div className={sheetBodyClasses} ref={bodyRef}>\n {isShown && children}\n </div>\n </motion.div>\n\n {hasBackdrop && isShown && <div className='bottom-sheet-backdrop' onClick={handleBackdropClick} />}\n </>,\n modalRoot\n ) as ReactElement;\n};\n\nexport default BottomSheet;\n"],"names":["OFFSET_POSITION","DEFAULT_OFFSET_PX","BottomSheet","props","show","onClose","width","height","title","detach","detachOffset","hasBackdrop","showCloseButton","showMaximizeButton","onHeightChange","bodyRef","bodyClassName","className","children","onBackdropClick","remainingProps","isShown","setIsShown","useState","isMaxHeight","setIsMaxHeight","useEffect","modalRoot","getOrCreatePortalRoot","handleToggle","newValue","isFunction","handleBackdropClick","handleMaximize","sheetClasses","classNames","sheetBodyClasses","sheetHeight","createPortal","jsxs","Fragment","motion","jsx"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"BottomSheet.js","sources":["../../../src/components/bottomSheet/BottomSheet.tsx"],"sourcesContent":["import {\n type MutableRefObject,\n type PropsWithChildren,\n type ReactElement,\n type ReactNode,\n useEffect,\n useState,\n} from 'react';\nimport { createPortal } from 'react-dom';\nimport classNames from 'classnames';\nimport { motion } from 'motion/react';\nimport { isFunction } from 'es-toolkit/predicate';\n\nimport { getOrCreatePortalRoot } from '../../utils/portalRoot';\n\nconst OFFSET_POSITION = -1000;\nconst DEFAULT_OFFSET_PX = 15;\n\nexport type BottomSheetProps = {\n /**\n * Set the visibility of the bottom sheet. The component is already mounted and just moved offscreen.\n *\n * @default false\n */\n show: boolean;\n\n /**\n * Callback for when the sheet closes.\n */\n onClose?: (isShown: boolean) => void;\n\n /**\n * The width of the bottom sheet. This is useful for desktop when not using the entire screen width.\n * When no width is given it will take the width of the content and maximum `100%` of the screen.\n * So it this case you might want to apply a `max-width-xxx` via `className` to control it better.\n */\n width?: number | string;\n\n /**\n * The height of the bottom sheet. If no height is given, the height is automatically\n * calculated from the content.\n */\n height?: number | string;\n\n /**\n * The title content shown in the header. If no title is given, the bottom sheet header is not shown.\n */\n title?: string | ReactNode;\n\n /**\n * Defines whether or not the close button is shown.\n * @default true\n */\n showCloseButton?: boolean;\n\n /**\n * Defines whether or not the maximize button in the header is shown.\n * @default false\n */\n showMaximizeButton?: boolean;\n\n /**\n * The callback function triggered when the maximize button is clicked and the height changes.\n *\n * @default () => {}\n */\n onHeightChange?: VoidFunction;\n\n /**\n * Set to `true` to detach the bottom sheet from the left side and the bottom and create a little offset.\n *\n * @default false\n */\n detach?: boolean;\n\n /**\n * Defines the amount of pixels for the sheet.\n *\n * @default 15\n */\n detachOffset?: number;\n\n /**\n * Set to `true` to render a modal like backdrop to emphasize the bottom sheet.\n *\n * @default false\n */\n hasBackdrop?: boolean;\n\n /**\n * Callback function triggered when the backdrop is clicked. Usually used to close the bottom sheet.\n *\n * @default () => {}\n */\n onBackdropClick?: VoidFunction;\n\n /**\n * A react ref added to the bottom sheet body.\n */\n bodyRef?: MutableRefObject<HTMLDivElement | null>;\n\n /**\n * Additional classes to be set on the body element.\n */\n bodyClassName?: string;\n\n /**\n * Additional classes to be set on the wrapping element.\n */\n className?: string;\n};\n\nconst BottomSheet = (props: BottomSheetProps & PropsWithChildren) => {\n const {\n show = false,\n onClose,\n width,\n height,\n title,\n detach = false,\n detachOffset = DEFAULT_OFFSET_PX,\n hasBackdrop = false,\n showCloseButton = true,\n showMaximizeButton = false,\n onHeightChange = () => {},\n bodyRef,\n bodyClassName,\n className,\n children,\n onBackdropClick = () => {},\n ...remainingProps\n } = props;\n\n const [isShown, setIsShown] = useState(show);\n const [isMaxHeight, setIsMaxHeight] = useState(false);\n\n useEffect(() => setIsShown(show), [show]);\n\n const modalRoot = getOrCreatePortalRoot();\n\n const handleToggle = () => {\n const newValue = !isShown;\n if (isFunction(onClose)) {\n onClose(newValue);\n } else {\n setIsShown(newValue);\n }\n };\n\n const handleBackdropClick = () => {\n onBackdropClick();\n handleToggle();\n };\n\n const handleMaximize = () => {\n const newValue = !isMaxHeight;\n setIsMaxHeight(newValue);\n onHeightChange();\n };\n\n const sheetClasses = classNames(\n 'bottom-sheet',\n 'position-fixed left-0',\n !height && !isMaxHeight && 'height-auto',\n 'bg-white',\n 'shadow-hard',\n detach ? 'rounded' : 'rounded-top-left rounded-top-right',\n className && className\n );\n\n const sheetBodyClasses = classNames('bottom-sheet-body', 'height-100pct', bodyClassName && bodyClassName);\n\n const sheetHeight = isMaxHeight ? window.innerHeight : height;\n\n // Note: we always have to kep the body element in the DOM as there might be a ref assigned to it.\n // Unmounting it will lead to losing the reference and breaking the functionality that is implemented on that ref.\n // That is the reason why there is no \"AnimatePresence\" with an \"exit\" animation here.\n // Instead, we change the \"animate\" values.\n\n return createPortal(\n <>\n <motion.div\n {...remainingProps}\n className={sheetClasses}\n style={{\n width,\n maxWidth: detach ? `calc(100% - ${DEFAULT_OFFSET_PX * 2}px)` : '100%',\n margin: detach ? `${DEFAULT_OFFSET_PX}px` : 0,\n }}\n initial={{ opacity: 0 }}\n animate={{\n opacity: isShown ? 1 : 0,\n y: 0,\n bottom: isShown ? 0 : OFFSET_POSITION,\n height: isShown ? sheetHeight : 0,\n }}\n >\n <div className='bottom-sheet-header'>\n {title && (\n <div\n className={\n 'bottom-sheet-title display-flex justify-content-between padding-15 ' +\n 'border border-top-none border-left-none border-right-none border-color-lighter'\n }\n >\n <div className='text-size-18'>{title}</div>\n </div>\n )}\n {showCloseButton && (\n <div className='bottom-sheet-close position-absolute top-10 right-10'>\n <button type='button' className='btn btn-muted btn-sm btn-icon-only' onClick={handleToggle}>\n <span className='rioglyph rioglyph-remove' />\n </button>\n </div>\n )}\n {showMaximizeButton && (\n <div\n className={\n 'bottom-sheet-maximize height-30 ' +\n 'position-absolute top-5 left-50pct translate-x-50 cursor-pointer'\n }\n onClick={handleMaximize}\n >\n <div className='height-5 width-40 rounded bg-lighter' />\n </div>\n )}\n </div>\n <div className={sheetBodyClasses} ref={bodyRef}>\n {isShown && children}\n </div>\n </motion.div>\n\n {hasBackdrop && isShown && <div className='bottom-sheet-backdrop' onClick={handleBackdropClick} />}\n </>,\n modalRoot\n ) as ReactElement;\n};\n\nexport default BottomSheet;\n"],"names":["OFFSET_POSITION","DEFAULT_OFFSET_PX","BottomSheet","props","show","onClose","width","height","title","detach","detachOffset","hasBackdrop","showCloseButton","showMaximizeButton","onHeightChange","bodyRef","bodyClassName","className","children","onBackdropClick","remainingProps","isShown","setIsShown","useState","isMaxHeight","setIsMaxHeight","useEffect","modalRoot","getOrCreatePortalRoot","handleToggle","newValue","isFunction","handleBackdropClick","handleMaximize","sheetClasses","classNames","sheetBodyClasses","sheetHeight","createPortal","jsxs","Fragment","motion","jsx"],"mappings":"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"}
|
|
@@ -4,6 +4,8 @@ type TimedBottomSheetProps = {
|
|
|
4
4
|
* The `dismissed` flag can be used to tell this component that the user has clicked on the content
|
|
5
5
|
* of the component like a button or a link. In this case, the bottom sheet will store a flag in the
|
|
6
6
|
* localStorage to hide the bottom sheet for the next time and it will close the sheet right away.
|
|
7
|
+
*
|
|
8
|
+
* @default false
|
|
7
9
|
*/
|
|
8
10
|
dismissed?: boolean;
|
|
9
11
|
/**
|
|
@@ -27,11 +29,13 @@ type TimedBottomSheetProps = {
|
|
|
27
29
|
hideAfter?: number;
|
|
28
30
|
/**
|
|
29
31
|
* With this enabled, the BottomSheet will not hide automatically.
|
|
32
|
+
*
|
|
30
33
|
* @default false
|
|
31
34
|
*/
|
|
32
35
|
alwaysOn?: boolean;
|
|
33
36
|
/**
|
|
34
37
|
* Enables or disabled the close button.
|
|
38
|
+
*
|
|
35
39
|
* @default true
|
|
36
40
|
*/
|
|
37
41
|
showCloseButton?: boolean;
|
|
@@ -41,6 +45,8 @@ type TimedBottomSheetProps = {
|
|
|
41
45
|
width?: number;
|
|
42
46
|
/**
|
|
43
47
|
* Flag to allow to remove the localStorage flag again once the component is not needed anymore.
|
|
48
|
+
*
|
|
49
|
+
* @default false
|
|
44
50
|
*/
|
|
45
51
|
cleanupLocalStorage?: boolean;
|
|
46
52
|
/**
|
|
@@ -51,11 +57,15 @@ type TimedBottomSheetProps = {
|
|
|
51
57
|
localStoragePrefix?: string;
|
|
52
58
|
/**
|
|
53
59
|
* Callback function that gets triggered when the user closed the bottom sheet with the close button.
|
|
60
|
+
*
|
|
61
|
+
* @default () => {}
|
|
54
62
|
* @returns void
|
|
55
63
|
*/
|
|
56
64
|
onClose?: () => void;
|
|
57
65
|
/**
|
|
58
66
|
* Optional className to be set on the body.
|
|
67
|
+
*
|
|
68
|
+
* @default 'padding-25 margin-right-25'
|
|
59
69
|
*/
|
|
60
70
|
bodyClassName?: string;
|
|
61
71
|
/**
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"TimedBottomSheet.js","sources":["../../../src/components/bottomSheet/TimedBottomSheet.tsx"],"sourcesContent":["import { useState, useEffect, type PropsWithChildren } from 'react';\nimport { noop } from 'es-toolkit/function';\n\nimport BottomSheet from './BottomSheet';\nimport useTimeout from '../../hooks/useTimeout';\nimport useLocalStorage from '../../useLocalStorage';\n\nconst DEFAULT_SHOW_AFTER = 0; // immediately after mount\nconst DEFAULT_HIDE_AFTER = 3_600_000; // after 1 hour\n\n// Features:\n// [x] show delayed\n// [x] option to hide automatically after x\n// [x] store closed user state in localStorage\n// [x] don't show when user has clicked to hide - per feature\n// [x] Cleanup localStorage feature\n// [x] hide on click inside of content (button or link, etc.) - control from outside\n// [-] GA tracking of user hide click - should be done outside\n\ntype TimedBottomSheetProps = {\n /**\n * The `dismissed` flag can be used to tell this component that the user has clicked on the content\n * of the component like a button or a link. In this case, the bottom sheet will store a flag in the\n * localStorage to hide the bottom sheet for the next time and it will close the sheet right away.\n */\n dismissed?: boolean;\n\n /**\n * The `featureName` prop is used to name the localStorage flag that is used to control the visibility.\n * It should be unique to avoid conflicts with other timed bottom sheets.\n */\n featureName: string;\n\n /**\n * Defines the time in milliseconds when the bottom sheet shall be shown. Default value is 0 to show it right away.\n *\n * @default 0\n */\n showAfter?: number;\n\n /**\n * Defines the time in milliseconds when the bottom sheet hides itself automatically. Default value is 3_600_000\n * to hide it after 1 hour. In this case, the localStorage flag is not set and the bottom sheet will be shown\n * on the next page load.\n *\n * @default 3_600_000\n */\n hideAfter?: number;\n\n /**\n * With this enabled, the BottomSheet will not hide automatically.\n * @default false\n */\n alwaysOn?: boolean;\n\n /**\n * Enables or disabled the close button.\n * @default true\n */\n showCloseButton?: boolean;\n\n /**\n * Optional width of the bottom sheet. Alternatively, you can set a `max-width-xxx` via className instead.\n */\n width?: number;\n\n /**\n * Flag to allow to remove the localStorage flag again once the component is not needed anymore.\n */\n cleanupLocalStorage?: boolean;\n\n /**\n * A prefix that will be used for the local storage flag to store whether the bottom sheet should be hidden.\n *\n * Use this prefix for your service name for instance.\n */\n localStoragePrefix?: string;\n\n /**\n * Callback function that gets triggered when the user closed the bottom sheet with the close button.\n * @returns void\n */\n onClose?: () => void;\n\n /**\n * Optional className to be set on the body.\n */\n bodyClassName?: string;\n\n /**\n * Optional className to be set on the component. Use this to define a max-width value.\n */\n className?: string;\n};\n\nconst sanitizeFeatureName = (value: string) => `${value.charAt(0).toUpperCase()}${value.slice(1)}`.replaceAll(' ', '');\n\n/**\n * A wrapper component for the BottomSheet that allows to control it's visibility via timers and to use\n * the localStorage to save user interaction.\n *\n * Don't forget to cleanup the localStorage for the user when removing a feature\n * by setting \"cleanupLocalStorage\" to \"true\" and deploy it like this.\n * The cleanup will remove the localStorage flag on mount and will not show the bottom sheet.\n *\n * @example\n const [isDismissed, setIsDismissed] = useState(false);\n\n const handleClose = () => { // If needed trigger Google Analytics here };\n\n return (\n <TimedBottomSheet\n dismissed={isDismissed}\n featureName='dummyBottomSheet'\n showAfter={1_000}\n hideAfter={15_000}\n className='max-width-500'\n onClose={handleClose}\n >\n <div className='display-flex align-items-center gap-20'>\n Lorem ipsum dolor sit amet\n <Button bsStyle={Button.PRIMARY} onClick={() => setIsDismissed(true)}>\n Got it\n </Button>\n </div>\n </TimedBottomSheet>\n );\n */\nexport const TimedBottomSheet = (props: PropsWithChildren<TimedBottomSheetProps>) => {\n const {\n dismissed = false,\n featureName,\n showAfter = DEFAULT_SHOW_AFTER,\n hideAfter = DEFAULT_HIDE_AFTER,\n alwaysOn = false,\n showCloseButton = true,\n width,\n cleanupLocalStorage = false,\n onClose = noop,\n bodyClassName = 'padding-25 margin-right-25',\n localStoragePrefix = '',\n className,\n children,\n ...remainingProps\n } = props;\n\n const [showBottomSheet, setShowBottomSheet] = useState(false);\n\n const [isHiddenByUser, setIsHiddenByUser, removeIsHiddenFlag] = useLocalStorage(\n `${localStoragePrefix}hide${sanitizeFeatureName(featureName)}`,\n false\n );\n\n // In case the visibility is controlled by the outside, means the user clicked on the\n // content of the bottom sheet, close the sheet and set the localStorage flag for not\n // showing it again\n const [prevDismissed, setPrevDismissed] = useState(dismissed);\n if (dismissed && dismissed !== prevDismissed) {\n setPrevDismissed(dismissed);\n setIsHiddenByUser(true);\n setShowBottomSheet(false);\n }\n\n // Show the bottom sheet automatically after a given amount of time\n useTimeout(() => {\n if (!dismissed && !isHiddenByUser && !cleanupLocalStorage) {\n setShowBottomSheet(true);\n }\n }, showAfter);\n\n // Hide the bottom sheet automatically after a given amount of time\n useTimeout(() => setShowBottomSheet(alwaysOn ? true : false), showAfter + hideAfter);\n\n // Cleanup functionality. The cleanup will remove the localStorage flag on mount\n // and will not show the bottom sheet.\n useEffect(() => {\n if (cleanupLocalStorage) {\n removeIsHiddenFlag();\n }\n }, []);\n\n const handleCloseBottomSheet = () => {\n setShowBottomSheet(false);\n setIsHiddenByUser(true);\n onClose();\n };\n\n return (\n <div {...remainingProps}>\n <BottomSheet\n show={showBottomSheet}\n width={width}\n detach\n showCloseButton={showCloseButton}\n onClose={handleCloseBottomSheet}\n className={className}\n bodyClassName={bodyClassName}\n >\n {children}\n </BottomSheet>\n </div>\n );\n};\n\nexport default TimedBottomSheet;\n"],"names":["DEFAULT_SHOW_AFTER","DEFAULT_HIDE_AFTER","sanitizeFeatureName","value","TimedBottomSheet","props","dismissed","featureName","showAfter","hideAfter","alwaysOn","showCloseButton","width","cleanupLocalStorage","onClose","noop","bodyClassName","localStoragePrefix","className","children","remainingProps","showBottomSheet","setShowBottomSheet","useState","isHiddenByUser","setIsHiddenByUser","removeIsHiddenFlag","useLocalStorage","prevDismissed","setPrevDismissed","useTimeout","useEffect","jsx","BottomSheet"],"mappings":";;;;;;AAOA,MAAMA,IAAqB,GACrBC,IAAqB,
|
|
1
|
+
{"version":3,"file":"TimedBottomSheet.js","sources":["../../../src/components/bottomSheet/TimedBottomSheet.tsx"],"sourcesContent":["import { useState, useEffect, type PropsWithChildren } from 'react';\nimport { noop } from 'es-toolkit/function';\n\nimport BottomSheet from './BottomSheet';\nimport useTimeout from '../../hooks/useTimeout';\nimport useLocalStorage from '../../useLocalStorage';\n\nconst DEFAULT_SHOW_AFTER = 0; // immediately after mount\nconst DEFAULT_HIDE_AFTER = 3_600_000; // after 1 hour\n\n// Features:\n// [x] show delayed\n// [x] option to hide automatically after x\n// [x] store closed user state in localStorage\n// [x] don't show when user has clicked to hide - per feature\n// [x] Cleanup localStorage feature\n// [x] hide on click inside of content (button or link, etc.) - control from outside\n// [-] GA tracking of user hide click - should be done outside\n\ntype TimedBottomSheetProps = {\n /**\n * The `dismissed` flag can be used to tell this component that the user has clicked on the content\n * of the component like a button or a link. In this case, the bottom sheet will store a flag in the\n * localStorage to hide the bottom sheet for the next time and it will close the sheet right away.\n *\n * @default false\n */\n dismissed?: boolean;\n\n /**\n * The `featureName` prop is used to name the localStorage flag that is used to control the visibility.\n * It should be unique to avoid conflicts with other timed bottom sheets.\n */\n featureName: string;\n\n /**\n * Defines the time in milliseconds when the bottom sheet shall be shown. Default value is 0 to show it right away.\n *\n * @default 0\n */\n showAfter?: number;\n\n /**\n * Defines the time in milliseconds when the bottom sheet hides itself automatically. Default value is 3_600_000\n * to hide it after 1 hour. In this case, the localStorage flag is not set and the bottom sheet will be shown\n * on the next page load.\n *\n * @default 3_600_000\n */\n hideAfter?: number;\n\n /**\n * With this enabled, the BottomSheet will not hide automatically.\n *\n * @default false\n */\n alwaysOn?: boolean;\n\n /**\n * Enables or disabled the close button.\n *\n * @default true\n */\n showCloseButton?: boolean;\n\n /**\n * Optional width of the bottom sheet. Alternatively, you can set a `max-width-xxx` via className instead.\n */\n width?: number;\n\n /**\n * Flag to allow to remove the localStorage flag again once the component is not needed anymore.\n *\n * @default false\n */\n cleanupLocalStorage?: boolean;\n\n /**\n * A prefix that will be used for the local storage flag to store whether the bottom sheet should be hidden.\n *\n * Use this prefix for your service name for instance.\n */\n localStoragePrefix?: string;\n\n /**\n * Callback function that gets triggered when the user closed the bottom sheet with the close button.\n *\n * @default () => {}\n * @returns void\n */\n onClose?: () => void;\n\n /**\n * Optional className to be set on the body.\n *\n * @default 'padding-25 margin-right-25'\n */\n bodyClassName?: string;\n\n /**\n * Optional className to be set on the component. Use this to define a max-width value.\n */\n className?: string;\n};\n\nconst sanitizeFeatureName = (value: string) => `${value.charAt(0).toUpperCase()}${value.slice(1)}`.replaceAll(' ', '');\n\n/**\n * A wrapper component for the BottomSheet that allows to control it's visibility via timers and to use\n * the localStorage to save user interaction.\n *\n * Don't forget to cleanup the localStorage for the user when removing a feature\n * by setting \"cleanupLocalStorage\" to \"true\" and deploy it like this.\n * The cleanup will remove the localStorage flag on mount and will not show the bottom sheet.\n *\n * @example\n const [isDismissed, setIsDismissed] = useState(false);\n\n const handleClose = () => { // If needed trigger Google Analytics here };\n\n return (\n <TimedBottomSheet\n dismissed={isDismissed}\n featureName='dummyBottomSheet'\n showAfter={1_000}\n hideAfter={15_000}\n className='max-width-500'\n onClose={handleClose}\n >\n <div className='display-flex align-items-center gap-20'>\n Lorem ipsum dolor sit amet\n <Button bsStyle={Button.PRIMARY} onClick={() => setIsDismissed(true)}>\n Got it\n </Button>\n </div>\n </TimedBottomSheet>\n );\n */\nexport const TimedBottomSheet = (props: PropsWithChildren<TimedBottomSheetProps>) => {\n const {\n dismissed = false,\n featureName,\n showAfter = DEFAULT_SHOW_AFTER,\n hideAfter = DEFAULT_HIDE_AFTER,\n alwaysOn = false,\n showCloseButton = true,\n width,\n cleanupLocalStorage = false,\n onClose = noop,\n bodyClassName = 'padding-25 margin-right-25',\n localStoragePrefix = '',\n className,\n children,\n ...remainingProps\n } = props;\n\n const [showBottomSheet, setShowBottomSheet] = useState(false);\n\n const [isHiddenByUser, setIsHiddenByUser, removeIsHiddenFlag] = useLocalStorage(\n `${localStoragePrefix}hide${sanitizeFeatureName(featureName)}`,\n false\n );\n\n // In case the visibility is controlled by the outside, means the user clicked on the\n // content of the bottom sheet, close the sheet and set the localStorage flag for not\n // showing it again\n const [prevDismissed, setPrevDismissed] = useState(dismissed);\n if (dismissed && dismissed !== prevDismissed) {\n setPrevDismissed(dismissed);\n setIsHiddenByUser(true);\n setShowBottomSheet(false);\n }\n\n // Show the bottom sheet automatically after a given amount of time\n useTimeout(() => {\n if (!dismissed && !isHiddenByUser && !cleanupLocalStorage) {\n setShowBottomSheet(true);\n }\n }, showAfter);\n\n // Hide the bottom sheet automatically after a given amount of time\n useTimeout(() => setShowBottomSheet(alwaysOn ? true : false), showAfter + hideAfter);\n\n // Cleanup functionality. The cleanup will remove the localStorage flag on mount\n // and will not show the bottom sheet.\n useEffect(() => {\n if (cleanupLocalStorage) {\n removeIsHiddenFlag();\n }\n }, []);\n\n const handleCloseBottomSheet = () => {\n setShowBottomSheet(false);\n setIsHiddenByUser(true);\n onClose();\n };\n\n return (\n <div {...remainingProps}>\n <BottomSheet\n show={showBottomSheet}\n width={width}\n detach\n showCloseButton={showCloseButton}\n onClose={handleCloseBottomSheet}\n className={className}\n bodyClassName={bodyClassName}\n >\n {children}\n </BottomSheet>\n </div>\n );\n};\n\nexport default TimedBottomSheet;\n"],"names":["DEFAULT_SHOW_AFTER","DEFAULT_HIDE_AFTER","sanitizeFeatureName","value","TimedBottomSheet","props","dismissed","featureName","showAfter","hideAfter","alwaysOn","showCloseButton","width","cleanupLocalStorage","onClose","noop","bodyClassName","localStoragePrefix","className","children","remainingProps","showBottomSheet","setShowBottomSheet","useState","isHiddenByUser","setIsHiddenByUser","removeIsHiddenFlag","useLocalStorage","prevDismissed","setPrevDismissed","useTimeout","useEffect","jsx","BottomSheet"],"mappings":";;;;;;AAOA,MAAMA,IAAqB,GACrBC,IAAqB,MAiGrBC,IAAsB,CAACC,MAAkB,GAAGA,EAAM,OAAO,CAAC,EAAE,YAAA,CAAa,GAAGA,EAAM,MAAM,CAAC,CAAC,GAAG,WAAW,KAAK,EAAE,GAiCxGC,IAAmB,CAACC,MAAoD;AACjF,QAAM;AAAA,IACF,WAAAC,IAAY;AAAA,IACZ,aAAAC;AAAA,IACA,WAAAC,IAAYR;AAAA,IACZ,WAAAS,IAAYR;AAAA,IACZ,UAAAS,IAAW;AAAA,IACX,iBAAAC,IAAkB;AAAA,IAClB,OAAAC;AAAA,IACA,qBAAAC,IAAsB;AAAA,IACtB,SAAAC,IAAUC;AAAA,IACV,eAAAC,IAAgB;AAAA,IAChB,oBAAAC,IAAqB;AAAA,IACrB,WAAAC;AAAA,IACA,UAAAC;AAAA,IACA,GAAGC;AAAA,EAAA,IACHf,GAEE,CAACgB,GAAiBC,CAAkB,IAAIC,EAAS,EAAK,GAEtD,CAACC,GAAgBC,GAAmBC,CAAkB,IAAIC;AAAA,IAC5D,GAAGV,CAAkB,OAAOf,EAAoBK,CAAW,CAAC;AAAA,IAC5D;AAAA,EAAA,GAME,CAACqB,GAAeC,CAAgB,IAAIN,EAASjB,CAAS;AAC5D,SAAIA,KAAaA,MAAcsB,MAC3BC,EAAiBvB,CAAS,GAC1BmB,EAAkB,EAAI,GACtBH,EAAmB,EAAK,IAI5BQ,EAAW,MAAM;AACb,IAAI,CAACxB,KAAa,CAACkB,KAAkB,CAACX,KAClCS,EAAmB,EAAI;AAAA,EAE/B,GAAGd,CAAS,GAGZsB,EAAW,MAAMR,EAAmB,EAAAZ,CAAuB,GAAGF,IAAYC,CAAS,GAInFsB,EAAU,MAAM;AACZ,IAAIlB,KACAa,EAAA;AAAA,EAER,GAAG,CAAA,CAAE,GASD,gBAAAM,EAAC,OAAA,EAAK,GAAGZ,GACL,UAAA,gBAAAY;AAAA,IAACC;AAAA,IAAA;AAAA,MACG,MAAMZ;AAAA,MACN,OAAAT;AAAA,MACA,QAAM;AAAA,MACN,iBAAAD;AAAA,MACA,SAbmB,MAAM;AACjC,QAAAW,EAAmB,EAAK,GACxBG,EAAkB,EAAI,GACtBX,EAAA;AAAA,MACJ;AAAA,MAUY,WAAAI;AAAA,MACA,eAAAF;AAAA,MAEC,UAAAG;AAAA,IAAA;AAAA,EAAA,GAET;AAER;"}
|
|
@@ -5,32 +5,30 @@ import { AnimatePresence as ae, motion as ne } from "motion/react";
|
|
|
5
5
|
import { noop as E } from "es-toolkit/compat";
|
|
6
6
|
import re from "../../hooks/useAfterMount.js";
|
|
7
7
|
import oe from "../../hooks/useElementSize.js";
|
|
8
|
-
import
|
|
9
|
-
import { hasDisplayClass as
|
|
10
|
-
const ye = 200, ve = 1, xe = 7, Ae = 0.2, _ = "page",
|
|
8
|
+
import le from "../../hooks/usePrevious.js";
|
|
9
|
+
import { hasDisplayClass as y, hasAlignItemsClass as k, hasOverflowClass as ie, hasBgClass as ce, hasBorderClass as me, hasRoundedClass as de, hasHoverScaleClass as pe, hasHoverTextColorClass as ue, hasPaddingClass as he, hasCursorClass as fe, hasTextColorClass as Ce, hasTextSizeClass as ge, hasAlignSelfClass as De, hasSpaceClass as F, hasUserSelectClass as M, hasFlexClass as Ne } from "../../utils/hasUtilityClass.js";
|
|
10
|
+
const ye = 200, ve = 1, xe = 7, Ae = 0.2, _ = "page", we = "pageBack", B = "ColumnItem", Se = {
|
|
11
11
|
pageEnter: (t) => ({
|
|
12
12
|
x: t === _ ? "60%" : "-60%",
|
|
13
13
|
opacity: 0
|
|
14
14
|
}),
|
|
15
15
|
pageCenter: () => ({ x: 0, opacity: 1 })
|
|
16
|
-
},
|
|
16
|
+
}, l = (t) => t.toISOString().split("T").at(0), O = (t) => [...t.classList].includes(B) ? t : O(t.children[0]), be = ee((t, b) => {
|
|
17
17
|
const {
|
|
18
|
-
minDayWith:
|
|
18
|
+
minDayWith: v = ye,
|
|
19
19
|
minDays: P = ve,
|
|
20
20
|
maxDays: R = xe,
|
|
21
|
-
renderDay:
|
|
21
|
+
renderDay: x,
|
|
22
22
|
skipWeekends: L = !1,
|
|
23
|
-
startDate:
|
|
23
|
+
startDate: i = /* @__PURE__ */ new Date(),
|
|
24
24
|
onNextClick: U = E,
|
|
25
25
|
onPreviousClick: z = E,
|
|
26
26
|
buttonClassName: s = "",
|
|
27
27
|
className: o = "",
|
|
28
28
|
daysWrapperClassName: m = "",
|
|
29
29
|
dayWrapperClassName: d = ""
|
|
30
|
-
} = t;
|
|
31
|
-
|
|
32
|
-
const [r, g] = h(l), [a, A] = h(1), [H, j] = h(!1), c = se(null), [S] = oe(c), V = ie(i(r)), w = i(r) > V ? _ : Se, [X, Y] = h(l);
|
|
33
|
-
i(l) !== i(X) && (g(l), Y(l)), re(() => {
|
|
30
|
+
} = t, [r, C] = h(i), [a, A] = h(1), [H, j] = h(!1), c = se(null), [w] = oe(c), V = le(l(r)), S = l(r) > V ? _ : we, [X, Y] = h(i);
|
|
31
|
+
l(i) !== l(X) && (C(i), Y(i)), re(() => {
|
|
34
32
|
j(!0);
|
|
35
33
|
}, []), te(() => {
|
|
36
34
|
if (!c.current)
|
|
@@ -38,44 +36,44 @@ const ye = 200, ve = 1, xe = 7, Ae = 0.2, _ = "page", Se = "pageBack", B = "Colu
|
|
|
38
36
|
const e = O(c.current.children[0]);
|
|
39
37
|
if (!e)
|
|
40
38
|
return;
|
|
41
|
-
const
|
|
42
|
-
if (u && (a + 1) *
|
|
43
|
-
const
|
|
44
|
-
A(
|
|
39
|
+
const g = e.getBoundingClientRect().width, D = a - 1 >= P, u = a + 1 <= R, Q = D && g <= v;
|
|
40
|
+
if (u && (a + 1) * v <= w) {
|
|
41
|
+
const N = a + 1;
|
|
42
|
+
A(N);
|
|
45
43
|
return;
|
|
46
44
|
}
|
|
47
45
|
if (Q) {
|
|
48
|
-
const
|
|
49
|
-
A(
|
|
46
|
+
const N = a - 1;
|
|
47
|
+
A(N);
|
|
50
48
|
return;
|
|
51
49
|
}
|
|
52
|
-
}, [
|
|
53
|
-
const
|
|
50
|
+
}, [w, c.current, a, r]);
|
|
51
|
+
const K = () => {
|
|
54
52
|
const e = new Date(r);
|
|
55
|
-
e.setDate(e.getDate() + a),
|
|
56
|
-
},
|
|
53
|
+
e.setDate(e.getDate() + a), C(e), U(e);
|
|
54
|
+
}, $ = () => {
|
|
57
55
|
const e = new Date(r);
|
|
58
|
-
e.setDate(e.getDate() - a),
|
|
56
|
+
e.setDate(e.getDate() - a), C(e), z(e);
|
|
59
57
|
}, p = [];
|
|
60
58
|
let I = !0, T = 1;
|
|
61
59
|
for (; I; ) {
|
|
62
60
|
const e = new Date(r);
|
|
63
61
|
e.setDate(r.getDate() + T);
|
|
64
|
-
const
|
|
62
|
+
const g = e.getDay() === 6, D = e.getDay() === 0, u = g || D;
|
|
65
63
|
u && !L ? p.push(e) : u || p.push(e), T++, p.length === a && (I = !1);
|
|
66
64
|
}
|
|
67
|
-
const
|
|
65
|
+
const q = f(
|
|
68
66
|
"CalenderStripe",
|
|
69
|
-
!
|
|
67
|
+
!y(o) && "display-flex",
|
|
70
68
|
!k(o) && "align-items-center",
|
|
71
|
-
!
|
|
69
|
+
!ie(o) && "overflow-hidden",
|
|
72
70
|
!ce(o) && "bg-white",
|
|
73
71
|
!me(o) && "border",
|
|
74
72
|
!de(o) && "rounded",
|
|
75
73
|
o
|
|
76
74
|
), W = f(
|
|
77
75
|
!k(s) && "align-items-center",
|
|
78
|
-
!
|
|
76
|
+
!y(s) && "display-flex",
|
|
79
77
|
!pe(s) && "hover-scale-105",
|
|
80
78
|
!ue(s) && "hover-text-color-darkest",
|
|
81
79
|
!he(s) && "padding-10",
|
|
@@ -85,7 +83,7 @@ const ye = 200, ve = 1, xe = 7, Ae = 0.2, _ = "page", Se = "pageBack", B = "Colu
|
|
|
85
83
|
!De(s) && "align-self-stretch",
|
|
86
84
|
s
|
|
87
85
|
), G = f(
|
|
88
|
-
!
|
|
86
|
+
!y(m) && "display-flex",
|
|
89
87
|
!F(m) && "space-x--1",
|
|
90
88
|
!M(m) && "user-select-none",
|
|
91
89
|
m
|
|
@@ -96,21 +94,21 @@ const ye = 200, ve = 1, xe = 7, Ae = 0.2, _ = "page", Se = "pageBack", B = "Colu
|
|
|
96
94
|
!M(d) && "user-select-none",
|
|
97
95
|
d
|
|
98
96
|
);
|
|
99
|
-
return /* @__PURE__ */ Z("div", { ref: b, className:
|
|
100
|
-
/* @__PURE__ */ n("div", { className: W, onClick:
|
|
101
|
-
/* @__PURE__ */ n("div", { className: "flex-1-1 overflow-hidden", ref: c, children: /* @__PURE__ */ n(ae, { mode: "wait", custom:
|
|
97
|
+
return /* @__PURE__ */ Z("div", { ref: b, className: q, children: [
|
|
98
|
+
/* @__PURE__ */ n("div", { className: W, onClick: $, children: /* @__PURE__ */ n("span", { className: "rioglyph rioglyph-chevron-left" }) }),
|
|
99
|
+
/* @__PURE__ */ n("div", { className: "flex-1-1 overflow-hidden", ref: c, children: /* @__PURE__ */ n(ae, { mode: "wait", custom: S, children: /* @__PURE__ */ n(
|
|
102
100
|
ne.div,
|
|
103
101
|
{
|
|
104
|
-
variants:
|
|
102
|
+
variants: Se,
|
|
105
103
|
initial: H ? "pageEnter" : !1,
|
|
106
104
|
animate: "pageCenter",
|
|
107
|
-
custom:
|
|
105
|
+
custom: S,
|
|
108
106
|
transition: { duration: Ae },
|
|
109
|
-
children: /* @__PURE__ */ n("div", { className: G, children: p.map((e) => /* @__PURE__ */ n("div", { className: J, children:
|
|
107
|
+
children: /* @__PURE__ */ n("div", { className: G, children: p.map((e) => /* @__PURE__ */ n("div", { className: J, children: x ? x(e) : null }, `${l(e)}`)) })
|
|
110
108
|
},
|
|
111
|
-
|
|
109
|
+
l(r)
|
|
112
110
|
) }) }),
|
|
113
|
-
/* @__PURE__ */ n("div", { className: W, onClick:
|
|
111
|
+
/* @__PURE__ */ n("div", { className: W, onClick: K, children: /* @__PURE__ */ n("span", { className: "rioglyph rioglyph-chevron-right" }) })
|
|
114
112
|
] });
|
|
115
113
|
});
|
|
116
114
|
export {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"CalendarStripe.js","sources":["../../../src/components/calendarStripe/CalendarStripe.tsx"],"sourcesContent":["import type React from 'react';\nimport { forwardRef, useEffect, useRef, useState } from 'react';\nimport classNames from 'classnames';\nimport { AnimatePresence, motion } from 'motion/react';\nimport { noop } from 'es-toolkit/compat';\n\nimport useAfterMount from '../../hooks/useAfterMount';\nimport useElementSize from '../../hooks/useElementSize';\nimport usePrevious from '../../hooks/usePrevious';\nimport {\n hasAlignItemsClass,\n hasAlignSelfClass,\n hasBgClass,\n hasBorderClass,\n hasCursorClass,\n hasDisplayClass,\n hasFlexClass,\n hasHoverScaleClass,\n hasHoverTextColorClass,\n hasOverflowClass,\n hasPaddingClass,\n hasRoundedClass,\n hasSpaceClass,\n hasTextColorClass,\n hasTextSizeClass,\n hasUserSelectClass,\n} from '../../utils/hasUtilityClass';\n\nconst DEFAULT_MIN_WITH = 200;\nconst DEFAULT_MIN_DAYS = 1;\nconst DEFAULT_MAX_DAYS = 7;\n\nconst ANIMATION_DURATION = 0.2;\nconst ANIMATION_NEXT = 'page';\nconst ANIMATION_BACK = 'pageBack';\n\nconst ITEM_NAME = 'ColumnItem';\n\nconst variants = {\n pageEnter: (pageDirection: typeof ANIMATION_NEXT | typeof ANIMATION_BACK) => ({\n x: pageDirection === ANIMATION_NEXT ? '60%' : '-60%',\n opacity: 0,\n }),\n pageCenter: () => ({ x: 0, opacity: 1 }),\n};\n\nconst getDateString = (date: Date) => date.toISOString().split('T').at(0) as string;\n\nconst getFirstColumnItem = (node: Element): Element => {\n if ([...node.classList].includes(ITEM_NAME)) {\n return node;\n }\n return getFirstColumnItem(node.children[0]);\n};\n\nexport type CalendarStripeProps = {\n /**\n * The minimum width in pixel of a single day column\n *\n * This value determines how many days are shown per page depending on the parent width.\n *\n * @default 200\n */\n minDayWith?: number;\n\n /**\n * The minimum amount of days that should be shown per page.\n *\n * @default 1\n */\n minDays?: number;\n\n /**\n * The maximum amount of days that should be shown per page.\n *\n * @default 7\n */\n maxDays?: number;\n\n /**\n * A function that renders each individual day to be displayed.\n *\n * @param date The day to render\n */\n renderDay?: (date: Date) => React.JSX.Element;\n\n /**\n * Defines whether the days for the weekends are included.\n *\n * @default false\n */\n skipWeekends?: boolean;\n\n /**\n * The date of the first day that are rendered.\n *\n * @default the current date\n */\n startDate?: Date;\n\n /**\n * Callback function for when the next button is clicked.\n *\n * @param newStartDate Date value that is now the start of the stripe.\n */\n onNextClick?: (newStartDate: Date) => void;\n\n /**\n * Callback function for when the previous button is clicked.\n *\n * @param newStartDate Date value that is now the start of the stripe.\n */\n onPreviousClick?: (newStartDate: Date) => void;\n\n /**\n * Additional classes set to the navigation buttons.\n */\n buttonClassName?: string;\n\n /**\n * Additional classes set to the calendar element.\n */\n className?: string;\n\n /**\n * Additional classes set to the days wrapper element.\n */\n daysWrapperClassName?: string;\n\n /**\n * Additional classes set to the days wrapper element.\n */\n dayWrapperClassName?: string;\n};\n\nconst CalendarStripe = forwardRef<HTMLDivElement, CalendarStripeProps>((props: CalendarStripeProps, ref) => {\n const {\n minDayWith = DEFAULT_MIN_WITH,\n minDays = DEFAULT_MIN_DAYS,\n maxDays = DEFAULT_MAX_DAYS,\n renderDay,\n skipWeekends = false,\n startDate = new Date(),\n onNextClick = noop,\n onPreviousClick = noop,\n buttonClassName = '',\n className = '',\n daysWrapperClassName = '',\n dayWrapperClassName = '',\n } = props;\n\n if (!renderDay) {\n console.error('CalendarStripe component is missing the required \"renderDay\" prop');\n }\n\n const [firstDate, setFirstDate] = useState(startDate);\n const [amountOfDaysToShow, setAmountOfDaysToShow] = useState(1);\n const [enableInitialAnimation, setEnableInitialAnimation] = useState(false);\n\n // The base for reacting on changing width of the wrapping element.\n // It uses a ResizeObserver under the hood.\n const columnWrapperRef = useRef<HTMLDivElement>(null);\n const [columnWrapperWidth] = useElementSize(columnWrapperRef);\n\n const previous = usePrevious(getDateString(firstDate));\n const animationDirection = getDateString(firstDate) > (previous as string) ? ANIMATION_NEXT : ANIMATION_BACK;\n\n // Update startDate from outside\n const [previousStartDate, setPreviousStartDate] = useState(startDate);\n if (getDateString(startDate) !== getDateString(previousStartDate)) {\n setFirstDate(startDate);\n setPreviousStartDate(startDate);\n }\n\n useAfterMount(() => {\n setEnableInitialAnimation(true);\n }, []);\n\n useEffect(() => {\n if (!columnWrapperRef.current) {\n return;\n }\n\n const firstItem = getFirstColumnItem(columnWrapperRef.current.children[0]);\n if (!firstItem) {\n return;\n }\n\n // Get the width of the first column to calculate how many columns fit on one page\n // according to the given minWidth per column\n const columnWidth = firstItem.getBoundingClientRect().width;\n\n // Limit columns per page for given min and max values\n const allowForLessColumns = amountOfDaysToShow - 1 >= minDays;\n const allowForMoreColumns = amountOfDaysToShow + 1 <= maxDays;\n\n const goSmaller = allowForLessColumns && columnWidth <= minDayWith;\n const goBigger =\n allowForMoreColumns && (amountOfDaysToShow + 1) * minDayWith <= (columnWrapperWidth as unknown as number);\n\n if (goBigger) {\n const newValue = amountOfDaysToShow + 1;\n setAmountOfDaysToShow(newValue);\n return;\n }\n\n if (goSmaller) {\n const newValue = amountOfDaysToShow - 1;\n setAmountOfDaysToShow(newValue);\n return;\n }\n }, [columnWrapperWidth, columnWrapperRef.current, amountOfDaysToShow, firstDate]);\n\n const handleNext = () => {\n const newFirstDate = new Date(firstDate);\n newFirstDate.setDate(newFirstDate.getDate() + amountOfDaysToShow);\n setFirstDate(newFirstDate);\n\n onNextClick(newFirstDate);\n };\n\n const handlePrev = () => {\n const newFirstDate = new Date(firstDate);\n newFirstDate.setDate(newFirstDate.getDate() - amountOfDaysToShow);\n setFirstDate(newFirstDate);\n\n onPreviousClick(newFirstDate);\n };\n\n // Re-calculate the dates to show depending on the amount of days to show\n const dates = [];\n\n let addDays = true;\n let index = 1;\n\n while (addDays) {\n const currentDate = new Date(firstDate);\n currentDate.setDate(firstDate.getDate() + index);\n\n const isSaturday = currentDate.getDay() === 6;\n const isSunday = currentDate.getDay() === 0;\n const isWeekend = isSaturday || isSunday;\n\n if (isWeekend && !skipWeekends) {\n dates.push(currentDate);\n } else if (!isWeekend) {\n dates.push(currentDate);\n }\n\n index++;\n\n if (dates.length === amountOfDaysToShow) {\n addDays = false;\n }\n }\n\n const wrapperClassNames = classNames(\n 'CalenderStripe',\n !hasDisplayClass(className) && 'display-flex',\n !hasAlignItemsClass(className) && 'align-items-center',\n !hasOverflowClass(className) && 'overflow-hidden',\n !hasBgClass(className) && 'bg-white',\n !hasBorderClass(className) && 'border',\n !hasRoundedClass(className) && 'rounded',\n className\n );\n\n const baseButtonClassNames = classNames(\n !hasAlignItemsClass(buttonClassName) && 'align-items-center',\n !hasDisplayClass(buttonClassName) && 'display-flex',\n !hasHoverScaleClass(buttonClassName) && 'hover-scale-105',\n !hasHoverTextColorClass(buttonClassName) && 'hover-text-color-darkest',\n !hasPaddingClass(buttonClassName) && 'padding-10',\n !hasCursorClass(buttonClassName) && 'cursor-pointer',\n !hasTextColorClass(buttonClassName) && 'text-color-darker',\n !hasTextSizeClass(buttonClassName) && 'text-size-12',\n !hasAlignSelfClass(buttonClassName) && 'align-self-stretch',\n buttonClassName\n );\n\n const daysWrapperClassNames = classNames(\n !hasDisplayClass(daysWrapperClassName) && 'display-flex',\n !hasSpaceClass(daysWrapperClassName) && 'space-x--1',\n !hasUserSelectClass(daysWrapperClassName) && 'user-select-none',\n daysWrapperClassName\n );\n\n const dayWrapperClassNames = classNames(\n ITEM_NAME,\n !hasFlexClass(dayWrapperClassName) && 'flex-1-1-0',\n !hasSpaceClass(dayWrapperClassName) && 'space-x--1',\n !hasUserSelectClass(dayWrapperClassName) && 'user-select-none',\n dayWrapperClassName\n );\n\n return (\n <div ref={ref} className={wrapperClassNames}>\n <div className={baseButtonClassNames} onClick={handlePrev}>\n <span className='rioglyph rioglyph-chevron-left' />\n </div>\n <div className='flex-1-1 overflow-hidden' ref={columnWrapperRef}>\n <AnimatePresence mode='wait' custom={animationDirection}>\n <motion.div\n key={getDateString(firstDate)}\n variants={variants}\n initial={enableInitialAnimation ? 'pageEnter' : false}\n animate='pageCenter'\n custom={animationDirection}\n transition={{ duration: ANIMATION_DURATION }}\n >\n <div className={daysWrapperClassNames}>\n {dates.map(date => (\n <div className={dayWrapperClassNames} key={`${getDateString(date)}`}>\n {renderDay ? renderDay(date) : null}\n </div>\n ))}\n </div>\n </motion.div>\n </AnimatePresence>\n </div>\n <div className={baseButtonClassNames} onClick={handleNext}>\n <span className='rioglyph rioglyph-chevron-right' />\n </div>\n </div>\n );\n});\n\nexport default CalendarStripe;\n"],"names":["DEFAULT_MIN_WITH","DEFAULT_MIN_DAYS","DEFAULT_MAX_DAYS","ANIMATION_DURATION","ANIMATION_NEXT","ANIMATION_BACK","ITEM_NAME","variants","pageDirection","getDateString","date","getFirstColumnItem","node","CalendarStripe","forwardRef","props","ref","minDayWith","minDays","maxDays","renderDay","skipWeekends","startDate","onNextClick","noop","onPreviousClick","buttonClassName","className","daysWrapperClassName","dayWrapperClassName","firstDate","setFirstDate","useState","amountOfDaysToShow","setAmountOfDaysToShow","enableInitialAnimation","setEnableInitialAnimation","columnWrapperRef","useRef","columnWrapperWidth","useElementSize","previous","usePrevious","animationDirection","previousStartDate","setPreviousStartDate","useAfterMount","useEffect","firstItem","columnWidth","allowForLessColumns","allowForMoreColumns","goSmaller","newValue","handleNext","newFirstDate","handlePrev","dates","addDays","index","currentDate","isSaturday","isSunday","isWeekend","wrapperClassNames","classNames","hasDisplayClass","hasAlignItemsClass","hasOverflowClass","hasBgClass","hasBorderClass","hasRoundedClass","baseButtonClassNames","hasHoverScaleClass","hasHoverTextColorClass","hasPaddingClass","hasCursorClass","hasTextColorClass","hasTextSizeClass","hasAlignSelfClass","daysWrapperClassNames","hasSpaceClass","hasUserSelectClass","dayWrapperClassNames","hasFlexClass","jsxs","jsx","AnimatePresence","motion"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"CalendarStripe.js","sources":["../../../src/components/calendarStripe/CalendarStripe.tsx"],"sourcesContent":["import type React from 'react';\nimport { forwardRef, useEffect, useRef, useState } from 'react';\nimport classNames from 'classnames';\nimport { AnimatePresence, motion } from 'motion/react';\nimport { noop } from 'es-toolkit/compat';\n\nimport useAfterMount from '../../hooks/useAfterMount';\nimport useElementSize from '../../hooks/useElementSize';\nimport usePrevious from '../../hooks/usePrevious';\nimport {\n hasAlignItemsClass,\n hasAlignSelfClass,\n hasBgClass,\n hasBorderClass,\n hasCursorClass,\n hasDisplayClass,\n hasFlexClass,\n hasHoverScaleClass,\n hasHoverTextColorClass,\n hasOverflowClass,\n hasPaddingClass,\n hasRoundedClass,\n hasSpaceClass,\n hasTextColorClass,\n hasTextSizeClass,\n hasUserSelectClass,\n} from '../../utils/hasUtilityClass';\n\nconst DEFAULT_MIN_WITH = 200;\nconst DEFAULT_MIN_DAYS = 1;\nconst DEFAULT_MAX_DAYS = 7;\n\nconst ANIMATION_DURATION = 0.2;\nconst ANIMATION_NEXT = 'page';\nconst ANIMATION_BACK = 'pageBack';\n\nconst ITEM_NAME = 'ColumnItem';\n\nconst variants = {\n pageEnter: (pageDirection: typeof ANIMATION_NEXT | typeof ANIMATION_BACK) => ({\n x: pageDirection === ANIMATION_NEXT ? '60%' : '-60%',\n opacity: 0,\n }),\n pageCenter: () => ({ x: 0, opacity: 1 }),\n};\n\nconst getDateString = (date: Date) => date.toISOString().split('T').at(0) as string;\n\nconst getFirstColumnItem = (node: Element): Element => {\n if ([...node.classList].includes(ITEM_NAME)) {\n return node;\n }\n return getFirstColumnItem(node.children[0]);\n};\n\nexport type CalendarStripeProps = {\n /**\n * The minimum width in pixel of a single day column\n *\n * This value determines how many days are shown per page depending on the parent width.\n *\n * @default 200\n */\n minDayWith?: number;\n\n /**\n * The minimum amount of days that should be shown per page.\n *\n * @default 1\n */\n minDays?: number;\n\n /**\n * The maximum amount of days that should be shown per page.\n *\n * @default 7\n */\n maxDays?: number;\n\n /**\n * A function that renders each individual day to be displayed.\n *\n * @param date The day to render\n */\n renderDay: (date: Date) => React.JSX.Element;\n\n /**\n * Defines whether the days for the weekends are included.\n *\n * @default false\n */\n skipWeekends?: boolean;\n\n /**\n * The date of the first day that are rendered.\n *\n * @default the current date\n */\n startDate?: Date;\n\n /**\n * Callback function for when the next button is clicked.\n *\n * @param newStartDate Date value that is now the start of the stripe.\n */\n onNextClick?: (newStartDate: Date) => void;\n\n /**\n * Callback function for when the previous button is clicked.\n *\n * @param newStartDate Date value that is now the start of the stripe.\n */\n onPreviousClick?: (newStartDate: Date) => void;\n\n /**\n * Additional classes set to the navigation buttons.\n */\n buttonClassName?: string;\n\n /**\n * Additional classes set to the calendar element.\n */\n className?: string;\n\n /**\n * Additional classes set to the days wrapper element.\n */\n daysWrapperClassName?: string;\n\n /**\n * Additional classes set to the days wrapper element.\n */\n dayWrapperClassName?: string;\n};\n\nconst CalendarStripe = forwardRef<HTMLDivElement, CalendarStripeProps>((props: CalendarStripeProps, ref) => {\n const {\n minDayWith = DEFAULT_MIN_WITH,\n minDays = DEFAULT_MIN_DAYS,\n maxDays = DEFAULT_MAX_DAYS,\n renderDay,\n skipWeekends = false,\n startDate = new Date(),\n onNextClick = noop,\n onPreviousClick = noop,\n buttonClassName = '',\n className = '',\n daysWrapperClassName = '',\n dayWrapperClassName = '',\n } = props;\n\n const [firstDate, setFirstDate] = useState(startDate);\n const [amountOfDaysToShow, setAmountOfDaysToShow] = useState(1);\n const [enableInitialAnimation, setEnableInitialAnimation] = useState(false);\n\n // The base for reacting on changing width of the wrapping element.\n // It uses a ResizeObserver under the hood.\n const columnWrapperRef = useRef<HTMLDivElement>(null);\n const [columnWrapperWidth] = useElementSize(columnWrapperRef);\n\n const previous = usePrevious(getDateString(firstDate));\n const animationDirection = getDateString(firstDate) > (previous as string) ? ANIMATION_NEXT : ANIMATION_BACK;\n\n // Update startDate from outside\n const [previousStartDate, setPreviousStartDate] = useState(startDate);\n if (getDateString(startDate) !== getDateString(previousStartDate)) {\n setFirstDate(startDate);\n setPreviousStartDate(startDate);\n }\n\n useAfterMount(() => {\n setEnableInitialAnimation(true);\n }, []);\n\n useEffect(() => {\n if (!columnWrapperRef.current) {\n return;\n }\n\n const firstItem = getFirstColumnItem(columnWrapperRef.current.children[0]);\n if (!firstItem) {\n return;\n }\n\n // Get the width of the first column to calculate how many columns fit on one page\n // according to the given minWidth per column\n const columnWidth = firstItem.getBoundingClientRect().width;\n\n // Limit columns per page for given min and max values\n const allowForLessColumns = amountOfDaysToShow - 1 >= minDays;\n const allowForMoreColumns = amountOfDaysToShow + 1 <= maxDays;\n\n const goSmaller = allowForLessColumns && columnWidth <= minDayWith;\n const goBigger =\n allowForMoreColumns && (amountOfDaysToShow + 1) * minDayWith <= (columnWrapperWidth as unknown as number);\n\n if (goBigger) {\n const newValue = amountOfDaysToShow + 1;\n setAmountOfDaysToShow(newValue);\n return;\n }\n\n if (goSmaller) {\n const newValue = amountOfDaysToShow - 1;\n setAmountOfDaysToShow(newValue);\n return;\n }\n }, [columnWrapperWidth, columnWrapperRef.current, amountOfDaysToShow, firstDate]);\n\n const handleNext = () => {\n const newFirstDate = new Date(firstDate);\n newFirstDate.setDate(newFirstDate.getDate() + amountOfDaysToShow);\n setFirstDate(newFirstDate);\n\n onNextClick(newFirstDate);\n };\n\n const handlePrev = () => {\n const newFirstDate = new Date(firstDate);\n newFirstDate.setDate(newFirstDate.getDate() - amountOfDaysToShow);\n setFirstDate(newFirstDate);\n\n onPreviousClick(newFirstDate);\n };\n\n // Re-calculate the dates to show depending on the amount of days to show\n const dates = [];\n\n let addDays = true;\n let index = 1;\n\n while (addDays) {\n const currentDate = new Date(firstDate);\n currentDate.setDate(firstDate.getDate() + index);\n\n const isSaturday = currentDate.getDay() === 6;\n const isSunday = currentDate.getDay() === 0;\n const isWeekend = isSaturday || isSunday;\n\n if (isWeekend && !skipWeekends) {\n dates.push(currentDate);\n } else if (!isWeekend) {\n dates.push(currentDate);\n }\n\n index++;\n\n if (dates.length === amountOfDaysToShow) {\n addDays = false;\n }\n }\n\n const wrapperClassNames = classNames(\n 'CalenderStripe',\n !hasDisplayClass(className) && 'display-flex',\n !hasAlignItemsClass(className) && 'align-items-center',\n !hasOverflowClass(className) && 'overflow-hidden',\n !hasBgClass(className) && 'bg-white',\n !hasBorderClass(className) && 'border',\n !hasRoundedClass(className) && 'rounded',\n className\n );\n\n const baseButtonClassNames = classNames(\n !hasAlignItemsClass(buttonClassName) && 'align-items-center',\n !hasDisplayClass(buttonClassName) && 'display-flex',\n !hasHoverScaleClass(buttonClassName) && 'hover-scale-105',\n !hasHoverTextColorClass(buttonClassName) && 'hover-text-color-darkest',\n !hasPaddingClass(buttonClassName) && 'padding-10',\n !hasCursorClass(buttonClassName) && 'cursor-pointer',\n !hasTextColorClass(buttonClassName) && 'text-color-darker',\n !hasTextSizeClass(buttonClassName) && 'text-size-12',\n !hasAlignSelfClass(buttonClassName) && 'align-self-stretch',\n buttonClassName\n );\n\n const daysWrapperClassNames = classNames(\n !hasDisplayClass(daysWrapperClassName) && 'display-flex',\n !hasSpaceClass(daysWrapperClassName) && 'space-x--1',\n !hasUserSelectClass(daysWrapperClassName) && 'user-select-none',\n daysWrapperClassName\n );\n\n const dayWrapperClassNames = classNames(\n ITEM_NAME,\n !hasFlexClass(dayWrapperClassName) && 'flex-1-1-0',\n !hasSpaceClass(dayWrapperClassName) && 'space-x--1',\n !hasUserSelectClass(dayWrapperClassName) && 'user-select-none',\n dayWrapperClassName\n );\n\n return (\n <div ref={ref} className={wrapperClassNames}>\n <div className={baseButtonClassNames} onClick={handlePrev}>\n <span className='rioglyph rioglyph-chevron-left' />\n </div>\n <div className='flex-1-1 overflow-hidden' ref={columnWrapperRef}>\n <AnimatePresence mode='wait' custom={animationDirection}>\n <motion.div\n key={getDateString(firstDate)}\n variants={variants}\n initial={enableInitialAnimation ? 'pageEnter' : false}\n animate='pageCenter'\n custom={animationDirection}\n transition={{ duration: ANIMATION_DURATION }}\n >\n <div className={daysWrapperClassNames}>\n {dates.map(date => (\n <div className={dayWrapperClassNames} key={`${getDateString(date)}`}>\n {renderDay ? renderDay(date) : null}\n </div>\n ))}\n </div>\n </motion.div>\n </AnimatePresence>\n </div>\n <div className={baseButtonClassNames} onClick={handleNext}>\n <span className='rioglyph rioglyph-chevron-right' />\n </div>\n </div>\n );\n});\n\nexport default CalendarStripe;\n"],"names":["DEFAULT_MIN_WITH","DEFAULT_MIN_DAYS","DEFAULT_MAX_DAYS","ANIMATION_DURATION","ANIMATION_NEXT","ANIMATION_BACK","ITEM_NAME","variants","pageDirection","getDateString","date","getFirstColumnItem","node","CalendarStripe","forwardRef","props","ref","minDayWith","minDays","maxDays","renderDay","skipWeekends","startDate","onNextClick","noop","onPreviousClick","buttonClassName","className","daysWrapperClassName","dayWrapperClassName","firstDate","setFirstDate","useState","amountOfDaysToShow","setAmountOfDaysToShow","enableInitialAnimation","setEnableInitialAnimation","columnWrapperRef","useRef","columnWrapperWidth","useElementSize","previous","usePrevious","animationDirection","previousStartDate","setPreviousStartDate","useAfterMount","useEffect","firstItem","columnWidth","allowForLessColumns","allowForMoreColumns","goSmaller","newValue","handleNext","newFirstDate","handlePrev","dates","addDays","index","currentDate","isSaturday","isSunday","isWeekend","wrapperClassNames","classNames","hasDisplayClass","hasAlignItemsClass","hasOverflowClass","hasBgClass","hasBorderClass","hasRoundedClass","baseButtonClassNames","hasHoverScaleClass","hasHoverTextColorClass","hasPaddingClass","hasCursorClass","hasTextColorClass","hasTextSizeClass","hasAlignSelfClass","daysWrapperClassNames","hasSpaceClass","hasUserSelectClass","dayWrapperClassNames","hasFlexClass","jsxs","jsx","AnimatePresence","motion"],"mappings":";;;;;;;;;AA4BA,MAAMA,KAAmB,KACnBC,KAAmB,GACnBC,KAAmB,GAEnBC,KAAqB,KACrBC,IAAiB,QACjBC,KAAiB,YAEjBC,IAAY,cAEZC,KAAW;AAAA,EACb,WAAW,CAACC,OAAkE;AAAA,IAC1E,GAAGA,MAAkBJ,IAAiB,QAAQ;AAAA,IAC9C,SAAS;AAAA,EAAA;AAAA,EAEb,YAAY,OAAO,EAAE,GAAG,GAAG,SAAS,EAAA;AACxC,GAEMK,IAAgB,CAACC,MAAeA,EAAK,YAAA,EAAc,MAAM,GAAG,EAAE,GAAG,CAAC,GAElEC,IAAqB,CAACC,MACpB,CAAC,GAAGA,EAAK,SAAS,EAAE,SAASN,CAAS,IAC/BM,IAEJD,EAAmBC,EAAK,SAAS,CAAC,CAAC,GAmFxCC,KAAiBC,GAAgD,CAACC,GAA4BC,MAAQ;AACxG,QAAM;AAAA,IACF,YAAAC,IAAajB;AAAA,IACb,SAAAkB,IAAUjB;AAAA,IACV,SAAAkB,IAAUjB;AAAA,IACV,WAAAkB;AAAA,IACA,cAAAC,IAAe;AAAA,IACf,WAAAC,wBAAgB,KAAA;AAAA,IAChB,aAAAC,IAAcC;AAAA,IACd,iBAAAC,IAAkBD;AAAA,IAClB,iBAAAE,IAAkB;AAAA,IAClB,WAAAC,IAAY;AAAA,IACZ,sBAAAC,IAAuB;AAAA,IACvB,qBAAAC,IAAsB;AAAA,EAAA,IACtBd,GAEE,CAACe,GAAWC,CAAY,IAAIC,EAASV,CAAS,GAC9C,CAACW,GAAoBC,CAAqB,IAAIF,EAAS,CAAC,GACxD,CAACG,GAAwBC,CAAyB,IAAIJ,EAAS,EAAK,GAIpEK,IAAmBC,GAAuB,IAAI,GAC9C,CAACC,CAAkB,IAAIC,GAAeH,CAAgB,GAEtDI,IAAWC,GAAYjC,EAAcqB,CAAS,CAAC,GAC/Ca,IAAqBlC,EAAcqB,CAAS,IAAKW,IAAsBrC,IAAiBC,IAGxF,CAACuC,GAAmBC,CAAoB,IAAIb,EAASV,CAAS;AACpE,EAAIb,EAAca,CAAS,MAAMb,EAAcmC,CAAiB,MAC5Db,EAAaT,CAAS,GACtBuB,EAAqBvB,CAAS,IAGlCwB,GAAc,MAAM;AAChB,IAAAV,EAA0B,EAAI;AAAA,EAClC,GAAG,CAAA,CAAE,GAELW,GAAU,MAAM;AACZ,QAAI,CAACV,EAAiB;AAClB;AAGJ,UAAMW,IAAYrC,EAAmB0B,EAAiB,QAAQ,SAAS,CAAC,CAAC;AACzE,QAAI,CAACW;AACD;AAKJ,UAAMC,IAAcD,EAAU,sBAAA,EAAwB,OAGhDE,IAAsBjB,IAAqB,KAAKf,GAChDiC,IAAsBlB,IAAqB,KAAKd,GAEhDiC,IAAYF,KAAuBD,KAAehC;AAIxD,QAFIkC,MAAwBlB,IAAqB,KAAKhB,KAAesB,GAEvD;AACV,YAAMc,IAAWpB,IAAqB;AACtC,MAAAC,EAAsBmB,CAAQ;AAC9B;AAAA,IACJ;AAEA,QAAID,GAAW;AACX,YAAMC,IAAWpB,IAAqB;AACtC,MAAAC,EAAsBmB,CAAQ;AAC9B;AAAA,IACJ;AAAA,EACJ,GAAG,CAACd,GAAoBF,EAAiB,SAASJ,GAAoBH,CAAS,CAAC;AAEhF,QAAMwB,IAAa,MAAM;AACrB,UAAMC,IAAe,IAAI,KAAKzB,CAAS;AACvC,IAAAyB,EAAa,QAAQA,EAAa,QAAA,IAAYtB,CAAkB,GAChEF,EAAawB,CAAY,GAEzBhC,EAAYgC,CAAY;AAAA,EAC5B,GAEMC,IAAa,MAAM;AACrB,UAAMD,IAAe,IAAI,KAAKzB,CAAS;AACvC,IAAAyB,EAAa,QAAQA,EAAa,QAAA,IAAYtB,CAAkB,GAChEF,EAAawB,CAAY,GAEzB9B,EAAgB8B,CAAY;AAAA,EAChC,GAGME,IAAQ,CAAA;AAEd,MAAIC,IAAU,IACVC,IAAQ;AAEZ,SAAOD,KAAS;AACZ,UAAME,IAAc,IAAI,KAAK9B,CAAS;AACtC,IAAA8B,EAAY,QAAQ9B,EAAU,QAAA,IAAY6B,CAAK;AAE/C,UAAME,IAAaD,EAAY,OAAA,MAAa,GACtCE,IAAWF,EAAY,OAAA,MAAa,GACpCG,IAAYF,KAAcC;AAEhC,IAAIC,KAAa,CAAC1C,IACdoC,EAAM,KAAKG,CAAW,IACdG,KACRN,EAAM,KAAKG,CAAW,GAG1BD,KAEIF,EAAM,WAAWxB,MACjByB,IAAU;AAAA,EAElB;AAEA,QAAMM,IAAoBC;AAAA,IACtB;AAAA,IACA,CAACC,EAAgBvC,CAAS,KAAK;AAAA,IAC/B,CAACwC,EAAmBxC,CAAS,KAAK;AAAA,IAClC,CAACyC,GAAiBzC,CAAS,KAAK;AAAA,IAChC,CAAC0C,GAAW1C,CAAS,KAAK;AAAA,IAC1B,CAAC2C,GAAe3C,CAAS,KAAK;AAAA,IAC9B,CAAC4C,GAAgB5C,CAAS,KAAK;AAAA,IAC/BA;AAAA,EAAA,GAGE6C,IAAuBP;AAAA,IACzB,CAACE,EAAmBzC,CAAe,KAAK;AAAA,IACxC,CAACwC,EAAgBxC,CAAe,KAAK;AAAA,IACrC,CAAC+C,GAAmB/C,CAAe,KAAK;AAAA,IACxC,CAACgD,GAAuBhD,CAAe,KAAK;AAAA,IAC5C,CAACiD,GAAgBjD,CAAe,KAAK;AAAA,IACrC,CAACkD,GAAelD,CAAe,KAAK;AAAA,IACpC,CAACmD,GAAkBnD,CAAe,KAAK;AAAA,IACvC,CAACoD,GAAiBpD,CAAe,KAAK;AAAA,IACtC,CAACqD,GAAkBrD,CAAe,KAAK;AAAA,IACvCA;AAAA,EAAA,GAGEsD,IAAwBf;AAAA,IAC1B,CAACC,EAAgBtC,CAAoB,KAAK;AAAA,IAC1C,CAACqD,EAAcrD,CAAoB,KAAK;AAAA,IACxC,CAACsD,EAAmBtD,CAAoB,KAAK;AAAA,IAC7CA;AAAA,EAAA,GAGEuD,IAAuBlB;AAAA,IACzB3D;AAAA,IACA,CAAC8E,GAAavD,CAAmB,KAAK;AAAA,IACtC,CAACoD,EAAcpD,CAAmB,KAAK;AAAA,IACvC,CAACqD,EAAmBrD,CAAmB,KAAK;AAAA,IAC5CA;AAAA,EAAA;AAGJ,SACI,gBAAAwD,EAAC,OAAA,EAAI,KAAArE,GAAU,WAAWgD,GACtB,UAAA;AAAA,IAAA,gBAAAsB,EAAC,OAAA,EAAI,WAAWd,GAAsB,SAAShB,GAC3C,UAAA,gBAAA8B,EAAC,QAAA,EAAK,WAAU,iCAAA,CAAiC,EAAA,CACrD;AAAA,IACA,gBAAAA,EAAC,OAAA,EAAI,WAAU,4BAA2B,KAAKjD,GAC3C,UAAA,gBAAAiD,EAACC,IAAA,EAAgB,MAAK,QAAO,QAAQ5C,GACjC,UAAA,gBAAA2C;AAAA,MAACE,GAAO;AAAA,MAAP;AAAA,QAEG,UAAAjF;AAAA,QACA,SAAS4B,IAAyB,cAAc;AAAA,QAChD,SAAQ;AAAA,QACR,QAAQQ;AAAA,QACR,YAAY,EAAE,UAAUxC,GAAA;AAAA,QAExB,UAAA,gBAAAmF,EAAC,SAAI,WAAWN,GACX,YAAM,IAAI,CAAAtE,MACP,gBAAA4E,EAAC,OAAA,EAAI,WAAWH,GACX,cAAY/D,EAAUV,CAAI,IAAI,QADQ,GAAGD,EAAcC,CAAI,CAAC,EAEjE,CACH,EAAA,CACL;AAAA,MAAA;AAAA,MAbKD,EAAcqB,CAAS;AAAA,IAAA,GAepC,EAAA,CACJ;AAAA,IACA,gBAAAwD,EAAC,OAAA,EAAI,WAAWd,GAAsB,SAASlB,GAC3C,UAAA,gBAAAgC,EAAC,QAAA,EAAK,WAAU,kCAAA,CAAkC,EAAA,CACtD;AAAA,EAAA,GACJ;AAER,CAAC;"}
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import { AreaProps as RechartsAreaProps } from 'recharts';
|
|
2
2
|
import { CurveType } from 'recharts/types/shape/Curve';
|
|
3
|
-
export type AreaProps = Omit<RechartsAreaProps, 'ref'> & {
|
|
3
|
+
export type AreaProps<T = any> = Omit<RechartsAreaProps, 'ref'> & {
|
|
4
4
|
strokeColor?: string;
|
|
5
|
-
dataKey?: string;
|
|
5
|
+
dataKey?: string | number | ((obj: T) => any);
|
|
6
6
|
unit?: string;
|
|
7
7
|
legendType?: string;
|
|
8
8
|
type?: CurveType;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Area.js","sources":["../../../src/components/charts/Area.tsx"],"sourcesContent":["
|
|
1
|
+
{"version":3,"file":"Area.js","sources":["../../../src/components/charts/Area.tsx"],"sourcesContent":["import type { AreaProps as RechartsAreaProps } from 'recharts';\nimport type { CurveType } from 'recharts/types/shape/Curve';\n\n// biome-ignore lint/suspicious/noExplicitAny: be less restrictive here\nexport type AreaProps<T = any> = Omit<RechartsAreaProps, 'ref'> & {\n strokeColor?: string;\n // biome-ignore lint/suspicious/noExplicitAny: see above\n dataKey?: string | number | ((obj: T) => any);\n unit?: string;\n legendType?: string;\n type?: CurveType;\n isAnimationActive?: boolean;\n};\n\nexport const getAreaDefaultProps = () => ({\n dataKey: 'value',\n unit: '',\n strokeColor: 'color-coldplay-fountain',\n legendType: 'square',\n type: 'monotone',\n isAnimationActive: true,\n});\n\nconst Area = (props: AreaProps) => null;\n\nexport default Area;\n"],"names":["getAreaDefaultProps","Area","props"],"mappings":"AAcO,MAAMA,IAAsB,OAAO;AAAA,EACtC,SAAS;AAAA,EACT,MAAM;AAAA,EACN,aAAa;AAAA,EACb,YAAY;AAAA,EACZ,MAAM;AAAA,EACN,mBAAmB;AACvB,IAEMC,IAAO,CAACC,MAAqB;"}
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import { LineProps as RechartsLineProps } from 'recharts';
|
|
2
2
|
import { CurveType } from 'recharts/types/shape/Curve';
|
|
3
|
-
export type LineProps = Omit<RechartsLineProps, 'ref'> & {
|
|
3
|
+
export type LineProps<T = any> = Omit<RechartsLineProps, 'ref'> & {
|
|
4
4
|
strokeColor?: string;
|
|
5
|
-
dataKey?: string;
|
|
5
|
+
dataKey?: string | number | ((obj: T) => any);
|
|
6
6
|
unit?: string;
|
|
7
7
|
legendType?: string;
|
|
8
8
|
type?: CurveType;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Line.js","sources":["../../../src/components/charts/Line.tsx"],"sourcesContent":["
|
|
1
|
+
{"version":3,"file":"Line.js","sources":["../../../src/components/charts/Line.tsx"],"sourcesContent":["import type { LineProps as RechartsLineProps } from 'recharts';\nimport type { CurveType } from 'recharts/types/shape/Curve';\n\n// biome-ignore lint/suspicious/noExplicitAny: be less restrictive here\nexport type LineProps<T = any> = Omit<RechartsLineProps, 'ref'> & {\n strokeColor?: string;\n // biome-ignore lint/suspicious/noExplicitAny: see above\n dataKey?: string | number | ((obj: T) => any);\n unit?: string;\n legendType?: string;\n type?: CurveType;\n isAnimationActive?: boolean;\n};\n\nexport const getLineDefaultProps = () => ({\n dataKey: 'value',\n unit: '',\n strokeColor: 'color-coldplay-fountain',\n legendType: 'square',\n type: 'monotone',\n isAnimationActive: true,\n});\n\nconst Line = (props: LineProps) => null;\n\nexport default Line;\n"],"names":["getLineDefaultProps","Line","props"],"mappings":"AAcO,MAAMA,IAAsB,OAAO;AAAA,EACtC,SAAS;AAAA,EACT,MAAM;AAAA,EACN,aAAa;AAAA,EACb,YAAY;AAAA,EACZ,MAAM;AAAA,EACN,mBAAmB;AACvB,IAEMC,IAAO,CAACC,MAAqB;"}
|
|
@@ -62,8 +62,6 @@ export type CheckboxProps = {
|
|
|
62
62
|
* `checkbox-text`.
|
|
63
63
|
*
|
|
64
64
|
* @example
|
|
65
|
-
*
|
|
66
|
-
* ```tsx
|
|
67
65
|
* <div className='checkbox-text-wrapper display-flex justify-content-between'>
|
|
68
66
|
* <div className='margin-right-15'>
|
|
69
67
|
* <div className='text-medium text-size-16 text-color-darker'>Option 1</div>
|
|
@@ -71,7 +69,6 @@ export type CheckboxProps = {
|
|
|
71
69
|
* </div>
|
|
72
70
|
* <div className='checkbox-text' />
|
|
73
71
|
* </div>
|
|
74
|
-
* ```
|
|
75
72
|
*/
|
|
76
73
|
custom?: boolean;
|
|
77
74
|
/**
|