@sanity/ui 0.38.3-next.18 → 0.38.3-next.36

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.
Files changed (38) hide show
  1. package/dist/sanity-ui.esm.js +9835 -0
  2. package/dist/sanity-ui.esm.js.map +1 -0
  3. package/dist/sanity-ui.js +9975 -1
  4. package/dist/sanity-ui.js.map +1 -1
  5. package/dist/types/src/index.d.ts +386 -384
  6. package/package.json +12 -19
  7. package/src/components/autocomplete/__workshop__/async.tsx +5 -3
  8. package/src/components/autocomplete/autocomplete.styles.tsx +0 -5
  9. package/src/components/autocomplete/autocomplete.tsx +51 -51
  10. package/src/components/autocomplete/constants.ts +3 -3
  11. package/src/components/menu/menu.test.tsx +2 -0
  12. package/src/components/toast/toast.test.tsx +2 -0
  13. package/src/constants.ts +17 -0
  14. package/src/primitives/badge/badge.test.tsx +2 -0
  15. package/src/primitives/button/button.test.tsx +2 -0
  16. package/src/primitives/popover/__workshop__/PlainStory.tsx +1 -0
  17. package/src/primitives/popover/__workshop__/RightAlignedStory.tsx +1 -0
  18. package/src/primitives/popover/__workshop__/TestStory.tsx +1 -0
  19. package/src/primitives/popover/popover.tsx +239 -197
  20. package/src/primitives/popover/{arrow.tsx → popoverArrow.tsx} +5 -5
  21. package/src/primitives/popover/popoverCard.tsx +160 -0
  22. package/src/primitives/tooltip/__workshop__/props.tsx +14 -9
  23. package/src/primitives/tooltip/tooltip.tsx +162 -92
  24. package/src/primitives/tooltip/tooltipArrow.tsx +25 -10
  25. package/src/styles/margin/marginsStyle.test.ts +2 -0
  26. package/src/styles/padding/paddingStyle.test.ts +2 -0
  27. package/src/theme/lib/color-fns/color-fns.test.ts +2 -0
  28. package/src/theme/lib/theme/color/color.test.ts +3 -1
  29. package/src/theme/theme.test.tsx +2 -0
  30. package/src/utils/boundaryElement/boundaryElement.test.tsx +2 -0
  31. package/src/utils/layer/layer.test.tsx +2 -0
  32. package/src/utils/portal/portal.test.tsx +2 -0
  33. package/dist/sanity-ui.mjs +0 -2
  34. package/dist/sanity-ui.mjs.map +0 -1
  35. package/src/primitives/popover/modifiers/getPopoverModifiers.ts +0 -137
  36. package/src/primitives/popover/modifiers/index.ts +0 -1
  37. package/src/primitives/popover/modifiers/types.ts +0 -18
  38. package/src/primitives/popover/modifiers/usePopoverModifiers.ts +0 -58
