adnbn-ui 0.0.1 → 0.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/.prettierignore +3 -0
- package/.prettierrc +28 -0
- package/.storybook/main.ts +22 -0
- package/.storybook/preview.tsx +100 -0
- package/.storybook/styles/custom.scss +59 -0
- package/.storybook/styles/preview.css +58 -0
- package/.storybook/vitest.setup.ts +9 -0
- package/README.md +1057 -0
- package/eslint.config.js +39 -0
- package/package.json +95 -4
- package/src/components/Avatar/Avatar.stories.tsx +118 -0
- package/src/components/Avatar/Avatar.tsx +65 -0
- package/src/components/Avatar/avatar.module.scss +77 -0
- package/src/components/Avatar/index.ts +2 -0
- package/src/components/BaseButton/BaseButton.tsx +36 -0
- package/src/components/BaseButton/base-button.module.scss +24 -0
- package/src/components/BaseButton/index.ts +2 -0
- package/src/components/Button/Button.stories.tsx +148 -0
- package/src/components/Button/Button.tsx +73 -0
- package/src/components/Button/button.module.scss +140 -0
- package/src/components/Button/index.ts +2 -0
- package/src/components/Checkbox/Checkbox.stories.tsx +180 -0
- package/src/components/Checkbox/Checkbox.tsx +71 -0
- package/src/components/Checkbox/checkbox.module.scss +82 -0
- package/src/components/Checkbox/index.ts +2 -0
- package/src/components/Dialog/Dialog.tsx +125 -0
- package/src/components/Dialog/dialog.module.scss +55 -0
- package/src/components/Dialog/index.ts +2 -0
- package/src/components/Drawer/Drawer.stories.tsx +89 -0
- package/src/components/Drawer/Drawer.tsx +57 -0
- package/src/components/Drawer/drawer.module.scss +170 -0
- package/src/components/Drawer/index.ts +2 -0
- package/src/components/Footer/Footer.stories.tsx +118 -0
- package/src/components/Footer/Footer.tsx +58 -0
- package/src/components/Footer/footer.module.scss +44 -0
- package/src/components/Footer/index.ts +2 -0
- package/src/components/Header/Header.stories.tsx +49 -0
- package/src/components/Header/Header.tsx +73 -0
- package/src/components/Header/header.module.scss +56 -0
- package/src/components/Header/index.ts +2 -0
- package/src/components/Highlight/Highlight.stories.tsx +83 -0
- package/src/components/Highlight/Highlight.tsx +40 -0
- package/src/components/Highlight/highlight.module.scss +47 -0
- package/src/components/Highlight/index.ts +2 -0
- package/src/components/Icon/Icon.tsx +46 -0
- package/src/components/Icon/icon.module.scss +17 -0
- package/src/components/Icon/index.ts +2 -0
- package/src/components/IconButton/IconButton.stories.tsx +179 -0
- package/src/components/IconButton/IconButton.tsx +65 -0
- package/src/components/IconButton/icon-button.module.scss +86 -0
- package/src/components/IconButton/index.ts +2 -0
- package/src/components/Layout/Layout.stories.tsx +88 -0
- package/src/components/Layout/Provider.tsx +47 -0
- package/src/components/Layout/context.ts +24 -0
- package/src/components/Layout/index.ts +2 -0
- package/src/components/Layout/layout.module.scss +17 -0
- package/src/components/List/List.stories.tsx +81 -0
- package/src/components/List/List.tsx +24 -0
- package/src/components/List/index.ts +2 -0
- package/src/components/List/list.module.scss +8 -0
- package/src/components/ListItem/ListItem.tsx +75 -0
- package/src/components/ListItem/index.ts +2 -0
- package/src/components/ListItem/list-item.module.scss +36 -0
- package/src/components/Modal/Modal.stories.tsx +95 -0
- package/src/components/Modal/Modal.tsx +94 -0
- package/src/components/Modal/index.ts +2 -0
- package/src/components/Modal/modal.module.scss +97 -0
- package/src/components/Odometer/Odometer.stories.tsx +66 -0
- package/src/components/Odometer/Odometer.tsx +45 -0
- package/src/components/Odometer/hooks/useOdometer.tsx +24 -0
- package/src/components/Odometer/index.ts +3 -0
- package/src/components/Odometer/odometer.module.scss +81 -0
- package/src/components/Odometer/odometr.d.ts +9 -0
- package/src/components/ScrollArea/ScrollArea.stories.tsx +58 -0
- package/src/components/ScrollArea/ScrollArea.tsx +63 -0
- package/src/components/ScrollArea/index.ts +2 -0
- package/src/components/ScrollArea/scroll-area.module.scss +54 -0
- package/src/components/SvgSprite/SvgSprite.tsx +21 -0
- package/src/components/SvgSprite/index.ts +2 -0
- package/src/components/Switch/Switch.stories.tsx +25 -0
- package/src/components/Switch/Switch.tsx +23 -0
- package/src/components/Switch/index.ts +2 -0
- package/src/components/Switch/switch.module.scss +65 -0
- package/src/components/Tag/Tag.stories.tsx +157 -0
- package/src/components/Tag/Tag.tsx +71 -0
- package/src/components/Tag/index.ts +2 -0
- package/src/components/Tag/tag.module.scss +118 -0
- package/src/components/TextArea/TextArea.stories.tsx +145 -0
- package/src/components/TextArea/TextArea.tsx +143 -0
- package/src/components/TextArea/index.ts +2 -0
- package/src/components/TextArea/text-area.module.scss +88 -0
- package/src/components/TextField/TextField.stories.tsx +177 -0
- package/src/components/TextField/TextField.tsx +162 -0
- package/src/components/TextField/index.ts +2 -0
- package/src/components/TextField/text-field.module.scss +129 -0
- package/src/components/Toast/Toast.stories.tsx +209 -0
- package/src/components/Toast/Toast.tsx +142 -0
- package/src/components/Toast/index.ts +2 -0
- package/src/components/Toast/toast.module.scss +267 -0
- package/src/components/Tooltip/Tooltip.stories.tsx +80 -0
- package/src/components/Tooltip/Tooltip.tsx +79 -0
- package/src/components/Tooltip/index.ts +2 -0
- package/src/components/Tooltip/tooltip.module.scss +93 -0
- package/src/components/View/View.stories.tsx +47 -0
- package/src/components/View/View.tsx +68 -0
- package/src/components/View/index.ts +2 -0
- package/src/components/View/view.module.scss +38 -0
- package/src/components/ViewDrawer/ViewDrawer.stories.tsx +75 -0
- package/src/components/ViewDrawer/ViewDrawer.tsx +24 -0
- package/src/components/ViewDrawer/index.ts +2 -0
- package/src/components/ViewModal/ViewModal.stories.tsx +68 -0
- package/src/components/ViewModal/ViewModal.tsx +24 -0
- package/src/components/ViewModal/index.ts +2 -0
- package/src/components/index.ts +29 -0
- package/src/components/types.ts +65 -0
- package/src/config/default.ts +3 -0
- package/src/config/index.ts +26 -0
- package/src/declaration.d.ts +8 -0
- package/src/index.ts +3 -0
- package/src/plugin/builder/ConfigBuilder.ts +32 -0
- package/src/plugin/builder/StyleBuilder.ts +34 -0
- package/src/plugin/builder/virtual.config.ts +7 -0
- package/src/plugin/finder/ConfigFinder.ts +26 -0
- package/src/plugin/finder/Finder.ts +76 -0
- package/src/plugin/finder/StyleFinder.ts +23 -0
- package/src/plugin/index.ts +70 -0
- package/src/plugin/types.ts +8 -0
- package/src/providers/UIProvider.tsx +26 -0
- package/src/providers/icons/IconsProvider.tsx +34 -0
- package/src/providers/icons/context.ts +22 -0
- package/src/providers/icons/index.ts +3 -0
- package/src/providers/index.ts +3 -0
- package/src/providers/theme/ThemeProvider.tsx +39 -0
- package/src/providers/theme/context.ts +30 -0
- package/src/providers/theme/index.ts +2 -0
- package/src/providers/theme/styles/default.scss +95 -0
- package/src/providers/theme/styles/reset.css +111 -0
- package/src/styles/mixins.scss +23 -0
- package/src/types/theme.ts +4 -0
- package/src/utils/index.ts +2 -0
- package/src/utils/react.ts +21 -0
- package/src/utils/utils.ts +12 -0
- package/tsconfig.json +18 -0
- package/vite.config.ts +11 -0
- package/vitest.workspace.ts +19 -0
- package/components/Button/index.ts +0 -0
@@ -0,0 +1,97 @@
|
|
1
|
+
@use "../../styles/mixins" as dir;
|
2
|
+
|
3
|
+
$root: modal;
|
4
|
+
|
5
|
+
.#{$root} {
|
6
|
+
&-overlay {
|
7
|
+
background-color: var(--modal-overlay-bg-color, var(--dialog-overlay-bg-color, #111));
|
8
|
+
}
|
9
|
+
|
10
|
+
&-content {
|
11
|
+
top: 50%;
|
12
|
+
left: 50%;
|
13
|
+
transform: translate(-50%, -50%);
|
14
|
+
width: var(--modal-width, 90vw);
|
15
|
+
max-width: var(--modal-max-width, 350px);
|
16
|
+
max-height: var(--modal-max-height, 85vh);
|
17
|
+
padding: var(--modal-padding, 0);
|
18
|
+
border-radius: var(--modal-border-radius, 10px);
|
19
|
+
box-shadow: var(--modal-box-shadow, 0 0 4px rgba(0, 0, 0, 0.5));
|
20
|
+
background-color: var(--modal-bg-color, var(--bg-primary-color));
|
21
|
+
transition:
|
22
|
+
background-color var(--transition-speed-sm),
|
23
|
+
color var(--transition-speed-sm);
|
24
|
+
|
25
|
+
&[data-state="open"] {
|
26
|
+
animation-name: contentShow;
|
27
|
+
}
|
28
|
+
|
29
|
+
&[data-state="closed"] {
|
30
|
+
animation-name: contentHide;
|
31
|
+
}
|
32
|
+
|
33
|
+
&--fullscreen {
|
34
|
+
max-width: 100%;
|
35
|
+
max-height: 100%;
|
36
|
+
width: 100%;
|
37
|
+
height: 100%;
|
38
|
+
border-radius: 0 !important;
|
39
|
+
}
|
40
|
+
|
41
|
+
&--none-radius {
|
42
|
+
border-radius: 0;
|
43
|
+
}
|
44
|
+
|
45
|
+
&--small-radius {
|
46
|
+
border-radius: var(--modal-border-radius-sm, 5px);
|
47
|
+
}
|
48
|
+
|
49
|
+
&--medium-radius {
|
50
|
+
border-radius: var(--modal-border-radius-sm, 15px);
|
51
|
+
}
|
52
|
+
|
53
|
+
&--large-radius {
|
54
|
+
border-radius: var(--modal-border-radius-sm, 20px);
|
55
|
+
}
|
56
|
+
}
|
57
|
+
|
58
|
+
&-children {
|
59
|
+
display: flex;
|
60
|
+
flex-direction: column;
|
61
|
+
}
|
62
|
+
|
63
|
+
&-close {
|
64
|
+
position: absolute !important;
|
65
|
+
top: var(--modal-close-offset, 5px);
|
66
|
+
|
67
|
+
@include dir.ltr {
|
68
|
+
right: var(--modal-close-offset, 5px);
|
69
|
+
}
|
70
|
+
|
71
|
+
@include dir.rtl {
|
72
|
+
left: var(--modal-close-offset, 5px);
|
73
|
+
}
|
74
|
+
}
|
75
|
+
}
|
76
|
+
|
77
|
+
@keyframes contentShow {
|
78
|
+
from {
|
79
|
+
opacity: 0;
|
80
|
+
transform: translate(-50%, -48%) scale(var(--modal-animation-content-scale, 0.96));
|
81
|
+
}
|
82
|
+
to {
|
83
|
+
opacity: 1;
|
84
|
+
transform: translate(-50%, -50%) scale(1);
|
85
|
+
}
|
86
|
+
}
|
87
|
+
|
88
|
+
@keyframes contentHide {
|
89
|
+
from {
|
90
|
+
opacity: 1;
|
91
|
+
transform: translate(-50%, -50%) scale(1);
|
92
|
+
}
|
93
|
+
to {
|
94
|
+
opacity: 0;
|
95
|
+
transform: translate(-50%, -48%) scale(var(--modal-animation-content-scale, 0.96));
|
96
|
+
}
|
97
|
+
}
|
@@ -0,0 +1,66 @@
|
|
1
|
+
import {useEffect, useState} from "react";
|
2
|
+
import {Meta, StoryObj} from "@storybook/react";
|
3
|
+
|
4
|
+
import {hideInTable} from "../../utils";
|
5
|
+
|
6
|
+
import OdometerComponent from "./Odometer";
|
7
|
+
|
8
|
+
const meta: Meta<typeof OdometerComponent> = {
|
9
|
+
title: "Components/Odometer",
|
10
|
+
component: OdometerComponent,
|
11
|
+
tags: ["autodocs"],
|
12
|
+
argTypes: {
|
13
|
+
value: {
|
14
|
+
description: "The number to display on the odometer.",
|
15
|
+
control: {type: "number"},
|
16
|
+
},
|
17
|
+
format: {
|
18
|
+
description: "Formatting string for odometer value.",
|
19
|
+
control: {type: "text"},
|
20
|
+
},
|
21
|
+
duration: {
|
22
|
+
description: "Animation duration in milliseconds.",
|
23
|
+
control: {type: "number"},
|
24
|
+
},
|
25
|
+
auto: hideInTable,
|
26
|
+
className: hideInTable,
|
27
|
+
},
|
28
|
+
};
|
29
|
+
|
30
|
+
export default meta;
|
31
|
+
|
32
|
+
export const Odometer: StoryObj<typeof OdometerComponent> = {
|
33
|
+
args: {
|
34
|
+
value: 1234,
|
35
|
+
duration: 500,
|
36
|
+
format: "d",
|
37
|
+
},
|
38
|
+
};
|
39
|
+
|
40
|
+
export const OdometerCount = () => {
|
41
|
+
const [value, setValue] = useState(100);
|
42
|
+
|
43
|
+
useEffect(() => {
|
44
|
+
const interval = setInterval(() => {
|
45
|
+
setValue(prev => ++prev);
|
46
|
+
}, 1000);
|
47
|
+
|
48
|
+
return () => clearInterval(interval);
|
49
|
+
}, []);
|
50
|
+
|
51
|
+
return <OdometerComponent value={value} />;
|
52
|
+
};
|
53
|
+
|
54
|
+
export const OdometerRandom = () => {
|
55
|
+
const [value, setValue] = useState(100);
|
56
|
+
|
57
|
+
useEffect(() => {
|
58
|
+
const interval = setInterval(() => {
|
59
|
+
setValue(prev => prev + Math.floor(Math.random() * 10) + 1);
|
60
|
+
}, 3000);
|
61
|
+
|
62
|
+
return () => clearInterval(interval);
|
63
|
+
}, []);
|
64
|
+
|
65
|
+
return <OdometerComponent value={value} duration={1000} />;
|
66
|
+
};
|
@@ -0,0 +1,45 @@
|
|
1
|
+
import React, {FC, memo, useRef} from "react";
|
2
|
+
|
3
|
+
import classNames from "classnames";
|
4
|
+
|
5
|
+
import {useComponentProps} from "../../providers";
|
6
|
+
|
7
|
+
import useOdometer, {OdometerOptions} from "./hooks/useOdometer";
|
8
|
+
|
9
|
+
import styles from "./odometer.module.scss";
|
10
|
+
|
11
|
+
export interface OdometerProps extends OdometerOptions {
|
12
|
+
value: number;
|
13
|
+
className?: string;
|
14
|
+
}
|
15
|
+
|
16
|
+
const Odometer: FC<OdometerProps> = props => {
|
17
|
+
const {
|
18
|
+
value,
|
19
|
+
auto = false,
|
20
|
+
format = "d",
|
21
|
+
duration = 250,
|
22
|
+
className,
|
23
|
+
...other
|
24
|
+
} = {...useComponentProps("odometer"), ...props};
|
25
|
+
|
26
|
+
const targetRef = useRef(null);
|
27
|
+
|
28
|
+
useOdometer(targetRef, value, {
|
29
|
+
...other,
|
30
|
+
auto,
|
31
|
+
format,
|
32
|
+
duration,
|
33
|
+
});
|
34
|
+
|
35
|
+
return (
|
36
|
+
<span
|
37
|
+
ref={targetRef}
|
38
|
+
dir="ltr"
|
39
|
+
style={{"--speed": `${duration}ms`} as React.CSSProperties}
|
40
|
+
className={classNames(styles["odometer"], className)}
|
41
|
+
/>
|
42
|
+
);
|
43
|
+
};
|
44
|
+
|
45
|
+
export default memo(Odometer);
|
@@ -0,0 +1,24 @@
|
|
1
|
+
import {RefObject, useEffect, useRef} from "react";
|
2
|
+
import Odometer from "odometer";
|
3
|
+
|
4
|
+
export interface OdometerOptions {
|
5
|
+
auto?: boolean;
|
6
|
+
format?: string;
|
7
|
+
duration?: number;
|
8
|
+
}
|
9
|
+
|
10
|
+
export default (ref: RefObject<HTMLElement | null>, value: number, options: OdometerOptions = {}) => {
|
11
|
+
const od = useRef<Odometer | null>(null);
|
12
|
+
|
13
|
+
useEffect(() => {
|
14
|
+
if (ref.current === null) return;
|
15
|
+
|
16
|
+
od.current = new Odometer({...options, el: ref.current, value});
|
17
|
+
}, [ref, options, value]);
|
18
|
+
|
19
|
+
useEffect(() => {
|
20
|
+
od.current?.update(value);
|
21
|
+
}, [value]);
|
22
|
+
|
23
|
+
return od.current;
|
24
|
+
};
|
@@ -0,0 +1,81 @@
|
|
1
|
+
$root: odometer;
|
2
|
+
|
3
|
+
.#{$root} {
|
4
|
+
display: inline-block;
|
5
|
+
position: relative;
|
6
|
+
color: var(--odometer-color, var(--text-primary-color));
|
7
|
+
font-family: var(--odometer-font-family, var(--font-family)), sans-serif;
|
8
|
+
|
9
|
+
&-digit {
|
10
|
+
display: inline-block;
|
11
|
+
position: relative;
|
12
|
+
|
13
|
+
&-spacer {
|
14
|
+
display: inline-block;
|
15
|
+
visibility: hidden;
|
16
|
+
}
|
17
|
+
|
18
|
+
&-inner {
|
19
|
+
text-align: left;
|
20
|
+
display: block;
|
21
|
+
position: absolute;
|
22
|
+
top: 0;
|
23
|
+
left: 0;
|
24
|
+
right: 0;
|
25
|
+
bottom: 0;
|
26
|
+
overflow: hidden;
|
27
|
+
}
|
28
|
+
}
|
29
|
+
|
30
|
+
&-ribbon {
|
31
|
+
display: block;
|
32
|
+
|
33
|
+
&-inner {
|
34
|
+
display: block;
|
35
|
+
-webkit-backface-visibility: hidden;
|
36
|
+
|
37
|
+
.#{$root}-animating-up & {
|
38
|
+
transition: transform var(--speed);
|
39
|
+
}
|
40
|
+
|
41
|
+
.#{$root}-animating-up.#{$root}-animating & {
|
42
|
+
transform: translateY(-100%);
|
43
|
+
}
|
44
|
+
|
45
|
+
.#{$root}-animating-down & {
|
46
|
+
transform: translateY(-100%);
|
47
|
+
}
|
48
|
+
|
49
|
+
.#{$root}-animating-down.#{$root}-animating & {
|
50
|
+
transition: transform var(--speed);
|
51
|
+
transform: translateY(0);
|
52
|
+
}
|
53
|
+
}
|
54
|
+
}
|
55
|
+
|
56
|
+
&-value {
|
57
|
+
display: block;
|
58
|
+
text-align: center;
|
59
|
+
transform: translateZ(0);
|
60
|
+
}
|
61
|
+
|
62
|
+
&-last-value {
|
63
|
+
position: absolute;
|
64
|
+
}
|
65
|
+
|
66
|
+
&-inside {
|
67
|
+
transition:
|
68
|
+
all var(--speed),
|
69
|
+
color var(--transition-speed-sm);
|
70
|
+
|
71
|
+
&:before {
|
72
|
+
content: "";
|
73
|
+
width: 0;
|
74
|
+
display: inline-block;
|
75
|
+
color: inherit;
|
76
|
+
transition:
|
77
|
+
all var(--speed),
|
78
|
+
color var(--transition-speed-sm);
|
79
|
+
}
|
80
|
+
}
|
81
|
+
}
|
@@ -0,0 +1,58 @@
|
|
1
|
+
import {Meta, StoryObj} from "@storybook/react";
|
2
|
+
|
3
|
+
import {hideInTable} from "../../utils";
|
4
|
+
|
5
|
+
import ScrollAreaComponent from "./ScrollArea";
|
6
|
+
|
7
|
+
const meta: Meta<typeof ScrollAreaComponent> = {
|
8
|
+
title: "Components/ScrollArea",
|
9
|
+
component: ScrollAreaComponent,
|
10
|
+
tags: ["autodocs"],
|
11
|
+
argTypes: {
|
12
|
+
type: {
|
13
|
+
description:
|
14
|
+
"Describes the nature of scrollbar visibility, similar to how the scrollbar preferences in MacOS control visibility of native scrollbars.",
|
15
|
+
options: ["auto", "always", "scroll", "hover"],
|
16
|
+
control: {type: "select"},
|
17
|
+
},
|
18
|
+
scrollHideDelay: {
|
19
|
+
description:
|
20
|
+
'If type is set to either "scroll" or "hover", this prop determines the length of time, in milliseconds, before the scrollbars are hidden after the user stops interacting with scrollbars.',
|
21
|
+
},
|
22
|
+
dir: {
|
23
|
+
description:
|
24
|
+
"The reading direction of the scroll area. If omitted, inherits globally from DirectionProvider or assumes LTR (left-to-right) reading mode.",
|
25
|
+
options: ["ltr", "rtl"],
|
26
|
+
control: {type: "select"},
|
27
|
+
},
|
28
|
+
|
29
|
+
style: hideInTable,
|
30
|
+
className: hideInTable,
|
31
|
+
thumbClassName: hideInTable,
|
32
|
+
cornerClassName: hideInTable,
|
33
|
+
viewportClassName: hideInTable,
|
34
|
+
scrollbarClassName: hideInTable,
|
35
|
+
},
|
36
|
+
};
|
37
|
+
|
38
|
+
export default meta;
|
39
|
+
|
40
|
+
export const ScrollArea: StoryObj<typeof ScrollAreaComponent> = {
|
41
|
+
args: {
|
42
|
+
type: "hover",
|
43
|
+
dir: "ltr",
|
44
|
+
xOffset: 3,
|
45
|
+
yOffset: 3,
|
46
|
+
scrollHideDelay: 600,
|
47
|
+
style: {
|
48
|
+
padding: "10px",
|
49
|
+
width: "300px",
|
50
|
+
height: "150px",
|
51
|
+
borderRadius: "10px",
|
52
|
+
color: "var(--text-secondary-color)",
|
53
|
+
background: "var(--bg-secondary-color)",
|
54
|
+
},
|
55
|
+
children:
|
56
|
+
"Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nullam vehicula, justo at congue malesuada, arcu elit malesuada eros, ut tempor justo libero a est. Donec sit amet tortor nec justo auctor sagittis. Suspendisse potenti. Fusce gravida, libero vel auctor pretium, odio risus vehicula nunc, et ultricies nunc arcu a neque. Aliquam erat volutpat. Morbi vulputate erat nec lectus vestibulum, at ullamcorper risus aliquet",
|
57
|
+
},
|
58
|
+
};
|
@@ -0,0 +1,63 @@
|
|
1
|
+
import React, {FC, memo} from "react";
|
2
|
+
import classnames from "classnames";
|
3
|
+
import {
|
4
|
+
Corner,
|
5
|
+
Root,
|
6
|
+
ScrollAreaProps as ScrollAreaRootProps,
|
7
|
+
Scrollbar,
|
8
|
+
Thumb,
|
9
|
+
Viewport,
|
10
|
+
} from "@radix-ui/react-scroll-area";
|
11
|
+
|
12
|
+
import {useComponentProps} from "../../providers";
|
13
|
+
|
14
|
+
import styles from "./scroll-area.module.scss";
|
15
|
+
|
16
|
+
export interface ScrollAreaProps extends ScrollAreaRootProps {
|
17
|
+
xOffset?: number;
|
18
|
+
yOffset?: number;
|
19
|
+
thumbClassName?: string;
|
20
|
+
cornerClassName?: string;
|
21
|
+
viewportClassName?: string;
|
22
|
+
scrollbarClassName?: string;
|
23
|
+
}
|
24
|
+
|
25
|
+
const ScrollArea: FC<ScrollAreaProps> = props => {
|
26
|
+
const {
|
27
|
+
xOffset,
|
28
|
+
yOffset,
|
29
|
+
children,
|
30
|
+
className,
|
31
|
+
thumbClassName,
|
32
|
+
cornerClassName,
|
33
|
+
viewportClassName,
|
34
|
+
scrollbarClassName,
|
35
|
+
...other
|
36
|
+
} = {...useComponentProps("scrollArea"), ...props};
|
37
|
+
|
38
|
+
return (
|
39
|
+
<Root className={classnames(styles["scroll-area"], className)} {...other}>
|
40
|
+
<Viewport className={classnames(styles["scroll-area__viewport"], viewportClassName)}>{children}</Viewport>
|
41
|
+
|
42
|
+
<Scrollbar
|
43
|
+
orientation="vertical"
|
44
|
+
style={{padding: `0 ${xOffset}px`}}
|
45
|
+
className={classnames(styles["scroll-area__scrollbar"], scrollbarClassName)}
|
46
|
+
>
|
47
|
+
<Thumb className={classnames(styles["scroll-area__thumb"], thumbClassName)} />
|
48
|
+
</Scrollbar>
|
49
|
+
|
50
|
+
<Scrollbar
|
51
|
+
orientation="horizontal"
|
52
|
+
style={{padding: `${yOffset}px 0`}}
|
53
|
+
className={classnames(styles["scroll-area__scrollbar"], scrollbarClassName)}
|
54
|
+
>
|
55
|
+
<Thumb className={classnames(styles["scroll-area__thumb"], thumbClassName)} />
|
56
|
+
</Scrollbar>
|
57
|
+
|
58
|
+
<Corner className={classnames(styles["scroll-area__corner"], cornerClassName)} />
|
59
|
+
</Root>
|
60
|
+
);
|
61
|
+
};
|
62
|
+
|
63
|
+
export default memo(ScrollArea);
|
@@ -0,0 +1,54 @@
|
|
1
|
+
$root: scroll-area;
|
2
|
+
|
3
|
+
.#{$root} {
|
4
|
+
box-sizing: border-box;
|
5
|
+
overflow: hidden;
|
6
|
+
|
7
|
+
&__viewport {
|
8
|
+
width: 100%;
|
9
|
+
height: 100%;
|
10
|
+
}
|
11
|
+
|
12
|
+
&__scrollbar {
|
13
|
+
display: flex;
|
14
|
+
user-select: none;
|
15
|
+
touch-action: none;
|
16
|
+
padding: var(--scroll-area-scrollbar-padding, 3px);
|
17
|
+
background: var(--scroll-area-scrollbar-bg-color, transparent);
|
18
|
+
transition: background var(--transition-speed-sm) ease-in-out;
|
19
|
+
|
20
|
+
&:hover {
|
21
|
+
background: var(--scroll-area-scrollbar-bg-color-hover, transparent);
|
22
|
+
}
|
23
|
+
|
24
|
+
&[data-orientation="vertical"] {
|
25
|
+
width: var(--scroll-area-scrollbar-size, 9px);
|
26
|
+
padding: 0 var(--scroll-area-scrollbar-offset, var(--scroll-area-scrollbar-x-offset, 2px));
|
27
|
+
}
|
28
|
+
|
29
|
+
&[data-orientation="horizontal"] {
|
30
|
+
flex-direction: column;
|
31
|
+
height: var(--scroll-area-scrollbar-size, 9px);
|
32
|
+
padding: var(--scroll-area-scrollbar-offset, var(--scroll-area-scrollbar-y-offset, 2px)) 0;
|
33
|
+
}
|
34
|
+
}
|
35
|
+
|
36
|
+
&__thumb {
|
37
|
+
flex: 1;
|
38
|
+
position: relative;
|
39
|
+
background: var(--scroll-area-thumb-bg-color);
|
40
|
+
border-radius: var(--scroll-area-thumb-border-radius, 100px);
|
41
|
+
|
42
|
+
&:hover {
|
43
|
+
background: var(--scroll-area-thumb-bg-color-hover, var(--scroll-area-thumb-bg-color));
|
44
|
+
}
|
45
|
+
}
|
46
|
+
|
47
|
+
&__corner {
|
48
|
+
background: var(--scroll-area-scrollbar-bg-color, transparent);
|
49
|
+
|
50
|
+
&:hover {
|
51
|
+
background: var(--scroll-area-scrollbar-bg-color-hover, transparent);
|
52
|
+
}
|
53
|
+
}
|
54
|
+
}
|
@@ -0,0 +1,21 @@
|
|
1
|
+
import React, {ComponentProps, FC, memo} from "react";
|
2
|
+
|
3
|
+
export interface SvgSpriteProps {
|
4
|
+
icons: Record<string, FC<ComponentProps<"svg">>>;
|
5
|
+
}
|
6
|
+
|
7
|
+
const SvgSprite: FC<SvgSpriteProps> = ({icons}) => {
|
8
|
+
return (
|
9
|
+
<svg style={{display: "none"}} aria-hidden="true">
|
10
|
+
<defs>
|
11
|
+
{Object.entries(icons).map(([name, Icon]) => (
|
12
|
+
<symbol id={name} key={name} viewBox="0 0 24 24">
|
13
|
+
<Icon />
|
14
|
+
</symbol>
|
15
|
+
))}
|
16
|
+
</defs>
|
17
|
+
</svg>
|
18
|
+
);
|
19
|
+
};
|
20
|
+
|
21
|
+
export default memo(SvgSprite);
|
@@ -0,0 +1,25 @@
|
|
1
|
+
import {Meta, StoryObj} from "@storybook/react";
|
2
|
+
|
3
|
+
import {hideInTable} from "../../utils";
|
4
|
+
|
5
|
+
import SwitchComponent from "./Switch";
|
6
|
+
|
7
|
+
const meta: Meta<typeof SwitchComponent> = {
|
8
|
+
title: "Components/Switch",
|
9
|
+
component: SwitchComponent,
|
10
|
+
tags: ["autodocs"],
|
11
|
+
argTypes: {
|
12
|
+
children: hideInTable,
|
13
|
+
className: hideInTable,
|
14
|
+
thumbClassName: hideInTable,
|
15
|
+
},
|
16
|
+
};
|
17
|
+
|
18
|
+
export default meta;
|
19
|
+
|
20
|
+
export const Switch: StoryObj<typeof SwitchComponent> = {
|
21
|
+
args: {
|
22
|
+
checked: true,
|
23
|
+
disabled: false,
|
24
|
+
},
|
25
|
+
};
|
@@ -0,0 +1,23 @@
|
|
1
|
+
import React, {FC, memo} from "react";
|
2
|
+
import classnames from "classnames";
|
3
|
+
import {Root, SwitchProps as SwitchRootProps, Thumb} from "@radix-ui/react-switch";
|
4
|
+
|
5
|
+
import {useComponentProps} from "../../providers";
|
6
|
+
|
7
|
+
import styles from "./switch.module.scss";
|
8
|
+
|
9
|
+
export interface SwitchProps extends SwitchRootProps {
|
10
|
+
thumbClassName?: string;
|
11
|
+
}
|
12
|
+
|
13
|
+
const Switch: FC<SwitchProps> = props => {
|
14
|
+
const {className, thumbClassName, ...other} = {...useComponentProps("switch"), ...props};
|
15
|
+
|
16
|
+
return (
|
17
|
+
<Root {...other} className={classnames(styles["switch"], className)}>
|
18
|
+
<Thumb className={classnames(styles["switch__thumb"], thumbClassName)} />
|
19
|
+
</Root>
|
20
|
+
);
|
21
|
+
};
|
22
|
+
|
23
|
+
export default memo(Switch);
|
@@ -0,0 +1,65 @@
|
|
1
|
+
@use "../../styles/mixins" as dir;
|
2
|
+
|
3
|
+
@function switch-width() {
|
4
|
+
@return var(--switch-width, 36px);
|
5
|
+
}
|
6
|
+
|
7
|
+
@function switch-height() {
|
8
|
+
@return var(--switch-height, 22px);
|
9
|
+
}
|
10
|
+
|
11
|
+
@function switch-thumb-width() {
|
12
|
+
@return var(--switch-thumb-width, 18px);
|
13
|
+
}
|
14
|
+
|
15
|
+
@function switch-thumb-height() {
|
16
|
+
@return var(--switch-thumb-height, 18px);
|
17
|
+
}
|
18
|
+
|
19
|
+
$root: switch;
|
20
|
+
|
21
|
+
.#{$root} {
|
22
|
+
margin: 0;
|
23
|
+
padding: 0;
|
24
|
+
border: none;
|
25
|
+
box-sizing: border-box;
|
26
|
+
cursor: pointer;
|
27
|
+
position: relative;
|
28
|
+
width: switch-width();
|
29
|
+
height: switch-height();
|
30
|
+
border-radius: var(--switch-border-radius, 9999px);
|
31
|
+
background: var(--switch-bg-color, #bbb);
|
32
|
+
will-change: background;
|
33
|
+
transition: background var(--transition-speed-sm);
|
34
|
+
|
35
|
+
&[data-state="checked"] {
|
36
|
+
background-color: var(--switch-cheked-bg-color, var(--primary-color));
|
37
|
+
}
|
38
|
+
|
39
|
+
&:disabled {
|
40
|
+
opacity: var(--switch-disabled-opacity, 0.6);
|
41
|
+
cursor: default;
|
42
|
+
}
|
43
|
+
|
44
|
+
&__thumb {
|
45
|
+
box-sizing: border-box;
|
46
|
+
display: block;
|
47
|
+
width: switch-thumb-width();
|
48
|
+
height: switch-thumb-height();
|
49
|
+
transform: translateX(calc((#{switch-height()} - #{switch-thumb-height()}) / 2));
|
50
|
+
background-color: var(--switch-thumb-bg-color, white);
|
51
|
+
border-radius: var(--switch-border-radius, 9999px);
|
52
|
+
will-change: transform;
|
53
|
+
transition: transform var(--transition-speed-sm) ease-in-out;
|
54
|
+
|
55
|
+
@include dir.rtl {
|
56
|
+
margin-right: calc(#{switch-width()} / 2);
|
57
|
+
}
|
58
|
+
|
59
|
+
&[data-state="checked"] {
|
60
|
+
transform: translateX(
|
61
|
+
calc(#{switch-width()} - #{switch-thumb-width()} - (#{switch-height()} - #{switch-thumb-height()}) / 2)
|
62
|
+
);
|
63
|
+
}
|
64
|
+
}
|
65
|
+
}
|