@charcoal-ui/react 2.6.0 → 3.0.0-beta.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/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@charcoal-ui/react",
3
- "version": "2.6.0",
3
+ "version": "3.0.0-beta.0",
4
4
  "license": "Apache-2.0",
5
5
  "main": "./dist/index.cjs.js",
6
6
  "module": "./dist/index.esm.js",
@@ -49,10 +49,10 @@
49
49
  "typescript": "^4.9.5"
50
50
  },
51
51
  "dependencies": {
52
- "@charcoal-ui/icons": "^2.6.0",
53
- "@charcoal-ui/styled": "^2.6.0",
54
- "@charcoal-ui/theme": "^2.6.0",
55
- "@charcoal-ui/utils": "^2.6.0",
52
+ "@charcoal-ui/icons": "^3.0.0-beta.0",
53
+ "@charcoal-ui/styled": "^3.0.0-beta.0",
54
+ "@charcoal-ui/theme": "^3.0.0-beta.0",
55
+ "@charcoal-ui/utils": "^3.0.0-beta.0",
56
56
  "@react-aria/button": "^3.7.0",
57
57
  "@react-aria/checkbox": "^3.8.0",
58
58
  "@react-aria/dialog": "^3.5.0",
@@ -88,5 +88,5 @@
88
88
  "url": "https://github.com/pixiv/charcoal.git",
89
89
  "directory": "packages/react"
90
90
  },
91
- "gitHead": "8579b406b316285a35858512030d2143524ae154"
91
+ "gitHead": "e3522bffb7136b259f31cef88920aebc7637a5b6"
92
92
  }