package/package.json CHANGED
@@ -1,18 +1,18 @@
1
1
  {
2
2
  "name": "@sanity/ui",
3
- "version": "0.38.3-next.18+f1216ee3",
3
+ "version": "0.38.3-next.36+073973df",
4
4
  "sideEffects": false,
5
5
  "types": "./dist/types/src/index.d.ts",
6
6
  "source": "./src/index.ts",
7
- "module": "./dist/sanity-ui.mjs",
7
+ "module": "./dist/sanity-ui.esm.js",
8
8
  "main": "./dist/sanity-ui.js",
9
9
  "exports": {
10
10
  ".": {
11
11
  "types": "./dist/types/src/index.d.ts",
12
12
  "source": "./src/index.ts",
13
- "import": "./dist/sanity-ui.mjs",
13
+ "import": "./dist/sanity-ui.esm.js",
14
14
  "require": "./dist/sanity-ui.js",
15
- "default": "./dist/sanity-ui.mjs"
15
+ "default": "./dist/sanity-ui.esm.js"
16
16
  }
17
17
  },
18
18
  "files": [
@@ -32,31 +32,24 @@
32
32
  "watch": "pkg watch --tsconfig tsconfig.dist.json"
33
33
  },
34
34
  "dependencies": {
35
- "@popperjs/core": "^2.11.6",
36
- "@sanity/color": "2.1.17-next.18+f1216ee3",
37
- "@sanity/icons": "1.3.7-next.18+f1216ee3",
38
- "framer-motion": "^7.3.5",
39
- "popper-max-size-modifier": "^0.2.0",
40
- "react-is": "^18.2.0",
41
- "react-popper": "^2.3.0",
35
+ "@floating-ui/react-dom": "^1.0.0",
36
+ "@sanity/color": "2.1.17-next.36+073973df",
37
+ "@sanity/icons": "1.3.7-next.36+073973df",
38
+ "framer-motion": "^7.5.2",
42
39
  "react-refractor": "^2.1.7"
43
40
  },
44
41
  "devDependencies": {
45
- "@floating-ui/react-dom": "^1.0.0",
46
42
  "@juggle/resize-observer": "^3.4.0",
47
- "@testing-library/dom": "^8.17.1",
48
- "@testing-library/jest-dom": "^5.16.5",
49
- "@testing-library/react": "^13.4.0",
50
43
  "@types/refractor": "^3.0.2",
51
- "framer-motion": "^7.3.5",
52
44
  "react": "^18.2.0",
53
45
  "react-dom": "^18.2.0",
54
- "react-refractor": "^2.1.7",
55
- "styled-components": "^5.3.5"
46
+ "react-is": "^18.2.0",
47
+ "styled-components": "^5.3.6"
56
48
  },
57
49
  "peerDependencies": {
58
50
  "react": "^18",
59
51
  "react-dom": "^18",
52
+ "react-is": "^18",
60
53
  "styled-components": "^5.2"
61
54
  },
62
55
  "repository": {
@@ -76,5 +69,5 @@
76
69
  "publishConfig": {
77
70
  "access": "public"
78
71
  },
79
- "gitHead": "f1216ee3ef45b3710598c841bda1b3fc47ea97ac"
72
+ "gitHead": "073973df407da1d34294c04d56e1a8085e7f3326"
80
73
  }
@@ -80,8 +80,8 @@ export default function AsyncStory() {
80
80
 
81
81
  return (
82
82
  <Box padding={[4, 5, 6]}>
83
- <Stack space={3}>
84
- <Text as="label" htmlFor="async" size={1} weight="semibold">
83
+ <Stack space={[3, 3, 4]}>
84
+ <Text as="label" htmlFor="async" size={[1, 1, 2]} weight="semibold">
85
85
  Country
86
86
  </Text>
87
87
  <LayerProvider zOffset={100}>
@@ -104,7 +104,9 @@ export default function AsyncStory() {
104
104
  </LayerProvider>
105
105
 
106
106
  <Card border overflow="auto" padding={3} radius={1}>
107
- <Code language="json">{JSON.stringify({loading, options, query, value}, null, 2)}</Code>
107
+ <Code language="json" size={[1, 1, 2]}>
108
+ {JSON.stringify({loading, options, query, value}, null, 2)}
109
+ </Code>
108
110
  </Card>
109
111
  </Stack>
110
112
  </Box>
@@ -24,11 +24,6 @@ export const ListBox = styled(Box)`
24
24
  * @internal
25
25
  */
26
26
  export const ResultsPopover = styled(Popover)`
27
- & > div {
28
- overflow: auto;
29
- -webkit-overflow-scrolling: touch;
30
- }
31
-
32
27
  &[data-popper-reference-hidden='true'] {
33
28
  display: none;
34
29
  }
@@ -1,8 +1,25 @@
1
1
  import {ChevronDownIcon} from '@sanity/icons'
2
- import {cloneElement, forwardRef, useCallback, useEffect, useMemo, useReducer, useRef} from 'react'
2
+ import {
3
+ ChangeEvent,
4
+ ElementType,
5
+ FocusEvent,
6
+ HTMLProps,
7
+ KeyboardEvent,
8
+ MouseEvent,
9
+ ReactElement,
10
+ ReactNode,
11
+ Ref,
12
+ cloneElement,
13
+ forwardRef,
14
+ useCallback,
15
+ useEffect,
16
+ useMemo,
17
+ useReducer,
18
+ useRef,
19
+ } from 'react'
3
20
  import {EMPTY_ARRAY, EMPTY_RECORD} from '../../constants'
4
21
  import {_hasFocus, _raf, focusFirstDescendant} from '../../helpers'
5
- import {useForwardedRef, useArrayProp} from '../../hooks'
22
+ import {useArrayProp, useForwardedRef} from '../../hooks'
6
23
  import {Box, BoxProps, Button, Card, PopoverProps, Stack, Text, TextInput} from '../../primitives'
7
24
  import {AnimatedSpinnerIcon, ListBox, ResultsPopover, Root} from './autocomplete.styles'
8
25
  import {AutocompleteOption} from './autocompleteOption'
@@ -23,53 +40,45 @@ export interface AutocompleteProps<Option extends BaseAutocompleteOption = BaseA
23
40
  customValidity?: string
24
41
  filterOption?: (query: string, option: Option) => boolean
25
42
  fontSize?: number | number[]
26
- icon?: React.ElementType | React.ReactNode
43
+ icon?: ElementType | ReactNode
27
44
  id: string
28
- /**
29
- * @beta
30
- */
45
+ /** @beta */
31
46
  listBox?: BoxProps
32
47
  loading?: boolean
33
48
  onChange?: (value: string) => void
34
49
  onQueryChange?: (query: string | null) => void
35
50
  onSelect?: (value: string) => void
36
- /**
37
- * @beta
38
- */
51
+ /** @beta */
39
52
  openButton?: boolean | AutocompleteOpenButtonProps
40
53
  options?: Option[]
41
54
  padding?: number | number[]
42
55
  popover?: Omit<PopoverProps, 'content' | 'onMouseEnter' | 'onMouseLeave' | 'open'> &
43
- Omit<React.HTMLProps<HTMLDivElement>, 'as' | 'children' | 'content' | 'ref' | 'width'>
44
- prefix?: React.ReactNode
56
+ Omit<HTMLProps<HTMLDivElement>, 'as' | 'children' | 'content' | 'ref' | 'width'>
57
+ prefix?: ReactNode
45
58
  radius?: number | number[]
46
- /**
47
- * @beta
48
- */
59
+ /** @beta */
49
60
  relatedElements?: HTMLElement[]
50
- renderOption?: (option: Option) => React.ReactElement
51
- /**
52
- * @beta
53
- */
61
+ renderOption?: (option: Option) => ReactElement
62
+ /** @beta */
54
63
  renderPopover?: (
55
64
  props: {
56
- content: React.ReactElement | null
65
+ content: ReactElement | null
57
66
  hidden: boolean
58
67
  inputElement: HTMLInputElement | null
59
68
  onMouseEnter: () => void
60
69
  onMouseLeave: () => void
61
70
  },
62
- ref: React.Ref<HTMLDivElement>
63
- ) => React.ReactNode
71
+ ref: Ref<HTMLDivElement>
72
+ ) => ReactNode
64
73
  renderValue?: (value: string, option?: Option) => string
65
- suffix?: React.ReactNode
74
+ suffix?: ReactNode
66
75
  value?: string
67
76
  }
68
77
 
69
- const defaultRenderValue = (value: string, option?: BaseAutocompleteOption) =>
78
+ const DEFAULT_RENDER_VALUE = (value: string, option?: BaseAutocompleteOption) =>
70
79
  option ? option.value : value
71
80
 
72
- const defaultFilterOption = (query: string, option: BaseAutocompleteOption) =>
81
+ const DEFAULT_FILTER_OPTION = (query: string, option: BaseAutocompleteOption) =>
73
82
  option.value.toLowerCase().indexOf(query.toLowerCase()) > -1
74
83
 
75
84
  const InnerAutocomplete = forwardRef(function InnerAutocomplete<
@@ -77,7 +86,7 @@ const InnerAutocomplete = forwardRef(function InnerAutocomplete<
77
86
  >(
78
87
  props: AutocompleteProps<Option> &
79
88
  Omit<
80
- React.HTMLProps<HTMLInputElement>,
89
+ HTMLProps<HTMLInputElement>,
81
90
  | 'aria-activedescendant'
82
91
  | 'aria-autocomplete'
83
92
  | 'aria-expanded'
@@ -97,7 +106,7 @@ const InnerAutocomplete = forwardRef(function InnerAutocomplete<
97
106
  | 'type'
98
107
  | 'value'
99
108
  >,
100
- ref: React.Ref<HTMLInputElement>
109
+ ref: Ref<HTMLInputElement>
101
110
  ) {
102
111
  const {
103
112
  border = true,
@@ -107,7 +116,7 @@ const InnerAutocomplete = forwardRef(function InnerAutocomplete<
107
116
  fontSize = 2,
108
117
  icon,
109
118
  id,
110
- listBox = {},
119
+ listBox = EMPTY_RECORD,
111
120
  loading,
112
121
  onBlur,
113
122
  onChange,
@@ -117,14 +126,14 @@ const InnerAutocomplete = forwardRef(function InnerAutocomplete<
117
126
  openButton,
118
127
  options: optionsProp,
119
128
  padding: paddingProp = 3,
120
- popover = {},
129
+ popover = EMPTY_RECORD,
121
130
  prefix,
122
131
  radius = 3,
123
132
  readOnly,
124
133
  relatedElements,
125
134
  renderOption: renderOptionProp,
126
135
  renderPopover,
127
- renderValue = defaultRenderValue,
136
+ renderValue = DEFAULT_RENDER_VALUE,
128
137
  suffix,
129
138
  value: valueProp,
130
139
  ...restProps
@@ -153,8 +162,9 @@ const InnerAutocomplete = forwardRef(function InnerAutocomplete<
153
162
 
154
163
  const renderOption =
155
164
  typeof renderOptionProp === 'function' ? renderOptionProp : defaultRenderOption
165
+
156
166
  const filterOption =
157
- typeof filterOptionProp === 'function' ? filterOptionProp : defaultFilterOption
167
+ typeof filterOptionProp === 'function' ? filterOptionProp : DEFAULT_FILTER_OPTION
158
168
 
159
169
  // Element refs
160
170
  const rootElementRef = useRef<HTMLDivElement | null>(null)
@@ -186,7 +196,7 @@ const InnerAutocomplete = forwardRef(function InnerAutocomplete<
186
196
  const expanded = (query !== null && loading) || (focused && query !== null)
187
197
 
188
198
  const handleRootBlur = useCallback(
189
- (event: React.FocusEvent<HTMLInputElement>) => {
199
+ (event: FocusEvent<HTMLInputElement>) => {
190
200
  setTimeout(() => {
191
201
  // NOTE: This is a workaround for a bug that may happen in Chrome (clicking the scrollbar
192
202
  // closes the results in certain situations):
@@ -222,7 +232,7 @@ const InnerAutocomplete = forwardRef(function InnerAutocomplete<
222
232
  [onBlur, onQueryChange, relatedElements]
223
233
  )
224
234
 
225
- const handleRootFocus = useCallback((event: React.FocusEvent) => {
235
+ const handleRootFocus = useCallback((event: FocusEvent<HTMLDivElement>) => {
226
236
  const listBoxElement = listBoxElementRef.current
227
237
  const focusedElement = event.target instanceof HTMLElement ? event.target : null
228
238
  const listFocused = listBoxElement?.contains(focusedElement) || false
@@ -253,7 +263,7 @@ const InnerAutocomplete = forwardRef(function InnerAutocomplete<
253
263
  )
254
264
 
255
265
  const handleRootKeyDown = useCallback(
256
- (event: React.KeyboardEvent<HTMLElement>) => {
266
+ (event: KeyboardEvent<HTMLElement>) => {
257
267
  if (event.key === 'ArrowDown') {
258
268
  event.preventDefault()
259
269
 
@@ -316,7 +326,7 @@ const InnerAutocomplete = forwardRef(function InnerAutocomplete<
316
326
  )
317
327
 
318
328
  const handleInputChange = useCallback(
319
- (event: React.ChangeEvent<HTMLInputElement>) => {
329
+ (event: ChangeEvent<HTMLInputElement>) => {
320
330
  const nextQuery = event.currentTarget.value
321
331
 
322
332
  dispatch({type: 'input/change', query: nextQuery})
@@ -327,7 +337,7 @@ const InnerAutocomplete = forwardRef(function InnerAutocomplete<
327
337
  )
328
338
 
329
339
  const handleInputFocus = useCallback(
330
- (event: React.FocusEvent<HTMLInputElement>) => {
340
+ (event: FocusEvent<HTMLInputElement>) => {
331
341
  if (!focused) {
332
342
  dispatch({type: 'input/focus'})
333
343
 
@@ -439,24 +449,14 @@ const InnerAutocomplete = forwardRef(function InnerAutocomplete<
439
449
  }),
440
450
  [padding]
441
451
  )
442
- const openButtonPadding = useMemo(
443
- () =>
444
- padding.map((v) => {
445
- if (v === 0) return 0
446
- if (v === 1) return 0
447
- if (v === 2) return 1
448
-
449
- return v - 1
450
- }),
451
- [padding]
452
- )
452
+ const openButtonPadding = useMemo(() => padding.map((v) => Math.max(v - 1, 0)), [padding])
453
453
  const openButtonProps: AutocompleteOpenButtonProps = useMemo(
454
454
  () => (typeof openButton === 'object' ? openButton : EMPTY_RECORD),
455
455
  [openButton]
456
456
  )
457
457
 
458
458
  const handleOpenClick = useCallback(
459
- (event: React.MouseEvent<HTMLButtonElement>) => {
459
+ (event: MouseEvent<HTMLButtonElement>) => {
460
460
  dispatch({
461
461
  type: 'root/open',
462
462
  query: value ? renderValue(value, currentOption) : '',
@@ -545,7 +545,7 @@ const InnerAutocomplete = forwardRef(function InnerAutocomplete<
545
545
  )
546
546
 
547
547
  const handleListBoxKeyDown = useCallback(
548
- (event: React.KeyboardEvent<HTMLDivElement>) => {
548
+ (event: KeyboardEvent<HTMLDivElement>) => {
549
549
  // If the focus is currently in the list, move focus to the input element
550
550
  if (event.key === 'Tab') {
551
551
  if (listFocused) inputElementRef.current?.focus()
@@ -679,7 +679,7 @@ const InnerAutocomplete = forwardRef(function InnerAutocomplete<
679
679
  export const Autocomplete = InnerAutocomplete as <Option extends BaseAutocompleteOption>(
680
680
  props: AutocompleteProps<Option> &
681
681
  Omit<
682
- React.HTMLProps<HTMLInputElement>,
682
+ HTMLProps<HTMLInputElement>,
683
683
  | 'aria-activedescendant'
684
684
  | 'aria-autocomplete'
685
685
  | 'aria-expanded'
@@ -699,6 +699,6 @@ export const Autocomplete = InnerAutocomplete as <Option extends BaseAutocomplet
699
699
  | 'type'
700
700
  | 'value'
701
701
  > & {
702
- ref?: React.Ref<HTMLInputElement>
702
+ ref?: Ref<HTMLInputElement>
703
703
  }
704
- ) => React.ReactElement
704
+ ) => ReactElement
@@ -20,14 +20,14 @@ export const AUTOCOMPLETE_LISTBOX_IGNORE_KEYS = [
20
20
  /**
21
21
  * @internal
22
22
  */
23
- export const AUTOCOMPLETE_POPOVER_MARGINS: PopoverMargins = [0, 1, 1, 1]
23
+ export const AUTOCOMPLETE_POPOVER_MARGINS: PopoverMargins = [0, 1, 0, 0]
24
24
 
25
25
  /**
26
26
  * @internal
27
27
  */
28
- export const AUTOCOMPLETE_POPOVER_PLACEMENT: Placement = 'bottom-start'
28
+ export const AUTOCOMPLETE_POPOVER_PLACEMENT: Placement = 'bottom'
29
29
 
30
30
  /**
31
31
  * @internal
32
32
  */
33
- export const AUTOCOMPLETE_POPOVER_FALLBACK_PLACEMENTS: Placement[] = ['top-start']
33
+ export const AUTOCOMPLETE_POPOVER_FALLBACK_PLACEMENTS: Placement[] = ['bottom', 'top']
@@ -1,3 +1,5 @@
1
+ /** @jest-environment jsdom */
2
+
1
3
  /* eslint-disable no-console */
2
4
 
3
5
  import React, {useCallback, useMemo} from 'react'
@@ -1,3 +1,5 @@
1
+ /** @jest-environment jsdom */
2
+
1
3
  import {render} from '../../../test'
2
4
  import {ToastContext} from './toastContext'
3
5
  import {ToastContextValue} from './types'
package/src/constants.ts CHANGED
@@ -1,2 +1,19 @@
1
+ /**
2
+ * @internal
3
+ */
1
4
  export const EMPTY_ARRAY: any[] = []
5
+
6
+ /**
7
+ * @internal
8
+ */
2
9
  export const EMPTY_RECORD: Record<string, any> = {}
10
+
11
+ /**
12
+ * @internal
13
+ */
14
+ export const FLOATING_STATIC_SIDES: Record<string, 'bottom' | 'left' | 'top' | 'right'> = {
15
+ top: 'bottom',
16
+ right: 'left',
17
+ bottom: 'top',
18
+ left: 'right',
19
+ }
@@ -1,3 +1,5 @@
1
+ /** @jest-environment jsdom */
2
+
1
3
  import {axe} from 'jest-axe'
2
4
  import {render} from '../../../test'
3
5
  import {Badge} from './badge'
@@ -1,3 +1,5 @@
1
+ /** @jest-environment jsdom */
2
+
1
3
  import {AddIcon} from '@sanity/icons'
2
4
  import {screen} from '@testing-library/react'
3
5
  import {axe} from 'jest-axe'
@@ -49,6 +49,7 @@ export default function PlainStory() {
49
49
  fallbackPlacements={['top', 'bottom']}
50
50
  matchReferenceWidth={matchReferenceWidth}
51
51
  open={open}
52
+ overflow="auto"
52
53
  padding={padding}
53
54
  placement={placement}
54
55
  portal={portal}
@@ -40,6 +40,7 @@ export default function RightAlignedStory() {
40
40
  constrainSize={constrainSize}
41
41
  content={content}
42
42
  open={open}
43
+ overflow="auto"
43
44
  padding={3}
44
45
  portal
45
46
  placement="bottom"
@@ -61,6 +61,7 @@ export default function TestStory(): ReactElement {
61
61
  fallbackPlacements={['left', 'bottom', 'right', 'top']}
62
62
  matchReferenceWidth={matchReferenceWidth}
63
63
  open={open}
64
+ overflow="auto"
64
65
  padding={3}
65
66
  placement={placement}
66
67
  portal