@basic-ui/material 1.0.0-alpha.30 → 1.0.0-alpha.32

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 CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@basic-ui/material",
3
- "version": "1.0.0-alpha.30",
3
+ "version": "1.0.0-alpha.32",
4
4
  "description": "Accessible React Components used as building blocks for UI patterns",
5
5
  "author": "Lucas Terra <lucasterra7@gmail.com>",
6
6
  "license": "MIT",
@@ -52,5 +52,5 @@
52
52
  "react": "^16.14.0 || ^17.0.0 || ^18.0.0",
53
53
  "react-dom": "^16.14.0 || ^17.0.0 || ^18.0.0"
54
54
  },
55
- "gitHead": "4c7fdd9ea2da383ea6f249ba864346e48da1e31a"
55
+ "gitHead": "42c1e44b1429227fe589e0f7a4bfeeb15b5e395a"
56
56
  }
@@ -1,41 +1,98 @@
1
+ import type { ReactElement } from 'react';
2
+ import { forwardRef } from 'react';
3
+
1
4
  import { Switch } from './';
2
5
  import { Box } from '../';
6
+ import type { CheckBoxIconProps } from '../CheckBox/CheckBoxIcon';
3
7
 
4
8
  export default {
5
9
  title: 'components/Switch',
6
10
  };
7
11
 
8
- const Example = () => {
12
+ const CheckBoxIcon = forwardRef<HTMLDivElement, CheckBoxIconProps>(
13
+ function CheckBoxIcon(
14
+ {
15
+ __css = {},
16
+ indeterminate,
17
+ checked,
18
+ // eslint-disable-next-line @typescript-eslint/no-unused-vars
19
+ disabled,
20
+ backgroundColor,
21
+ borderColor,
22
+ opacity,
23
+ ...otherProps
24
+ },
25
+ forwardedRef
26
+ ) {
27
+ return (
28
+ <Box
29
+ as="span"
30
+ ref={forwardedRef}
31
+ __css={{
32
+ display: 'inline-flex',
33
+ pointerEvents: 'none',
34
+ '& svg': {
35
+ width: 'var(--switch-icon-size)',
36
+ height: 'var(--switch-icon-size)',
37
+ },
38
+ __css,
39
+ }}
40
+ {...otherProps}
41
+ >
42
+ <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 96 960 960">
43
+ {checked ? (
44
+ <path
45
+ d="M378 810 154 586l43-43 181 181 384-384 43 43-427 427Z"
46
+ fill="currentColor"
47
+ />
48
+ ) : (
49
+ <path
50
+ d="m249 849-42-42 231-231-231-231 42-42 231 231 231-231 42 42-231 231 231 231-42 42-231-231-231 231Z"
51
+ fill="currentColor"
52
+ />
53
+ )}
54
+ </svg>
55
+ </Box>
56
+ );
57
+ }
58
+ );
59
+
60
+ const Example = ({ icon }: { icon?: ReactElement<any> }) => {
9
61
  return (
10
62
  <>
11
63
  <Box>
12
- <Switch>off/on</Switch>
13
- <Switch disabled>off/on</Switch>
14
- <Switch disabled defaultChecked={true}>
64
+ <Switch icon={icon}>off/on</Switch>
65
+ <Switch icon={icon} disabled>
66
+ off/on
67
+ </Switch>
68
+ <Switch icon={icon} disabled defaultChecked={true}>
15
69
  off/on
16
70
  </Switch>
17
71
  </Box>
18
72
  <Box>
19
- <Switch />
20
- <Switch disabled />
21
- <Switch disabled defaultChecked={true} />
73
+ <Switch icon={icon} />
74
+ <Switch icon={icon} disabled />
75
+ <Switch icon={icon} disabled defaultChecked={true} />
22
76
  </Box>
23
77
  <Box>
24
- <Switch size="small">off/on</Switch>
25
- <Switch disabled size="small">
78
+ <Switch icon={icon} size="small">
79
+ off/on
80
+ </Switch>
81
+ <Switch icon={icon} disabled size="small">
26
82
  off/on
27
83
  </Switch>
28
- <Switch disabled defaultChecked={true} size="small">
84
+ <Switch icon={icon} disabled defaultChecked={true} size="small">
29
85
  off/on
30
86
  </Switch>
31
87
  </Box>
32
88
  <Box>
33
- <Switch size="small" />
34
- <Switch disabled size="small" />
35
- <Switch disabled defaultChecked={true} size="small" />
89
+ <Switch icon={icon} size="small" />
90
+ <Switch icon={icon} disabled size="small" />
91
+ <Switch icon={icon} disabled defaultChecked={true} size="small" />
36
92
  </Box>
37
93
  </>
38
94
  );
39
95
  };
40
96
 
41
97
  export const Default = () => <Example />;
98
+ export const WithIcon = () => <Example icon={<CheckBoxIcon />} />;
@@ -1,5 +1,5 @@
1
- import type { ElementType, FC, InputHTMLAttributes } from 'react';
2
- import { forwardRef } from 'react';
1
+ import type { ElementType, FC, InputHTMLAttributes, ReactElement } from 'react';
2
+ import { cloneElement, forwardRef } from 'react';
3
3
  import { CheckBox as _CheckBoxCore } from '@basic-ui/core';
4
4
  import { rem } from 'polished';
5
5
 
@@ -26,9 +26,10 @@ export interface SwitchProps
26
26
  checked?: boolean;
27
27
  disabled?: boolean;
28
28
  size?: 'small' | 'default';
29
+ icon?: ReactElement<{ checked?: boolean; disabled?: boolean }>;
29
30
  }
30
31
 
