@carrier-dpx/air-react-library 0.7.37 → 0.7.39
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/package.json +4 -1
- package/src/components/Breadcrumbs/Breadcrumbs.tsx +0 -1
- package/src/components/Tabs/Tab.horizontal.figma.tsx +185 -0
- package/src/components/Tabs/Tab.tsx +65 -0
- package/src/components/Tabs/Tab.vertical.figma.tsx +171 -0
- package/src/components/Tabs/TabContext.tsx +15 -0
- package/src/components/Tabs/TabList.tsx +66 -0
- package/src/components/Tabs/TabPanel.tsx +35 -0
- package/src/components/Tabs/TabScrollButton.tsx +23 -0
- package/src/components/Tabs/Tabs.horizontal.figma.tsx +86 -0
- package/src/components/Tabs/Tabs.tsx +160 -0
- package/src/components/Tabs/Tabs.vertical.figma.tsx +88 -0
- package/src/components/Tabs/index.ts +19 -0
- package/src/components/Tabs/styles.ts +9 -0
- package/src/index.ts +9 -0
- package/src/components/Icon/ArrowLeftIcon.figma.tsx +0 -33
- package/src/components/Icon/ArrowRightIcon.figma.tsx +0 -33
- package/src/components/Icon/CheckIcon.figma.tsx +0 -33
- package/src/components/Icon/CloseIcon.figma.tsx +0 -33
- package/src/components/Icon/HomeIcon.figma.tsx +0 -33
- package/src/components/Icon/InfoIcon.figma.tsx +0 -33
- package/src/components/Icon/MenuIcon.figma.tsx +0 -33
- package/src/components/Icon/SearchIcon.figma.tsx +0 -33
- package/src/components/Icon/SettingsIcon.figma.tsx +0 -61
- package/src/components/Icon/UserIcon.figma.tsx +0 -33
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@carrier-dpx/air-react-library",
|
|
3
|
-
"version": "0.7.
|
|
3
|
+
"version": "0.7.39",
|
|
4
4
|
"description": "Air web React component library for Figma Make",
|
|
5
5
|
"main": "src/index.ts",
|
|
6
6
|
"types": "src/index.ts",
|
|
@@ -45,6 +45,7 @@
|
|
|
45
45
|
"@emotion/react": "^11.0.0",
|
|
46
46
|
"@emotion/styled": "^11.0.0",
|
|
47
47
|
"@mui/icons-material": "^5.0.0 || ^7.0.0",
|
|
48
|
+
"@mui/lab": "^5.0.0-alpha",
|
|
48
49
|
"@mui/material": "^5.0.0 || ^7.0.0",
|
|
49
50
|
"react": "^18.0.0",
|
|
50
51
|
"react-dom": "^18.0.0"
|
|
@@ -53,6 +54,8 @@
|
|
|
53
54
|
"@emotion/react": "^11.11.0",
|
|
54
55
|
"@emotion/styled": "^11.11.0",
|
|
55
56
|
"@figma/code-connect": "^1.4.0",
|
|
57
|
+
"@mui/icons-material": "^5.15.0",
|
|
58
|
+
"@mui/lab": "^5.0.0-alpha.177",
|
|
56
59
|
"@mui/material": "^5.15.0",
|
|
57
60
|
"@types/react": "^18.0.0",
|
|
58
61
|
"@types/react-dom": "^18.0.0",
|
|
@@ -0,0 +1,185 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Figma Code Connect Configuration for Tab Component (Horizontal)
|
|
3
|
+
*
|
|
4
|
+
* Figma URL: https://www.figma.com/design/vkoHdM6rchIhH9IWetZeP0/Air--Components?node-id=23369-17683
|
|
5
|
+
*
|
|
6
|
+
* Figma Properties:
|
|
7
|
+
* - selected (true, false)
|
|
8
|
+
* - indicatorWidth (content, full)
|
|
9
|
+
* - invertIndicator (true, false)
|
|
10
|
+
* - disabled (true, false)
|
|
11
|
+
* - state (enabled, hover, focus) - visual state, not a prop
|
|
12
|
+
* - label (true, false) - boolean hide/show
|
|
13
|
+
* - startAdornment (true, false) - boolean hide/show
|
|
14
|
+
* - endAdornment (true, false) - boolean hide/show
|
|
15
|
+
*
|
|
16
|
+
* Note: indicatorWidth and invertIndicator are Tabs-level props, but are included
|
|
17
|
+
* here as they may be visually represented in Figma's Tab component.
|
|
18
|
+
*/
|
|
19
|
+
|
|
20
|
+
import figma from "@figma/code-connect";
|
|
21
|
+
import Tab from "./Tab";
|
|
22
|
+
|
|
23
|
+
figma.connect(
|
|
24
|
+
Tab,
|
|
25
|
+
"https://www.figma.com/design/vkoHdM6rchIhH9IWetZeP0/Air--Components?node-id=23369-17683",
|
|
26
|
+
{
|
|
27
|
+
props: {
|
|
28
|
+
/**
|
|
29
|
+
* SELECTED STATE
|
|
30
|
+
* Maps Figma's "selected" boolean to React's "selected" prop
|
|
31
|
+
*/
|
|
32
|
+
selected: figma.boolean("selected"),
|
|
33
|
+
|
|
34
|
+
/**
|
|
35
|
+
* INDICATOR WIDTH
|
|
36
|
+
* Maps Figma's "indicatorWidth" property
|
|
37
|
+
* Note: This is typically a Tabs-level prop, but may be visually represented in Figma
|
|
38
|
+
*/
|
|
39
|
+
indicatorWidth: figma.enum("indicatorWidth", {
|
|
40
|
+
content: "content",
|
|
41
|
+
full: "full",
|
|
42
|
+
}),
|
|
43
|
+
|
|
44
|
+
/**
|
|
45
|
+
* INVERT INDICATOR
|
|
46
|
+
* Maps Figma's "invertIndicator" boolean
|
|
47
|
+
* Note: This is typically a Tabs-level prop, but may be visually represented in Figma
|
|
48
|
+
*/
|
|
49
|
+
invertIndicator: figma.boolean("invertIndicator"),
|
|
50
|
+
|
|
51
|
+
/**
|
|
52
|
+
* DISABLED STATE
|
|
53
|
+
* Maps Figma's "disabled" boolean to React's "disabled" prop
|
|
54
|
+
*/
|
|
55
|
+
disabled: figma.boolean("disabled"),
|
|
56
|
+
|
|
57
|
+
/**
|
|
58
|
+
* LABEL VISIBILITY
|
|
59
|
+
* Maps Figma's "label" boolean - controls visibility of label text
|
|
60
|
+
*/
|
|
61
|
+
showLabel: figma.boolean("label"),
|
|
62
|
+
|
|
63
|
+
/**
|
|
64
|
+
* LABEL TEXT CONTENT
|
|
65
|
+
* Maps text content from nested "Label" Typography component
|
|
66
|
+
*/
|
|
67
|
+
labelText: figma.nestedProps("Label", {
|
|
68
|
+
children: figma.children("Label"),
|
|
69
|
+
}),
|
|
70
|
+
|
|
71
|
+
/**
|
|
72
|
+
* START ADORNMENT VISIBILITY
|
|
73
|
+
* Maps Figma's "startAdornment" boolean - controls visibility of start icon
|
|
74
|
+
*/
|
|
75
|
+
showStartAdornment: figma.boolean("startAdornment"),
|
|
76
|
+
|
|
77
|
+
/**
|
|
78
|
+
* START ADORNMENT ICON INSTANCE
|
|
79
|
+
* Maps nested Icon component instance when startAdornment is visible
|
|
80
|
+
* Uses figma.instance() to get the Icon component instance
|
|
81
|
+
*/
|
|
82
|
+
startIcon: figma.instance("startAdornment"),
|
|
83
|
+
|
|
84
|
+
/**
|
|
85
|
+
* END ADORNMENT VISIBILITY
|
|
86
|
+
* Maps Figma's "endAdornment" boolean - controls visibility of end icon
|
|
87
|
+
*/
|
|
88
|
+
showEndAdornment: figma.boolean("endAdornment"),
|
|
89
|
+
|
|
90
|
+
/**
|
|
91
|
+
* END ADORNMENT ICON INSTANCE
|
|
92
|
+
* Maps nested Icon component instance when endAdornment is visible
|
|
93
|
+
* Uses figma.instance() to get the Icon component instance
|
|
94
|
+
*/
|
|
95
|
+
endIcon: figma.instance("endAdornment"),
|
|
96
|
+
},
|
|
97
|
+
|
|
98
|
+
/**
|
|
99
|
+
* EXAMPLE CODE TEMPLATE
|
|
100
|
+
* Horizontal Tab - handles label, startAdornment, and endAdornment visibility
|
|
101
|
+
*/
|
|
102
|
+
example: ({ selected, disabled, showLabel, labelText, showStartAdornment, startIcon, showEndAdornment, endIcon }) => {
|
|
103
|
+
// Handle case with label and both adornments
|
|
104
|
+
// Note: MUI Tab only supports one icon, so we prioritize startAdornment
|
|
105
|
+
if (showLabel && labelText && labelText.children && showStartAdornment && startIcon && showEndAdornment && endIcon) {
|
|
106
|
+
return (
|
|
107
|
+
<Tab
|
|
108
|
+
selected={selected}
|
|
109
|
+
disabled={disabled}
|
|
110
|
+
label={labelText.children}
|
|
111
|
+
icon={startIcon}
|
|
112
|
+
iconPosition="start"
|
|
113
|
+
/>
|
|
114
|
+
);
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
// Handle case with label and startAdornment only
|
|
118
|
+
if (showLabel && labelText && labelText.children && showStartAdornment && startIcon) {
|
|
119
|
+
return (
|
|
120
|
+
<Tab
|
|
121
|
+
selected={selected}
|
|
122
|
+
disabled={disabled}
|
|
123
|
+
label={labelText.children}
|
|
124
|
+
icon={startIcon}
|
|
125
|
+
iconPosition="start"
|
|
126
|
+
/>
|
|
127
|
+
);
|
|
128
|
+
}
|
|
129
|
+
|
|
130
|
+
// Handle case with label and endAdornment only
|
|
131
|
+
if (showLabel && labelText && labelText.children && showEndAdornment && endIcon) {
|
|
132
|
+
return (
|
|
133
|
+
<Tab
|
|
134
|
+
selected={selected}
|
|
135
|
+
disabled={disabled}
|
|
136
|
+
label={labelText.children}
|
|
137
|
+
icon={endIcon}
|
|
138
|
+
iconPosition="end"
|
|
139
|
+
/>
|
|
140
|
+
);
|
|
141
|
+
}
|
|
142
|
+
|
|
143
|
+
// Handle case with label only
|
|
144
|
+
if (showLabel && labelText && labelText.children) {
|
|
145
|
+
return (
|
|
146
|
+
<Tab
|
|
147
|
+
selected={selected}
|
|
148
|
+
disabled={disabled}
|
|
149
|
+
label={labelText.children}
|
|
150
|
+
/>
|
|
151
|
+
);
|
|
152
|
+
}
|
|
153
|
+
|
|
154
|
+
// Handle case with startAdornment only (no label)
|
|
155
|
+
if (showStartAdornment && startIcon) {
|
|
156
|
+
return (
|
|
157
|
+
<Tab
|
|
158
|
+
selected={selected}
|
|
159
|
+
disabled={disabled}
|
|
160
|
+
icon={startIcon}
|
|
161
|
+
/>
|
|
162
|
+
);
|
|
163
|
+
}
|
|
164
|
+
|
|
165
|
+
// Handle case with endAdornment only (no label)
|
|
166
|
+
if (showEndAdornment && endIcon) {
|
|
167
|
+
return (
|
|
168
|
+
<Tab
|
|
169
|
+
selected={selected}
|
|
170
|
+
disabled={disabled}
|
|
171
|
+
icon={endIcon}
|
|
172
|
+
/>
|
|
173
|
+
);
|
|
174
|
+
}
|
|
175
|
+
|
|
176
|
+
// Default case - no label, no adornments
|
|
177
|
+
return (
|
|
178
|
+
<Tab
|
|
179
|
+
selected={selected}
|
|
180
|
+
disabled={disabled}
|
|
181
|
+
/>
|
|
182
|
+
);
|
|
183
|
+
},
|
|
184
|
+
}
|
|
185
|
+
);
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
import { forwardRef, Ref } from "react";
|
|
2
|
+
|
|
3
|
+
import MuiTab, { TabProps as MuiTabProps } from "@mui/material/Tab";
|
|
4
|
+
import { TouchRippleActions } from "@mui/material/ButtonBase/TouchRipple";
|
|
5
|
+
import { CSSObject, Theme } from "@mui/material/styles";
|
|
6
|
+
import { getSxStyles } from "../utils/styles";
|
|
7
|
+
|
|
8
|
+
export interface TabProps extends MuiTabProps {
|
|
9
|
+
/**
|
|
10
|
+
*
|
|
11
|
+
* A ref that points to the TouchRipple element.
|
|
12
|
+
*/
|
|
13
|
+
touchRippleRef?: Ref<TouchRippleActions>;
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
/** Tab
|
|
17
|
+
*
|
|
18
|
+
* `import Tab from '@carrier-io/air-react/Tab'`
|
|
19
|
+
*/
|
|
20
|
+
const Tab = forwardRef<HTMLDivElement, TabProps>(({ sx, ...rest }, ref) => {
|
|
21
|
+
return (
|
|
22
|
+
<MuiTab
|
|
23
|
+
sx={(theme: Theme) =>
|
|
24
|
+
({
|
|
25
|
+
...getSxStyles(theme, sx),
|
|
26
|
+
...theme.typography.body2Semibold,
|
|
27
|
+
textTransform: "capitalize",
|
|
28
|
+
// Default/unselected: label and icon use base.state.active
|
|
29
|
+
color: theme.palette.base?.state.active,
|
|
30
|
+
"& .MuiTab-iconWrapper": {
|
|
31
|
+
color: theme.palette.base?.state.active,
|
|
32
|
+
},
|
|
33
|
+
// Hover state: label and icon use base.text.primary
|
|
34
|
+
"&:hover": {
|
|
35
|
+
color: theme.palette.base?.text.primary,
|
|
36
|
+
"& .MuiTab-iconWrapper": {
|
|
37
|
+
color: theme.palette.base?.text.primary,
|
|
38
|
+
},
|
|
39
|
+
},
|
|
40
|
+
// Selected tab: label and icon use base.text.primary
|
|
41
|
+
"&.Mui-selected": {
|
|
42
|
+
color: theme.palette.base?.text.primary,
|
|
43
|
+
"& .MuiTab-iconWrapper": {
|
|
44
|
+
color: theme.palette.base?.text.primary,
|
|
45
|
+
},
|
|
46
|
+
},
|
|
47
|
+
// Disabled tab: label and icon use base.text.disabled
|
|
48
|
+
"&.Mui-disabled": {
|
|
49
|
+
color: theme.palette.base?.text.disabled,
|
|
50
|
+
"& .MuiTab-iconWrapper": {
|
|
51
|
+
color: theme.palette.base?.state.disabledContent,
|
|
52
|
+
},
|
|
53
|
+
},
|
|
54
|
+
} as CSSObject)
|
|
55
|
+
}
|
|
56
|
+
{...rest}
|
|
57
|
+
ref={ref}
|
|
58
|
+
/>
|
|
59
|
+
);
|
|
60
|
+
});
|
|
61
|
+
|
|
62
|
+
Tab.displayName = "Tab";
|
|
63
|
+
|
|
64
|
+
export default Tab;
|
|
65
|
+
export type { TabProps };
|
|
@@ -0,0 +1,171 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Figma Code Connect Configuration for Tab Component (Vertical)
|
|
3
|
+
*
|
|
4
|
+
* Figma URL: https://www.figma.com/design/vkoHdM6rchIhH9IWetZeP0/Air--Components?node-id=23626-42929
|
|
5
|
+
*
|
|
6
|
+
* Figma Properties:
|
|
7
|
+
* - selected (true, false)
|
|
8
|
+
* - invertIndicator (true, false)
|
|
9
|
+
* - disabled (true, false)
|
|
10
|
+
* - state (enabled, hover, focus) - visual state, not a prop
|
|
11
|
+
* - label (true, false) - boolean hide/show
|
|
12
|
+
* - startAdornment (true, false) - boolean hide/show
|
|
13
|
+
* - endAdornment (true, false) - boolean hide/show
|
|
14
|
+
*/
|
|
15
|
+
|
|
16
|
+
import figma from "@figma/code-connect";
|
|
17
|
+
import Tab from "./Tab";
|
|
18
|
+
|
|
19
|
+
figma.connect(
|
|
20
|
+
Tab,
|
|
21
|
+
"https://www.figma.com/design/vkoHdM6rchIhH9IWetZeP0/Air--Components?node-id=23626-42929",
|
|
22
|
+
{
|
|
23
|
+
props: {
|
|
24
|
+
/**
|
|
25
|
+
* SELECTED STATE
|
|
26
|
+
* Maps Figma's "selected" boolean to React's "selected" prop
|
|
27
|
+
*/
|
|
28
|
+
selected: figma.boolean("selected"),
|
|
29
|
+
|
|
30
|
+
/**
|
|
31
|
+
* INVERT INDICATOR
|
|
32
|
+
* Maps Figma's "invertIndicator" boolean
|
|
33
|
+
* Note: This is typically a Tabs-level prop, but may be visually represented in Figma
|
|
34
|
+
*/
|
|
35
|
+
invertIndicator: figma.boolean("invertIndicator"),
|
|
36
|
+
|
|
37
|
+
/**
|
|
38
|
+
* DISABLED STATE
|
|
39
|
+
* Maps Figma's "disabled" boolean to React's "disabled" prop
|
|
40
|
+
*/
|
|
41
|
+
disabled: figma.boolean("disabled"),
|
|
42
|
+
|
|
43
|
+
/**
|
|
44
|
+
* LABEL VISIBILITY
|
|
45
|
+
* Maps Figma's "label" boolean - controls visibility of label text
|
|
46
|
+
*/
|
|
47
|
+
showLabel: figma.boolean("label"),
|
|
48
|
+
|
|
49
|
+
/**
|
|
50
|
+
* LABEL TEXT CONTENT
|
|
51
|
+
* Maps text content from nested "Label" Typography component
|
|
52
|
+
*/
|
|
53
|
+
labelText: figma.nestedProps("Label", {
|
|
54
|
+
children: figma.children("Label"),
|
|
55
|
+
}),
|
|
56
|
+
|
|
57
|
+
/**
|
|
58
|
+
* START ADORNMENT VISIBILITY
|
|
59
|
+
* Maps Figma's "startAdornment" boolean - controls visibility of start icon
|
|
60
|
+
*/
|
|
61
|
+
showStartAdornment: figma.boolean("startAdornment"),
|
|
62
|
+
|
|
63
|
+
/**
|
|
64
|
+
* START ADORNMENT ICON INSTANCE
|
|
65
|
+
* Maps nested Icon component instance when startAdornment is visible
|
|
66
|
+
* Uses figma.instance() to get the Icon component instance
|
|
67
|
+
*/
|
|
68
|
+
startIcon: figma.instance("startAdornment"),
|
|
69
|
+
|
|
70
|
+
/**
|
|
71
|
+
* END ADORNMENT VISIBILITY
|
|
72
|
+
* Maps Figma's "endAdornment" boolean - controls visibility of end icon
|
|
73
|
+
*/
|
|
74
|
+
showEndAdornment: figma.boolean("endAdornment"),
|
|
75
|
+
|
|
76
|
+
/**
|
|
77
|
+
* END ADORNMENT ICON INSTANCE
|
|
78
|
+
* Maps nested Icon component instance when endAdornment is visible
|
|
79
|
+
* Uses figma.instance() to get the Icon component instance
|
|
80
|
+
*/
|
|
81
|
+
endIcon: figma.instance("endAdornment"),
|
|
82
|
+
},
|
|
83
|
+
|
|
84
|
+
/**
|
|
85
|
+
* EXAMPLE CODE TEMPLATE
|
|
86
|
+
* Vertical Tab - handles label, startAdornment, and endAdornment visibility
|
|
87
|
+
*/
|
|
88
|
+
example: ({ selected, disabled, showLabel, labelText, showStartAdornment, startIcon, showEndAdornment, endIcon }) => {
|
|
89
|
+
// Handle case with label and both adornments
|
|
90
|
+
// Note: MUI Tab only supports one icon, so we prioritize startAdornment
|
|
91
|
+
if (showLabel && labelText && labelText.children && showStartAdornment && startIcon && showEndAdornment && endIcon) {
|
|
92
|
+
return (
|
|
93
|
+
<Tab
|
|
94
|
+
selected={selected}
|
|
95
|
+
disabled={disabled}
|
|
96
|
+
label={labelText.children}
|
|
97
|
+
icon={startIcon}
|
|
98
|
+
iconPosition="start"
|
|
99
|
+
/>
|
|
100
|
+
);
|
|
101
|
+
}
|
|
102
|
+
|
|
103
|
+
// Handle case with label and startAdornment only
|
|
104
|
+
if (showLabel && labelText && labelText.children && showStartAdornment && startIcon) {
|
|
105
|
+
return (
|
|
106
|
+
<Tab
|
|
107
|
+
selected={selected}
|
|
108
|
+
disabled={disabled}
|
|
109
|
+
label={labelText.children}
|
|
110
|
+
icon={startIcon}
|
|
111
|
+
iconPosition="start"
|
|
112
|
+
/>
|
|
113
|
+
);
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
// Handle case with label and endAdornment only
|
|
117
|
+
if (showLabel && labelText && labelText.children && showEndAdornment && endIcon) {
|
|
118
|
+
return (
|
|
119
|
+
<Tab
|
|
120
|
+
selected={selected}
|
|
121
|
+
disabled={disabled}
|
|
122
|
+
label={labelText.children}
|
|
123
|
+
icon={endIcon}
|
|
124
|
+
iconPosition="end"
|
|
125
|
+
/>
|
|
126
|
+
);
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
// Handle case with label only
|
|
130
|
+
if (showLabel && labelText && labelText.children) {
|
|
131
|
+
return (
|
|
132
|
+
<Tab
|
|
133
|
+
selected={selected}
|
|
134
|
+
disabled={disabled}
|
|
135
|
+
label={labelText.children}
|
|
136
|
+
/>
|
|
137
|
+
);
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
// Handle case with startAdornment only (no label)
|
|
141
|
+
if (showStartAdornment && startIcon) {
|
|
142
|
+
return (
|
|
143
|
+
<Tab
|
|
144
|
+
selected={selected}
|
|
145
|
+
disabled={disabled}
|
|
146
|
+
icon={startIcon}
|
|
147
|
+
/>
|
|
148
|
+
);
|
|
149
|
+
}
|
|
150
|
+
|
|
151
|
+
// Handle case with endAdornment only (no label)
|
|
152
|
+
if (showEndAdornment && endIcon) {
|
|
153
|
+
return (
|
|
154
|
+
<Tab
|
|
155
|
+
selected={selected}
|
|
156
|
+
disabled={disabled}
|
|
157
|
+
icon={endIcon}
|
|
158
|
+
/>
|
|
159
|
+
);
|
|
160
|
+
}
|
|
161
|
+
|
|
162
|
+
// Default case - no label, no adornments
|
|
163
|
+
return (
|
|
164
|
+
<Tab
|
|
165
|
+
selected={selected}
|
|
166
|
+
disabled={disabled}
|
|
167
|
+
/>
|
|
168
|
+
);
|
|
169
|
+
},
|
|
170
|
+
}
|
|
171
|
+
);
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import MuiTabContext, {
|
|
2
|
+
TabContextProps as MuiTabContextProps,
|
|
3
|
+
} from "@mui/lab/TabContext";
|
|
4
|
+
|
|
5
|
+
export interface TabContextProps extends MuiTabContextProps {}
|
|
6
|
+
|
|
7
|
+
/** TabContext
|
|
8
|
+
*
|
|
9
|
+
* `import { TabContext } from '@carrier-io/air-react'`
|
|
10
|
+
*/
|
|
11
|
+
export default function TabContext(props: TabContextProps) {
|
|
12
|
+
return <MuiTabContext {...props} />;
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
export type { TabContextProps };
|
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
import { forwardRef } from "react";
|
|
2
|
+
|
|
3
|
+
import MuiTabList, { TabListProps as MuiTabListProps } from "@mui/lab/TabList";
|
|
4
|
+
|
|
5
|
+
export interface TabListProps extends MuiTabListProps {
|
|
6
|
+
/**
|
|
7
|
+
*
|
|
8
|
+
* Invert the indicator on the tab. Default set to bottom for "horizontal" orientation and right for "vertical" orientation.
|
|
9
|
+
*/
|
|
10
|
+
invertIndicator?: boolean;
|
|
11
|
+
|
|
12
|
+
/**
|
|
13
|
+
* indicator variant
|
|
14
|
+
* @default "line"
|
|
15
|
+
*/
|
|
16
|
+
indicatorVariant?: "line" | "standard";
|
|
17
|
+
|
|
18
|
+
/**
|
|
19
|
+
* indicator width
|
|
20
|
+
*/
|
|
21
|
+
indicatorWidth?: "content" | "full";
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
/** TabList
|
|
25
|
+
*
|
|
26
|
+
* `import { TabList } from '@carrier-io/air-react'`
|
|
27
|
+
*/
|
|
28
|
+
|
|
29
|
+
const indicatorInvertStyle = {
|
|
30
|
+
right: "unset",
|
|
31
|
+
borderBottomRightRadius: 4,
|
|
32
|
+
borderBottomLeftRadius: 0,
|
|
33
|
+
borderTopLeftRadius: 0,
|
|
34
|
+
borderTopRightRadius: 4,
|
|
35
|
+
};
|
|
36
|
+
|
|
37
|
+
const TabList = forwardRef<HTMLButtonElement, TabListProps>(
|
|
38
|
+
({ invertIndicator, indicatorVariant, indicatorWidth, ...props }, ref) => {
|
|
39
|
+
const rootClassNames = `${
|
|
40
|
+
indicatorWidth === "full"
|
|
41
|
+
? "MuiTab-indicator__full"
|
|
42
|
+
: "MuiTab-indicator__content"
|
|
43
|
+
}`;
|
|
44
|
+
const indicatorClassNames = `${
|
|
45
|
+
indicatorVariant === "line"
|
|
46
|
+
? "MuiTab-indicator__line"
|
|
47
|
+
: "MuiTab-indicator__standard"
|
|
48
|
+
}`;
|
|
49
|
+
return (
|
|
50
|
+
<MuiTabList
|
|
51
|
+
{...props}
|
|
52
|
+
ref={ref}
|
|
53
|
+
TabIndicatorProps={{
|
|
54
|
+
...(invertIndicator ? { style: indicatorInvertStyle } : undefined),
|
|
55
|
+
...props.TabIndicatorProps,
|
|
56
|
+
}}
|
|
57
|
+
className={[rootClassNames, indicatorClassNames].join(" ")}
|
|
58
|
+
/>
|
|
59
|
+
);
|
|
60
|
+
}
|
|
61
|
+
);
|
|
62
|
+
|
|
63
|
+
TabList.displayName = "TabList";
|
|
64
|
+
|
|
65
|
+
export default TabList;
|
|
66
|
+
export type { TabListProps };
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
import { forwardRef } from "react";
|
|
2
|
+
|
|
3
|
+
import MuiTabPanel, {
|
|
4
|
+
TabPanelProps as MuiTabPanelProps,
|
|
5
|
+
} from "@mui/lab/TabPanel";
|
|
6
|
+
import { Theme } from "@mui/material/styles";
|
|
7
|
+
import { getSxStyles } from "../utils/styles";
|
|
8
|
+
|
|
9
|
+
export interface TabPanelProps extends MuiTabPanelProps {}
|
|
10
|
+
|
|
11
|
+
/** TabPanel
|
|
12
|
+
*
|
|
13
|
+
* `import { TabPanel } from '@carrier-io/air-react'`
|
|
14
|
+
*/
|
|
15
|
+
|
|
16
|
+
const TabPanel = forwardRef<unknown, TabPanelProps>(({ sx, ...props }, ref) => {
|
|
17
|
+
return (
|
|
18
|
+
<MuiTabPanel
|
|
19
|
+
sx={
|
|
20
|
+
((theme: Theme) => ({
|
|
21
|
+
...getSxStyles(theme, sx),
|
|
22
|
+
// Apply base.text.primary color to panel content for dark theme support
|
|
23
|
+
color: theme.palette.base?.text.primary || theme.palette.text.primary,
|
|
24
|
+
})) as any
|
|
25
|
+
}
|
|
26
|
+
{...props}
|
|
27
|
+
ref={ref}
|
|
28
|
+
/>
|
|
29
|
+
);
|
|
30
|
+
});
|
|
31
|
+
|
|
32
|
+
TabPanel.displayName = "TabPanel";
|
|
33
|
+
|
|
34
|
+
export default TabPanel;
|
|
35
|
+
export type { TabPanelProps };
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import { forwardRef } from "react";
|
|
2
|
+
|
|
3
|
+
import MuiTabScrollButton, {
|
|
4
|
+
TabScrollButtonProps as MuiTabScrollButtonProps,
|
|
5
|
+
} from "@mui/material/TabScrollButton";
|
|
6
|
+
|
|
7
|
+
export interface TabScrollButtonProps extends MuiTabScrollButtonProps {}
|
|
8
|
+
|
|
9
|
+
/** TabScrollButton
|
|
10
|
+
*
|
|
11
|
+
* `import { TabScrollButton } from '@carrier-io/air-react'`
|
|
12
|
+
*/
|
|
13
|
+
|
|
14
|
+
const TabScrollButton = forwardRef<HTMLDivElement, TabScrollButtonProps>(
|
|
15
|
+
(props, ref) => {
|
|
16
|
+
return <MuiTabScrollButton {...props} ref={ref} />;
|
|
17
|
+
}
|
|
18
|
+
);
|
|
19
|
+
|
|
20
|
+
TabScrollButton.displayName = "TabScrollButton";
|
|
21
|
+
|
|
22
|
+
export default TabScrollButton;
|
|
23
|
+
export type { TabScrollButtonProps };
|
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Figma Code Connect Configuration for Tabs Component (Horizontal)
|
|
3
|
+
*
|
|
4
|
+
* Figma URL: https://www.figma.com/design/vkoHdM6rchIhH9IWetZeP0/Air--Components?node-id=17801-86244
|
|
5
|
+
*
|
|
6
|
+
* Figma Properties:
|
|
7
|
+
* - variant (group-left, group-center, group-right, full-width, scrollable)
|
|
8
|
+
* - disabled (true, false)
|
|
9
|
+
* - divider (true, false)
|
|
10
|
+
*
|
|
11
|
+
* Structure:
|
|
12
|
+
* - Tab 1-8: Multiple Tab instances with numbered layer names
|
|
13
|
+
*/
|
|
14
|
+
|
|
15
|
+
import figma from "@figma/code-connect";
|
|
16
|
+
import Tabs from "./Tabs";
|
|
17
|
+
import Tab from "./Tab";
|
|
18
|
+
|
|
19
|
+
figma.connect(
|
|
20
|
+
Tabs,
|
|
21
|
+
"https://www.figma.com/design/vkoHdM6rchIhH9IWetZeP0/Air--Components?node-id=17801-86244",
|
|
22
|
+
{
|
|
23
|
+
props: {
|
|
24
|
+
/**
|
|
25
|
+
* VARIANT MAPPING
|
|
26
|
+
* Maps Figma's "variant" property to React's "variant" prop
|
|
27
|
+
*/
|
|
28
|
+
variant: figma.enum("variant", {
|
|
29
|
+
"group-left": "group-left",
|
|
30
|
+
"group-center": "group-center",
|
|
31
|
+
"group-right": "group-right",
|
|
32
|
+
"full-width": "full-width",
|
|
33
|
+
scrollable: "scrollable",
|
|
34
|
+
}),
|
|
35
|
+
|
|
36
|
+
/**
|
|
37
|
+
* DISABLED STATE
|
|
38
|
+
* Maps Figma's "disabled" boolean to React's "disabled" prop
|
|
39
|
+
*/
|
|
40
|
+
disabled: figma.boolean("disabled"),
|
|
41
|
+
|
|
42
|
+
/**
|
|
43
|
+
* DIVIDER VISIBILITY
|
|
44
|
+
* Maps Figma's "divider" boolean - controls divider visibility
|
|
45
|
+
*/
|
|
46
|
+
divider: figma.boolean("divider"),
|
|
47
|
+
|
|
48
|
+
/**
|
|
49
|
+
* TAB CHILDREN
|
|
50
|
+
* Maps nested Tab instances from Figma
|
|
51
|
+
* Each "Tab X" is an instance of the Tab component
|
|
52
|
+
*/
|
|
53
|
+
tab1: figma.children("Tab 1"),
|
|
54
|
+
tab2: figma.children("Tab 2"),
|
|
55
|
+
tab3: figma.children("Tab 3"),
|
|
56
|
+
tab4: figma.children("Tab 4"),
|
|
57
|
+
tab5: figma.children("Tab 5"),
|
|
58
|
+
tab6: figma.children("Tab 6"),
|
|
59
|
+
tab7: figma.children("Tab 7"),
|
|
60
|
+
tab8: figma.children("Tab 8"),
|
|
61
|
+
},
|
|
62
|
+
|
|
63
|
+
/**
|
|
64
|
+
* EXAMPLE CODE TEMPLATE
|
|
65
|
+
* Horizontal Tabs - sets orientation="horizontal"
|
|
66
|
+
*/
|
|
67
|
+
example: ({ variant, disabled, tab1, tab2, tab3, tab4, tab5, tab6, tab7, tab8 }) => (
|
|
68
|
+
<Tabs
|
|
69
|
+
orientation="horizontal"
|
|
70
|
+
variant={variant}
|
|
71
|
+
disabled={disabled}
|
|
72
|
+
value={0}
|
|
73
|
+
onChange={() => {}}
|
|
74
|
+
>
|
|
75
|
+
{tab1}
|
|
76
|
+
{tab2}
|
|
77
|
+
{tab3}
|
|
78
|
+
{tab4}
|
|
79
|
+
{tab5}
|
|
80
|
+
{tab6}
|
|
81
|
+
{tab7}
|
|
82
|
+
{tab8}
|
|
83
|
+
</Tabs>
|
|
84
|
+
),
|
|
85
|
+
}
|
|
86
|
+
);
|