@@ -58,7 +58,7 @@ Small.args = {
58
58
 
59
59
  export const Fixed: Story<ButtonProps> = DefaultStory.bind({})
60
60
  Fixed.args = {
61
- fixed: true,
61
+ fullWidth: true,
62
62
  }
63
63
 
64
64
  export const Disabled: Story<ButtonProps> = DefaultStory.bind({})
@@ -121,10 +121,10 @@ const LayoutExampleStory = (args: ButtonProps) => (
121
121
  gap: 8px;
122
122
  `}
123
123
  >
124
- <Button {...args} variant="Primary" fixed>
124
+ <Button {...args} variant="Primary" fullWidth>
125
125
  Submit
126
126
  </Button>
127
- <Button {...args} variant="Default" fixed>
127
+ <Button {...args} variant="Default" fullWidth>
128
128
  Cancel
129
129
  </Button>
130
130
  </div>
@@ -156,10 +156,10 @@ const LayoutExampleStory = (args: ButtonProps) => (
156
156
  }
157
157
  `}
158
158
  >
159
- <Button {...args} variant="Primary" fixed>
159
+ <Button {...args} variant="Primary" fullWidth>
160
160
  Submit
161
161
  </Button>
162
- <Button {...args} variant="Default" fixed>
162
+ <Button {...args} variant="Default" fullWidth>
163
163
  Cancel
164
164
  </Button>
165
165
  </div>
@@ -174,7 +174,7 @@ const LayoutExampleStory = (args: ButtonProps) => (
174
174
  }
175
175
  `}
176
176
  >
177
- <Button {...args} variant="Primary" fixed>
177
+ <Button {...args} variant="Primary" fullWidth>
178
178
  すべて見る
179
179
  </Button>
180
180
  <Button {...args} variant="Default">
@@ -19,7 +19,7 @@ interface StyledProps {
19
19
  /**
20
20
  * 幅を最大まで広げて描画
21
21
  */
22
- fixed: boolean
22
+ fullWidth: boolean
23
23
  }
24
24
 
25
25
  export type ButtonProps = Partial<StyledProps> & ClickableProps
@@ -29,7 +29,7 @@ const Button = React.forwardRef<ClickableElement, ButtonProps>(function Button(
29
29
  children,
30
30
  variant = 'Default',
31
31
  size = 'M',
32
- fixed = false,
32
+ fullWidth: fixed = false,
33
33
  disabled = false,
34
34
  ...rest
35
35
  },
@@ -41,7 +41,7 @@ const Button = React.forwardRef<ClickableElement, ButtonProps>(function Button(
41
41
  disabled={disabled}
42
42
  variant={variant}
43
43
  size={size}
44
- fixed={fixed}
44
+ fullWidth={fixed}
45
45
  ref={ref}
46
46
  >
47
47
  {children}
@@ -54,11 +54,11 @@ const StyledButton = styled(Clickable)
54
54
  .withConfig<StyledProps>({
55
55
  shouldForwardProp(prop) {
56
56
  // fixed は <button> 要素に渡ってはいけない
57
- return prop !== 'fixed'
57
+ return prop !== 'fullWidth'
58
58
  },
59
59
  })
60
60
  .attrs<StyledProps, ReturnType<typeof styledProps>>(styledProps)`
61
- width: ${(p) => (p.fixed ? 'stretch' : 'min-content')};
61
+ width: ${(p) => (p.fullWidth ? 'stretch' : 'min-content')};
62
62
  display: inline-grid;
63
63
  align-items: center;
64
64
  justify-content: center;
@@ -107,8 +107,12 @@ const CheckboxInput = styled.input`
107
107
  border-color: ${({ theme }) => theme.color.text4};
108
108
  }
109
109
  ${theme((o) => [o.outline.default.focus, o.borderRadius(4)])}
110
+
111
+ /* FIXME: o.outline.default.focus の transition に o.bg.brand の transition が打ち消されてしまう */
112
+ transition: all 0.2s !important;
110
113
  }
111
114
  `
115
+
112
116
  const CheckboxInputOverlay = styled.div<{ checked?: boolean }>`
113
117
  position: absolute;
114
118
  top: -2px;
@@ -2,7 +2,6 @@ import React from 'react'
2
2
  import { ModalTitle } from '.'
3
3
  import styled from 'styled-components'
4
4
  import { theme } from '../../styled'
5
- import { maxWidth } from '@charcoal-ui/utils'
6
5
 
7
6
  export function ModalHeader() {
8
7
  return (
@@ -24,11 +23,7 @@ const StyledModalTitle = styled(ModalTitle)`
24
23
  `
25
24
 
26
25
  export const ModalAlign = styled.div`
27
- ${theme((o) => [o.padding.horizontal(24)])}
28
-
29
- @media ${({ theme }) => maxWidth(theme.breakpoint.screen1)} {
30
- ${theme((o) => [o.padding.horizontal(16)])}
31
- }
26
+ ${theme((o) => [o.padding.horizontal(16)])}
32
27
  `
33
28
 
34
29
  export const ModalBody = styled.div`
@@ -39,9 +34,6 @@ export const ModalButtons = styled.div`
39
34
  display: grid;
40
35
  grid-auto-flow: row;
41
36
  grid-row-gap: 8px;
42
- ${theme((o) => [o.padding.horizontal(24).top(16)])}
43
37
 
44
- @media ${({ theme }) => maxWidth(theme.breakpoint.screen1)} {
45
- ${theme((o) => [o.padding.horizontal(16)])}
46
- }
38
+ ${theme((o) => [o.padding.horizontal(16).top(16)])}
47
39
  `
@@ -76,10 +76,10 @@ const DefaultStory = (args: ModalProps) => {
76
76
  </ModalAlign>
77
77
  </ModalVStack>
78
78
  <ModalButtons>
79
- <Button variant="Primary" onClick={() => state.close()} fixed>
79
+ <Button variant="Primary" onClick={() => state.close()} fullWidth>
80
80
  Apply
81
81
  </Button>
82
- <Button onClick={() => state.close()} fixed>
82
+ <Button onClick={() => state.close()} fullWidth>
83
83
  Cancel
84
84
  </Button>
85
85
  </ModalButtons>
@@ -140,10 +140,10 @@ const FullBottomSheetStory = (args: ModalProps) => {
140
140
  </ModalAlign>
141
141
  </ModalVStack>
142
142
  <ModalButtons>
143
- <Button variant="Primary" onClick={() => state.close()} fixed>
143
+ <Button variant="Primary" onClick={() => state.close()} fullWidth>
144
144
  Apply
145
145
  </Button>
146
- <Button onClick={() => state.close()} fixed>
146
+ <Button onClick={() => state.close()} fullWidth>
147
147
  Cancel
148
148
  </Button>
149
149
  </ModalButtons>
@@ -181,7 +181,7 @@ const BottomSheetStory = (args: ModalProps) => {
181
181
  </StyledModalText>
182
182
  </ModalVStack>
183
183
  <ModalButtons>
184
- <Button variant="Danger" onClick={() => state.close()} fixed>
184
+ <Button variant="Danger" onClick={() => state.close()} fullWidth>
185
185
  削除する
186
186
  </Button>
187
187
  <ModalDismissButton>キャンセル</ModalDismissButton>
@@ -263,7 +263,7 @@ export function ModalDismissButton({ children, ...props }: ButtonProps) {
263
263
  }
264
264
 
265
265
  return (
266
- <Button {...props} onClick={close} fixed>
266
+ <Button {...props} onClick={close} fullWidth>
267
267
  {children}
268
268
  </Button>
269
269
  )
@@ -110,6 +110,9 @@ export const RadioInput = styled.input.attrs({ type: 'radio' })<{
110
110
  }
111
111
 
112
112
  ${theme((o) => o.outline.default.focus)}
113
+
114
+ /* FIXME: o.outline.default.focus の transition に o.bg.brand の transition が打ち消されてしまう */
115
+ transition: all 0.2s !important;
113
116
  }
114
117
  `
115
118
 
@@ -1,5 +1,5 @@
1
1
  import { action } from '@storybook/addon-actions'
2
- import React from 'react'
2
+ import React, { useState } from 'react'
3
3
  import { Story } from '../../_lib/compat'
4
4
  import Switch from '.'
5
5
 
@@ -13,6 +13,25 @@ interface Props {
13
13
  disabled: boolean
14
14
  }
15
15
 
16
+ export const Playground: Story<Props> = (props: Props) => {
17
+ const [checked, setChecked] = useState(false)
18
+ return (
19
+ <div>
20
+ <Switch
21
+ {...props}
22
+ name="name"
23
+ onChange={(v) => {
24
+ setChecked(v)
25
+ action('onChange')
26
+ }}
27
+ checked={checked}
28
+ >
29
+ 選択する
30
+ </Switch>
31
+ </div>
32
+ )
33
+ }
34
+
16
35
  export const Labelled: Story<Props> = (props: Props) => (
17
36
  <div>
18
37
  <Switch {...props} name="name" onChange={action('onChange')}>
@@ -64,6 +64,10 @@ const Label = styled.label`
64
64
 
65
65
  ${theme((o) => o.disabled)}
66
66
 
67
+ :active > input {
68
+ box-shadow: 0 0 0 4px rgba(0, 150, 250, 0.32);
69
+ }
70
+
67
71
  ${disabledSelector} {
68
72
  cursor: default;
69
73
  }
@@ -80,42 +84,63 @@ const LabelInner = styled.div`
80
84
  const SwitchInput = styled.input.attrs({
81
85
  type: 'checkbox',
82
86
  })`
83
- &[type='checkbox'] {
84
- appearance: none;
85
- display: inline-flex;
86
- position: relative;
87
- box-sizing: border-box;
88
- width: 28px;
89
- border: 2px solid transparent;
90
- transition: box-shadow 0.2s, background-color 0.2s;
91
- cursor: inherit;
92
- ${theme((o) => [
93
- o.borderRadius(16),
94
- o.height.px(16),
95
- o.bg.text4.hover.press,
96
- o.outline.default.focus,
97
- o.margin.all(0),
98
- ])}
87
+ appearance: none;
88
+ display: inline-flex;
89
+ position: relative;
90
+ box-sizing: border-box;
91
+ width: 28px;
92
+ border: 2px solid transparent;
99
93
 
100
- &::after {
101
- content: '';
102
- position: absolute;
103
- display: block;
104
- top: 0;
105
- left: 0;
106
- width: 12px;
107
- height: 12px;
108
- transform: translateX(0);
109
- transition: transform 0.2s;
110
- ${theme((o) => [o.bg.text5.hover.press, o.borderRadius('oval')])}
111
- }
94
+ transition-property: background-color, box-shadow;
95
+ transition-duration: 0.2s;
96
+ cursor: inherit;
97
+
98
+ outline: none;
99
+ border-radius: 16px;
100
+ height: 16px;
101
+ margin: 0;
102
+ background-color: var(--charcoal-text4);
103
+ :hover {
104
+ background-color: var(--charcoal-text4-hover);
105
+ }
106
+ :active {
107
+ background-color: var(--charcoal-text4-press);
108
+ }
109
+ :focus {
110
+ box-shadow: 0 0 0 4px rgba(0, 150, 250, 0.32);
111
+ }
112
112
 
113
- &:checked {
114
- ${theme((o) => o.bg.brand.hover.press)}
113
+ &::after {
114
+ content: '';
115
+ position: absolute;
116
+ display: block;
117
+ top: 0;
118
+ left: 0;
119
+ width: 12px;
120
+ height: 12px;
121
+ transform: translateX(0);
122
+ transition: transform 0.2s;
123
+ border-radius: 1024px;
124
+ background-color: var(--charcoal-text5);
125
+ :hover {
126
+ background-color: var(--charcoal-text5-hover);
127
+ }
128
+ :active {
129
+ background-color: var(--charcoal-text5-press);
130
+ }
131
+ }
115
132
 
116
- &::after {
117
- transform: translateX(12px);
118
- }
133
+ &:checked {
134
+ background-color: var(--charcoal-brand);
135
+ :hover {
136
+ background-color: var(--charcoal-brand-hover);
137
+ }
138
+ :active {
139
+ background-color: var(--charcoal-brand-press);
140
+ }
141
+ &::after {
142
+ transform: translateX(12px);
143
+ transition: transform 0.2s;
119
144
  }
120
145
  }
121
146
  `
@@ -25,6 +25,7 @@ Default.args = {
25
25
  href: '',
26
26
  rel: '',
27
27
  target: '',
28
+ className: '',
28
29
  }
29
30
 
30
31
  export const Playground: Story<TagItemProps> = ({
@@ -24,6 +24,7 @@ export type TagItemProps = {
24
24
  status?: 'default' | 'active' | 'inactive'
25
25
  size?: keyof typeof sizeMap
26
26
  disabled?: boolean
27
+ className?: string
27
28
  } & Pick<ComponentPropsWithoutRef<'a'>, 'href' | 'target' | 'rel' | 'onClick'>
28
29
 
29
30
  const TagItem = forwardRef<HTMLAnchorElement, TagItemProps>(
@@ -36,6 +37,7 @@ const TagItem = forwardRef<HTMLAnchorElement, TagItemProps>(
36
37
  size = 'M',
37
38
  disabled,
38
39
  status = 'default',
40
+ className,
39
41
  ...props
40
42
  },
41
43
  _ref
@@ -60,6 +62,7 @@ const TagItem = forwardRef<HTMLAnchorElement, TagItemProps>(
60
62
  size={hasTranslatedLabel ? 'M' : size}
61
63
  status={status}
62
64
  {...buttonProps}
65
+ className={className}
63
66
  >
64
67
  <Background bgColor={bgColor} bgImage={bgImage} status={status} />
65
68
 
@@ -417,6 +417,13 @@ const StyledTextareaContainer = styled.div<{ rows: number; invalid: boolean }>`
417
417
  o.borderRadius(4),
418
418
  ])}
419
419
 
420
+ /**
421
+ * FIXME: o.outline.default を &:focus-within 内に書いてると、外れるときに transition が効かない
422
+ * 本来 o.outline.default.focus と書けば足してくれるような transition の内容を一旦明示している
423
+ * o.outline.default.focusWithin のようなものがあればこの行は不要になるはず
424
+ */
425
+ transition: box-shadow 0.2s;
426
+
420
427
  &:focus-within {
421
428
  ${(p) =>
422
429
  theme((o) => (p.invalid ? o.outline.assertive : o.outline.default))}