31
- function getSizeCssVariables(size: 'small' | 'default') {
32
+ function getSizeCssVariables(size: 'small' | 'default', hasIcon: boolean) {
32
33
  const multiplier = size === 'small' ? 0.75 : 1;
33
34
  const BORDER_WIDTH = 2;
34
35
  const TRAIL_WIDTH = 52 * multiplier;
@@ -37,6 +38,7 @@ function getSizeCssVariables(size: 'small' | 'default') {
37
38
  ['--switch-border-width']: rem(BORDER_WIDTH),
38
39
  ['--switch-trail-width']: rem(TRAIL_WIDTH),
39
40
  ['--switch-trail-height']: rem(TRAIL_HEIGHT),
41
+ ['--switch-icon-size']: rem(TRAIL_HEIGHT / 2),
40
42
  ['--switch-state-layer-size']: rem(40 * multiplier),
41
43
  ['--switch-thumb-size-checked-inactive']: rem(
42
44
  TRAIL_HEIGHT - BORDER_WIDTH * 4
@@ -48,6 +50,12 @@ function getSizeCssVariables(size: 'small' | 'default') {
48
50
  ['--switch-thumb-size-unchecked-active']: rem(
49
51
  TRAIL_HEIGHT - BORDER_WIDTH * 2
50
52
  ),
53
+ ...(hasIcon && {
54
+ ['--switch-thumb-size-unchecked-inactive']:
55
+ 'var(--switch-thumb-size-checked-inactive)',
56
+ ['--switch-thumb-size-unchecked-active']:
57
+ 'var(--switch-thumb-size-checked-active)',
58
+ }),
51
59
  };
52
60
  }
53
61
 
@@ -60,6 +68,7 @@ const SwitchInner = forwardRef<HTMLInputElement, SwitchProps>(
60
68
  onChange,
61
69
  size = 'default',
62
70
  __css,
71
+ icon,
63
72
  ...otherProps
64
73
  } = props;
65
74
  const color = checked ? 'primary' : 'on.surface';
@@ -70,7 +79,7 @@ const SwitchInner = forwardRef<HTMLInputElement, SwitchProps>(
70
79
  display="inline-block"
71
80
  position="relative"
72
81
  minWidth="auto"
73
- sx={getSizeCssVariables(size)}
82
+ sx={getSizeCssVariables(size, Boolean(icon))}
74
83
  >
75
84
  <SwitchTrail checked={checked} disabled={disabled} />
76
85
  <SwitchThumb checked={checked}>
@@ -114,7 +123,15 @@ const SwitchInner = forwardRef<HTMLInputElement, SwitchProps>(
114
123
  ...__css,
115
124
  }}
116
125
  />
117
- <SwitchCircle checked={checked} />
126
+ <SwitchCircle checked={checked}>
127
+ {icon
128
+ ? cloneElement(icon, {
129
+ checked,
130
+ ['data-checkbox-icon' as any]: '',
131
+ disabled,
132
+ })
133
+ : null}
134
+ </SwitchCircle>
118
135
  </SwitchThumb>
119
136
  </Box>
120
137
  );
@@ -125,13 +142,14 @@ export const Switch = forwardRef<HTMLInputElement, SwitchProps>(function Switch(
125
142
  props,
126
143
  forwardedRef
127
144
  ) {
128
- const { as = 'input', disabled, children, ...otherProps } = props;
145
+ const { as = 'input', icon, disabled, children, ...otherProps } = props;
129
146
 
130
147
  const inner = (
131
148
  <CheckBoxCore
132
149
  as={SwitchInner}
133
150
  innerAs={as}
134
151
  ref={forwardedRef}
152
+ icon={icon}
135
153
  disabled={disabled}
136
154
  {...otherProps}
137
155
  />
@@ -64,6 +64,9 @@ export const SwitchCircle = ({ checked = false, ...otherProps }) => (
64
64
  <Box
65
65
  __css={{
66
66
  position: 'absolute',
67
+ display: 'inline-flex',
68
+ alignItems: 'center',
69
+ justifyContent: 'center',
67
70
  width: checked
68
71
  ? CIRCLE_SIZE_INACTIVE_CHECKED
69
72
  : CIRCLE_SIZE_INACTIVE_UNCHECKED,
@@ -75,6 +78,7 @@ export const SwitchCircle = ({ checked = false, ...otherProps }) => (
75
78
  pointerEvents: 'none',
76
79
  zIndex: 1,
77
80
  backgroundColor: checked ? 'on.primary' : 'outline',
81
+ color: checked ? 'primary' : 'on.outline',
78
82
  top: '50%',
79
83
  left: '50%',
80
84
  transform: 'translate(-50%, -50%)',
@@ -82,6 +86,7 @@ export const SwitchCircle = ({ checked = false, ...otherProps }) => (
82
86
  '[data-switch-thumb=""]:active ~ &, [data-switch-thumb=""]:focus-visible ~ &, [data-switch-thumb=""]:hover ~ &':
83
87
  {
84
88
  backgroundColor: checked ? 'primary-container' : 'on.surface-variant',
89
+ color: checked ? 'on.primary-container' : 'surface-variant',
85
90
  },
86
91
  '[data-switch-thumb=""]:active ~ &, [data-switch-thumb=""]:focus-visible ~ &':
87
92
  {
@@ -95,6 +100,7 @@ export const SwitchCircle = ({ checked = false, ...otherProps }) => (
95
100
  '[data-switch-thumb=""]:disabled ~ &': {
96
101
  opacity: checked ? 1 : 0.38,
97
102
  backgroundColor: checked ? 'surface' : 'on.surface',
103
+ color: checked ? 'on.surface' : 'surface',
98
104
  height: checked
99
105
  ? CIRCLE_SIZE_INACTIVE_CHECKED
100
106
  : CIRCLE_SIZE_INACTIVE_UNCHECKED,