@instructure/ui-menu 8.14.1-snapshot.7 → 8.15.1-snapshot.2

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/CHANGELOG.md CHANGED
@@ -3,6 +3,10 @@
3
3
  All notable changes to this project will be documented in this file.
4
4
  See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
5
5
 
6
+ # [8.15.0](https://github.com/instructure/instructure-ui/compare/v8.14.0...v8.15.0) (2022-01-26)
7
+
8
+ **Note:** Version bump only for package @instructure/ui-menu
9
+
6
10
  # [8.14.0](https://github.com/instructure/instructure-ui/compare/v8.13.0...v8.14.0) (2021-12-16)
7
11
 
8
12
  **Note:** Version bump only for package @instructure/ui-menu
@@ -25,7 +25,7 @@ var _dec, _dec2, _class, _class2, _temp;
25
25
  */
26
26
 
27
27
  /** @jsx jsx */
28
- import { Children, Component } from 'react';
28
+ import React, { Children, Component } from 'react';
29
29
  import { withStyle, jsx } from '@instructure/emotion';
30
30
  import { omitProps, safeCloneElement, matchComponentTypes } from '@instructure/ui-react-utils';
31
31
  import { uid } from '@instructure/uid';
@@ -163,6 +163,7 @@ let MenuItemGroup = (_dec = withStyle(generateStyle, generateComponentTheme), _d
163
163
  tabIndex: isTabbable && index === 0 ? 0 : -1,
164
164
  controls,
165
165
  value,
166
+ children: child.props.children,
166
167
  type: allowMultiple ? 'checkbox' : 'radio',
167
168
  ref: this.props.itemRef,
168
169
  disabled: disabled || child.props.disabled,
package/es/Menu/index.js CHANGED
@@ -292,6 +292,7 @@ let Menu = (_dec = withStyle(generateStyle, generateComponentTheme), _dec2 = tes
292
292
  role: "none"
293
293
  }, safeCloneElement(child, {
294
294
  controls,
295
+ children: child.props.children,
295
296
  disabled: disabled || child.props.disabled,
296
297
  onFocus: this.handleMenuItemFocus,
297
298
  onBlur: this.handleMenuItemBlur,
@@ -305,6 +306,7 @@ let Menu = (_dec = withStyle(generateStyle, generateComponentTheme), _dec2 = tes
305
306
  return jsx("li", {
306
307
  role: "none"
307
308
  }, safeCloneElement(child, {
309
+ label: child.props.label,
308
310
  controls,
309
311
  disabled: disabled || child.props.disabled,
310
312
  onFocus: this.handleMenuItemFocus,
@@ -1,5 +1,7 @@
1
1
  "use strict";
2
2
 
3
+ var _interopRequireWildcard = require("@babel/runtime/helpers/interopRequireWildcard").default;
4
+
3
5
  var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault").default;
4
6
 
5
7
  Object.defineProperty(exports, "__esModule", {
@@ -7,7 +9,7 @@ Object.defineProperty(exports, "__esModule", {
7
9
  });
8
10
  exports.default = exports.MenuItemGroup = void 0;
9
11
 
10
- var _react = require("react");
12
+ var _react = _interopRequireWildcard(require("react"));
11
13
 
12
14
  var _emotion = require("@instructure/emotion");
13
15
 
@@ -162,6 +164,7 @@ let MenuItemGroup = (_dec = (0, _emotion.withStyle)(_styles.default, _theme.defa
162
164
  tabIndex: isTabbable && index === 0 ? 0 : -1,
163
165
  controls,
164
166
  value,
167
+ children: child.props.children,
165
168
  type: allowMultiple ? 'checkbox' : 'radio',
166
169
  ref: this.props.itemRef,
167
170
  disabled: disabled || child.props.disabled,
package/lib/Menu/index.js CHANGED
@@ -314,6 +314,7 @@ let Menu = (_dec = (0, _emotion.withStyle)(_styles.default, _theme.default), _de
314
314
  role: "none"
315
315
  }, (0, _safeCloneElement.safeCloneElement)(child, {
316
316
  controls,
317
+ children: child.props.children,
317
318
  disabled: disabled || child.props.disabled,
318
319
  onFocus: this.handleMenuItemFocus,
319
320
  onBlur: this.handleMenuItemBlur,
@@ -327,6 +328,7 @@ let Menu = (_dec = (0, _emotion.withStyle)(_styles.default, _theme.default), _de
327
328
  return (0, _emotion.jsx)("li", {
328
329
  role: "none"
329
330
  }, (0, _safeCloneElement.safeCloneElement)(child, {
331
+ label: child.props.label,
330
332
  controls,
331
333
  disabled: disabled || child.props.disabled,
332
334
  onFocus: this.handleMenuItemFocus,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@instructure/ui-menu",
3
- "version": "8.14.1-snapshot.7+845d7ec6c",
3
+ "version": "8.15.1-snapshot.2+00f55c738",
4
4
  "description": "A dropdown menu component",
5
5
  "author": "Instructure, Inc. Engineering and Product Design",
6
6
  "type": "commonjs",
@@ -24,28 +24,28 @@
24
24
  },
25
25
  "license": "MIT",
26
26
  "devDependencies": {
27
- "@instructure/ui-babel-preset": "8.14.1-snapshot.7+845d7ec6c",
28
- "@instructure/ui-color-utils": "8.14.1-snapshot.7+845d7ec6c",
29
- "@instructure/ui-test-locator": "8.14.1-snapshot.7+845d7ec6c",
30
- "@instructure/ui-test-queries": "8.14.1-snapshot.7+845d7ec6c",
31
- "@instructure/ui-test-utils": "8.14.1-snapshot.7+845d7ec6c",
32
- "@instructure/ui-themes": "8.14.1-snapshot.7+845d7ec6c"
27
+ "@instructure/ui-babel-preset": "8.15.1-snapshot.2+00f55c738",
28
+ "@instructure/ui-color-utils": "8.15.1-snapshot.2+00f55c738",
29
+ "@instructure/ui-test-locator": "8.15.1-snapshot.2+00f55c738",
30
+ "@instructure/ui-test-queries": "8.15.1-snapshot.2+00f55c738",
31
+ "@instructure/ui-test-utils": "8.15.1-snapshot.2+00f55c738",
32
+ "@instructure/ui-themes": "8.15.1-snapshot.2+00f55c738"
33
33
  },
34
34
  "dependencies": {
35
35
  "@babel/runtime": "^7.13.10",
36
- "@instructure/console": "8.14.1-snapshot.7+845d7ec6c",
37
- "@instructure/emotion": "8.14.1-snapshot.7+845d7ec6c",
38
- "@instructure/shared-types": "8.14.1-snapshot.7+845d7ec6c",
39
- "@instructure/ui-a11y-utils": "8.14.1-snapshot.7+845d7ec6c",
40
- "@instructure/ui-dom-utils": "8.14.1-snapshot.7+845d7ec6c",
41
- "@instructure/ui-icons": "8.14.1-snapshot.7+845d7ec6c",
42
- "@instructure/ui-popover": "8.14.1-snapshot.7+845d7ec6c",
43
- "@instructure/ui-position": "8.14.1-snapshot.7+845d7ec6c",
44
- "@instructure/ui-prop-types": "8.14.1-snapshot.7+845d7ec6c",
45
- "@instructure/ui-react-utils": "8.14.1-snapshot.7+845d7ec6c",
46
- "@instructure/ui-testable": "8.14.1-snapshot.7+845d7ec6c",
47
- "@instructure/ui-utils": "8.14.1-snapshot.7+845d7ec6c",
48
- "@instructure/uid": "8.14.1-snapshot.7+845d7ec6c",
36
+ "@instructure/console": "8.15.1-snapshot.2+00f55c738",
37
+ "@instructure/emotion": "8.15.1-snapshot.2+00f55c738",
38
+ "@instructure/shared-types": "8.15.1-snapshot.2+00f55c738",
39
+ "@instructure/ui-a11y-utils": "8.15.1-snapshot.2+00f55c738",
40
+ "@instructure/ui-dom-utils": "8.15.1-snapshot.2+00f55c738",
41
+ "@instructure/ui-icons": "8.15.1-snapshot.2+00f55c738",
42
+ "@instructure/ui-popover": "8.15.1-snapshot.2+00f55c738",
43
+ "@instructure/ui-position": "8.15.1-snapshot.2+00f55c738",
44
+ "@instructure/ui-prop-types": "8.15.1-snapshot.2+00f55c738",
45
+ "@instructure/ui-react-utils": "8.15.1-snapshot.2+00f55c738",
46
+ "@instructure/ui-testable": "8.15.1-snapshot.2+00f55c738",
47
+ "@instructure/ui-utils": "8.15.1-snapshot.2+00f55c738",
48
+ "@instructure/uid": "8.15.1-snapshot.2+00f55c738",
49
49
  "keycode": "^2",
50
50
  "prop-types": "^15"
51
51
  },
@@ -56,5 +56,5 @@
56
56
  "access": "public"
57
57
  },
58
58
  "sideEffects": false,
59
- "gitHead": "845d7ec6c159d8946b22caa9d8fb3d0175167a6f"
59
+ "gitHead": "00f55c7382e82209ea553c107951c4356ba202bf"
60
60
  }
@@ -23,7 +23,7 @@
23
23
  */
24
24
 
25
25
  /** @jsx jsx */
26
- import { Children, Component, ReactElement } from 'react'
26
+ import React, { Children, Component } from 'react'
27
27
 
28
28
  import { withStyle, jsx } from '@instructure/emotion'
29
29
  import {
@@ -36,13 +36,21 @@ import { hasVisibleChildren } from '@instructure/ui-a11y-utils'
36
36
  import { testable } from '@instructure/ui-testable'
37
37
 
38
38
  import { MenuItem } from '../MenuItem'
39
+ import type { OnMenuItemSelect, MenuItemProps } from '../MenuItem/props'
40
+ import { MenuItemSeparator } from '../MenuItemSeparator'
41
+ import type { MenuSeparatorProps } from '../MenuItemSeparator/props'
39
42
 
40
43
  import generateStyle from './styles'
41
44
  import generateComponentTheme from './theme'
42
45
 
43
46
  import { propTypes, allowedProps } from './props'
44
47
  import type { MenuGroupProps, MenuGroupState } from './props'
45
- import type { OnMenuItemSelect, MenuItemProps } from '../MenuItem/props'
48
+
49
+ type MenuItemChild = React.ComponentElement<MenuItemProps, MenuItem>
50
+ type MenuSeparatorChild = React.ComponentElement<
51
+ MenuSeparatorProps,
52
+ MenuItemSeparator
53
+ >
46
54
 
47
55
  /**
48
56
  ---
@@ -147,9 +155,11 @@ class MenuItemGroup extends Component<MenuGroupProps, MenuGroupState> {
147
155
  const { children, allowMultiple } = props
148
156
  const selected: MenuGroupState['selected'] = []
149
157
 
150
- const items = Children.toArray(children).filter((child) => {
151
- return matchComponentTypes(child as MenuItem, [MenuItem])
152
- }) as MenuItem[]
158
+ const items = (
159
+ Children.toArray(children) as (MenuItemChild | MenuSeparatorChild)[]
160
+ ).filter((child) => {
161
+ return matchComponentTypes<MenuItemChild>(child, [MenuItem])
162
+ }) as MenuItemChild[]
153
163
 
154
164
  items.forEach((item, index) => {
155
165
  if (
@@ -189,21 +199,25 @@ class MenuItemGroup extends Component<MenuGroupProps, MenuGroupState> {
189
199
  renderChildren() {
190
200
  const { disabled, controls, allowMultiple, isTabbable, onMouseOver } =
191
201
  this.props
192
- const children = this.props.children as ReactElement[]
202
+ const children = this.props.children as (
203
+ | MenuItemChild
204
+ | MenuSeparatorChild
205
+ )[]
193
206
  let index = -1
194
207
 
195
208
  return Children.map(children, (child) => {
196
- if (matchComponentTypes(child, [MenuItem])) {
209
+ if (matchComponentTypes<MenuItemChild>(child, [MenuItem])) {
197
210
  ++index
198
211
  const value = child.props.value || index
199
212
 
200
213
  return (
201
214
  <li role="none">
202
215
  {' '}
203
- {safeCloneElement(child as ReactElement, {
216
+ {safeCloneElement(child, {
204
217
  tabIndex: isTabbable && index === 0 ? 0 : -1,
205
218
  controls,
206
219
  value,
220
+ children: child.props.children,
207
221
  type: allowMultiple ? 'checkbox' : 'radio',
208
222
  ref: this.props.itemRef,
209
223
  disabled: disabled || child.props.disabled,
@@ -73,7 +73,7 @@ type MenuGroupOwnProps = {
73
73
  /**
74
74
  * returns a reference to the `MenuItem`
75
75
  */
76
- itemRef?: (element: Element | null) => void
76
+ itemRef?: (element: MenuItem | null) => void
77
77
  disabled?: boolean
78
78
  /**
79
79
  * should the group appear in the tab order (the first item will have a tabIndex of 0)
@@ -37,9 +37,11 @@ import { testable } from '@instructure/ui-testable'
37
37
 
38
38
  import { MenuContext } from '../MenuContext'
39
39
  import { MenuItem } from './MenuItem'
40
- import type { OnMenuItemSelect, MenuItemProps } from './MenuItem/props'
40
+ import type { MenuItemProps } from './MenuItem/props'
41
41
  import { MenuItemGroup } from './MenuItemGroup'
42
+ import type { MenuGroupProps } from './MenuItemGroup/props'
42
43
  import { MenuItemSeparator } from './MenuItemSeparator'
44
+ import type { MenuSeparatorProps } from './MenuItemSeparator/props'
43
45
  import { withStyle, jsx } from '@instructure/emotion'
44
46
 
45
47
  import generateStyle from './styles'
@@ -48,6 +50,14 @@ import generateComponentTheme from './theme'
48
50
  import { propTypes, allowedProps } from './props'
49
51
  import type { MenuProps } from './props'
50
52
 
53
+ type MenuChild = React.ComponentElement<MenuProps, Menu>
54
+ type MenuItemChild = React.ComponentElement<MenuItemProps, MenuItem>
55
+ type MenuGroupChild = React.ComponentElement<MenuGroupProps, MenuItemGroup>
56
+ type MenuSeparatorChild = React.ComponentElement<
57
+ MenuSeparatorProps,
58
+ MenuItemSeparator
59
+ >
60
+
51
61
  /**
52
62
  ---
53
63
  category: components
@@ -182,7 +192,12 @@ class Menu extends Component<MenuProps> {
182
192
  }
183
193
  }
184
194
 
185
- handleMenuItemSelect: OnMenuItemSelect = (event, value, selected, item) => {
195
+ handleMenuItemSelect: MenuProps['onSelect'] = (
196
+ event,
197
+ value,
198
+ selected,
199
+ item
200
+ ) => {
186
201
  if (this.props.shouldHideOnSelect) {
187
202
  this.hide(event)
188
203
  }
@@ -220,7 +235,7 @@ class Menu extends Component<MenuProps> {
220
235
  }
221
236
 
222
237
  handleSubMenuDismiss = (
223
- event: React.MouseEvent | React.KeyboardEvent,
238
+ event: React.UIEvent | React.FocusEvent,
224
239
  documentClick: boolean
225
240
  ) => {
226
241
  if (
@@ -231,7 +246,7 @@ class Menu extends Component<MenuProps> {
231
246
  }
232
247
  }
233
248
 
234
- hide = (event: React.MouseEvent | React.KeyboardEvent) => {
249
+ hide = (event: React.UIEvent | React.FocusEvent) => {
235
250
  if (this._popover) {
236
251
  this._popover.hide(event)
237
252
  }
@@ -295,102 +310,111 @@ class Menu extends Component<MenuProps> {
295
310
 
296
311
  let count = 0
297
312
 
298
- return Children.map(children, (child) => {
299
- if (
300
- !matchComponentTypes(child, [
301
- 'MenuItemSeparator',
302
- 'MenuItem',
303
- 'MenuItemGroup',
304
- 'Menu'
305
- ])
306
- ) {
307
- return
308
- }
309
-
310
- count += 1
311
-
312
- const isTabbable = !this.state.hasFocus && count === 1
313
-
314
- if (matchComponentTypes(child, ['MenuItemSeparator'])) {
315
- return <li role="none">{child}</li>
316
- }
317
- const menuItemChild = child as MenuItem
318
-
319
- const controls =
320
- menuItemChild.props['aria-controls'] ||
321
- menuItemChild.props.controls ||
322
- this.props['aria-controls'] ||
323
- this.props.controls
324
-
325
- if (matchComponentTypes(child, ['MenuItem'])) {
326
- return (
327
- <li role="none">
328
- {safeCloneElement(
329
- child as ReactElement,
330
- {
313
+ return Children.map(
314
+ children as
315
+ | MenuChild
316
+ | MenuItemChild
317
+ | MenuGroupChild
318
+ | MenuSeparatorChild,
319
+ (child) => {
320
+ if (
321
+ !matchComponentTypes(child, [
322
+ 'MenuItemSeparator',
323
+ 'MenuItem',
324
+ 'MenuItemGroup',
325
+ 'Menu'
326
+ ])
327
+ ) {
328
+ return
329
+ }
330
+
331
+ count += 1
332
+
333
+ const isTabbable = !this.state.hasFocus && count === 1
334
+
335
+ if (
336
+ matchComponentTypes<MenuSeparatorChild>(child, ['MenuItemSeparator'])
337
+ ) {
338
+ return <li role="none">{child}</li>
339
+ }
340
+
341
+ const menuItemChild = child
342
+
343
+ const controls =
344
+ menuItemChild.props['aria-controls'] ||
345
+ menuItemChild.props.controls ||
346
+ this.props['aria-controls'] ||
347
+ this.props.controls
348
+
349
+ if (matchComponentTypes<MenuItemChild>(child, ['MenuItem'])) {
350
+ return (
351
+ <li role="none">
352
+ {safeCloneElement(child, {
331
353
  controls,
332
- disabled: disabled || (child as MenuItem).props.disabled,
354
+ children: child.props.children,
355
+ disabled: disabled || child.props.disabled,
333
356
  onFocus: this.handleMenuItemFocus,
334
357
  onBlur: this.handleMenuItemBlur,
335
358
  onSelect: this.handleMenuItemSelect,
336
359
  onMouseOver: this.handleMenuItemMouseOver,
337
360
  tabIndex: isTabbable ? 0 : -1
338
- } as Partial<MenuItemProps>
339
- )}
340
- </li>
341
- )
342
- }
343
-
344
- if (matchComponentTypes(child, ['MenuItemGroup'])) {
345
- return (
346
- <li role="none">
347
- {safeCloneElement(child as ReactElement, {
348
- controls,
349
- disabled: disabled || (child as MenuItemGroup).props.disabled,
350
- onFocus: this.handleMenuItemFocus,
351
- onBlur: this.handleMenuItemBlur,
352
- onSelect: this.handleMenuItemSelect,
353
- onMouseOver: this.handleMenuItemMouseOver,
354
- isTabbable
355
- })}
356
- </li>
357
- )
358
- }
359
-
360
- if (matchComponentTypes(child, ['Menu'])) {
361
- const submenuDisabled = disabled || (child as Menu).props.disabled
362
-
363
- return (
364
- <li role="none">
365
- {safeCloneElement(child as ReactElement, {
366
- type: 'flyout',
367
- controls,
368
- disabled: submenuDisabled,
369
- onSelect: this.handleMenuItemSelect,
370
- placement: 'end top',
371
- offsetX: -5,
372
- offsetY: 5,
373
- withArrow: false,
374
- onToggle: this.handleSubMenuToggle,
375
- onDismiss: this.handleSubMenuDismiss,
376
- trigger: (
377
- <MenuItem
378
- onMouseOver={this.handleMenuItemMouseOver}
379
- onFocus={this.handleMenuItemFocus}
380
- onBlur={this.handleMenuItemBlur}
381
- tabIndex={isTabbable ? 0 : -1}
382
- type="flyout"
383
- disabled={submenuDisabled}
384
- >
385
- {(child as Menu).props.title || (child as Menu).props.label}
386
- </MenuItem>
387
- )
388
- })}
389
- </li>
390
- )
361
+ })}
362
+ </li>
363
+ )
364
+ }
365
+
366
+ if (matchComponentTypes<MenuGroupChild>(child, ['MenuItemGroup'])) {
367
+ return (
368
+ <li role="none">
369
+ {safeCloneElement(child, {
370
+ label: child.props.label,
371
+ controls,
372
+ disabled: disabled || child.props.disabled,
373
+ onFocus: this.handleMenuItemFocus,
374
+ onBlur: this.handleMenuItemBlur,
375
+ onSelect: this.handleMenuItemSelect,
376
+ onMouseOver: this.handleMenuItemMouseOver,
377
+ isTabbable
378
+ })}
379
+ </li>
380
+ )
381
+ }
382
+
383
+ if (matchComponentTypes(child, ['Menu'])) {
384
+ const submenuDisabled = disabled || child.props.disabled
385
+
386
+ return (
387
+ <li role="none">
388
+ {safeCloneElement(child, {
389
+ type: 'flyout',
390
+ controls,
391
+ disabled: submenuDisabled,
392
+ onSelect: this.handleMenuItemSelect,
393
+ placement: 'end top',
394
+ offsetX: -5,
395
+ offsetY: 5,
396
+ withArrow: false,
397
+ onToggle: this.handleSubMenuToggle,
398
+ onDismiss: this.handleSubMenuDismiss,
399
+ trigger: (
400
+ <MenuItem
401
+ onMouseOver={this.handleMenuItemMouseOver}
402
+ onFocus={this.handleMenuItemFocus}
403
+ onBlur={this.handleMenuItemBlur}
404
+ tabIndex={isTabbable ? 0 : -1}
405
+ type="flyout"
406
+ disabled={submenuDisabled}
407
+ >
408
+ {child.props.title || child.props.label}
409
+ </MenuItem>
410
+ )
411
+ })}
412
+ </li>
413
+ )
414
+ }
415
+ return
391
416
  }
392
- return
393
- })
417
+ )
394
418
  }
395
419
 
396
420
  renderMenu() {
package/src/Menu/props.ts CHANGED
@@ -30,7 +30,6 @@ import {
30
30
  controllable,
31
31
  Children as ChildrenPropTypes
32
32
  } from '@instructure/ui-prop-types'
33
- import type { Menu } from './index'
34
33
 
35
34
  import type {
36
35
  PropValidators,
@@ -43,9 +42,12 @@ import type {
43
42
  PositionConstraint,
44
43
  PositionMountNode
45
44
  } from '@instructure/ui-position'
46
- import type { OnMenuItemSelect } from './MenuItem/props'
47
45
  import type { Popover } from '@instructure/ui-popover'
48
46
 
47
+ import { MenuItem } from './MenuItem'
48
+ import type { Menu } from './index'
49
+ import type { MenuItemProps } from './MenuItem/props'
50
+
49
51
  type MenuOwnProps = {
50
52
  /**
51
53
  * Children of type `Menu.Item`, `Menu.Group`, `Menu.Separator`, or `Menu`
@@ -83,7 +85,12 @@ type MenuOwnProps = {
83
85
  /**
84
86
  * Callback fired when an item within the `<Menu />` is selected
85
87
  */
86
- onSelect?: OnMenuItemSelect
88
+ onSelect?: (
89
+ e: React.MouseEvent,
90
+ value: MenuItemProps['value'] | MenuItemProps['value'][],
91
+ selected: MenuItemProps['selected'],
92
+ args: MenuItem
93
+ ) => void
87
94
  /**
88
95
  * If a trigger is supplied, callback fired when the `<Menu />` is closed
89
96
  */
@@ -161,7 +168,10 @@ type AllowedPropKeys = Readonly<Array<PropKeys>>
161
168
 
162
169
  type MenuProps = MenuOwnProps &
163
170
  WithStyleProps<MenuTheme, MenuStyle> &
164
- OtherHTMLAttributes<MenuOwnProps>
171
+ // controls can be passed in renderChildren and used later as aria-controls
172
+ Omit<OtherHTMLAttributes<MenuOwnProps>, 'controls'> & {
173
+ controls?: React.AriaAttributes['aria-controls']
174
+ }
165
175
 
166
176
  type MenuStyle = ComponentStyle<'menu'>
167
177