@uniai-fe/uds-primitives 0.4.7 → 0.4.8

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.
@@ -0,0 +1,244 @@
1
+ .badge {
2
+ --badge-height: var(--theme-badge-height-xsmall);
3
+ --badge-padding-inline: var(--theme-badge-padding-inline-xsmall);
4
+ --badge-radius: var(--theme-badge-radius-xsmall);
5
+ --badge-font-size: var(--theme-badge-font-size-xsmall);
6
+ --badge-font-weight: var(--theme-badge-font-weight-xsmall);
7
+ --badge-line-height: var(--theme-badge-line-height-xsmall);
8
+ --badge-letter-spacing: var(--theme-badge-letter-spacing-xsmall);
9
+ --badge-dot-size: var(--theme-badge-dot-size);
10
+ display: flex;
11
+ align-items: center;
12
+ justify-content: center;
13
+ gap: var(--theme-badge-gap);
14
+ width: fit-content;
15
+ height: var(--badge-height);
16
+ margin: 0;
17
+ padding-inline: var(--badge-padding-inline);
18
+ padding-block: 0;
19
+ border: 0;
20
+ box-sizing: border-box;
21
+ border-radius: var(--badge-radius);
22
+ white-space: nowrap;
23
+ font-family: var(--theme-badge-font-family);
24
+ font-size: var(--badge-font-size);
25
+ font-weight: var(--badge-font-weight);
26
+ line-height: var(--badge-line-height);
27
+ letter-spacing: var(--badge-letter-spacing);
28
+ }
29
+
30
+ .badge:where([data-size="small"]) {
31
+ --badge-height: var(--theme-badge-height-small);
32
+ --badge-padding-inline: var(--theme-badge-padding-inline-small);
33
+ --badge-radius: var(--theme-badge-radius-small);
34
+ --badge-font-size: var(--theme-badge-font-size-small);
35
+ --badge-font-weight: var(--theme-badge-font-weight-small);
36
+ --badge-line-height: var(--theme-badge-line-height-small);
37
+ --badge-letter-spacing: var(--theme-badge-letter-spacing-small);
38
+ }
39
+
40
+ .badge:where([data-size="medium"]) {
41
+ --badge-height: var(--theme-badge-height-medium);
42
+ --badge-padding-inline: var(--theme-badge-padding-inline-medium);
43
+ --badge-radius: var(--theme-badge-radius-medium);
44
+ --badge-font-size: var(--theme-badge-font-size-medium);
45
+ --badge-font-weight: var(--theme-badge-font-weight-medium);
46
+ --badge-line-height: var(--theme-badge-line-height-medium);
47
+ --badge-letter-spacing: var(--theme-badge-letter-spacing-medium);
48
+ }
49
+
50
+ /* 변경: 새 color props를 기본 계약으로 삼고, semantic preset은 style별 selector에서 보정한다. */
51
+ .badge:where([data-style="fill"]) {
52
+ background-color: var(
53
+ --badge-background-color,
54
+ var(--theme-badge-fill-background-default)
55
+ );
56
+ color: var(--badge-text-color, var(--theme-badge-fill-text-default));
57
+ border-color: transparent;
58
+ }
59
+
60
+ .badge:where([data-style="outlined"]) {
61
+ background-color: var(
62
+ --badge-background-color,
63
+ var(--theme-badge-outlined-background-default)
64
+ );
65
+ color: var(--badge-text-color, var(--theme-badge-outlined-text-default));
66
+ border-width: 1px;
67
+ border-style: solid;
68
+ border-color: var(
69
+ --badge-border-color,
70
+ var(--theme-badge-outlined-border-default)
71
+ );
72
+ }
73
+
74
+ .badge:where([data-style="count"]) {
75
+ background-color: var(
76
+ --badge-background-color,
77
+ var(--theme-badge-count-background-default)
78
+ );
79
+ color: var(--badge-text-color, var(--theme-badge-count-text-default));
80
+ border-color: transparent;
81
+ border-radius: calc(var(--badge-height) / 2);
82
+ }
83
+
84
+ .badge:where([data-style="count"][data-size="xsmall"]) {
85
+ border-radius: var(--theme-badge-count-radius-xsmall);
86
+ }
87
+
88
+ .badge:where([data-style="dot"]) {
89
+ width: var(--badge-dot-size);
90
+ min-width: 0;
91
+ height: var(--badge-dot-size);
92
+ padding: 0;
93
+ border-width: 0;
94
+ border-radius: var(--badge-dot-size);
95
+ background-color: transparent;
96
+ }
97
+
98
+ .badge:where([data-style="dot"]) .badge-dot {
99
+ width: var(--badge-dot-size);
100
+ height: var(--badge-dot-size);
101
+ flex-shrink: 0;
102
+ border-radius: 999px;
103
+ background-color: var(
104
+ --badge-background-color,
105
+ var(--theme-badge-dot-background-default)
106
+ );
107
+ }
108
+
109
+ .badge :where(.badge-label) {
110
+ display: flex;
111
+ align-items: center;
112
+ color: inherit;
113
+ line-height: inherit;
114
+ }
115
+
116
+ .badge:where([data-style="dot"]) .badge-label {
117
+ width: 0;
118
+ height: 0;
119
+ overflow: hidden;
120
+ font-size: 0;
121
+ line-height: 0;
122
+ }
123
+
124
+ .badge:where([data-style="fill"][data-preset="primary"]) {
125
+ --badge-background-color: var(--color-primary-default);
126
+ --badge-text-color: var(--color-common-100);
127
+ }
128
+
129
+ .badge:where([data-style="fill"][data-preset="secondary"]) {
130
+ --badge-background-color: var(--color-secondary-default);
131
+ --badge-text-color: var(--color-primary-default);
132
+ }
133
+
134
+ .badge:where([data-style="fill"][data-preset="tertiary"]) {
135
+ --badge-background-color: var(--color-cool-gray-10);
136
+ --badge-text-color: var(--color-common-100);
137
+ }
138
+
139
+ .badge:where([data-style="fill"][data-preset="gray"]) {
140
+ --badge-background-color: var(--color-surface-neutral);
141
+ --badge-text-color: var(--color-label-neutral);
142
+ }
143
+
144
+ .badge:where([data-style="fill"][data-preset="green"]) {
145
+ --badge-background-color: var(--color-green-95);
146
+ --badge-text-color: var(--color-green-45);
147
+ }
148
+
149
+ .badge:where([data-style="fill"][data-preset="yellow"]) {
150
+ --badge-background-color: var(--color-yellow-95);
151
+ --badge-text-color: var(--color-yellow-45);
152
+ }
153
+
154
+ .badge:where([data-style="fill"][data-preset="orange"]) {
155
+ --badge-background-color: var(--color-orange-95);
156
+ --badge-text-color: var(--color-orange-55);
157
+ }
158
+
159
+ .badge:where([data-style="fill"][data-preset="red"]) {
160
+ --badge-background-color: var(--color-red-95);
161
+ --badge-text-color: var(--color-red-55);
162
+ }
163
+
164
+ .badge:where([data-style="outlined"][data-preset="primary"]) {
165
+ --badge-border-color: var(--color-primary-default);
166
+ --badge-text-color: var(--color-primary-default);
167
+ }
168
+
169
+ .badge:where([data-style="outlined"][data-preset="secondary"]) {
170
+ --badge-border-color: var(--color-border-standard-blue);
171
+ --badge-text-color: var(--color-primary-strong);
172
+ }
173
+
174
+ .badge:where([data-style="outlined"][data-preset="tertiary"]) {
175
+ --badge-border-color: var(--color-border-heavy);
176
+ --badge-text-color: var(--color-label-strong);
177
+ }
178
+
179
+ .badge:where([data-style="outlined"][data-preset="gray"]) {
180
+ --badge-border-color: var(--color-border-assistive);
181
+ --badge-text-color: var(--color-label-standard);
182
+ }
183
+
184
+ .badge:where([data-style="outlined"][data-preset="green"]) {
185
+ --badge-border-color: var(--color-green-45);
186
+ --badge-text-color: var(--color-green-45);
187
+ }
188
+
189
+ .badge:where([data-style="outlined"][data-preset="yellow"]) {
190
+ --badge-border-color: var(--color-yellow-60);
191
+ --badge-text-color: var(--color-yellow-45);
192
+ }
193
+
194
+ .badge:where([data-style="outlined"][data-preset="orange"]) {
195
+ --badge-border-color: var(--color-orange-70);
196
+ --badge-text-color: var(--color-orange-55);
197
+ }
198
+
199
+ .badge:where([data-style="outlined"][data-preset="red"]) {
200
+ --badge-border-color: var(--color-red-70);
201
+ --badge-text-color: var(--color-red-55);
202
+ }
203
+
204
+ .badge:where([data-style="count"][data-preset="primary"]) {
205
+ --badge-background-color: var(--color-primary-default);
206
+ --badge-text-color: var(--color-common-100);
207
+ }
208
+
209
+ .badge:where([data-style="count"][data-preset="gray"]) {
210
+ --badge-background-color: var(--color-cool-gray-90);
211
+ --badge-text-color: var(--color-label-standard);
212
+ }
213
+
214
+ .badge:where([data-style="dot"][data-preset="primary"]) {
215
+ --badge-background-color: var(--color-primary-default);
216
+ }
217
+
218
+ .badge:where([data-style="dot"][data-preset="secondary"]) {
219
+ --badge-background-color: var(--color-secondary-default);
220
+ }
221
+
222
+ .badge:where([data-style="dot"][data-preset="tertiary"]) {
223
+ --badge-background-color: var(--color-cool-gray-10);
224
+ }
225
+
226
+ .badge:where([data-style="dot"][data-preset="gray"]) {
227
+ --badge-background-color: var(--color-cool-gray-90);
228
+ }
229
+
230
+ .badge:where([data-style="dot"][data-preset="green"]) {
231
+ --badge-background-color: var(--color-green-45);
232
+ }
233
+
234
+ .badge:where([data-style="dot"][data-preset="yellow"]) {
235
+ --badge-background-color: var(--color-yellow-45);
236
+ }
237
+
238
+ .badge:where([data-style="dot"][data-preset="orange"]) {
239
+ --badge-background-color: var(--color-orange-55);
240
+ }
241
+
242
+ .badge:where([data-style="dot"][data-preset="red"]) {
243
+ --badge-background-color: var(--color-red-55);
244
+ }
@@ -1,187 +1,2 @@
1
- :root {
2
- --theme-badge-height-xsmall: var(--theme-size-small-1, 20px);
3
- --theme-badge-height-small: var(--theme-size-small-2, 24px);
4
- --theme-badge-padding-inline-xsmall: var(--spacing-padding-3, 6px);
5
- --theme-badge-padding-inline-small: var(--spacing-padding-4, 8px);
6
- --theme-badge-radius: var(--theme-radius-medium-1, 6px);
7
- --theme-badge-font-family: var(--font-caption-medium-family, inherit);
8
- --theme-badge-font-size: var(--font-caption-medium-size, 11px);
9
- // 변경: Badge label font-weight는 디자인 규칙에 맞춰 400으로 고정한다.
10
- --theme-badge-font-weight: 400;
11
- --theme-badge-line-height: var(--font-caption-medium-line-height, 1.5);
12
- --theme-badge-letter-spacing: var(--font-caption-medium-letter-spacing, 0);
13
- --theme-badge-dot-size: var(--spacing-gap-3, 8px);
14
- }
15
-
16
- .badge {
17
- --badge-height: var(--theme-badge-height-xsmall);
18
- --badge-padding-inline: var(--theme-badge-padding-inline-xsmall);
19
- --badge-gap: var(--spacing-gap-1, 4px);
20
- --badge-fill-bg-color: var(--color-primary-default, #1a6aff);
21
- --badge-fill-label-color: var(--color-common-100, #ffffff);
22
- --badge-outline-border-color: var(--color-primary-default, #1a6aff);
23
- --badge-outline-label-color: var(--color-primary-default, #1a6aff);
24
- --badge-dot-color: var(--color-primary-default, #1a6aff);
25
- --badge-dot-size: var(--theme-badge-dot-size);
26
- display: flex;
27
- align-items: center;
28
- justify-content: center;
29
- gap: var(--badge-gap);
30
- height: var(--badge-height);
31
- padding-inline: var(--badge-padding-inline);
32
- padding-block: 0;
33
- border-radius: var(--theme-badge-radius);
34
- border: 0;
35
- font-family: var(--theme-badge-font-family);
36
- font-size: var(--theme-badge-font-size);
37
- font-weight: var(--theme-badge-font-weight);
38
- line-height: 1;
39
- letter-spacing: var(--theme-badge-letter-spacing);
40
- white-space: nowrap;
41
- box-sizing: border-box;
42
- margin: 0;
43
- width: fit-content;
44
- }
45
-
46
- .badge:where([data-size="small"]) {
47
- --badge-height: var(--theme-badge-height-small);
48
- --badge-padding-inline: var(--theme-badge-padding-inline-small);
49
- }
50
-
51
- .badge:where([data-style="fill"]) {
52
- background-color: var(--badge-fill-bg-color);
53
- color: var(--badge-fill-label-color);
54
- border-color: transparent;
55
- }
56
-
57
- .badge:where([data-style="outlined"]) {
58
- background-color: var(--color-surface-static-white, #ffffff);
59
- border-width: 1px;
60
- border-style: solid;
61
- border-color: var(--badge-outline-border-color);
62
- color: var(--badge-outline-label-color);
63
- }
64
-
65
- .badge:where([data-style="dot"]) {
66
- padding: 0;
67
- border-width: 0;
68
- width: var(--badge-dot-size);
69
- height: var(--badge-dot-size);
70
- min-width: 0;
71
- border-radius: var(--badge-dot-size);
72
- background-color: transparent;
73
- }
74
-
75
- .badge-dot {
76
- width: var(--badge-dot-size);
77
- height: var(--badge-dot-size);
78
- border-radius: 999px;
79
- background-color: var(--badge-dot-color);
80
- flex-shrink: 0;
81
- }
82
-
83
- .badge-label {
84
- display: inline-flex;
85
- align-items: center;
86
- color: inherit;
87
- line-height: 1;
88
- }
89
-
90
- .badge:where([data-style="dot"]) .badge-label {
91
- font-size: 0;
92
- line-height: 0;
93
- height: 0;
94
- width: 0;
95
- overflow: hidden;
96
- }
97
-
98
- /* fill intent 별 배경/라벨 컬러 정의 */
99
- .badge:where([data-style="fill"][data-intent="primary"]) {
100
- --badge-fill-bg-color: var(--color-primary-default, #1a6aff);
101
- --badge-fill-label-color: var(--color-common-100, #ffffff);
102
- }
103
-
104
- .badge:where([data-style="fill"][data-intent="secondary"]) {
105
- --badge-fill-bg-color: var(--color-secondary-default, #e5eeff);
106
- --badge-fill-label-color: var(--color-primary-default, #1a6aff);
107
- }
108
-
109
- .badge:where([data-style="fill"][data-intent="tertiary"]) {
110
- --badge-fill-bg-color: var(--color-cool-gray-10, #18191b);
111
- --badge-fill-label-color: var(--color-common-100, #ffffff);
112
- }
113
-
114
- .badge:where([data-style="fill"][data-intent="gray"]) {
115
- --badge-fill-bg-color: var(--color-surface-neutral, #f2f2f2);
116
- --badge-fill-label-color: var(--color-label-neutral, #797e86);
117
- }
118
-
119
- .badge:where([data-style="fill"][data-intent="green"]) {
120
- --badge-fill-bg-color: var(--color-green-95, #e9fcef);
121
- --badge-fill-label-color: var(--color-green-45, #1dc956);
122
- }
123
-
124
- .badge:where([data-style="fill"][data-intent="yellow"]) {
125
- --badge-fill-bg-color: var(--color-yellow-95, #fefae7);
126
- --badge-fill-label-color: var(--color-yellow-45, #dab80b);
127
- }
128
-
129
- .badge:where([data-style="fill"][data-intent="orange"]) {
130
- --badge-fill-bg-color: var(--color-orange-95, #ffeee5);
131
- --badge-fill-label-color: var(--color-orange-55, #ff661a);
132
- }
133
-
134
- .badge:where([data-style="fill"][data-intent="red"]) {
135
- --badge-fill-bg-color: var(--color-red-95, #fde8e7);
136
- --badge-fill-label-color: var(--color-red-55, #f43625);
137
- }
138
-
139
- /* outlined intent 별 border/label 컬러 정의 */
140
- .badge:where([data-style="outlined"][data-intent="primary"]) {
141
- --badge-outline-border-color: var(--color-primary-default, #1a6aff);
142
- --badge-outline-label-color: var(--color-primary-default, #1a6aff);
143
- }
144
-
145
- .badge:where([data-style="outlined"][data-intent="secondary"]) {
146
- --badge-outline-border-color: var(--color-border-standard-blue, #ccdeff);
147
- --badge-outline-label-color: var(--color-primary-strong, #0050e5);
148
- }
149
-
150
- .badge:where([data-style="outlined"][data-intent="tertiary"]) {
151
- --badge-outline-border-color: var(--color-border-heavy, #313235);
152
- --badge-outline-label-color: var(--color-label-strong, #18191b);
153
- }
154
-
155
- .badge:where([data-style="outlined"][data-intent="gray"]) {
156
- --badge-outline-border-color: var(--color-border-assistive, #e4e5e7);
157
- --badge-outline-label-color: var(--color-label-standard, #3d3f43);
158
- }
159
-
160
- .badge:where([data-style="outlined"][data-intent="green"]) {
161
- --badge-outline-border-color: var(--color-green-45, #1dc956);
162
- --badge-outline-label-color: var(--color-green-45, #1dc956);
163
- }
164
-
165
- .badge:where([data-style="outlined"][data-intent="yellow"]) {
166
- --badge-outline-border-color: var(--color-yellow-60, #f5d63d);
167
- --badge-outline-label-color: var(--color-yellow-45, #dab80b);
168
- }
169
-
170
- .badge:where([data-style="outlined"][data-intent="orange"]) {
171
- --badge-outline-border-color: var(--color-orange-70, #ff9966);
172
- --badge-outline-label-color: var(--color-orange-55, #ff661a);
173
- }
174
-
175
- .badge:where([data-style="outlined"][data-intent="red"]) {
176
- --badge-outline-border-color: var(--color-red-70, #f7796e);
177
- --badge-outline-label-color: var(--color-red-55, #f43625);
178
- }
179
-
180
- /* dot tone 별 포인트 컬러 */
181
- .badge:where([data-style="dot"][data-tone="primary"]) {
182
- --badge-dot-color: var(--color-primary-default, #1a6aff);
183
- }
184
-
185
- .badge:where([data-style="dot"][data-tone="feedback"]) {
186
- --badge-dot-color: var(--color-red-55, #f43625);
187
- }
1
+ @use "./variables.scss";
2
+ @use "./badge.scss";
@@ -0,0 +1,41 @@
1
+ /* Badge 기본 토큰 래핑 */
2
+ :root {
3
+ --theme-badge-height-xsmall: var(--theme-size-small-1);
4
+ --theme-badge-height-small: var(--theme-size-small-2);
5
+ /* 변경: Figma 2421:619 기준 medium 배지 높이 32px를 추가한다. */
6
+ --theme-badge-height-medium: var(--theme-size-small-3);
7
+ --theme-badge-padding-inline-xsmall: var(--spacing-padding-3);
8
+ --theme-badge-padding-inline-small: var(--spacing-padding-4);
9
+ --theme-badge-padding-inline-medium: var(--spacing-padding-5);
10
+ --theme-badge-radius-xsmall: var(--theme-radius-medium-1);
11
+ --theme-badge-radius-small: var(--theme-radius-medium-1);
12
+ --theme-badge-radius-medium: var(--theme-radius-medium-3);
13
+ --theme-badge-font-family: var(--font-caption-medium-family);
14
+ --theme-badge-font-size-xsmall: var(--font-caption-medium-size);
15
+ --theme-badge-font-size-small: var(--font-caption-large-size);
16
+ --theme-badge-font-size-medium: var(--font-body-xsmall-size);
17
+ /* 변경: Figma badge size 축은 모두 Regular(400) 기준으로 고정한다. */
18
+ --theme-badge-font-weight-xsmall: 400;
19
+ --theme-badge-font-weight-small: 400;
20
+ --theme-badge-font-weight-medium: 400;
21
+ --theme-badge-line-height-xsmall: var(--font-caption-medium-line-height);
22
+ --theme-badge-line-height-small: var(--font-caption-large-line-height);
23
+ --theme-badge-line-height-medium: var(--font-body-xsmall-line-height);
24
+ --theme-badge-letter-spacing-xsmall: var(
25
+ --font-caption-medium-letter-spacing
26
+ );
27
+ --theme-badge-letter-spacing-small: var(--font-caption-large-letter-spacing);
28
+ --theme-badge-letter-spacing-medium: var(--font-body-xsmall-letter-spacing);
29
+ /* 변경: Count xsmall은 Figma 1620:844 기준으로 radius 10px를 사용한다. */
30
+ --theme-badge-count-radius-xsmall: var(--theme-radius-medium-4);
31
+ --theme-badge-dot-size: var(--spacing-gap-3);
32
+ --theme-badge-gap: var(--spacing-gap-1);
33
+ --theme-badge-fill-background-default: var(--color-primary-default);
34
+ --theme-badge-fill-text-default: var(--color-common-100);
35
+ --theme-badge-outlined-background-default: var(--color-surface-static-white);
36
+ --theme-badge-outlined-border-default: var(--color-primary-default);
37
+ --theme-badge-outlined-text-default: var(--color-primary-default);
38
+ --theme-badge-dot-background-default: var(--color-primary-default);
39
+ --theme-badge-count-background-default: var(--color-primary-default);
40
+ --theme-badge-count-text-default: var(--color-common-100);
41
+ }
@@ -1,79 +1,5 @@
1
- import type { CSSProperties, ComponentPropsWithoutRef, ReactNode } from "react";
2
-
3
- export const BADGE_SIZES = ["xsmall", "small"] as const;
4
- export const BADGE_STYLES = ["fill", "outlined", "dot"] as const;
5
- export const BADGE_INTENTS = [
6
- "primary",
7
- "secondary",
8
- "tertiary",
9
- "gray",
10
- "green",
11
- "yellow",
12
- "orange",
13
- "red",
14
- ] as const;
15
- export const BADGE_TONES = ["primary", "feedback"] as const;
16
-
17
- export type BadgeSize = (typeof BADGE_SIZES)[number];
18
- export type BadgeStyle = (typeof BADGE_STYLES)[number];
19
- export type BadgeIntent = (typeof BADGE_INTENTS)[number];
20
- export type BadgeTone = (typeof BADGE_TONES)[number];
21
-
22
- type NativeFigureProps = Omit<ComponentPropsWithoutRef<"figure">, "style">;
23
-
24
1
  /**
25
- * Badge Props; status/info label badge public props
26
- * @property {ReactNode} [children] 표시할 라벨이다. 생략하면 dot만 렌더링한다.
27
- * @property {"xsmall" | "small"} [size] Figma size 축이다.
28
- * @property {"fill" | "outlined" | "dot"} [style] badge 시각 스타일 축이다.
29
- * @property {"primary" | "secondary" | "tertiary" | "gray" | "green" | "yellow" | "orange" | "red"} [intent] fill/outlined 변형의 색상 의도다.
30
- * @property {"primary" | "feedback"} [tone] dot 변형 전용 tone 축이다.
31
- * @property {CSSProperties} [inlineStyle] 원본 figure 요소에 적용할 inline style이다.
2
+ * Badge Types; barrel export 전용 파일
32
3
  */
33
- export interface BadgeProps extends Omit<NativeFigureProps, "children"> {
34
- /**
35
- * 표시할 라벨. 생략하면 dot 스타일만 렌더링된다.
36
- */
37
- children?: ReactNode;
38
- /**
39
- * Figma size 축 (xsmall/small)
40
- */
41
- size?: BadgeSize;
42
- /**
43
- * style 축 (fill/outlined/dot)
44
- */
45
- style?: BadgeStyle;
46
- /**
47
- * fill/outlined 변형의 intent 축. dot 스타일에는 tone을 사용한다.
48
- */
49
- intent?: BadgeIntent;
50
- /**
51
- * dot 변형 전용 tone 축(primary/feedback).
52
- */
53
- tone?: BadgeTone;
54
- /**
55
- * 원본 figure 요소에 적용할 인라인 스타일.
56
- */
57
- inlineStyle?: CSSProperties;
58
- }
59
-
60
- /**
61
- * Badge ClassName Options; badge root className 조합 입력값
62
- * @property {"xsmall" | "small"} size badge size 축이다.
63
- * @property {"fill" | "outlined" | "dot"} style badge style 축이다.
64
- * @property {string} [className] 외부 className override다.
65
- */
66
- export interface BadgeClassNameOptions {
67
- /**
68
- * badge size 축이다.
69
- */
70
- size: BadgeSize;
71
- /**
72
- * badge style 축이다.
73
- */
74
- style: BadgeStyle;
75
- /**
76
- * 외부 className override다.
77
- */
78
- className?: string;
79
- }
4
+ export type * from "./options";
5
+ export type * from "./props";
@@ -0,0 +1,25 @@
1
+ /**
2
+ * Badge Types; size 옵션
3
+ * @typedef {"xsmall" | "small" | "medium"} BadgeSize
4
+ */
5
+ export type BadgeSize = "xsmall" | "small" | "medium";
6
+
7
+ /**
8
+ * Badge Types; style 옵션
9
+ * @typedef {"fill" | "outlined" | "dot" | "count"} BadgeStyle
10
+ */
11
+ export type BadgeStyle = "fill" | "outlined" | "dot" | "count";
12
+
13
+ /**
14
+ * Badge Types; preset 옵션
15
+ * @typedef {"primary" | "secondary" | "tertiary" | "gray" | "green" | "yellow" | "orange" | "red"} BadgePreset
16
+ */
17
+ export type BadgePreset =
18
+ | "primary"
19
+ | "secondary"
20
+ | "tertiary"
21
+ | "gray"
22
+ | "green"
23
+ | "yellow"
24
+ | "orange"
25
+ | "red";
@@ -0,0 +1,53 @@
1
+ import type { CSSProperties, ComponentPropsWithoutRef, ReactNode } from "react";
2
+ import type { BadgePreset, BadgeSize, BadgeStyle } from "./options";
3
+
4
+ type NativeFigureProps = Omit<ComponentPropsWithoutRef<"figure">, "style">;
5
+
6
+ /**
7
+ * Badge Props; status/info label badge public props
8
+ * @property {ReactNode} [children] 표시할 라벨이다. 생략하면 dot만 렌더링한다.
9
+ * @property {"xsmall" | "small" | "medium"} [size] Figma size 축이다.
10
+ * @property {"fill" | "outlined" | "dot" | "count"} [style] badge 시각 스타일 축이다.
11
+ * @property {"primary" | "secondary" | "tertiary" | "gray" | "green" | "yellow" | "orange" | "red"} [preset] style에 대응하는 semantic 색상 preset이다.
12
+ * @property {string} [textColor] 라벨 텍스트 색상 CSS 값 또는 토큰 참조 문자열이다.
13
+ * @property {string} [backgroundColor] 배경 또는 dot 색상 CSS 값 또는 토큰 참조 문자열이다.
14
+ * @property {string} [borderColor] 외곽선 색상 CSS 값 또는 토큰 참조 문자열이다.
15
+ * @property {CSSProperties} [inlineStyle] 원본 figure 요소에 적용할 inline style이다.
16
+ */
17
+ export interface BadgeProps extends Omit<NativeFigureProps, "children"> {
18
+ /**
19
+ * 표시할 라벨. 생략하면 dot 스타일만 렌더링된다.
20
+ */
21
+ children?: ReactNode;
22
+ /**
23
+ * Figma size 축 (xsmall/small/medium)
24
+ */
25
+ size?: BadgeSize;
26
+ /**
27
+ * style 축 (fill/outlined/dot/count)
28
+ */
29
+ style?: BadgeStyle;
30
+ /**
31
+ * style에 대응하는 semantic 색상 preset이다.
32
+ */
33
+ preset?: BadgePreset;
34
+ /**
35
+ * 라벨 텍스트 색상 CSS 값 또는 토큰 참조 문자열이다.
36
+ * 예: `var(--color-common-100)`
37
+ */
38
+ textColor?: string;
39
+ /**
40
+ * 배경 또는 dot 색상 CSS 값 또는 토큰 참조 문자열이다.
41
+ * 예: `var(--color-primary-default)`
42
+ */
43
+ backgroundColor?: string;
44
+ /**
45
+ * 외곽선 색상 CSS 값 또는 토큰 참조 문자열이다.
46
+ * 예: `var(--color-border-assistive)`
47
+ */
48
+ borderColor?: string;
49
+ /**
50
+ * 원본 figure 요소에 적용할 인라인 스타일.
51
+ */
52
+ inlineStyle?: CSSProperties;
53
+ }
@@ -3,11 +3,10 @@
3
3
  * @desc
4
4
  * - `TabRoot`: tabs value 상태를 관리하는 루트다.
5
5
  * - `TabList`, `TabTrigger`, `TabContent`: tabs anatomy 도구다.
6
- * - `TabContext`, `useTabContext`: tab 스타일 context util이다.
6
+ * - `TabContext`, `useTabContext`: tab 스타일 공유 context util이다.
7
7
  */
8
8
  import "./index.scss";
9
9
 
10
10
  export * from "./markup";
11
- export * from "./hooks";
12
11
  export type * from "./types";
13
12
  export * from "./utils";
@@ -0,0 +1,22 @@
1
+ import clsx from "clsx";
2
+ import { Slot } from "../../slot";
3
+ import type { TabLabelProps } from "../types";
4
+
5
+ /**
6
+ * Tab Label; trigger label className 고정 텍스트 슬롯
7
+ * @component
8
+ * @param {TabLabelProps} props
9
+ * @param {React.ElementType} [props.as] 렌더링할 요소. 기본값은 span.
10
+ * @param {React.ReactNode} [props.children] 라벨 콘텐츠.
11
+ * @param {string} [props.className] 라벨 className.
12
+ */
13
+ const TabLabel = ({ className, ...restProps }: TabLabelProps) => {
14
+ return (
15
+ <Slot.Text
16
+ className={clsx("tab-trigger-label", className)}
17
+ {...restProps}
18
+ />
19
+ );
20
+ };
21
+
22
+ export { TabLabel };