@mirohq/design-system-button 3.1.37 → 3.2.0-deprecated-button.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/dist/module.js CHANGED
@@ -1,290 +1,299 @@
1
1
  import { jsx, jsxs, Fragment } from 'react/jsx-runtime';
2
- import React from 'react';
2
+ import React, { useRef } from 'react';
3
+ import { useButton } from '@react-aria/button';
4
+ import { mergeProps } from '@react-aria/utils';
3
5
  import { Spinner } from '@mirohq/design-system-spinner';
4
- import { booleanify, addPropsToChildren } from '@mirohq/design-system-utils';
5
- import { styles, isIconComponent } from '@mirohq/design-system-base-icon';
6
+ import { useLink } from '@react-aria/link';
7
+ import { useFocusRing } from '@react-aria/focus';
6
8
  import { Primitive } from '@mirohq/design-system-primitive';
7
9
  import { styled } from '@mirohq/design-system-stitches';
8
- import { BaseButton, sizes } from '@mirohq/design-system-base-button';
9
- import { focus } from '@mirohq/design-system-styles';
10
10
 
11
- const StyledIconSlot = styled(Primitive.div, {});
12
- const IconSlot = React.forwardRef(({ children, ...restProps }, forwardRef) => /* @__PURE__ */ jsx(StyledIconSlot, { ...restProps, ref: forwardRef, "aria-hidden": true, asChild: true, children }));
13
-
14
- const disabledSelector = '&[disabled], &[aria-disabled="true"]';
15
- const iconSlotSelector = "& ".concat(StyledIconSlot);
16
- const externalIconSelector = "& svg:not([data-icon-component]), & img:not([data-icon-component])";
17
- const solidDisabled = {
18
- [disabledSelector]: {
19
- backgroundColor: "$background-neutrals-disabled",
20
- color: "$text-neutrals-disabled",
21
- [iconSlotSelector]: {
22
- color: "$icon-neutrals-disabled"
23
- }
11
+ const focusFilled = {
12
+ "&[data-focused]": {
13
+ boxShadow: "inset 0 0 0 1px white, 0 0 0 1px rgba(104, 129, 255, 1), 0 0 0 5px rgba(217, 224, 255, 1)"
24
14
  }
25
15
  };
26
- const outlineDisabled = {
27
- [disabledSelector]: {
28
- backgroundColor: "$background-neutrals",
29
- borderColor: "$border-neutrals-disabled",
30
- color: "$text-neutrals-disabled",
31
- [iconSlotSelector]: {
32
- color: "$icon-neutrals-disabled"
33
- }
16
+ const focusOutline = {
17
+ "&[data-focused]": {
18
+ boxShadow: "0 0 0 1px rgba(104, 129, 255, 1), 0 0 0 5px rgba(217, 224, 255, 1)",
19
+ borderColor: "transparent"
34
20
  }
35
21
  };
36
- const ghostDisabled = {
37
- [disabledSelector]: {
38
- color: "$text-neutrals-disabled",
39
- backgroundColor: "$transparent",
40
- [iconSlotSelector]: {
41
- color: "$icon-neutrals-disabled"
42
- }
22
+ const focusDefault = {
23
+ "&[data-focused]": {
24
+ boxShadow: "0 0 0 1px rgba(104, 129, 255, 1), 0 0 0 5px rgba(217, 224, 255, 1)"
43
25
  }
44
26
  };
45
- const LABEL_OFFSET = 2;
46
- const StyledButton = styled(BaseButton, {
27
+ const pressedSelector = "&:active, &[data-pressed]";
28
+ const StyledButton = styled(Primitive.button, {
29
+ boxSizing: "border-box",
30
+ display: "inline-block",
31
+ outline: "none",
47
32
  whiteSpace: "nowrap",
48
33
  textOverflow: "ellipsis",
49
34
  textAlign: "center",
35
+ verticalAlign: "middle",
36
+ userSelect: "none",
37
+ fontFamily: "inherit",
38
+ fontStyle: "normal",
39
+ fontStretch: "normal",
40
+ letterSpacing: "normal",
41
+ fontWeight: "normal",
50
42
  position: "relative",
51
- width: "fit-content",
52
- maxWidth: "100%",
53
- lineHeight: 1.5,
54
- border: "1px solid transparent",
55
- // to make outline and solid/ghost variants the same width
56
- ...focus.css({
57
- boxShadow: "$focus-small-outline",
58
- borderColor: "$blue-400 !important"
59
- }),
60
- ["& ".concat(StyledIconSlot, ":first-child")]: {
61
- marginLeft: -LABEL_OFFSET,
62
- marginRight: "calc($50 + ".concat(LABEL_OFFSET, "px)")
63
- },
64
- ["& ".concat(StyledIconSlot, ":last-child")]: {
65
- marginRight: -LABEL_OFFSET,
66
- marginLeft: "calc($50 + ".concat(LABEL_OFFSET, "px)")
43
+ cursor: "pointer",
44
+ border: "none",
45
+ textDecoration: "none",
46
+ backgroundColor: "transparent",
47
+ "&[disabled]": {
48
+ pointerEvents: "none",
49
+ opacity: 0.4
67
50
  },
68
51
  variants: {
69
52
  variant: {
70
- "solid-prominent": {
71
- backgroundColor: "$background-primary-prominent",
72
- color: "$text-primary-inverted",
73
- [iconSlotSelector]: {
74
- color: "$icon-primary-inverted"
75
- },
76
- "&[data-hovered]": {
77
- backgroundColor: "$background-primary-prominent-hover"
78
- },
79
- "&[data-pressed]": {
80
- backgroundColor: "$background-primary-prominent-active"
81
- },
82
- ...solidDisabled
83
- },
84
- "outline-prominent": {
85
- backgroundColor: "$background-neutrals",
86
- borderColor: "$border-primary",
87
- color: "$text-primary",
88
- [iconSlotSelector]: {
89
- color: "$icon-primary"
90
- },
91
- "&[data-hovered]": {
92
- backgroundColor: "$background-primary-subtle-hover",
93
- borderColor: "$border-primary-hover",
94
- color: "$text-primary-hover",
95
- [iconSlotSelector]: {
96
- color: "$icon-primary-hover"
97
- }
98
- },
99
- "&[data-pressed]": {
100
- backgroundColor: "$background-primary-subtle-active",
101
- borderColor: "$border-primary-active",
102
- color: "$text-primary-active",
103
- [iconSlotSelector]: {
104
- color: "$icon-primary-active"
105
- }
106
- },
107
- ...outlineDisabled
108
- },
109
- "ghost-prominent": {
110
- backgroundColor: "transparent",
111
- color: "$text-primary",
112
- "&[data-hovered]": {
113
- backgroundColor: "$background-primary-subtle-hover",
114
- color: "$text-primary-hover",
115
- [iconSlotSelector]: {
116
- color: "$icon-primary-hover"
117
- }
118
- },
119
- "&[data-pressed]": {
120
- backgroundColor: "$background-primary-subtle-active",
121
- color: "$text-primary-active",
122
- [iconSlotSelector]: {
123
- color: "$icon-primary-active"
124
- }
125
- },
126
- ...ghostDisabled
127
- },
128
- "solid-subtle": {
129
- backgroundColor: "$background-neutrals-subtle",
130
- color: "$text-neutrals",
131
- [iconSlotSelector]: {
132
- color: "$icon-neutrals"
133
- },
134
- "&[data-hovered]": {
135
- backgroundColor: "$background-neutrals-subtle-hover"
136
- },
137
- "&[data-pressed]": {
138
- backgroundColor: "$background-neutrals-subtle-active"
139
- },
140
- ...solidDisabled
53
+ primary: {},
54
+ secondary: {},
55
+ danger: {}
56
+ },
57
+ appearance: {
58
+ filled: {},
59
+ outlined: {},
60
+ flat: {}
61
+ },
62
+ size: {
63
+ large: {
64
+ padding: "14px 32px 18px 32px",
65
+ fontSize: "20px",
66
+ lineHeight: "28px",
67
+ height: "60px"
141
68
  },
142
- "outline-subtle": {
143
- backgroundColor: "$background-neutrals",
144
- border: "1px solid $border-neutrals",
145
- color: "$text-neutrals",
146
- [iconSlotSelector]: {
147
- color: "$icon-neutrals"
148
- },
149
- "&[data-hovered]": {
150
- backgroundColor: "$background-neutrals-subtle-hover",
151
- borderColor: "$border-neutrals-hover"
152
- },
153
- "&[data-pressed]": {
154
- backgroundColor: "$background-neutrals-subtle-active",
155
- borderColor: "$border-neutrals-active"
156
- },
157
- ...outlineDisabled
69
+ medium: {
70
+ padding: "11px 24px 13px 24px",
71
+ fontSize: "16px",
72
+ lineHeight: "24px",
73
+ height: "48px"
158
74
  },
159
- "ghost-subtle": {
160
- backgroundColor: "transparent",
161
- color: "$text-neutrals",
162
- [iconSlotSelector]: {
163
- color: "$icon-neutrals"
164
- },
165
- "&[data-hovered]": {
166
- backgroundColor: "$background-neutrals-subtle-hover"
167
- },
168
- "&[data-pressed]": {
169
- backgroundColor: "$background-neutrals-subtle-active"
170
- },
171
- ...ghostDisabled
75
+ small: {
76
+ padding: "7px 16px 9px 16px",
77
+ fontSize: "14px",
78
+ lineHeight: "20px",
79
+ height: "36px"
172
80
  },
173
- "solid-danger": {
174
- backgroundColor: "$background-danger-prominent",
175
- color: "$text-danger-inverted",
176
- [iconSlotSelector]: {
177
- color: "$icon-danger-inverted"
178
- },
179
- "&[data-hovered]": {
180
- backgroundColor: "$background-danger-prominent-hover"
181
- },
182
- "&[data-pressed]": {
183
- backgroundColor: "$background-danger-prominent-active"
184
- },
185
- ...solidDisabled
81
+ "x-small": {
82
+ padding: "5px 12px 7px",
83
+ fontSize: "14px",
84
+ lineHeight: "20px",
85
+ height: "32px"
186
86
  },
187
- "outline-danger": {
188
- backgroundColor: "$background-neutrals",
189
- borderColor: "$border-danger",
190
- color: "$text-danger",
191
- [iconSlotSelector]: {
192
- color: "$icon-danger"
193
- },
194
- "&[data-hovered]": {
195
- backgroundColor: "$background-danger-subtle",
196
- color: "$text-danger-hover",
197
- [iconSlotSelector]: {
198
- color: "$icon-danger-hover"
199
- }
200
- },
201
- "&[data-pressed]": {
202
- backgroundColor: "$background-danger-subtle-hover",
203
- color: "$text-danger-active",
204
- [iconSlotSelector]: {
205
- color: "$icon-danger-active"
87
+ "xx-small": {
88
+ padding: "3px 12px",
89
+ fontSize: "12px",
90
+ lineHeight: "18px",
91
+ height: "24px"
92
+ }
93
+ },
94
+ rounded: {
95
+ true: {
96
+ borderRadius: "$half"
97
+ }
98
+ },
99
+ loading: {
100
+ true: {
101
+ "&[disabled]": {
102
+ cursor: "default",
103
+ opacity: 1,
104
+ pointerEvents: "none",
105
+ "& > span": {
106
+ visibility: "hidden"
206
107
  }
108
+ }
109
+ }
110
+ },
111
+ fluid: {
112
+ true: {
113
+ width: "100%",
114
+ display: "block"
115
+ }
116
+ }
117
+ },
118
+ compoundVariants: [
119
+ {
120
+ size: "small",
121
+ rounded: true,
122
+ css: {
123
+ padding: "10px 16px",
124
+ height: "40px"
125
+ }
126
+ },
127
+ {
128
+ size: "large",
129
+ rounded: false,
130
+ css: {
131
+ borderRadius: "$50"
132
+ }
133
+ },
134
+ {
135
+ size: "medium",
136
+ rounded: false,
137
+ css: {
138
+ borderRadius: "$50"
139
+ }
140
+ },
141
+ {
142
+ size: "small",
143
+ rounded: false,
144
+ css: {
145
+ borderRadius: "$50"
146
+ }
147
+ },
148
+ {
149
+ size: "x-small",
150
+ rounded: false,
151
+ css: {
152
+ borderRadius: "$50"
153
+ }
154
+ },
155
+ {
156
+ size: "xx-small",
157
+ rounded: false,
158
+ css: {
159
+ borderRadius: "$25"
160
+ }
161
+ },
162
+ {
163
+ variant: "primary",
164
+ appearance: "filled",
165
+ css: {
166
+ color: "#FFFFFF",
167
+ backgroundColor: "#3859FF",
168
+ ...focusFilled,
169
+ "&:hover": {
170
+ color: "#FFFFFF",
171
+ backgroundColor: "#3F53D9"
207
172
  },
208
- ...outlineDisabled
209
- },
210
- "ghost-danger": {
211
- backgroundColor: "transparent",
212
- color: "$text-danger",
213
- [iconSlotSelector]: {
214
- color: "$icon-danger"
215
- },
216
- "&[data-hovered]": {
217
- backgroundColor: "$background-danger-subtle",
218
- color: "$text-danger-hover",
219
- [iconSlotSelector]: {
220
- color: "$icon-danger-hover"
221
- }
173
+ [pressedSelector]: {
174
+ backgroundColor: "#122277"
175
+ }
176
+ }
177
+ },
178
+ {
179
+ variant: "primary",
180
+ appearance: "outlined",
181
+ css: {
182
+ color: "rgba(66, 98, 255, 1)",
183
+ border: "1px solid rgba(66, 98, 255, 1)",
184
+ ...focusOutline,
185
+ "&:hover": {
186
+ color: "rgba(66, 98, 255, 1)",
187
+ backgroundColor: "rgba(244, 246, 255, 1)"
222
188
  },
223
- "&[data-pressed]": {
224
- backgroundColor: "$background-danger-subtle-hover",
225
- color: "$text-danger-active",
226
- [iconSlotSelector]: {
227
- color: "$icon-danger-active"
228
- }
189
+ [pressedSelector]: {
190
+ backgroundColor: "rgba(240, 242, 255, 1)"
191
+ }
192
+ }
193
+ },
194
+ {
195
+ variant: "primary",
196
+ appearance: "flat",
197
+ css: {
198
+ color: "rgba(66, 98, 255, 1)",
199
+ ...focusDefault,
200
+ "&:hover": {
201
+ color: "rgba(69, 91, 237, 1)",
202
+ backgroundColor: "rgba(245, 245, 247, 1)"
229
203
  },
230
- ...ghostDisabled
204
+ [pressedSelector]: {
205
+ color: "rgba(61, 81, 212, 1)"
206
+ }
231
207
  }
232
208
  },
233
- size: {
234
- "x-large": {
235
- height: sizes.xLarge,
236
- fontSize: "$200",
237
- paddingX: "calc($200 + ".concat(LABEL_OFFSET, "px)"),
238
- [externalIconSelector]: {
239
- ...styles.size.medium,
240
- ...styles.weight.normal
209
+ {
210
+ variant: "secondary",
211
+ appearance: "filled",
212
+ css: {
213
+ color: "rgba(5, 0, 56, 1)",
214
+ backgroundColor: "rgba(245, 245, 247, 1)",
215
+ ...focusFilled,
216
+ "&:hover": {
217
+ color: "rgba(5, 0, 56, 1)",
218
+ backgroundColor: "rgba(240, 240, 243, 1)"
219
+ },
220
+ [pressedSelector]: {
221
+ backgroundColor: "rgba(235, 235, 239, 1)"
241
222
  }
242
- },
243
- large: {
244
- height: sizes.large,
245
- fontSize: "$200",
246
- paddingX: "calc($150 + ".concat(LABEL_OFFSET, "px)"),
247
- [externalIconSelector]: {
248
- ...styles.size.medium,
249
- ...styles.weight.normal
223
+ }
224
+ },
225
+ {
226
+ variant: "secondary",
227
+ appearance: "outlined",
228
+ css: {
229
+ color: "rgba(5, 0, 56, 1)",
230
+ border: "1px solid rgba(205, 204, 215, 1)",
231
+ ...focusOutline,
232
+ "&:hover": {
233
+ color: "rgba(5, 0, 56, 1)",
234
+ backgroundColor: "rgba(245, 245, 247, 1)"
235
+ },
236
+ [pressedSelector]: {
237
+ backgroundColor: "rgba(235, 235, 239, 1)"
250
238
  }
251
- },
252
- medium: {
253
- height: sizes.medium,
254
- fontSize: "$175",
255
- paddingX: "calc($100 + ".concat(LABEL_OFFSET, "px)"),
256
- [externalIconSelector]: {
257
- ...styles.size.small,
258
- ...styles.weight.thin
239
+ }
240
+ },
241
+ {
242
+ variant: "secondary",
243
+ appearance: "flat",
244
+ css: {
245
+ color: "rgba(5, 0, 56, 1)",
246
+ ...focusDefault,
247
+ "&:hover": {
248
+ color: "rgba(5, 0, 56, 1)",
249
+ backgroundColor: "rgba(245, 245, 247, 1)"
259
250
  }
260
- },
261
- small: {
262
- fontSize: "$175",
263
- height: "$6",
264
- paddingX: "calc($100 + ".concat(LABEL_OFFSET, "px)"),
265
- [externalIconSelector]: {
266
- ...styles.size.small,
267
- ...styles.weight.thin
251
+ }
252
+ },
253
+ {
254
+ variant: "danger",
255
+ appearance: "filled",
256
+ css: {
257
+ color: "#FFFFFF",
258
+ backgroundColor: "rgba(217, 41, 41, 1)",
259
+ ...focusFilled,
260
+ "&:hover": {
261
+ backgroundColor: "rgba(199, 20, 20, 1)"
262
+ },
263
+ [pressedSelector]: {
264
+ backgroundColor: "rgba(184, 13, 13, 1)"
268
265
  }
269
266
  }
270
267
  },
271
- rounded: {
272
- true: {
273
- borderRadius: "$half"
268
+ {
269
+ variant: "danger",
270
+ appearance: "outlined",
271
+ css: {
272
+ color: "rgba(217, 41, 41, 1)",
273
+ border: "1px solid rgba(217, 41, 41, 1)",
274
+ ...focusOutline,
275
+ "&:hover": {
276
+ color: "rgba(217, 41, 41, 1)",
277
+ backgroundColor: "rgba(254, 247, 247, 1)"
278
+ },
279
+ [pressedSelector]: {
280
+ backgroundColor: "rgba(253, 242, 242, 1)"
281
+ }
274
282
  }
275
283
  },
276
- fluid: {
277
- true: {
278
- display: "flex",
279
- justifyContent: "center",
280
- maxWidth: "100%",
281
- width: "100%"
284
+ {
285
+ variant: "danger",
286
+ appearance: "flat",
287
+ css: {
288
+ color: "rgba(217, 41, 41, 1)",
289
+ ...focusDefault,
290
+ "&:hover": {
291
+ color: "rgba(217, 41, 41, 1)",
292
+ backgroundColor: "rgba(245, 245, 247, 1)"
293
+ }
282
294
  }
283
295
  }
284
- }
285
- });
286
- const StyledHiddenContent = styled(Primitive.span, {
287
- visibility: "hidden"
296
+ ]
288
297
  });
289
298
  const StyledSpinnerBox = styled(Primitive.div, {
290
299
  display: "flex",
@@ -298,76 +307,97 @@ const StyledSpinnerBox = styled(Primitive.div, {
298
307
  margin: "auto"
299
308
  });
300
309
 
301
- const Label = Primitive.span;
302
- Label.displayName = "Label";
303
-
304
- const buttonIconSizes = {
305
- small: "small",
306
- medium: "small",
307
- large: "medium",
308
- "x-large": "medium"
309
- };
310
- const buttonIconWeights = {
311
- small: "thin",
312
- medium: "thin",
313
- large: "normal",
314
- "x-large": "normal"
315
- };
316
310
  const Button = React.forwardRef(
317
311
  ({
318
- variant = "solid-prominent",
319
- size = "large",
312
+ variant = "primary",
313
+ appearance = "filled",
314
+ size = "medium",
320
315
  loading = false,
321
316
  rounded = false,
322
317
  fluid = false,
323
- "aria-disabled": ariaDisabled,
318
+ disabled = false,
319
+ href,
320
+ target,
321
+ rel,
324
322
  children,
323
+ onPress,
324
+ onClick,
325
+ asChild,
325
326
  ...restProps
326
327
  }, forwardRef) => {
327
- let spinnerSize = "medium";
328
- if (typeof size === "string" && ["small", "medium"].includes(size)) {
329
- spinnerSize = "small";
328
+ let spinnerSize;
329
+ if (typeof size === "string") {
330
+ spinnerSize = ["x-small", "xx-small"].includes(size) ? "small" : "medium";
331
+ } else {
332
+ spinnerSize = "medium";
330
333
  }
331
- const shouldHaveAriaDisabled = booleanify(ariaDisabled) || loading;
332
- const formattedChildren = React.Children.map(
333
- React.Children.toArray(children),
334
- (child) => {
335
- if (React.isValidElement(child) && child.type === IconSlot) {
336
- const iconSlotChildren = addPropsToChildren(
337
- child.props.children,
338
- (innerChild) => isIconComponent(innerChild),
339
- {
340
- "data-icon-component": "",
341
- size: buttonIconSizes[size],
342
- weight: buttonIconWeights[size]
343
- }
344
- );
345
- return React.cloneElement(child, { ...child.props }, iconSlotChildren);
346
- }
347
- return child;
348
- }
334
+ const _loading = loading === "true" || loading === true;
335
+ const shouldBeDisabled = disabled || _loading;
336
+ const asLink = href != null;
337
+ const ref = useRef(null);
338
+ const refWithFallback = forwardRef != null ? forwardRef : ref;
339
+ const { buttonProps, isPressed } = useButton(
340
+ {
341
+ isDisabled: shouldBeDisabled,
342
+ href,
343
+ onPress: onPress != null ? onPress : onClick,
344
+ // @ts-expect-error
345
+ allowFocusWhenDisabled: false,
346
+ ...restProps
347
+ },
348
+ refWithFallback
349
+ );
350
+ const { linkProps } = useLink(
351
+ {
352
+ isDisabled: disabled,
353
+ onPress: onPress != null ? onPress : onClick,
354
+ ...restProps
355
+ },
356
+ // @ts-expect-error
357
+ refWithFallback
358
+ );
359
+ const Content = /* @__PURE__ */ jsxs(Fragment, { children: [
360
+ _loading && /* @__PURE__ */ jsx(StyledSpinnerBox, { children: /* @__PURE__ */ jsx(Spinner, { size: spinnerSize }) }),
361
+ /* @__PURE__ */ jsx("span", { children })
362
+ ] });
363
+ const tabIndexProp = shouldBeDisabled && {
364
+ tabIndex: -1
365
+ };
366
+ const { isFocusVisible, focusProps } = useFocusRing();
367
+ const elementProps = mergeProps(
368
+ restProps,
369
+ asLink ? linkProps : buttonProps,
370
+ focusProps
349
371
  );
350
- const Content = loading ? /* @__PURE__ */ jsxs(Fragment, { children: [
351
- /* @__PURE__ */ jsx(StyledSpinnerBox, { children: /* @__PURE__ */ jsx(Spinner, { size: spinnerSize }) }),
352
- /* @__PURE__ */ jsx(StyledHiddenContent, { children: formattedChildren })
353
- ] }) : formattedChildren;
354
372
  return /* @__PURE__ */ jsx(
355
373
  StyledButton,
356
374
  {
357
- ...restProps,
375
+ ...elementProps,
358
376
  variant,
377
+ appearance,
378
+ size,
379
+ loading,
359
380
  rounded,
360
381
  fluid,
361
- size,
362
- "aria-disabled": shouldHaveAriaDisabled ? true : void 0,
363
- ref: forwardRef,
364
- children: Content
382
+ disabled: shouldBeDisabled,
383
+ asChild: asLink || asChild,
384
+ ...tabIndexProp,
385
+ "data-pressed": isPressed ? "" : void 0,
386
+ "data-focused": isFocusVisible ? "" : void 0,
387
+ ref: refWithFallback,
388
+ children: asLink ? /* @__PURE__ */ jsx(
389
+ "a",
390
+ {
391
+ href,
392
+ target,
393
+ rel: target === "_blank" ? "noopener noreferrer ".concat(rel) : rel,
394
+ children: Content
395
+ }
396
+ ) : Content
365
397
  }
366
398
  );
367
399
  }
368
400
  );
369
- Button.IconSlot = IconSlot;
370
- Button.Label = Label;
371
401
 
372
402
  export { Button };
373
403
  //# sourceMappingURL=module.js.map