@sanity/ui 0.37.5 → 0.37.6
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/lib/dts/components/autocomplete/autocomplete.d.ts.map +1 -1
- package/lib/dts/components/autocomplete/autocomplete.styles.d.ts.map +1 -1
- package/lib/dts/components/menu/useMenuController.d.ts.map +1 -1
- package/lib/dts/components/tab/tab.d.ts +1 -1
- package/lib/dts/components/tab/tab.d.ts.map +1 -1
- package/lib/dts/components/tree/tree.d.ts +1 -1
- package/lib/dts/components/tree/tree.d.ts.map +1 -1
- package/lib/dts/components/tree/treeGroup.d.ts +1 -1
- package/lib/dts/components/tree/treeGroup.d.ts.map +1 -1
- package/lib/dts/components/tree/treeItem.d.ts +1 -1
- package/lib/dts/components/tree/treeItem.d.ts.map +1 -1
- package/lib/dts/hooks/usePrefersDark.d.ts.map +1 -1
- package/lib/dts/primitives/textInput/textInput.d.ts.map +1 -1
- package/lib/dts/styles/input/textInputStyle.d.ts.map +1 -1
- package/lib/dts/utils/errorBoundary.d.ts.map +1 -1
- package/lib/sanity-ui.js +64 -37
- package/lib/sanity-ui.js.map +1 -1
- package/lib/sanity-ui.modern.js +76 -38
- package/lib/sanity-ui.modern.js.map +1 -1
- package/lib/sanity-ui.module.js +65 -38
- package/lib/sanity-ui.module.js.map +1 -1
- package/package.json +10 -10
- package/src/components/autocomplete/__workshop__/custom.tsx +10 -4
- package/src/components/autocomplete/__workshop__/example.tsx +38 -15
- package/src/components/autocomplete/__workshop__/fullscreen.tsx +31 -30
- package/src/components/autocomplete/autocomplete.styles.tsx +1 -0
- package/src/components/autocomplete/autocomplete.tsx +24 -3
- package/src/components/menu/useMenuController.ts +4 -8
- package/src/components/tab/tab.tsx +1 -1
- package/src/components/tree/__workshop__/basic.perf.ts +32 -0
- package/src/components/tree/__workshop__/basic.tsx +92 -56
- package/src/components/tree/__workshop__/index.ts +6 -1
- package/src/components/tree/tree.tsx +168 -144
- package/src/components/tree/treeGroup.tsx +3 -3
- package/src/components/tree/treeItem.tsx +4 -4
- package/src/hooks/usePrefersDark.ts +10 -4
- package/src/primitives/textInput/__workshop__/plain.tsx +49 -18
- package/src/primitives/textInput/textInput.tsx +23 -3
- package/src/styles/input/textInputStyle.ts +2 -0
- package/src/theme/{themeContext.ts → ThemeContext.ts} +0 -0
- package/src/utils/errorBoundary.tsx +3 -1
|
@@ -1,4 +1,5 @@
|
|
|
1
|
-
import React, {useCallback, useEffect, useMemo, useRef, useState} from 'react'
|
|
1
|
+
import React, {forwardRef, memo, useCallback, useEffect, useMemo, useRef, useState} from 'react'
|
|
2
|
+
import {useForwardedRef} from '../../hooks'
|
|
2
3
|
import {Stack} from '../../primitives'
|
|
3
4
|
import {_findNextItemElement, _findPrevItemElement, _focusItemElement} from './helpers'
|
|
4
5
|
import {TreeContext} from './treeContext'
|
|
@@ -16,174 +17,197 @@ export interface TreeProps {
|
|
|
16
17
|
* This API might change. DO NOT USE IN PRODUCTION.
|
|
17
18
|
* @beta
|
|
18
19
|
*/
|
|
19
|
-
export
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
[]
|
|
49
|
-
)
|
|
50
|
-
|
|
51
|
-
const setExpanded = useCallback((path: string, expanded: boolean) => {
|
|
52
|
-
setState((s) => {
|
|
53
|
-
const itemState = s[path]
|
|
54
|
-
|
|
55
|
-
if (!itemState) return s
|
|
56
|
-
|
|
57
|
-
return {...s, [path]: {...itemState, expanded}}
|
|
58
|
-
})
|
|
59
|
-
}, [])
|
|
60
|
-
|
|
61
|
-
const contextValue: TreeContextValue = useMemo(
|
|
62
|
-
() => ({
|
|
63
|
-
version: 0.0,
|
|
64
|
-
focusedElement: focusedElement || itemElements[0] || null,
|
|
65
|
-
level: 0,
|
|
66
|
-
path,
|
|
67
|
-
registerItem,
|
|
68
|
-
setExpanded,
|
|
69
|
-
setFocusedElement,
|
|
70
|
-
space,
|
|
71
|
-
state,
|
|
72
|
-
}),
|
|
73
|
-
[focusedElement, itemElements, path, registerItem, setExpanded, space, state]
|
|
74
|
-
)
|
|
75
|
-
|
|
76
|
-
const handleKeyDown = useCallback(
|
|
77
|
-
(event: React.KeyboardEvent<HTMLDivElement>) => {
|
|
78
|
-
if (!focusedElement) return
|
|
79
|
-
|
|
80
|
-
if (event.key === 'ArrowDown') {
|
|
81
|
-
event.preventDefault()
|
|
82
|
-
|
|
83
|
-
const nextEl = _findNextItemElement(state, itemElements, focusedElement)
|
|
84
|
-
|
|
85
|
-
if (nextEl) {
|
|
86
|
-
_focusItemElement(nextEl)
|
|
87
|
-
setFocusedElement(nextEl)
|
|
20
|
+
export const Tree = memo(
|
|
21
|
+
forwardRef(function Tree(
|
|
22
|
+
props: TreeProps &
|
|
23
|
+
Omit<React.HTMLProps<HTMLDivElement>, 'align' | 'as' | 'height' | 'ref' | 'role' | 'wrap'>,
|
|
24
|
+
ref: React.ForwardedRef<HTMLDivElement>
|
|
25
|
+
): React.ReactElement {
|
|
26
|
+
const {children, space = 1, ...restProps} = props
|
|
27
|
+
const forwardedRef = useForwardedRef(ref)
|
|
28
|
+
const [focusedElement, setFocusedElement] = useState<HTMLElement | null>(null)
|
|
29
|
+
const focusedElementRef = useRef(focusedElement)
|
|
30
|
+
const path: string[] = useMemo(() => [], [])
|
|
31
|
+
const [itemElements, setItemElements] = useState<HTMLElement[]>([])
|
|
32
|
+
const [state, setState] = useState<TreeState>({})
|
|
33
|
+
const stateRef = useRef(state)
|
|
34
|
+
|
|
35
|
+
useEffect(() => {
|
|
36
|
+
focusedElementRef.current = focusedElement
|
|
37
|
+
}, [focusedElement])
|
|
38
|
+
|
|
39
|
+
useEffect(() => {
|
|
40
|
+
stateRef.current = state
|
|
41
|
+
}, [state])
|
|
42
|
+
|
|
43
|
+
const registerItem = useCallback(
|
|
44
|
+
(element: HTMLElement, path: string, expanded: boolean, selected: boolean) => {
|
|
45
|
+
setState((s) => ({...s, [path]: {element, expanded}}))
|
|
46
|
+
|
|
47
|
+
if (selected) {
|
|
48
|
+
setFocusedElement(element)
|
|
88
49
|
}
|
|
89
50
|
|
|
90
|
-
return
|
|
91
|
-
|
|
51
|
+
return () => {
|
|
52
|
+
setState((s) => {
|
|
53
|
+
const newState = {...s}
|
|
92
54
|
|
|
93
|
-
|
|
94
|
-
event.preventDefault()
|
|
55
|
+
delete newState[path]
|
|
95
56
|
|
|
96
|
-
|
|
57
|
+
return newState
|
|
58
|
+
})
|
|
59
|
+
}
|
|
60
|
+
},
|
|
61
|
+
[]
|
|
62
|
+
)
|
|
63
|
+
|
|
64
|
+
const setExpanded = useCallback((path: string, expanded: boolean) => {
|
|
65
|
+
setState((s) => {
|
|
66
|
+
const itemState = s[path]
|
|
67
|
+
|
|
68
|
+
if (!itemState) return s
|
|
69
|
+
|
|
70
|
+
return {...s, [path]: {...itemState, expanded}}
|
|
71
|
+
})
|
|
72
|
+
}, [])
|
|
73
|
+
|
|
74
|
+
const contextValue: TreeContextValue = useMemo(
|
|
75
|
+
() => ({
|
|
76
|
+
version: 0.0,
|
|
77
|
+
focusedElement: focusedElement || itemElements[0] || null,
|
|
78
|
+
level: 0,
|
|
79
|
+
path,
|
|
80
|
+
registerItem,
|
|
81
|
+
setExpanded,
|
|
82
|
+
setFocusedElement,
|
|
83
|
+
space,
|
|
84
|
+
state,
|
|
85
|
+
}),
|
|
86
|
+
[focusedElement, itemElements, path, registerItem, setExpanded, space, state]
|
|
87
|
+
)
|
|
88
|
+
|
|
89
|
+
const handleKeyDown = useCallback(
|
|
90
|
+
(event: React.KeyboardEvent<HTMLDivElement>) => {
|
|
91
|
+
if (!focusedElementRef.current) return
|
|
92
|
+
|
|
93
|
+
if (event.key === 'ArrowDown') {
|
|
94
|
+
event.preventDefault()
|
|
95
|
+
|
|
96
|
+
const nextEl = _findNextItemElement(
|
|
97
|
+
stateRef.current,
|
|
98
|
+
itemElements,
|
|
99
|
+
focusedElementRef.current
|
|
100
|
+
)
|
|
101
|
+
|
|
102
|
+
if (nextEl) {
|
|
103
|
+
_focusItemElement(nextEl)
|
|
104
|
+
setFocusedElement(nextEl)
|
|
105
|
+
}
|
|
97
106
|
|
|
98
|
-
|
|
99
|
-
_focusItemElement(prevEl)
|
|
100
|
-
setFocusedElement(prevEl)
|
|
107
|
+
return
|
|
101
108
|
}
|
|
102
109
|
|
|
103
|
-
|
|
104
|
-
|
|
110
|
+
if (event.key === 'ArrowUp') {
|
|
111
|
+
event.preventDefault()
|
|
105
112
|
|
|
106
|
-
|
|
107
|
-
|
|
113
|
+
const prevEl = _findPrevItemElement(
|
|
114
|
+
stateRef.current,
|
|
115
|
+
itemElements,
|
|
116
|
+
focusedElementRef.current
|
|
117
|
+
)
|
|
108
118
|
|
|
109
|
-
|
|
119
|
+
if (prevEl) {
|
|
120
|
+
_focusItemElement(prevEl)
|
|
121
|
+
setFocusedElement(prevEl)
|
|
122
|
+
}
|
|
110
123
|
|
|
111
|
-
|
|
124
|
+
return
|
|
125
|
+
}
|
|
112
126
|
|
|
113
|
-
|
|
127
|
+
if (event.key === 'ArrowLeft') {
|
|
128
|
+
event.preventDefault()
|
|
114
129
|
|
|
115
|
-
|
|
130
|
+
const itemKey = focusedElementRef.current.getAttribute('data-tree-key')
|
|
116
131
|
|
|
117
|
-
|
|
118
|
-
setState((s) => {
|
|
119
|
-
const itemState = s[itemKey]
|
|
132
|
+
if (!itemKey) return
|
|
120
133
|
|
|
121
|
-
|
|
134
|
+
const itemState = stateRef.current[itemKey]
|
|
122
135
|
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
136
|
+
if (!itemState) return
|
|
137
|
+
|
|
138
|
+
if (itemState.expanded) {
|
|
139
|
+
setState((s) => {
|
|
140
|
+
const itemState = s[itemKey]
|
|
127
141
|
|
|
128
|
-
|
|
142
|
+
if (!itemState) return s
|
|
129
143
|
|
|
130
|
-
|
|
131
|
-
|
|
144
|
+
return {...s, [itemKey]: {...itemState, expanded: false}}
|
|
145
|
+
})
|
|
146
|
+
} else {
|
|
147
|
+
const itemPath = itemKey.split('/')
|
|
132
148
|
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
149
|
+
itemPath.pop()
|
|
150
|
+
|
|
151
|
+
const parentKey = itemPath.join('/')
|
|
152
|
+
const parentState = parentKey && stateRef.current[parentKey]
|
|
153
|
+
|
|
154
|
+
if (parentState) {
|
|
155
|
+
parentState.element.focus()
|
|
156
|
+
setFocusedElement(parentState.element)
|
|
157
|
+
}
|
|
136
158
|
}
|
|
159
|
+
|
|
160
|
+
return
|
|
137
161
|
}
|
|
138
162
|
|
|
139
|
-
|
|
140
|
-
|
|
163
|
+
if (event.key === 'ArrowRight') {
|
|
164
|
+
event.preventDefault()
|
|
141
165
|
|
|
142
|
-
|
|
143
|
-
event.preventDefault()
|
|
166
|
+
const focusedKey = focusedElementRef.current.getAttribute('data-tree-key')
|
|
144
167
|
|
|
145
|
-
|
|
168
|
+
if (!focusedKey) return
|
|
146
169
|
|
|
147
|
-
|
|
170
|
+
if (!stateRef.current[focusedKey]?.expanded) {
|
|
171
|
+
setState((s) => {
|
|
172
|
+
const itemState = s[focusedKey]
|
|
148
173
|
|
|
149
|
-
|
|
150
|
-
setState((s) => {
|
|
151
|
-
const itemState = s[focusedKey]
|
|
174
|
+
if (!itemState) return s
|
|
152
175
|
|
|
153
|
-
|
|
176
|
+
return {...s, [focusedKey]: {...itemState, expanded: true}}
|
|
177
|
+
})
|
|
178
|
+
}
|
|
154
179
|
|
|
155
|
-
|
|
156
|
-
})
|
|
180
|
+
return
|
|
157
181
|
}
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
|
|
183
|
-
|
|
184
|
-
>
|
|
185
|
-
|
|
186
|
-
|
|
187
|
-
|
|
188
|
-
|
|
189
|
-
|
|
182
|
+
},
|
|
183
|
+
[itemElements]
|
|
184
|
+
)
|
|
185
|
+
|
|
186
|
+
useEffect(() => {
|
|
187
|
+
if (!forwardedRef.current) return
|
|
188
|
+
const _itemElements = Array.from(
|
|
189
|
+
forwardedRef.current.querySelectorAll('[data-ui="TreeItem"]')
|
|
190
|
+
) as HTMLElement[]
|
|
191
|
+
|
|
192
|
+
setItemElements(_itemElements)
|
|
193
|
+
}, [children, forwardedRef])
|
|
194
|
+
|
|
195
|
+
return (
|
|
196
|
+
<TreeContext.Provider value={contextValue}>
|
|
197
|
+
<Stack
|
|
198
|
+
as="ul"
|
|
199
|
+
data-ui="Tree"
|
|
200
|
+
{...restProps}
|
|
201
|
+
onKeyDown={handleKeyDown}
|
|
202
|
+
ref={forwardedRef}
|
|
203
|
+
role="tree"
|
|
204
|
+
space={space}
|
|
205
|
+
>
|
|
206
|
+
{children}
|
|
207
|
+
</Stack>
|
|
208
|
+
</TreeContext.Provider>
|
|
209
|
+
)
|
|
210
|
+
})
|
|
211
|
+
)
|
|
212
|
+
|
|
213
|
+
Tree.displayName = 'Tree'
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import React from 'react'
|
|
1
|
+
import React, {memo} from 'react'
|
|
2
2
|
import {Stack} from '../../primitives'
|
|
3
3
|
import {useTree} from './useTree'
|
|
4
4
|
|
|
@@ -6,7 +6,7 @@ export interface TreeGroupProps {
|
|
|
6
6
|
expanded?: boolean
|
|
7
7
|
}
|
|
8
8
|
|
|
9
|
-
export function TreeGroup(
|
|
9
|
+
export const TreeGroup = memo(function TreeGroup(
|
|
10
10
|
props: TreeGroupProps &
|
|
11
11
|
Omit<React.HTMLProps<HTMLDivElement>, 'as' | 'height' | 'ref' | 'role' | 'wrap'>
|
|
12
12
|
): React.ReactElement {
|
|
@@ -26,4 +26,4 @@ export function TreeGroup(
|
|
|
26
26
|
{children}
|
|
27
27
|
</Stack>
|
|
28
28
|
)
|
|
29
|
-
}
|
|
29
|
+
})
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import {useId} from '@reach/auto-id'
|
|
2
2
|
import {ToggleArrowRightIcon} from '@sanity/icons'
|
|
3
|
-
import React, {createElement, useCallback, useEffect, useMemo, useRef} from 'react'
|
|
3
|
+
import React, {createElement, memo, useCallback, useEffect, useMemo, useRef} from 'react'
|
|
4
4
|
import styled from 'styled-components'
|
|
5
5
|
import {Box, Flex, Text} from '../../primitives'
|
|
6
6
|
import {ThemeFontWeightKey} from '../../theme'
|
|
@@ -27,7 +27,7 @@ export interface TreeItemProps {
|
|
|
27
27
|
weight?: ThemeFontWeightKey
|
|
28
28
|
}
|
|
29
29
|
|
|
30
|
-
const Root = styled.li(treeItemRootStyle, treeItemRootColorStyle)
|
|
30
|
+
const Root = memo(styled.li(treeItemRootStyle, treeItemRootColorStyle))
|
|
31
31
|
|
|
32
32
|
const TreeItemBox = styled(Box).attrs({forwardedAs: 'a'})<TreeItemBoxStyleProps>(treeItemBoxStyle)
|
|
33
33
|
|
|
@@ -41,7 +41,7 @@ const ToggleArrowText = styled(Text)`
|
|
|
41
41
|
* This API might change. DO NOT USE IN PRODUCTION.
|
|
42
42
|
* @beta
|
|
43
43
|
*/
|
|
44
|
-
export function TreeItem(
|
|
44
|
+
export const TreeItem = memo(function TreeItem(
|
|
45
45
|
props: TreeItemProps & Omit<React.HTMLProps<HTMLLIElement>, 'as' | 'ref' | 'role'>
|
|
46
46
|
): React.ReactElement {
|
|
47
47
|
const {
|
|
@@ -191,4 +191,4 @@ export function TreeItem(
|
|
|
191
191
|
</TreeContext.Provider>
|
|
192
192
|
</Root>
|
|
193
193
|
)
|
|
194
|
-
}
|
|
194
|
+
})
|
|
@@ -1,13 +1,19 @@
|
|
|
1
|
-
import {useEffect, useState} from 'react'
|
|
1
|
+
import {useEffect, useMemo, useState} from 'react'
|
|
2
2
|
|
|
3
3
|
/**
|
|
4
4
|
* @public
|
|
5
5
|
*/
|
|
6
6
|
export function usePrefersDark(): boolean {
|
|
7
|
-
const
|
|
7
|
+
const mq = useMemo(() => {
|
|
8
|
+
if (typeof window === 'undefined') return undefined
|
|
9
|
+
|
|
10
|
+
return window.matchMedia('(prefers-color-scheme: dark)')
|
|
11
|
+
}, [])
|
|
12
|
+
|
|
13
|
+
const [dark, setDark] = useState(mq?.matches || false)
|
|
8
14
|
|
|
9
15
|
useEffect(() => {
|
|
10
|
-
|
|
16
|
+
if (!mq) return undefined
|
|
11
17
|
|
|
12
18
|
setDark(mq.matches)
|
|
13
19
|
|
|
@@ -16,7 +22,7 @@ export function usePrefersDark(): boolean {
|
|
|
16
22
|
mq.addEventListener('change', handleChange)
|
|
17
23
|
|
|
18
24
|
return () => mq.removeEventListener('change', handleChange)
|
|
19
|
-
}, [])
|
|
25
|
+
}, [mq])
|
|
20
26
|
|
|
21
27
|
return dark
|
|
22
28
|
}
|
|
@@ -1,7 +1,8 @@
|
|
|
1
1
|
import {icons, IconSymbol} from '@sanity/icons'
|
|
2
2
|
import {Container, Flex, Stack, Text, TextInput} from '@sanity/ui'
|
|
3
|
-
import {useBoolean, useSelect, useText} from '@sanity/ui-workshop'
|
|
4
|
-
import
|
|
3
|
+
import {PerfTestProps, useBoolean, usePerfTest, useSelect, useText} from '@sanity/ui-workshop'
|
|
4
|
+
import {fireEvent} from '@testing-library/dom'
|
|
5
|
+
import React, {useCallback, useState} from 'react'
|
|
5
6
|
import {
|
|
6
7
|
WORKSHOP_TEXT_FONT_SIZE_OPTIONS,
|
|
7
8
|
WORKSHOP_FONT_WEIGHT_OPTIONS,
|
|
@@ -10,7 +11,25 @@ import {
|
|
|
10
11
|
WORKSHOP_SPACE_OPTIONS,
|
|
11
12
|
} from '../../../__workshop__/constants'
|
|
12
13
|
|
|
14
|
+
const typingPerfTest: PerfTestProps<HTMLInputElement> = {
|
|
15
|
+
name: 'typing',
|
|
16
|
+
title: 'Typing',
|
|
17
|
+
description: 'This test types one character at a time',
|
|
18
|
+
run({target}) {
|
|
19
|
+
const text = 'Hello, world & Hello, world & Hello, world'
|
|
20
|
+
const len = text.length
|
|
21
|
+
|
|
22
|
+
for (let i = 0; i < len; i += 1) {
|
|
23
|
+
const value = text.slice(0, i + 1)
|
|
24
|
+
|
|
25
|
+
fireEvent.change(target, {target: {value}})
|
|
26
|
+
}
|
|
27
|
+
},
|
|
28
|
+
}
|
|
29
|
+
|
|
13
30
|
export default function PlainStory() {
|
|
31
|
+
const {ref, Wrapper} = usePerfTest(typingPerfTest)
|
|
32
|
+
|
|
14
33
|
const border = useBoolean('Border', true, 'Props')
|
|
15
34
|
const customValidity = useText('Custom validity', '', 'Props') || undefined
|
|
16
35
|
const disabled = useBoolean('Disabled', false, 'Props')
|
|
@@ -29,6 +48,13 @@ export default function PlainStory() {
|
|
|
29
48
|
const space = useSelect('Space', WORKSHOP_SPACE_OPTIONS, 3, 'Props')
|
|
30
49
|
const weight = useSelect('Weight', WORKSHOP_FONT_WEIGHT_OPTIONS, '', 'Props') || undefined
|
|
31
50
|
|
|
51
|
+
const [value, setValue] = useState('')
|
|
52
|
+
|
|
53
|
+
const handleChange = useCallback(
|
|
54
|
+
(event: React.ChangeEvent<HTMLInputElement>) => setValue(event.currentTarget.value),
|
|
55
|
+
[]
|
|
56
|
+
)
|
|
57
|
+
|
|
32
58
|
return (
|
|
33
59
|
<Flex align="center" height="fill" justify="center" padding={[4, 5, 6]} sizing="border">
|
|
34
60
|
<Container width={0}>
|
|
@@ -36,22 +62,27 @@ export default function PlainStory() {
|
|
|
36
62
|
<Text as="label" htmlFor="text-input-example" size={1} weight="semibold">
|
|
37
63
|
TextInput
|
|
38
64
|
</Text>
|
|
39
|
-
<
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
65
|
+
<Wrapper>
|
|
66
|
+
<TextInput
|
|
67
|
+
border={border}
|
|
68
|
+
customValidity={customValidity}
|
|
69
|
+
disabled={disabled}
|
|
70
|
+
fontSize={fontSize}
|
|
71
|
+
icon={icon && icons[icon]}
|
|
72
|
+
iconRight={iconRight && icons[iconRight]}
|
|
73
|
+
id="text-input-example"
|
|
74
|
+
name="email"
|
|
75
|
+
onChange={handleChange}
|
|
76
|
+
padding={padding}
|
|
77
|
+
placeholder={placeholder}
|
|
78
|
+
radius={radius}
|
|
79
|
+
readOnly={readOnly}
|
|
80
|
+
ref={ref}
|
|
81
|
+
space={space}
|
|
82
|
+
value={value}
|
|
83
|
+
weight={weight}
|
|
84
|
+
/>
|
|
85
|
+
</Wrapper>
|
|
55
86
|
</Stack>
|
|
56
87
|
</Container>
|
|
57
88
|
</Flex>
|
|
@@ -226,8 +226,28 @@ export const TextInput = forwardRef(function TextInput(
|
|
|
226
226
|
)
|
|
227
227
|
|
|
228
228
|
// Render clear button (memoized)
|
|
229
|
-
const clearButtonBoxPadding = useMemo(
|
|
230
|
-
|
|
229
|
+
const clearButtonBoxPadding = useMemo(
|
|
230
|
+
() =>
|
|
231
|
+
padding.map((v) => {
|
|
232
|
+
if (v === 0) return 0
|
|
233
|
+
if (v === 1) return 1
|
|
234
|
+
if (v === 2) return 1
|
|
235
|
+
|
|
236
|
+
return v - 2
|
|
237
|
+
}),
|
|
238
|
+
[padding]
|
|
239
|
+
)
|
|
240
|
+
const clearButtonPadding = useMemo(
|
|
241
|
+
() =>
|
|
242
|
+
padding.map((v) => {
|
|
243
|
+
if (v === 0) return 0
|
|
244
|
+
if (v === 1) return 0
|
|
245
|
+
if (v === 2) return 1
|
|
246
|
+
|
|
247
|
+
return v - 1
|
|
248
|
+
}),
|
|
249
|
+
[padding]
|
|
250
|
+
)
|
|
231
251
|
const clearButtonProps: TextInputClearButtonProps = useMemo(
|
|
232
252
|
() => (typeof clearButton === 'object' ? clearButton : EMPTY_RECORD),
|
|
233
253
|
[clearButton]
|
|
@@ -249,7 +269,7 @@ export const TextInput = forwardRef(function TextInput(
|
|
|
249
269
|
icon={CloseIcon}
|
|
250
270
|
mode="bleed"
|
|
251
271
|
padding={clearButtonPadding}
|
|
252
|
-
radius={radius
|
|
272
|
+
radius={radius}
|
|
253
273
|
{...clearButtonProps}
|
|
254
274
|
onClick={handleClearClick}
|
|
255
275
|
onMouseDown={handleClearMouseDown}
|
|
File without changes
|
|
@@ -37,7 +37,9 @@ export class ErrorBoundary extends React.Component<ErrorBoundaryProps, ErrorBoun
|
|
|
37
37
|
const {error} = this.state
|
|
38
38
|
|
|
39
39
|
if (error) {
|
|
40
|
-
|
|
40
|
+
const message = typeof error?.message === 'string' ? error.message : 'Error'
|
|
41
|
+
|
|
42
|
+
return <Code>{message}</Code>
|
|
41
43
|
}
|
|
42
44
|
|
|
43
45
|
return this.props.children
|