@snack-uikit/segmented-control 0.4.20 → 0.6.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/CHANGELOG.md +22 -0
- package/README.md +2 -1
- package/dist/cjs/components/SegmentedControl.d.ts +5 -1
- package/dist/cjs/components/SegmentedControl.js +8 -3
- package/dist/cjs/components/styles.module.css +11 -0
- package/dist/cjs/constants.d.ts +1 -0
- package/dist/cjs/constants.js +1 -0
- package/dist/cjs/helperComponents/Segment/Segment.js +2 -2
- package/dist/cjs/helperComponents/Segment/styles.module.css +29 -0
- package/dist/cjs/utils.d.ts +1 -1
- package/dist/cjs/utils.js +4 -1
- package/dist/esm/components/SegmentedControl.d.ts +5 -1
- package/dist/esm/components/SegmentedControl.js +2 -2
- package/dist/esm/components/styles.module.css +11 -0
- package/dist/esm/constants.d.ts +1 -0
- package/dist/esm/constants.js +1 -0
- package/dist/esm/helperComponents/Segment/Segment.js +1 -1
- package/dist/esm/helperComponents/Segment/styles.module.css +29 -0
- package/dist/esm/utils.d.ts +1 -1
- package/dist/esm/utils.js +4 -1
- package/package.json +2 -2
- package/src/components/SegmentedControl.tsx +6 -0
- package/src/components/styles.module.scss +16 -5
- package/src/constants.ts +1 -0
- package/src/helperComponents/Segment/Segment.tsx +2 -2
- package/src/helperComponents/Segment/styles.module.scss +16 -6
- package/src/utils.ts +5 -1
package/CHANGELOG.md
CHANGED
|
@@ -3,6 +3,28 @@
|
|
|
3
3
|
All notable changes to this project will be documented in this file.
|
|
4
4
|
See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
|
|
5
5
|
|
|
6
|
+
# 0.6.0 (2025-05-28)
|
|
7
|
+
|
|
8
|
+
|
|
9
|
+
### Features
|
|
10
|
+
|
|
11
|
+
* **PDS-1990:** added xs size for segmented control ([0f8fb0d](https://github.com/cloud-ru-tech/snack-uikit/commit/0f8fb0de09568eb983c685118068870a03ad3f92))
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
# 0.5.0 (2025-05-21)
|
|
18
|
+
|
|
19
|
+
|
|
20
|
+
### Features
|
|
21
|
+
|
|
22
|
+
* **FF-6410:** add name for segment control ([b6e5488](https://github.com/cloud-ru-tech/snack-uikit/commit/b6e548889cdae95e87c3bd0e615c1c97f0489b12))
|
|
23
|
+
|
|
24
|
+
|
|
25
|
+
|
|
26
|
+
|
|
27
|
+
|
|
6
28
|
## 0.4.20 (2025-05-16)
|
|
7
29
|
|
|
8
30
|
### Only dependencies have been changed
|
package/README.md
CHANGED
|
@@ -19,9 +19,10 @@ SegmentedControl
|
|
|
19
19
|
| defaultValue | `IdType` | - | ID выбранного по умолчанию сегмента. (в uncontrolled режиме) |
|
|
20
20
|
| onChange | `(value: Value) => void` | - | Колбек смены выбранного сегмента. |
|
|
21
21
|
| className | `string` | - | CSS-класс контейнера. |
|
|
22
|
-
| size | enum Size: `"s"`, `"m"`, `"l"` | m | Размер компонента. |
|
|
22
|
+
| size | enum Size: `"xs"`, `"s"`, `"m"`, `"l"` | m | Размер компонента. |
|
|
23
23
|
| outline | `boolean` | - | Обводка |
|
|
24
24
|
| width | enum Width: `"auto"`, `"full"` | auto | Управление шириной компонента. |
|
|
25
|
+
| name | `string` | - | Имя поля |
|
|
25
26
|
|
|
26
27
|
|
|
27
28
|
[//]: DOCUMENTATION_SECTION_END
|
|
@@ -33,8 +33,12 @@ export type SegmentedControlProps<Value extends IdType = IdType> = WithSupportPr
|
|
|
33
33
|
* Управление шириной компонента.
|
|
34
34
|
*/
|
|
35
35
|
width?: Width;
|
|
36
|
+
/**
|
|
37
|
+
* Имя поля
|
|
38
|
+
*/
|
|
39
|
+
name?: string;
|
|
36
40
|
}>;
|
|
37
41
|
/**
|
|
38
42
|
* SegmentedControl
|
|
39
43
|
*/
|
|
40
|
-
export declare function SegmentedControl<Value extends IdType>({ defaultValue, size, className, onChange, items, value, outline, width, ...other }: SegmentedControlProps<Value>): import("react/jsx-runtime").JSX.Element;
|
|
44
|
+
export declare function SegmentedControl<Value extends IdType>({ defaultValue, size, className, onChange, items, value, outline, width, name, ...other }: SegmentedControlProps<Value>): import("react/jsx-runtime").JSX.Element;
|
|
@@ -38,9 +38,10 @@ function SegmentedControl(_a) {
|
|
|
38
38
|
items,
|
|
39
39
|
value,
|
|
40
40
|
outline,
|
|
41
|
-
width = constants_1.WIDTH.Auto
|
|
41
|
+
width = constants_1.WIDTH.Auto,
|
|
42
|
+
name
|
|
42
43
|
} = _a,
|
|
43
|
-
other = __rest(_a, ["defaultValue", "size", "className", "onChange", "items", "value", "outline", "width"]);
|
|
44
|
+
other = __rest(_a, ["defaultValue", "size", "className", "onChange", "items", "value", "outline", "width", "name"]);
|
|
44
45
|
const [selected, setSelected] = (0, uncontrollable_1.useUncontrolledProp)(value, defaultValue, onChange);
|
|
45
46
|
const {
|
|
46
47
|
focusableSegmentValue,
|
|
@@ -106,7 +107,11 @@ function SegmentedControl(_a) {
|
|
|
106
107
|
"data-outline": outline || undefined,
|
|
107
108
|
"data-width": width
|
|
108
109
|
}, (0, utils_1.extractDataTestProps)(other), (0, utils_1.extractSupportProps)(other), {
|
|
109
|
-
children: [(0, jsx_runtime_1.jsx)("
|
|
110
|
+
children: [name && (0, jsx_runtime_1.jsx)("input", {
|
|
111
|
+
type: 'hidden',
|
|
112
|
+
value: selected,
|
|
113
|
+
name: name
|
|
114
|
+
}), (0, jsx_runtime_1.jsx)("div", {
|
|
110
115
|
"data-size": size,
|
|
111
116
|
style: selectionPosition,
|
|
112
117
|
className: styles_module_scss_1.default.selection,
|
|
@@ -28,6 +28,10 @@
|
|
|
28
28
|
.container[data-width=full]{
|
|
29
29
|
display:flex;
|
|
30
30
|
}
|
|
31
|
+
.container[data-size=xs]::before{
|
|
32
|
+
border-width:var(--border-width-segmented-control-single, 1px);
|
|
33
|
+
border-radius:var(--radius-segmented-control-container-xs, 8px);
|
|
34
|
+
}
|
|
31
35
|
.container[data-size=s]::before{
|
|
32
36
|
border-width:var(--border-width-segmented-control-single, 1px);
|
|
33
37
|
border-radius:var(--radius-segmented-control-container-s, 12px);
|
|
@@ -59,6 +63,13 @@
|
|
|
59
63
|
background-color:var(--sys-neutral-background2-level, #ffffff);
|
|
60
64
|
transition:left 0.15s ease-in-out, width 0.15s ease-in-out;
|
|
61
65
|
}
|
|
66
|
+
.selection[data-size=xs]{
|
|
67
|
+
border-radius:var(--radius-segmented-control-segment-s, 10px);
|
|
68
|
+
padding-left:var(--space-segmented-control-segment-s-icon-only, 2px);
|
|
69
|
+
padding-right:var(--space-segmented-control-segment-s-icon-only, 2px);
|
|
70
|
+
gap:var(--space-segmented-control-segment-s-gap, 4px);
|
|
71
|
+
height:var(--size-segmented-control-segment-s, 28px);
|
|
72
|
+
}
|
|
62
73
|
.selection[data-size=s]{
|
|
63
74
|
border-radius:var(--radius-segmented-control-segment-s, 10px);
|
|
64
75
|
padding-left:var(--space-segmented-control-segment-s-icon-only, 2px);
|
package/dist/cjs/constants.d.ts
CHANGED
package/dist/cjs/constants.js
CHANGED
|
@@ -45,7 +45,7 @@ function Segment(_ref) {
|
|
|
45
45
|
"data-test-id": `section-${value}`,
|
|
46
46
|
"data-active": selected || undefined,
|
|
47
47
|
"data-disabled": disabled || undefined,
|
|
48
|
-
"data-layout": (0, utils_1.getLayout)(icon, label),
|
|
48
|
+
"data-layout": (0, utils_1.getLayout)(icon, label, size),
|
|
49
49
|
className: (0, classnames_1.default)(styles_module_scss_1.default.segment),
|
|
50
50
|
onClick: onClick,
|
|
51
51
|
"data-size": size,
|
|
@@ -54,7 +54,7 @@ function Segment(_ref) {
|
|
|
54
54
|
"aria-checked": selected,
|
|
55
55
|
role: 'radio',
|
|
56
56
|
type: 'button',
|
|
57
|
-
children: [icon && (0, jsx_runtime_1.jsx)("div", {
|
|
57
|
+
children: [size !== 'xs' && icon && (0, jsx_runtime_1.jsx)("div", {
|
|
58
58
|
className: styles_module_scss_1.default.icon,
|
|
59
59
|
children: icon
|
|
60
60
|
}), label && (0, jsx_runtime_1.jsx)(truncate_string_1.TruncateString, {
|
|
@@ -29,6 +29,27 @@
|
|
|
29
29
|
outline-offset:calc(var(--border-state-focus-s-border-width, 2px) * -1);
|
|
30
30
|
outline-color:var(--sys-available-complementary, #1c1c24);
|
|
31
31
|
}
|
|
32
|
+
.segment[data-size=xs][data-layout=label-only]{
|
|
33
|
+
border-radius:var(--radius-segmented-control-segment-xs, 6px);
|
|
34
|
+
padding-left:var(--space-segmented-control-segment-xs-from-label, 8px);
|
|
35
|
+
padding-right:var(--space-segmented-control-segment-xs-from-label, 8px);
|
|
36
|
+
gap:var(--space-segmented-control-segment-xs-gap, 2px);
|
|
37
|
+
height:var(--size-segmented-control-segment-xs, 20px);
|
|
38
|
+
}
|
|
39
|
+
.segment[data-size=xs][data-layout=icon-before]{
|
|
40
|
+
border-radius:var(--radius-segmented-control-segment-s, 10px);
|
|
41
|
+
padding-left:var(--space-segmented-control-segment-s-from-icon, 8px);
|
|
42
|
+
padding-right:var(--space-segmented-control-segment-s-from-label, 16px);
|
|
43
|
+
gap:var(--space-segmented-control-segment-s-gap, 4px);
|
|
44
|
+
height:var(--size-segmented-control-segment-s, 28px);
|
|
45
|
+
}
|
|
46
|
+
.segment[data-size=xs][data-layout=icon-only]{
|
|
47
|
+
border-radius:var(--radius-segmented-control-segment-s, 10px);
|
|
48
|
+
padding-left:var(--space-segmented-control-segment-s-icon-only, 2px);
|
|
49
|
+
padding-right:var(--space-segmented-control-segment-s-icon-only, 2px);
|
|
50
|
+
gap:var(--space-segmented-control-segment-s-gap, 4px);
|
|
51
|
+
height:var(--size-segmented-control-segment-s, 28px);
|
|
52
|
+
}
|
|
32
53
|
.segment[data-size=s][data-layout=label-only]{
|
|
33
54
|
border-radius:var(--radius-segmented-control-segment-s, 10px);
|
|
34
55
|
padding-left:var(--space-segmented-control-segment-s-from-label, 16px);
|
|
@@ -99,6 +120,14 @@
|
|
|
99
120
|
align-items:center;
|
|
100
121
|
}
|
|
101
122
|
|
|
123
|
+
.label[data-size=xs]{
|
|
124
|
+
font-family:var(--sans-label-m-font-family, SB Sans Interface);
|
|
125
|
+
font-weight:var(--sans-label-m-font-weight, Semibold);
|
|
126
|
+
line-height:var(--sans-label-m-line-height, 16px);
|
|
127
|
+
font-size:var(--sans-label-m-font-size, 12px);
|
|
128
|
+
letter-spacing:var(--sans-label-m-letter-spacing, 0px);
|
|
129
|
+
paragraph-spacing:var(--sans-label-m-paragraph-spacing, 6.6px);
|
|
130
|
+
}
|
|
102
131
|
.label[data-size=s]{
|
|
103
132
|
font-family:var(--sans-label-m-font-family, SB Sans Interface);
|
|
104
133
|
font-weight:var(--sans-label-m-font-weight, Semibold);
|
package/dist/cjs/utils.d.ts
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
1
|
import { ReactNode } from 'react';
|
|
2
|
-
export declare const getLayout: (icon?: ReactNode, label?: string) => "
|
|
2
|
+
export declare const getLayout: (icon?: ReactNode, label?: string, size?: string) => "label-only" | "icon-before" | "icon-only";
|
package/dist/cjs/utils.js
CHANGED
|
@@ -4,7 +4,10 @@ Object.defineProperty(exports, "__esModule", {
|
|
|
4
4
|
value: true
|
|
5
5
|
});
|
|
6
6
|
exports.getLayout = void 0;
|
|
7
|
-
const getLayout = (icon, label) => {
|
|
7
|
+
const getLayout = (icon, label, size) => {
|
|
8
|
+
if (size === 'xs') {
|
|
9
|
+
return 'label-only';
|
|
10
|
+
}
|
|
8
11
|
if (icon && label) {
|
|
9
12
|
return 'icon-before';
|
|
10
13
|
}
|
|
@@ -33,8 +33,12 @@ export type SegmentedControlProps<Value extends IdType = IdType> = WithSupportPr
|
|
|
33
33
|
* Управление шириной компонента.
|
|
34
34
|
*/
|
|
35
35
|
width?: Width;
|
|
36
|
+
/**
|
|
37
|
+
* Имя поля
|
|
38
|
+
*/
|
|
39
|
+
name?: string;
|
|
36
40
|
}>;
|
|
37
41
|
/**
|
|
38
42
|
* SegmentedControl
|
|
39
43
|
*/
|
|
40
|
-
export declare function SegmentedControl<Value extends IdType>({ defaultValue, size, className, onChange, items, value, outline, width, ...other }: SegmentedControlProps<Value>): import("react/jsx-runtime").JSX.Element;
|
|
44
|
+
export declare function SegmentedControl<Value extends IdType>({ defaultValue, size, className, onChange, items, value, outline, width, name, ...other }: SegmentedControlProps<Value>): import("react/jsx-runtime").JSX.Element;
|
|
@@ -22,7 +22,7 @@ import styles from './styles.module.css';
|
|
|
22
22
|
* SegmentedControl
|
|
23
23
|
*/
|
|
24
24
|
export function SegmentedControl(_a) {
|
|
25
|
-
var { defaultValue, size = 'm', className, onChange, items, value, outline, width = WIDTH.Auto } = _a, other = __rest(_a, ["defaultValue", "size", "className", "onChange", "items", "value", "outline", "width"]);
|
|
25
|
+
var { defaultValue, size = 'm', className, onChange, items, value, outline, width = WIDTH.Auto, name } = _a, other = __rest(_a, ["defaultValue", "size", "className", "onChange", "items", "value", "outline", "width", "name"]);
|
|
26
26
|
const [selected, setSelected] = useUncontrolledProp(value, defaultValue, onChange);
|
|
27
27
|
const { focusableSegmentValue, onGetFocusable, onKeyDown } = useFocusControl({ selected, items });
|
|
28
28
|
const containerRef = useRef(null);
|
|
@@ -60,5 +60,5 @@ export function SegmentedControl(_a) {
|
|
|
60
60
|
const itemsJSX = useMemo(() => items.map(props => (_jsx("div", { className: styles.segmentHolder, "data-width": width, children: _jsx(Segment, Object.assign({}, props, { size: size, onGetFocusable: onGetFocusable, selected: selected === props.value, onClick: () => setSelected(props.value), focusable: focusableSegmentValue === props.value, onSelectionUpdated: updateSelectionPosition })) }, props.value))), [items, width, size, onGetFocusable, selected, focusableSegmentValue, updateSelectionPosition, setSelected]);
|
|
61
61
|
return (
|
|
62
62
|
// eslint-disable-next-line jsx-a11y/interactive-supports-focus
|
|
63
|
-
_jsxs("div", Object.assign({ ref: containerRef, "data-size": size, onKeyDown: onKeyDown, className: cn(styles.container, className), role: 'radiogroup', "data-outline": outline || undefined, "data-width": width }, extractDataTestProps(other), extractSupportProps(other), { children: [_jsx("div", { "data-size": size, style: selectionPosition, className: styles.selection, "aria-hidden": true }), itemsJSX] })));
|
|
63
|
+
_jsxs("div", Object.assign({ ref: containerRef, "data-size": size, onKeyDown: onKeyDown, className: cn(styles.container, className), role: 'radiogroup', "data-outline": outline || undefined, "data-width": width }, extractDataTestProps(other), extractSupportProps(other), { children: [name && _jsx("input", { type: 'hidden', value: selected, name: name }), _jsx("div", { "data-size": size, style: selectionPosition, className: styles.selection, "aria-hidden": true }), itemsJSX] })));
|
|
64
64
|
}
|
|
@@ -28,6 +28,10 @@
|
|
|
28
28
|
.container[data-width=full]{
|
|
29
29
|
display:flex;
|
|
30
30
|
}
|
|
31
|
+
.container[data-size=xs]::before{
|
|
32
|
+
border-width:var(--border-width-segmented-control-single, 1px);
|
|
33
|
+
border-radius:var(--radius-segmented-control-container-xs, 8px);
|
|
34
|
+
}
|
|
31
35
|
.container[data-size=s]::before{
|
|
32
36
|
border-width:var(--border-width-segmented-control-single, 1px);
|
|
33
37
|
border-radius:var(--radius-segmented-control-container-s, 12px);
|
|
@@ -59,6 +63,13 @@
|
|
|
59
63
|
background-color:var(--sys-neutral-background2-level, #ffffff);
|
|
60
64
|
transition:left 0.15s ease-in-out, width 0.15s ease-in-out;
|
|
61
65
|
}
|
|
66
|
+
.selection[data-size=xs]{
|
|
67
|
+
border-radius:var(--radius-segmented-control-segment-s, 10px);
|
|
68
|
+
padding-left:var(--space-segmented-control-segment-s-icon-only, 2px);
|
|
69
|
+
padding-right:var(--space-segmented-control-segment-s-icon-only, 2px);
|
|
70
|
+
gap:var(--space-segmented-control-segment-s-gap, 4px);
|
|
71
|
+
height:var(--size-segmented-control-segment-s, 28px);
|
|
72
|
+
}
|
|
62
73
|
.selection[data-size=s]{
|
|
63
74
|
border-radius:var(--radius-segmented-control-segment-s, 10px);
|
|
64
75
|
padding-left:var(--space-segmented-control-segment-s-icon-only, 2px);
|
package/dist/esm/constants.d.ts
CHANGED
package/dist/esm/constants.js
CHANGED
|
@@ -16,6 +16,6 @@ export function Segment({ size, label, value, selected, onClick, disabled, icon,
|
|
|
16
16
|
onSelectionUpdated(buttonRef.current);
|
|
17
17
|
}
|
|
18
18
|
}, [selected, buttonRef, onSelectionUpdated]);
|
|
19
|
-
const segment = (_jsxs("button", { ref: buttonRef, "data-test-id": `section-${value}`, "data-active": selected || undefined, "data-disabled": disabled || undefined, "data-layout": getLayout(icon, label), className: cn(styles.segment), onClick: onClick, "data-size": size, disabled: disabled, tabIndex: focusable ? 0 : -1, "aria-checked": selected, role: 'radio', type: 'button', children: [icon && _jsx("div", { className: styles.icon, children: icon }), label && _jsx(TruncateString, { className: styles.label, "data-size": size, text: label })] }));
|
|
19
|
+
const segment = (_jsxs("button", { ref: buttonRef, "data-test-id": `section-${value}`, "data-active": selected || undefined, "data-disabled": disabled || undefined, "data-layout": getLayout(icon, label, size), className: cn(styles.segment), onClick: onClick, "data-size": size, disabled: disabled, tabIndex: focusable ? 0 : -1, "aria-checked": selected, role: 'radio', type: 'button', children: [size !== 'xs' && icon && _jsx("div", { className: styles.icon, children: icon }), label && _jsx(TruncateString, { className: styles.label, "data-size": size, text: label })] }));
|
|
20
20
|
return renderWrapSegment ? renderWrapSegment(segment) : segment;
|
|
21
21
|
}
|
|
@@ -29,6 +29,27 @@
|
|
|
29
29
|
outline-offset:calc(var(--border-state-focus-s-border-width, 2px) * -1);
|
|
30
30
|
outline-color:var(--sys-available-complementary, #1c1c24);
|
|
31
31
|
}
|
|
32
|
+
.segment[data-size=xs][data-layout=label-only]{
|
|
33
|
+
border-radius:var(--radius-segmented-control-segment-xs, 6px);
|
|
34
|
+
padding-left:var(--space-segmented-control-segment-xs-from-label, 8px);
|
|
35
|
+
padding-right:var(--space-segmented-control-segment-xs-from-label, 8px);
|
|
36
|
+
gap:var(--space-segmented-control-segment-xs-gap, 2px);
|
|
37
|
+
height:var(--size-segmented-control-segment-xs, 20px);
|
|
38
|
+
}
|
|
39
|
+
.segment[data-size=xs][data-layout=icon-before]{
|
|
40
|
+
border-radius:var(--radius-segmented-control-segment-s, 10px);
|
|
41
|
+
padding-left:var(--space-segmented-control-segment-s-from-icon, 8px);
|
|
42
|
+
padding-right:var(--space-segmented-control-segment-s-from-label, 16px);
|
|
43
|
+
gap:var(--space-segmented-control-segment-s-gap, 4px);
|
|
44
|
+
height:var(--size-segmented-control-segment-s, 28px);
|
|
45
|
+
}
|
|
46
|
+
.segment[data-size=xs][data-layout=icon-only]{
|
|
47
|
+
border-radius:var(--radius-segmented-control-segment-s, 10px);
|
|
48
|
+
padding-left:var(--space-segmented-control-segment-s-icon-only, 2px);
|
|
49
|
+
padding-right:var(--space-segmented-control-segment-s-icon-only, 2px);
|
|
50
|
+
gap:var(--space-segmented-control-segment-s-gap, 4px);
|
|
51
|
+
height:var(--size-segmented-control-segment-s, 28px);
|
|
52
|
+
}
|
|
32
53
|
.segment[data-size=s][data-layout=label-only]{
|
|
33
54
|
border-radius:var(--radius-segmented-control-segment-s, 10px);
|
|
34
55
|
padding-left:var(--space-segmented-control-segment-s-from-label, 16px);
|
|
@@ -99,6 +120,14 @@
|
|
|
99
120
|
align-items:center;
|
|
100
121
|
}
|
|
101
122
|
|
|
123
|
+
.label[data-size=xs]{
|
|
124
|
+
font-family:var(--sans-label-m-font-family, SB Sans Interface);
|
|
125
|
+
font-weight:var(--sans-label-m-font-weight, Semibold);
|
|
126
|
+
line-height:var(--sans-label-m-line-height, 16px);
|
|
127
|
+
font-size:var(--sans-label-m-font-size, 12px);
|
|
128
|
+
letter-spacing:var(--sans-label-m-letter-spacing, 0px);
|
|
129
|
+
paragraph-spacing:var(--sans-label-m-paragraph-spacing, 6.6px);
|
|
130
|
+
}
|
|
102
131
|
.label[data-size=s]{
|
|
103
132
|
font-family:var(--sans-label-m-font-family, SB Sans Interface);
|
|
104
133
|
font-weight:var(--sans-label-m-font-weight, Semibold);
|
package/dist/esm/utils.d.ts
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
1
|
import { ReactNode } from 'react';
|
|
2
|
-
export declare const getLayout: (icon?: ReactNode, label?: string) => "
|
|
2
|
+
export declare const getLayout: (icon?: ReactNode, label?: string, size?: string) => "label-only" | "icon-before" | "icon-only";
|
package/dist/esm/utils.js
CHANGED
package/package.json
CHANGED
|
@@ -4,7 +4,7 @@
|
|
|
4
4
|
"access": "public"
|
|
5
5
|
},
|
|
6
6
|
"title": "Segmented Control",
|
|
7
|
-
"version": "0.
|
|
7
|
+
"version": "0.6.0",
|
|
8
8
|
"sideEffects": [
|
|
9
9
|
"*.css",
|
|
10
10
|
"*.woff",
|
|
@@ -41,5 +41,5 @@
|
|
|
41
41
|
"classnames": "2.5.1",
|
|
42
42
|
"uncontrollable": "8.0.4"
|
|
43
43
|
},
|
|
44
|
-
"gitHead": "
|
|
44
|
+
"gitHead": "c7d15bfb4027c8177ba19f9b55be31d6f7cfcdbb"
|
|
45
45
|
}
|
|
@@ -43,6 +43,10 @@ export type SegmentedControlProps<Value extends IdType = IdType> = WithSupportPr
|
|
|
43
43
|
* Управление шириной компонента.
|
|
44
44
|
*/
|
|
45
45
|
width?: Width;
|
|
46
|
+
/**
|
|
47
|
+
* Имя поля
|
|
48
|
+
*/
|
|
49
|
+
name?: string;
|
|
46
50
|
}>;
|
|
47
51
|
|
|
48
52
|
/**
|
|
@@ -57,6 +61,7 @@ export function SegmentedControl<Value extends IdType>({
|
|
|
57
61
|
value,
|
|
58
62
|
outline,
|
|
59
63
|
width = WIDTH.Auto,
|
|
64
|
+
name,
|
|
60
65
|
...other
|
|
61
66
|
}: SegmentedControlProps<Value>) {
|
|
62
67
|
const [selected, setSelected] = useUncontrolledProp(value, defaultValue, onChange);
|
|
@@ -129,6 +134,7 @@ export function SegmentedControl<Value extends IdType>({
|
|
|
129
134
|
{...extractDataTestProps(other)}
|
|
130
135
|
{...extractSupportProps(other)}
|
|
131
136
|
>
|
|
137
|
+
{name && <input type='hidden' value={selected} name={name} />}
|
|
132
138
|
<div data-size={size} style={selectionPosition} className={styles.selection} aria-hidden={true} />
|
|
133
139
|
{itemsJSX}
|
|
134
140
|
</div>
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
@use '@snack-uikit/figma-tokens/build/scss/components/styles-tokens-segmentedControl';
|
|
2
2
|
|
|
3
|
-
$sizes: 's', 'm', 'l';
|
|
3
|
+
$sizes: 'xs', 's', 'm', 'l';
|
|
4
4
|
|
|
5
5
|
.container {
|
|
6
6
|
@include styles-tokens-segmentedControl.composite-var(styles-tokens-segmentedControl.$segmented-control-container);
|
|
@@ -40,7 +40,11 @@ $sizes: 's', 'm', 'l';
|
|
|
40
40
|
|
|
41
41
|
@each $size in $sizes {
|
|
42
42
|
&[data-size='#{$size}']::before {
|
|
43
|
-
@include styles-tokens-segmentedControl.composite-var(
|
|
43
|
+
@include styles-tokens-segmentedControl.composite-var(
|
|
44
|
+
styles-tokens-segmentedControl.$segmented-control,
|
|
45
|
+
'background',
|
|
46
|
+
$size
|
|
47
|
+
);
|
|
44
48
|
}
|
|
45
49
|
}
|
|
46
50
|
}
|
|
@@ -67,11 +71,18 @@ $sizes: 's', 'm', 'l';
|
|
|
67
71
|
|
|
68
72
|
background-color: styles-tokens-segmentedControl.$sys-neutral-background2-level;
|
|
69
73
|
|
|
70
|
-
transition:
|
|
74
|
+
transition:
|
|
75
|
+
left 0.15s ease-in-out,
|
|
76
|
+
width 0.15s ease-in-out;
|
|
71
77
|
|
|
72
78
|
@each $size in $sizes {
|
|
73
79
|
&[data-size='#{$size}'] {
|
|
74
|
-
@include styles-tokens-segmentedControl.composite-var(
|
|
80
|
+
@include styles-tokens-segmentedControl.composite-var(
|
|
81
|
+
styles-tokens-segmentedControl.$segmented-control,
|
|
82
|
+
'segment',
|
|
83
|
+
$size,
|
|
84
|
+
'icon-only'
|
|
85
|
+
);
|
|
75
86
|
}
|
|
76
87
|
}
|
|
77
|
-
}
|
|
88
|
+
}
|
package/src/constants.ts
CHANGED
|
@@ -49,7 +49,7 @@ export function Segment({
|
|
|
49
49
|
data-test-id={`section-${value}`}
|
|
50
50
|
data-active={selected || undefined}
|
|
51
51
|
data-disabled={disabled || undefined}
|
|
52
|
-
data-layout={getLayout(icon, label)}
|
|
52
|
+
data-layout={getLayout(icon, label, size)}
|
|
53
53
|
className={cn(styles.segment)}
|
|
54
54
|
onClick={onClick}
|
|
55
55
|
data-size={size}
|
|
@@ -59,7 +59,7 @@ export function Segment({
|
|
|
59
59
|
role='radio'
|
|
60
60
|
type='button'
|
|
61
61
|
>
|
|
62
|
-
{icon && <div className={styles.icon}>{icon}</div>}
|
|
62
|
+
{size !== 'xs' && icon && <div className={styles.icon}>{icon}</div>}
|
|
63
63
|
{label && <TruncateString className={styles.label} data-size={size} text={label} />}
|
|
64
64
|
</button>
|
|
65
65
|
);
|
|
@@ -1,9 +1,10 @@
|
|
|
1
1
|
@use '@snack-uikit/figma-tokens/build/scss/components/styles-tokens-segmentedControl';
|
|
2
|
-
@use
|
|
2
|
+
@use '@snack-uikit/figma-tokens/build/scss/components/styles-tokens-element';
|
|
3
3
|
|
|
4
|
-
$sizes: 's', 'm', 'l';
|
|
4
|
+
$sizes: 'xs', 's', 'm', 'l';
|
|
5
5
|
$layouts: 'label-only', 'icon-before', 'icon-only';
|
|
6
6
|
$typographies: (
|
|
7
|
+
'xs': styles-tokens-segmentedControl.$sans-label-m,
|
|
7
8
|
's': styles-tokens-segmentedControl.$sans-label-m,
|
|
8
9
|
'm': styles-tokens-segmentedControl.$sans-label-m,
|
|
9
10
|
'l': styles-tokens-segmentedControl.$sans-label-l,
|
|
@@ -29,7 +30,8 @@ $typographies: (
|
|
|
29
30
|
color: styles-tokens-segmentedControl.$sys-neutral-text-main;
|
|
30
31
|
}
|
|
31
32
|
|
|
32
|
-
&[data-disabled],
|
|
33
|
+
&[data-disabled],
|
|
34
|
+
&[data-disabled]:hover {
|
|
33
35
|
cursor: not-allowed;
|
|
34
36
|
color: styles-tokens-segmentedControl.$sys-neutral-text-disabled;
|
|
35
37
|
}
|
|
@@ -37,7 +39,8 @@ $typographies: (
|
|
|
37
39
|
&[data-active] {
|
|
38
40
|
color: styles-tokens-segmentedControl.$sys-neutral-text-main;
|
|
39
41
|
|
|
40
|
-
&[data-disabled],
|
|
42
|
+
&[data-disabled],
|
|
43
|
+
&[data-disabled]:hover {
|
|
41
44
|
color: styles-tokens-segmentedControl.$sys-neutral-text-disabled;
|
|
42
45
|
}
|
|
43
46
|
}
|
|
@@ -45,14 +48,21 @@ $typographies: (
|
|
|
45
48
|
&:focus-visible {
|
|
46
49
|
@include styles-tokens-segmentedControl.outline-inside-var(styles-tokens-element.$container-focused-s);
|
|
47
50
|
|
|
48
|
-
outline-color: styles-tokens-segmentedControl.simple-var(
|
|
51
|
+
outline-color: styles-tokens-segmentedControl.simple-var(
|
|
52
|
+
styles-tokens-segmentedControl.$sys-available-complementary
|
|
53
|
+
);
|
|
49
54
|
}
|
|
50
55
|
|
|
51
56
|
@each $size in $sizes {
|
|
52
57
|
&[data-size='#{$size}'] {
|
|
53
58
|
@each $layout in $layouts {
|
|
54
59
|
&[data-layout='#{$layout}'] {
|
|
55
|
-
@include styles-tokens-segmentedControl.composite-var(
|
|
60
|
+
@include styles-tokens-segmentedControl.composite-var(
|
|
61
|
+
styles-tokens-segmentedControl.$segmented-control,
|
|
62
|
+
'segment',
|
|
63
|
+
$size,
|
|
64
|
+
$layout
|
|
65
|
+
);
|
|
56
66
|
}
|
|
57
67
|
}
|
|
58
68
|
}
|
package/src/utils.ts
CHANGED
|
@@ -1,6 +1,10 @@
|
|
|
1
1
|
import { ReactNode } from 'react';
|
|
2
2
|
|
|
3
|
-
export const getLayout = (icon?: ReactNode, label?: string) => {
|
|
3
|
+
export const getLayout = (icon?: ReactNode, label?: string, size?: string) => {
|
|
4
|
+
if (size === 'xs') {
|
|
5
|
+
return 'label-only';
|
|
6
|
+
}
|
|
7
|
+
|
|
4
8
|
if (icon && label) {
|
|
5
9
|
return 'icon-before';
|
|
6
10
|
}
|