@fluentui/react-menu 0.0.0-nightly-20230109-0423.1 → 0.0.0-nightly-20230111-0423.1

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.json CHANGED
@@ -2,9 +2,9 @@
2
2
  "name": "@fluentui/react-menu",
3
3
  "entries": [
4
4
  {
5
- "date": "Mon, 09 Jan 2023 04:30:03 GMT",
6
- "tag": "@fluentui/react-menu_v0.0.0-nightly-20230109-0423.1",
7
- "version": "0.0.0-nightly-20230109-0423.1",
5
+ "date": "Wed, 11 Jan 2023 04:31:50 GMT",
6
+ "tag": "@fluentui/react-menu_v0.0.0-nightly-20230111-0423.1",
7
+ "version": "0.0.0-nightly-20230111-0423.1",
8
8
  "comments": {
9
9
  "prerelease": [
10
10
  {
@@ -16,62 +16,144 @@
16
16
  {
17
17
  "author": "beachball",
18
18
  "package": "@fluentui/react-menu",
19
- "comment": "Bump @fluentui/react-aria to v0.0.0-nightly-20230109-0423.1",
20
- "commit": "1e5c97a5b5d38645be89c0c493a50fd29b15d405"
19
+ "comment": "Bump @fluentui/react-aria to v0.0.0-nightly-20230111-0423.1",
20
+ "commit": "71fa585bf9e77adef73d7d3d8d84f53907a0785e"
21
21
  },
22
22
  {
23
23
  "author": "beachball",
24
24
  "package": "@fluentui/react-menu",
25
- "comment": "Bump @fluentui/keyboard-keys to v0.0.0-nightly-20230109-0423.1",
26
- "commit": "1e5c97a5b5d38645be89c0c493a50fd29b15d405"
25
+ "comment": "Bump @fluentui/keyboard-keys to v0.0.0-nightly-20230111-0423.1",
26
+ "commit": "71fa585bf9e77adef73d7d3d8d84f53907a0785e"
27
27
  },
28
28
  {
29
29
  "author": "beachball",
30
30
  "package": "@fluentui/react-menu",
31
- "comment": "Bump @fluentui/react-context-selector to v0.0.0-nightly-20230109-0423.1",
32
- "commit": "1e5c97a5b5d38645be89c0c493a50fd29b15d405"
31
+ "comment": "Bump @fluentui/react-context-selector to v0.0.0-nightly-20230111-0423.1",
32
+ "commit": "71fa585bf9e77adef73d7d3d8d84f53907a0785e"
33
33
  },
34
34
  {
35
35
  "author": "beachball",
36
36
  "package": "@fluentui/react-menu",
37
- "comment": "Bump @fluentui/react-portal to v0.0.0-nightly-20230109-0423.1",
38
- "commit": "1e5c97a5b5d38645be89c0c493a50fd29b15d405"
37
+ "comment": "Bump @fluentui/react-portal to v0.0.0-nightly-20230111-0423.1",
38
+ "commit": "71fa585bf9e77adef73d7d3d8d84f53907a0785e"
39
39
  },
40
40
  {
41
41
  "author": "beachball",
42
42
  "package": "@fluentui/react-menu",
43
- "comment": "Bump @fluentui/react-positioning to v0.0.0-nightly-20230109-0423.1",
44
- "commit": "1e5c97a5b5d38645be89c0c493a50fd29b15d405"
43
+ "comment": "Bump @fluentui/react-positioning to v0.0.0-nightly-20230111-0423.1",
44
+ "commit": "71fa585bf9e77adef73d7d3d8d84f53907a0785e"
45
45
  },
46
46
  {
47
47
  "author": "beachball",
48
48
  "package": "@fluentui/react-menu",
49
- "comment": "Bump @fluentui/react-shared-contexts to v0.0.0-nightly-20230109-0423.1",
50
- "commit": "1e5c97a5b5d38645be89c0c493a50fd29b15d405"
49
+ "comment": "Bump @fluentui/react-shared-contexts to v0.0.0-nightly-20230111-0423.1",
50
+ "commit": "71fa585bf9e77adef73d7d3d8d84f53907a0785e"
51
51
  },
52
52
  {
53
53
  "author": "beachball",
54
54
  "package": "@fluentui/react-menu",
55
- "comment": "Bump @fluentui/react-tabster to v0.0.0-nightly-20230109-0423.1",
56
- "commit": "1e5c97a5b5d38645be89c0c493a50fd29b15d405"
55
+ "comment": "Bump @fluentui/react-tabster to v0.0.0-nightly-20230111-0423.1",
56
+ "commit": "71fa585bf9e77adef73d7d3d8d84f53907a0785e"
57
57
  },
58
58
  {
59
59
  "author": "beachball",
60
60
  "package": "@fluentui/react-menu",
61
- "comment": "Bump @fluentui/react-theme to v0.0.0-nightly-20230109-0423.1",
62
- "commit": "1e5c97a5b5d38645be89c0c493a50fd29b15d405"
61
+ "comment": "Bump @fluentui/react-theme to v0.0.0-nightly-20230111-0423.1",
62
+ "commit": "71fa585bf9e77adef73d7d3d8d84f53907a0785e"
63
63
  },
64
64
  {
65
65
  "author": "beachball",
66
66
  "package": "@fluentui/react-menu",
67
- "comment": "Bump @fluentui/react-utilities to v0.0.0-nightly-20230109-0423.1",
68
- "commit": "1e5c97a5b5d38645be89c0c493a50fd29b15d405"
67
+ "comment": "Bump @fluentui/react-utilities to v0.0.0-nightly-20230111-0423.1",
68
+ "commit": "71fa585bf9e77adef73d7d3d8d84f53907a0785e"
69
69
  },
70
70
  {
71
71
  "author": "beachball",
72
72
  "package": "@fluentui/react-menu",
73
- "comment": "Bump @fluentui/react-conformance-griffel to v0.0.0-nightly-20230109-0423.1",
74
- "commit": "1e5c97a5b5d38645be89c0c493a50fd29b15d405"
73
+ "comment": "Bump @fluentui/react-conformance-griffel to v0.0.0-nightly-20230111-0423.1",
74
+ "commit": "71fa585bf9e77adef73d7d3d8d84f53907a0785e"
75
+ }
76
+ ]
77
+ }
78
+ },
79
+ {
80
+ "date": "Mon, 09 Jan 2023 21:51:23 GMT",
81
+ "tag": "@fluentui/react-menu_v9.6.1",
82
+ "version": "9.6.1",
83
+ "comments": {
84
+ "patch": [
85
+ {
86
+ "author": "lingfangao@hotmail.com",
87
+ "package": "@fluentui/react-menu",
88
+ "commit": "fb5708446f369a57f48b87a0141d6a651acddbde",
89
+ "comment": "revert: MenuItem root slot only supports div"
90
+ }
91
+ ]
92
+ }
93
+ },
94
+ {
95
+ "date": "Mon, 09 Jan 2023 14:34:57 GMT",
96
+ "tag": "@fluentui/react-menu_v9.6.0",
97
+ "version": "9.6.0",
98
+ "comments": {
99
+ "patch": [
100
+ {
101
+ "author": "lingfangao@hotmail.com",
102
+ "package": "@fluentui/react-menu",
103
+ "commit": "307d7988ee9c589c17dce78f1c36719c6ebb91c2",
104
+ "comment": "fix: MenuList props should win over context props"
105
+ }
106
+ ],
107
+ "minor": [
108
+ {
109
+ "author": "bernardo.sunderhus@gmail.com",
110
+ "package": "@fluentui/react-menu",
111
+ "commit": "26f0364b3837056ee8e0df42a7932c298c68290e",
112
+ "comment": "Stops using ARIAButton types for MenuItem root"
113
+ },
114
+ {
115
+ "author": "beachball",
116
+ "package": "@fluentui/react-menu",
117
+ "comment": "Bump @fluentui/react-aria to v9.3.5",
118
+ "commit": "d246e70eba59a37ec311dbf933b0745d34cb700d"
119
+ },
120
+ {
121
+ "author": "beachball",
122
+ "package": "@fluentui/react-menu",
123
+ "comment": "Bump @fluentui/react-context-selector to v9.1.5",
124
+ "commit": "d246e70eba59a37ec311dbf933b0745d34cb700d"
125
+ },
126
+ {
127
+ "author": "beachball",
128
+ "package": "@fluentui/react-menu",
129
+ "comment": "Bump @fluentui/react-portal to v9.1.0",
130
+ "commit": "d246e70eba59a37ec311dbf933b0745d34cb700d"
131
+ },
132
+ {
133
+ "author": "beachball",
134
+ "package": "@fluentui/react-menu",
135
+ "comment": "Bump @fluentui/react-positioning to v9.3.7",
136
+ "commit": "d246e70eba59a37ec311dbf933b0745d34cb700d"
137
+ },
138
+ {
139
+ "author": "beachball",
140
+ "package": "@fluentui/react-menu",
141
+ "comment": "Bump @fluentui/react-tabster to v9.3.6",
142
+ "commit": "d246e70eba59a37ec311dbf933b0745d34cb700d"
143
+ },
144
+ {
145
+ "author": "beachball",
146
+ "package": "@fluentui/react-menu",
147
+ "comment": "Bump @fluentui/react-utilities to v9.4.0",
148
+ "commit": "d246e70eba59a37ec311dbf933b0745d34cb700d"
149
+ }
150
+ ],
151
+ "none": [
152
+ {
153
+ "author": "martinhochel@microsoft.com",
154
+ "package": "@fluentui/react-menu",
155
+ "commit": "abae9f7a10d544d8d6b530b974fff235cfd2f956",
156
+ "comment": "chore: introduce more barrel file api within /scripts"
75
157
  }
76
158
  ]
77
159
  }
package/CHANGELOG.md CHANGED
@@ -1,27 +1,55 @@
1
1
  # Change Log - @fluentui/react-menu
2
2
 
3
- This log was last generated on Mon, 09 Jan 2023 04:30:03 GMT and should not be manually modified.
3
+ This log was last generated on Wed, 11 Jan 2023 04:31:50 GMT and should not be manually modified.
4
4
 
5
5
  <!-- Start content -->
6
6
 
7
- ## [0.0.0-nightly-20230109-0423.1](https://github.com/microsoft/fluentui/tree/@fluentui/react-menu_v0.0.0-nightly-20230109-0423.1)
7
+ ## [0.0.0-nightly-20230111-0423.1](https://github.com/microsoft/fluentui/tree/@fluentui/react-menu_v0.0.0-nightly-20230111-0423.1)
8
8
 
9
- Mon, 09 Jan 2023 04:30:03 GMT
10
- [Compare changes](https://github.com/microsoft/fluentui/compare/@fluentui/react-menu_v9.5.4..@fluentui/react-menu_v0.0.0-nightly-20230109-0423.1)
9
+ Wed, 11 Jan 2023 04:31:50 GMT
10
+ [Compare changes](https://github.com/microsoft/fluentui/compare/@fluentui/react-menu_v9.6.1..@fluentui/react-menu_v0.0.0-nightly-20230111-0423.1)
11
11
 
12
12
  ### Changes
13
13
 
14
14
  - Release nightly v9 ([commit](https://github.com/microsoft/fluentui/commit/not available) by fluentui-internal@service.microsoft.com)
15
- - Bump @fluentui/react-aria to v0.0.0-nightly-20230109-0423.1 ([commit](https://github.com/microsoft/fluentui/commit/1e5c97a5b5d38645be89c0c493a50fd29b15d405) by beachball)
16
- - Bump @fluentui/keyboard-keys to v0.0.0-nightly-20230109-0423.1 ([commit](https://github.com/microsoft/fluentui/commit/1e5c97a5b5d38645be89c0c493a50fd29b15d405) by beachball)
17
- - Bump @fluentui/react-context-selector to v0.0.0-nightly-20230109-0423.1 ([commit](https://github.com/microsoft/fluentui/commit/1e5c97a5b5d38645be89c0c493a50fd29b15d405) by beachball)
18
- - Bump @fluentui/react-portal to v0.0.0-nightly-20230109-0423.1 ([commit](https://github.com/microsoft/fluentui/commit/1e5c97a5b5d38645be89c0c493a50fd29b15d405) by beachball)
19
- - Bump @fluentui/react-positioning to v0.0.0-nightly-20230109-0423.1 ([commit](https://github.com/microsoft/fluentui/commit/1e5c97a5b5d38645be89c0c493a50fd29b15d405) by beachball)
20
- - Bump @fluentui/react-shared-contexts to v0.0.0-nightly-20230109-0423.1 ([commit](https://github.com/microsoft/fluentui/commit/1e5c97a5b5d38645be89c0c493a50fd29b15d405) by beachball)
21
- - Bump @fluentui/react-tabster to v0.0.0-nightly-20230109-0423.1 ([commit](https://github.com/microsoft/fluentui/commit/1e5c97a5b5d38645be89c0c493a50fd29b15d405) by beachball)
22
- - Bump @fluentui/react-theme to v0.0.0-nightly-20230109-0423.1 ([commit](https://github.com/microsoft/fluentui/commit/1e5c97a5b5d38645be89c0c493a50fd29b15d405) by beachball)
23
- - Bump @fluentui/react-utilities to v0.0.0-nightly-20230109-0423.1 ([commit](https://github.com/microsoft/fluentui/commit/1e5c97a5b5d38645be89c0c493a50fd29b15d405) by beachball)
24
- - Bump @fluentui/react-conformance-griffel to v0.0.0-nightly-20230109-0423.1 ([commit](https://github.com/microsoft/fluentui/commit/1e5c97a5b5d38645be89c0c493a50fd29b15d405) by beachball)
15
+ - Bump @fluentui/react-aria to v0.0.0-nightly-20230111-0423.1 ([commit](https://github.com/microsoft/fluentui/commit/71fa585bf9e77adef73d7d3d8d84f53907a0785e) by beachball)
16
+ - Bump @fluentui/keyboard-keys to v0.0.0-nightly-20230111-0423.1 ([commit](https://github.com/microsoft/fluentui/commit/71fa585bf9e77adef73d7d3d8d84f53907a0785e) by beachball)
17
+ - Bump @fluentui/react-context-selector to v0.0.0-nightly-20230111-0423.1 ([commit](https://github.com/microsoft/fluentui/commit/71fa585bf9e77adef73d7d3d8d84f53907a0785e) by beachball)
18
+ - Bump @fluentui/react-portal to v0.0.0-nightly-20230111-0423.1 ([commit](https://github.com/microsoft/fluentui/commit/71fa585bf9e77adef73d7d3d8d84f53907a0785e) by beachball)
19
+ - Bump @fluentui/react-positioning to v0.0.0-nightly-20230111-0423.1 ([commit](https://github.com/microsoft/fluentui/commit/71fa585bf9e77adef73d7d3d8d84f53907a0785e) by beachball)
20
+ - Bump @fluentui/react-shared-contexts to v0.0.0-nightly-20230111-0423.1 ([commit](https://github.com/microsoft/fluentui/commit/71fa585bf9e77adef73d7d3d8d84f53907a0785e) by beachball)
21
+ - Bump @fluentui/react-tabster to v0.0.0-nightly-20230111-0423.1 ([commit](https://github.com/microsoft/fluentui/commit/71fa585bf9e77adef73d7d3d8d84f53907a0785e) by beachball)
22
+ - Bump @fluentui/react-theme to v0.0.0-nightly-20230111-0423.1 ([commit](https://github.com/microsoft/fluentui/commit/71fa585bf9e77adef73d7d3d8d84f53907a0785e) by beachball)
23
+ - Bump @fluentui/react-utilities to v0.0.0-nightly-20230111-0423.1 ([commit](https://github.com/microsoft/fluentui/commit/71fa585bf9e77adef73d7d3d8d84f53907a0785e) by beachball)
24
+ - Bump @fluentui/react-conformance-griffel to v0.0.0-nightly-20230111-0423.1 ([commit](https://github.com/microsoft/fluentui/commit/71fa585bf9e77adef73d7d3d8d84f53907a0785e) by beachball)
25
+
26
+ ## [9.6.1](https://github.com/microsoft/fluentui/tree/@fluentui/react-menu_v9.6.1)
27
+
28
+ Mon, 09 Jan 2023 21:51:23 GMT
29
+ [Compare changes](https://github.com/microsoft/fluentui/compare/@fluentui/react-menu_v9.6.0..@fluentui/react-menu_v9.6.1)
30
+
31
+ ### Patches
32
+
33
+ - revert: MenuItem root slot only supports div ([PR #26261](https://github.com/microsoft/fluentui/pull/26261) by lingfangao@hotmail.com)
34
+
35
+ ## [9.6.0](https://github.com/microsoft/fluentui/tree/@fluentui/react-menu_v9.6.0)
36
+
37
+ Mon, 09 Jan 2023 14:34:57 GMT
38
+ [Compare changes](https://github.com/microsoft/fluentui/compare/@fluentui/react-menu_v9.5.4..@fluentui/react-menu_v9.6.0)
39
+
40
+ ### Minor changes
41
+
42
+ - Stops using ARIAButton types for MenuItem root ([PR #26257](https://github.com/microsoft/fluentui/pull/26257) by bernardo.sunderhus@gmail.com)
43
+ - Bump @fluentui/react-aria to v9.3.5 ([PR #26255](https://github.com/microsoft/fluentui/pull/26255) by beachball)
44
+ - Bump @fluentui/react-context-selector to v9.1.5 ([PR #26255](https://github.com/microsoft/fluentui/pull/26255) by beachball)
45
+ - Bump @fluentui/react-portal to v9.1.0 ([PR #26255](https://github.com/microsoft/fluentui/pull/26255) by beachball)
46
+ - Bump @fluentui/react-positioning to v9.3.7 ([PR #26255](https://github.com/microsoft/fluentui/pull/26255) by beachball)
47
+ - Bump @fluentui/react-tabster to v9.3.6 ([PR #26255](https://github.com/microsoft/fluentui/pull/26255) by beachball)
48
+ - Bump @fluentui/react-utilities to v9.4.0 ([PR #26255](https://github.com/microsoft/fluentui/pull/26255) by beachball)
49
+
50
+ ### Patches
51
+
52
+ - fix: MenuList props should win over context props ([PR #26252](https://github.com/microsoft/fluentui/pull/26252) by lingfangao@hotmail.com)
25
53
 
26
54
  ## [9.5.4](https://github.com/microsoft/fluentui/tree/@fluentui/react-menu_v9.5.4)
27
55
 
package/dist/index.d.ts CHANGED
@@ -1,8 +1,7 @@
1
1
  /// <reference types="react" />
2
2
 
3
- import type { ARIAButtonElement } from '@fluentui/react-aria';
3
+ import { ARIAButtonElement } from '@fluentui/react-aria';
4
4
  import { ARIAButtonResultProps } from '@fluentui/react-aria';
5
- import type { ARIAButtonSlotProps } from '@fluentui/react-aria';
6
5
  import { ARIAButtonType } from '@fluentui/react-aria';
7
6
  import type { ComponentProps } from '@fluentui/react-utilities';
8
7
  import type { ComponentState } from '@fluentui/react-utilities';
@@ -148,6 +147,12 @@ export declare type MenuItemProps = ComponentProps<Partial<MenuItemSlots>> & {
148
147
  * @default false
149
148
  */
150
149
  persistOnClick?: boolean;
150
+ disabled?: boolean;
151
+ /**
152
+ * @deprecated this property does nothing.
153
+ * disabled focusable is by default by simply using `disabled` property
154
+ */
155
+ disabledFocusable?: boolean;
151
156
  };
152
157
 
153
158
  /**
@@ -188,7 +193,7 @@ export declare type MenuItemSelectableState = MenuItemSelectableProps & {
188
193
  };
189
194
 
190
195
  export declare type MenuItemSlots = {
191
- root: Slot<ARIAButtonSlotProps<'div'>>;
196
+ root: Slot<'div'>;
192
197
  /**
193
198
  * Icon slot rendered before children content
194
199
  */
@@ -213,9 +218,7 @@ export declare type MenuItemSlots = {
213
218
  secondaryContent?: Slot<'span'>;
214
219
  };
215
220
 
216
- export declare type MenuItemState = ComponentState<MenuItemSlots> & Required<Pick<MenuItemProps, 'disabled' | 'hasSubmenu' | 'persistOnClick'>> & {
217
- isNativeButton: boolean;
218
- };
221
+ export declare type MenuItemState = ComponentState<MenuItemSlots> & Required<Pick<MenuItemProps, 'disabled' | 'hasSubmenu' | 'persistOnClick'>>;
219
222
 
220
223
  /**
221
224
  * Define a styled MenuList, using the `useMenuList_unstable` hook.
@@ -279,7 +282,7 @@ export declare type MenuListSlots = {
279
282
  root: Slot<'div'>;
280
283
  };
281
284
 
282
- export declare type MenuListState = ComponentState<MenuListSlots> & Required<Pick<MenuListProps, 'checkedValues' | 'hasCheckmarks' | 'hasIcons'>> & {
285
+ export declare type MenuListState = ComponentState<MenuListSlots> & Required<Pick<MenuListProps, 'checkedValues' | 'hasCheckmarks' | 'hasIcons'>> & Pick<MenuListProps, 'defaultCheckedValues' | 'onCheckedValueChange'> & {
283
286
  /**
284
287
  * Selects a radio item, will de-select the currently selected ratio item
285
288
  */
@@ -289,21 +292,6 @@ export declare type MenuListState = ComponentState<MenuListSlots> & Required<Pic
289
292
  */
290
293
  setFocusByFirstCharacter: NonNullable<MenuListContextValue['setFocusByFirstCharacter']>;
291
294
  toggleCheckbox: SelectableHandler;
292
- /**
293
- * Default values to be checked on mount
294
- * @deprecated this property is not used internally anymore,
295
- * the signature remains just to avoid breaking changes
296
- */
297
- defaultCheckedValues?: Record<string, string[]>;
298
- /**
299
- * Callback when checked items change for value with a name
300
- *
301
- * @param event - React's original SyntheticEvent
302
- * @param data - A data object with relevant information
303
- * @deprecated this property is not used internally anymore,
304
- * the signature remains just to avoid breaking changes
305
- */
306
- onCheckedValueChange?: (e: MenuCheckedValueChangeEvent, data: MenuCheckedValueChangeData) => void;
307
295
  };
308
296
 
309
297
  /**
@@ -7,7 +7,6 @@ import { useFocusFinders } from '@fluentui/react-tabster';
7
7
  import { useMenuContext_unstable } from '../../contexts/menuContext';
8
8
  import { MENU_ENTER_EVENT, useOnMenuMouseEnter } from '../../utils/index';
9
9
  import { useIsSubmenu } from '../../utils/useIsSubmenu';
10
- import { Tab } from '@fluentui/keyboard-keys';
11
10
  /**
12
11
  * Create the state required to render Menu.
13
12
  *
@@ -138,8 +137,6 @@ const useMenuOpenState = state => {
138
137
  return (_a = state.onOpenChange) === null || _a === void 0 ? void 0 : _a.call(state, e, data);
139
138
  });
140
139
  const shouldHandleCloseRef = React.useRef(false);
141
- const shouldHandleTabRef = React.useRef(false);
142
- const pressedShiftRef = React.useRef(false);
143
140
  const setOpenTimeout = React.useRef(0);
144
141
  const enteringTriggerRef = React.useRef(false);
145
142
  const [open, setOpenState] = useControllableState({
@@ -159,12 +156,6 @@ const useMenuOpenState = state => {
159
156
  state.setContextTarget(undefined);
160
157
  shouldHandleCloseRef.current = true;
161
158
  }
162
- if (e.type === 'keydown') {
163
- if (e.key === Tab) {
164
- shouldHandleTabRef.current = true;
165
- pressedShiftRef.current = e.shiftKey;
166
- }
167
- }
168
159
  if (data.bubble) {
169
160
  parentSetOpen(e, {
170
161
  ...data
@@ -240,39 +231,29 @@ const useMenuOpenState = state => {
240
231
  }, []);
241
232
  // Manage focus for open state
242
233
  const {
243
- findFirstFocusable,
244
- findNextFocusable,
245
- findPrevFocusable
234
+ findFirstFocusable
246
235
  } = useFocusFinders();
247
236
  const focusFirst = React.useCallback(() => {
248
237
  const firstFocusable = findFirstFocusable(state.menuPopoverRef.current);
249
238
  firstFocusable === null || firstFocusable === void 0 ? void 0 : firstFocusable.focus();
250
239
  }, [findFirstFocusable, state.menuPopoverRef]);
251
- const focusAfterMenuTrigger = React.useCallback(() => {
252
- const nextFocusable = findNextFocusable(state.triggerRef.current);
253
- nextFocusable === null || nextFocusable === void 0 ? void 0 : nextFocusable.focus();
254
- }, [findNextFocusable, state.triggerRef]);
255
- const focusBeforeMenuTrigger = React.useCallback(() => {
256
- const prevFocusable = findPrevFocusable(state.triggerRef.current);
257
- prevFocusable === null || prevFocusable === void 0 ? void 0 : prevFocusable.focus();
258
- }, [findPrevFocusable, state.triggerRef]);
259
240
  React.useEffect(() => {
260
241
  var _a;
261
242
  if (open) {
262
243
  focusFirst();
263
244
  } else {
264
245
  if (shouldHandleCloseRef.current) {
265
- if (shouldHandleTabRef.current && !state.isSubmenu) {
266
- pressedShiftRef.current ? focusBeforeMenuTrigger() : focusAfterMenuTrigger();
267
- } else {
268
- (_a = state.triggerRef.current) === null || _a === void 0 ? void 0 : _a.focus();
269
- }
246
+ // We know that React effects are sync so we focus the trigger here
247
+ // after any event handler (event handlers will update state and re-render).
248
+ // Since the browser only performs the default behaviour for the Tab key once
249
+ // keyboard events have fully bubbled up the window, the browser will move
250
+ // focus to the next tabbable element before/after the trigger if needed.
251
+ // If the Tab key was not pressed, focus will remain on the trigger as expected.
252
+ (_a = state.triggerRef.current) === null || _a === void 0 ? void 0 : _a.focus();
270
253
  }
271
254
  }
272
255
  shouldHandleCloseRef.current = false;
273
- shouldHandleTabRef.current = false;
274
- pressedShiftRef.current = false;
275
- }, [state.triggerRef, state.isSubmenu, open, focusFirst, focusAfterMenuTrigger, focusBeforeMenuTrigger]);
256
+ }, [state.triggerRef, state.isSubmenu, open, focusFirst]);
276
257
  return [open, setOpen];
277
258
  };
278
259
  //# sourceMappingURL=useMenu.js.map
@@ -1 +1 @@
1
- {"version":3,"mappings":"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","names":["React","usePositioningMouseTarget","usePositioning","resolvePositioningShorthand","useControllableState","useId","useOnClickOutside","useEventCallback","useOnScrollOutside","useFluent_unstable","useFluent","elementContains","useFocusFinders","useMenuContext_unstable","MENU_ENTER_EVENT","useOnMenuMouseEnter","useIsSubmenu","Tab","useMenu_unstable","props","isSubmenu","hoverDelay","inline","hasCheckmarks","hasIcons","closeOnScroll","openOnContext","persistOnItemClick","openOnHover","defaultCheckedValues","triggerId","contextTarget","setContextTarget","positioningState","position","align","target","undefined","positioning","children","Children","toArray","process","env","NODE_ENV","length","console","warn","menuTrigger","menuPopover","targetRef","triggerRef","containerRef","menuPopoverRef","open","setOpen","useMenuOpenState","defaultOpen","onOpenChange","checkedValues","onCheckedValueChange","useMenuSelectableState","components","setCheckedValues","state","defaultState","initialState","e","name","checkedItems","currentValue","targetDocument","parentSetOpen","context","data","shouldHandleCloseRef","useRef","shouldHandleTabRef","pressedShiftRef","setOpenTimeout","enteringTriggerRef","setOpenState","trySetOpen","event","CustomEvent","type","detail","nativeEvent","current","key","shiftKey","bubble","clearTimeout","Event","persist","contains","setTimeout","disabled","element","refs","filter","Boolean","callback","useEffect","findFirstFocusable","findNextFocusable","findPrevFocusable","focusFirst","useCallback","firstFocusable","focus","focusAfterMenuTrigger","nextFocusable","focusBeforeMenuTrigger","prevFocusable"],"sourceRoot":"","sources":["../../../../../../../../../packages/react-components/react-menu/src/components/Menu/useMenu.tsx"],"sourcesContent":["import * as React from 'react';\nimport { usePositioningMouseTarget, usePositioning, resolvePositioningShorthand } from '@fluentui/react-positioning';\nimport {\n useControllableState,\n useId,\n useOnClickOutside,\n useEventCallback,\n useOnScrollOutside,\n} from '@fluentui/react-utilities';\nimport { useFluent_unstable as useFluent } from '@fluentui/react-shared-contexts';\nimport { elementContains } from '@fluentui/react-portal';\nimport { useFocusFinders } from '@fluentui/react-tabster';\nimport { useMenuContext_unstable } from '../../contexts/menuContext';\nimport { MENU_ENTER_EVENT, useOnMenuMouseEnter } from '../../utils/index';\nimport { useIsSubmenu } from '../../utils/useIsSubmenu';\nimport type { MenuOpenChangeData, MenuOpenEvent, MenuProps, MenuState } from './Menu.types';\nimport { Tab } from '@fluentui/keyboard-keys';\n\n/**\n * Create the state required to render Menu.\n *\n * The returned state can be modified with hooks such as useMenuStyles,\n * before being passed to renderMenu_unstable.\n *\n * @param props - props from this instance of Menu\n */\nexport const useMenu_unstable = (props: MenuProps): MenuState => {\n const isSubmenu = useIsSubmenu();\n const {\n hoverDelay = 500,\n inline = false,\n hasCheckmarks = false,\n hasIcons = false,\n closeOnScroll = false,\n openOnContext = false,\n persistOnItemClick = false,\n openOnHover = isSubmenu,\n defaultCheckedValues,\n } = props;\n const triggerId = useId('menu');\n const [contextTarget, setContextTarget] = usePositioningMouseTarget();\n\n const positioningState = {\n position: isSubmenu ? 'after' : 'below',\n align: isSubmenu ? 'top' : 'start',\n target: props.openOnContext ? contextTarget : undefined,\n ...resolvePositioningShorthand(props.positioning),\n } as const;\n\n const children = React.Children.toArray(props.children) as React.ReactElement[];\n\n if (process.env.NODE_ENV !== 'production') {\n if (children.length === 0) {\n // eslint-disable-next-line no-console\n console.warn('Menu must contain at least one child');\n }\n\n if (children.length > 2) {\n // eslint-disable-next-line no-console\n console.warn('Menu must contain at most two children');\n }\n }\n\n let menuTrigger: React.ReactElement | undefined = undefined;\n let menuPopover: React.ReactElement | undefined = undefined;\n if (children.length === 2) {\n menuTrigger = children[0];\n menuPopover = children[1];\n } else if (children.length === 1) {\n menuPopover = children[0];\n }\n\n const { targetRef: triggerRef, containerRef: menuPopoverRef } = usePositioning(positioningState);\n\n // TODO Better way to narrow types ?\n const [open, setOpen] = useMenuOpenState({\n hoverDelay,\n isSubmenu,\n setContextTarget,\n closeOnScroll,\n menuPopoverRef,\n triggerRef,\n open: props.open,\n defaultOpen: props.defaultOpen,\n onOpenChange: props.onOpenChange,\n openOnContext,\n });\n\n const [checkedValues, onCheckedValueChange] = useMenuSelectableState({\n checkedValues: props.checkedValues,\n defaultCheckedValues,\n onCheckedValueChange: props.onCheckedValueChange,\n });\n\n return {\n inline,\n hoverDelay,\n triggerId,\n isSubmenu,\n openOnHover,\n contextTarget,\n setContextTarget,\n hasCheckmarks,\n hasIcons,\n closeOnScroll,\n menuTrigger,\n menuPopover,\n triggerRef,\n menuPopoverRef,\n components: {},\n openOnContext,\n open,\n setOpen,\n checkedValues,\n onCheckedValueChange,\n persistOnItemClick,\n };\n};\n\n/**\n * Adds appropriate state values and handlers for selectable items\n * i.e checkboxes and radios\n */\nconst useMenuSelectableState = (\n props: Pick<MenuProps, 'checkedValues' | 'defaultCheckedValues' | 'onCheckedValueChange'>,\n) => {\n const [checkedValues, setCheckedValues] = useControllableState({\n state: props.checkedValues,\n defaultState: props.defaultCheckedValues,\n initialState: {},\n });\n const onCheckedValueChange: MenuState['onCheckedValueChange'] = useEventCallback((e, { name, checkedItems }) => {\n props.onCheckedValueChange?.(e, { name, checkedItems });\n\n setCheckedValues(currentValue => ({\n ...currentValue,\n [name]: checkedItems,\n }));\n });\n\n return [checkedValues, onCheckedValueChange] as const;\n};\n\nconst useMenuOpenState = (\n state: Pick<\n MenuState,\n | 'isSubmenu'\n | 'menuPopoverRef'\n | 'setContextTarget'\n | 'triggerRef'\n | 'openOnContext'\n | 'closeOnScroll'\n | 'hoverDelay'\n > &\n Pick<MenuProps, 'open' | 'defaultOpen' | 'onOpenChange'>,\n) => {\n const { targetDocument } = useFluent();\n const parentSetOpen = useMenuContext_unstable(context => context.setOpen);\n const onOpenChange: MenuProps['onOpenChange'] = useEventCallback((e, data) => state.onOpenChange?.(e, data));\n\n const shouldHandleCloseRef = React.useRef(false);\n const shouldHandleTabRef = React.useRef(false);\n const pressedShiftRef = React.useRef(false);\n const setOpenTimeout = React.useRef(0);\n const enteringTriggerRef = React.useRef(false);\n\n const [open, setOpenState] = useControllableState({\n state: state.open,\n defaultState: state.defaultOpen,\n initialState: false,\n });\n\n const trySetOpen = useEventCallback((e: MenuOpenEvent, data: MenuOpenChangeData) => {\n const event = e instanceof CustomEvent && e.type === MENU_ENTER_EVENT ? e.detail.nativeEvent : e;\n onOpenChange?.(event, { ...data });\n if (data.open && e.type === 'contextmenu') {\n state.setContextTarget(e as React.MouseEvent);\n }\n\n if (!data.open) {\n state.setContextTarget(undefined);\n shouldHandleCloseRef.current = true;\n }\n\n if (e.type === 'keydown') {\n if ((e as React.KeyboardEvent<HTMLElement>).key === Tab) {\n shouldHandleTabRef.current = true;\n pressedShiftRef.current = (e as React.KeyboardEvent<HTMLElement>).shiftKey;\n }\n }\n\n if (data.bubble) {\n parentSetOpen(e, { ...data });\n }\n\n setOpenState(data.open);\n });\n\n const setOpen = useEventCallback((e: MenuOpenEvent, data: MenuOpenChangeData) => {\n clearTimeout(setOpenTimeout.current);\n if (!(e instanceof Event) && e.persist) {\n // < React 17 still uses pooled synthetic events\n e.persist();\n }\n\n if (e.type === 'mouseleave' || e.type === 'mouseenter' || e.type === 'mousemove' || e.type === MENU_ENTER_EVENT) {\n if (state.triggerRef.current?.contains(e.target as HTMLElement)) {\n enteringTriggerRef.current = e.type === 'mouseenter' || e.type === 'mousemove';\n }\n\n // FIXME leaking Node timeout type\n // eslint-disable-next-line @typescript-eslint/ban-ts-comment\n // @ts-ignore\n setOpenTimeout.current = setTimeout(() => trySetOpen(e, data), state.hoverDelay);\n } else {\n trySetOpen(e, data);\n }\n });\n\n useOnClickOutside({\n contains: elementContains,\n disabled: !open,\n element: targetDocument,\n refs: [state.menuPopoverRef, !state.openOnContext && state.triggerRef].filter(\n Boolean,\n ) as React.MutableRefObject<HTMLElement>[],\n callback: event => setOpen(event, { open: false, type: 'clickOutside', event }),\n });\n\n // only close on scroll for context, or when closeOnScroll is specified\n const closeOnScroll = state.openOnContext || state.closeOnScroll;\n useOnScrollOutside({\n contains: elementContains,\n element: targetDocument,\n callback: event => setOpen(event, { open: false, type: 'scrollOutside', event }),\n refs: [state.menuPopoverRef, !state.openOnContext && state.triggerRef].filter(\n Boolean,\n ) as React.MutableRefObject<HTMLElement>[],\n disabled: !open || !closeOnScroll,\n });\n\n useOnMenuMouseEnter({\n element: targetDocument,\n callback: event => {\n // When moving from a menu directly back to its trigger, this handler can close the menu\n // Explicitly check a flag to see if this situation happens\n if (!enteringTriggerRef.current) {\n setOpen(event, { open: false, type: 'menuMouseEnter', event });\n }\n },\n disabled: !open,\n refs: [state.menuPopoverRef],\n });\n\n // Clear timeout on unmount\n // Setting state after a component unmounts can cause memory leaks\n React.useEffect(() => {\n return () => {\n clearTimeout(setOpenTimeout.current);\n };\n }, []);\n\n // Manage focus for open state\n const { findFirstFocusable, findNextFocusable, findPrevFocusable } = useFocusFinders();\n const focusFirst = React.useCallback(() => {\n const firstFocusable = findFirstFocusable(state.menuPopoverRef.current);\n firstFocusable?.focus();\n }, [findFirstFocusable, state.menuPopoverRef]);\n\n const focusAfterMenuTrigger = React.useCallback(() => {\n const nextFocusable = findNextFocusable(state.triggerRef.current);\n nextFocusable?.focus();\n }, [findNextFocusable, state.triggerRef]);\n\n const focusBeforeMenuTrigger = React.useCallback(() => {\n const prevFocusable = findPrevFocusable(state.triggerRef.current);\n prevFocusable?.focus();\n }, [findPrevFocusable, state.triggerRef]);\n\n React.useEffect(() => {\n if (open) {\n focusFirst();\n } else {\n if (shouldHandleCloseRef.current) {\n if (shouldHandleTabRef.current && !state.isSubmenu) {\n pressedShiftRef.current ? focusBeforeMenuTrigger() : focusAfterMenuTrigger();\n } else {\n state.triggerRef.current?.focus();\n }\n }\n }\n\n shouldHandleCloseRef.current = false;\n shouldHandleTabRef.current = false;\n pressedShiftRef.current = false;\n }, [state.triggerRef, state.isSubmenu, open, focusFirst, focusAfterMenuTrigger, focusBeforeMenuTrigger]);\n\n return [open, setOpen] as const;\n};\n"]}
1
+ {"version":3,"mappings":"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","names":["React","usePositioningMouseTarget","usePositioning","resolvePositioningShorthand","useControllableState","useId","useOnClickOutside","useEventCallback","useOnScrollOutside","useFluent_unstable","useFluent","elementContains","useFocusFinders","useMenuContext_unstable","MENU_ENTER_EVENT","useOnMenuMouseEnter","useIsSubmenu","useMenu_unstable","props","isSubmenu","hoverDelay","inline","hasCheckmarks","hasIcons","closeOnScroll","openOnContext","persistOnItemClick","openOnHover","defaultCheckedValues","triggerId","contextTarget","setContextTarget","positioningState","position","align","target","undefined","positioning","children","Children","toArray","process","env","NODE_ENV","length","console","warn","menuTrigger","menuPopover","targetRef","triggerRef","containerRef","menuPopoverRef","open","setOpen","useMenuOpenState","defaultOpen","onOpenChange","checkedValues","onCheckedValueChange","useMenuSelectableState","components","setCheckedValues","state","defaultState","initialState","e","name","checkedItems","currentValue","targetDocument","parentSetOpen","context","data","shouldHandleCloseRef","useRef","setOpenTimeout","enteringTriggerRef","setOpenState","trySetOpen","event","CustomEvent","type","detail","nativeEvent","current","bubble","clearTimeout","Event","persist","contains","setTimeout","disabled","element","refs","filter","Boolean","callback","useEffect","findFirstFocusable","focusFirst","useCallback","firstFocusable","focus"],"sourceRoot":"","sources":["../../../../../../../../../packages/react-components/react-menu/src/components/Menu/useMenu.tsx"],"sourcesContent":["import * as React from 'react';\nimport { usePositioningMouseTarget, usePositioning, resolvePositioningShorthand } from '@fluentui/react-positioning';\nimport {\n useControllableState,\n useId,\n useOnClickOutside,\n useEventCallback,\n useOnScrollOutside,\n} from '@fluentui/react-utilities';\nimport { useFluent_unstable as useFluent } from '@fluentui/react-shared-contexts';\nimport { elementContains } from '@fluentui/react-portal';\nimport { useFocusFinders } from '@fluentui/react-tabster';\nimport { useMenuContext_unstable } from '../../contexts/menuContext';\nimport { MENU_ENTER_EVENT, useOnMenuMouseEnter } from '../../utils/index';\nimport { useIsSubmenu } from '../../utils/useIsSubmenu';\nimport type { MenuOpenChangeData, MenuOpenEvent, MenuProps, MenuState } from './Menu.types';\n\n/**\n * Create the state required to render Menu.\n *\n * The returned state can be modified with hooks such as useMenuStyles,\n * before being passed to renderMenu_unstable.\n *\n * @param props - props from this instance of Menu\n */\nexport const useMenu_unstable = (props: MenuProps): MenuState => {\n const isSubmenu = useIsSubmenu();\n const {\n hoverDelay = 500,\n inline = false,\n hasCheckmarks = false,\n hasIcons = false,\n closeOnScroll = false,\n openOnContext = false,\n persistOnItemClick = false,\n openOnHover = isSubmenu,\n defaultCheckedValues,\n } = props;\n const triggerId = useId('menu');\n const [contextTarget, setContextTarget] = usePositioningMouseTarget();\n\n const positioningState = {\n position: isSubmenu ? 'after' : 'below',\n align: isSubmenu ? 'top' : 'start',\n target: props.openOnContext ? contextTarget : undefined,\n ...resolvePositioningShorthand(props.positioning),\n } as const;\n\n const children = React.Children.toArray(props.children) as React.ReactElement[];\n\n if (process.env.NODE_ENV !== 'production') {\n if (children.length === 0) {\n // eslint-disable-next-line no-console\n console.warn('Menu must contain at least one child');\n }\n\n if (children.length > 2) {\n // eslint-disable-next-line no-console\n console.warn('Menu must contain at most two children');\n }\n }\n\n let menuTrigger: React.ReactElement | undefined = undefined;\n let menuPopover: React.ReactElement | undefined = undefined;\n if (children.length === 2) {\n menuTrigger = children[0];\n menuPopover = children[1];\n } else if (children.length === 1) {\n menuPopover = children[0];\n }\n\n const { targetRef: triggerRef, containerRef: menuPopoverRef } = usePositioning(positioningState);\n\n // TODO Better way to narrow types ?\n const [open, setOpen] = useMenuOpenState({\n hoverDelay,\n isSubmenu,\n setContextTarget,\n closeOnScroll,\n menuPopoverRef,\n triggerRef,\n open: props.open,\n defaultOpen: props.defaultOpen,\n onOpenChange: props.onOpenChange,\n openOnContext,\n });\n\n const [checkedValues, onCheckedValueChange] = useMenuSelectableState({\n checkedValues: props.checkedValues,\n defaultCheckedValues,\n onCheckedValueChange: props.onCheckedValueChange,\n });\n\n return {\n inline,\n hoverDelay,\n triggerId,\n isSubmenu,\n openOnHover,\n contextTarget,\n setContextTarget,\n hasCheckmarks,\n hasIcons,\n closeOnScroll,\n menuTrigger,\n menuPopover,\n triggerRef,\n menuPopoverRef,\n components: {},\n openOnContext,\n open,\n setOpen,\n checkedValues,\n onCheckedValueChange,\n persistOnItemClick,\n };\n};\n\n/**\n * Adds appropriate state values and handlers for selectable items\n * i.e checkboxes and radios\n */\nconst useMenuSelectableState = (\n props: Pick<MenuProps, 'checkedValues' | 'defaultCheckedValues' | 'onCheckedValueChange'>,\n) => {\n const [checkedValues, setCheckedValues] = useControllableState({\n state: props.checkedValues,\n defaultState: props.defaultCheckedValues,\n initialState: {},\n });\n const onCheckedValueChange: MenuState['onCheckedValueChange'] = useEventCallback((e, { name, checkedItems }) => {\n props.onCheckedValueChange?.(e, { name, checkedItems });\n\n setCheckedValues(currentValue => ({\n ...currentValue,\n [name]: checkedItems,\n }));\n });\n\n return [checkedValues, onCheckedValueChange] as const;\n};\n\nconst useMenuOpenState = (\n state: Pick<\n MenuState,\n | 'isSubmenu'\n | 'menuPopoverRef'\n | 'setContextTarget'\n | 'triggerRef'\n | 'openOnContext'\n | 'closeOnScroll'\n | 'hoverDelay'\n > &\n Pick<MenuProps, 'open' | 'defaultOpen' | 'onOpenChange'>,\n) => {\n const { targetDocument } = useFluent();\n const parentSetOpen = useMenuContext_unstable(context => context.setOpen);\n const onOpenChange: MenuProps['onOpenChange'] = useEventCallback((e, data) => state.onOpenChange?.(e, data));\n\n const shouldHandleCloseRef = React.useRef(false);\n const setOpenTimeout = React.useRef(0);\n const enteringTriggerRef = React.useRef(false);\n\n const [open, setOpenState] = useControllableState({\n state: state.open,\n defaultState: state.defaultOpen,\n initialState: false,\n });\n\n const trySetOpen = useEventCallback((e: MenuOpenEvent, data: MenuOpenChangeData) => {\n const event = e instanceof CustomEvent && e.type === MENU_ENTER_EVENT ? e.detail.nativeEvent : e;\n onOpenChange?.(event, { ...data });\n if (data.open && e.type === 'contextmenu') {\n state.setContextTarget(e as React.MouseEvent);\n }\n\n if (!data.open) {\n state.setContextTarget(undefined);\n shouldHandleCloseRef.current = true;\n }\n\n if (data.bubble) {\n parentSetOpen(e, { ...data });\n }\n\n setOpenState(data.open);\n });\n\n const setOpen = useEventCallback((e: MenuOpenEvent, data: MenuOpenChangeData) => {\n clearTimeout(setOpenTimeout.current);\n if (!(e instanceof Event) && e.persist) {\n // < React 17 still uses pooled synthetic events\n e.persist();\n }\n\n if (e.type === 'mouseleave' || e.type === 'mouseenter' || e.type === 'mousemove' || e.type === MENU_ENTER_EVENT) {\n if (state.triggerRef.current?.contains(e.target as HTMLElement)) {\n enteringTriggerRef.current = e.type === 'mouseenter' || e.type === 'mousemove';\n }\n\n // FIXME leaking Node timeout type\n // eslint-disable-next-line @typescript-eslint/ban-ts-comment\n // @ts-ignore\n setOpenTimeout.current = setTimeout(() => trySetOpen(e, data), state.hoverDelay);\n } else {\n trySetOpen(e, data);\n }\n });\n\n useOnClickOutside({\n contains: elementContains,\n disabled: !open,\n element: targetDocument,\n refs: [state.menuPopoverRef, !state.openOnContext && state.triggerRef].filter(\n Boolean,\n ) as React.MutableRefObject<HTMLElement>[],\n callback: event => setOpen(event, { open: false, type: 'clickOutside', event }),\n });\n\n // only close on scroll for context, or when closeOnScroll is specified\n const closeOnScroll = state.openOnContext || state.closeOnScroll;\n useOnScrollOutside({\n contains: elementContains,\n element: targetDocument,\n callback: event => setOpen(event, { open: false, type: 'scrollOutside', event }),\n refs: [state.menuPopoverRef, !state.openOnContext && state.triggerRef].filter(\n Boolean,\n ) as React.MutableRefObject<HTMLElement>[],\n disabled: !open || !closeOnScroll,\n });\n\n useOnMenuMouseEnter({\n element: targetDocument,\n callback: event => {\n // When moving from a menu directly back to its trigger, this handler can close the menu\n // Explicitly check a flag to see if this situation happens\n if (!enteringTriggerRef.current) {\n setOpen(event, { open: false, type: 'menuMouseEnter', event });\n }\n },\n disabled: !open,\n refs: [state.menuPopoverRef],\n });\n\n // Clear timeout on unmount\n // Setting state after a component unmounts can cause memory leaks\n React.useEffect(() => {\n return () => {\n clearTimeout(setOpenTimeout.current);\n };\n }, []);\n\n // Manage focus for open state\n const { findFirstFocusable } = useFocusFinders();\n const focusFirst = React.useCallback(() => {\n const firstFocusable = findFirstFocusable(state.menuPopoverRef.current);\n firstFocusable?.focus();\n }, [findFirstFocusable, state.menuPopoverRef]);\n\n React.useEffect(() => {\n if (open) {\n focusFirst();\n } else {\n if (shouldHandleCloseRef.current) {\n // We know that React effects are sync so we focus the trigger here\n // after any event handler (event handlers will update state and re-render).\n // Since the browser only performs the default behaviour for the Tab key once\n // keyboard events have fully bubbled up the window, the browser will move\n // focus to the next tabbable element before/after the trigger if needed.\n // If the Tab key was not pressed, focus will remain on the trigger as expected.\n state.triggerRef.current?.focus();\n }\n }\n\n shouldHandleCloseRef.current = false;\n }, [state.triggerRef, state.isSubmenu, open, focusFirst]);\n\n return [open, setOpen] as const;\n};\n"]}
@@ -1 +1 @@
1
- {"version":3,"file":"MenuItem.types.js","sourceRoot":"","sources":["../../../../../../../../../packages/react-components/react-menu/src/components/MenuItem/MenuItem.types.ts"],"names":[],"mappings":"","sourcesContent":["import type { ARIAButtonSlotProps } from '@fluentui/react-aria';\nimport type { ComponentProps, ComponentState, Slot } from '@fluentui/react-utilities';\n\nexport type MenuItemSlots = {\n root: Slot<ARIAButtonSlotProps<'div'>>;\n\n /**\n * Icon slot rendered before children content\n */\n icon?: Slot<'span'>;\n\n /**\n * A helper slot for alignment when a menu item is used with selectable menuitems\n * Avoid using this slot as a replacement for MenuItemCheckbox and MenuItemRadio components\n */\n checkmark?: Slot<'span'>;\n\n /**\n * Icon slot that shows the indicator for a submenu\n */\n submenuIndicator?: Slot<'span'>;\n\n /**\n * Component children are placed in this slot\n * Avoid using the `children` property in this slot in favour of Component children whenever possible\n */\n content?: Slot<'span'>;\n\n /**\n * Secondary content rendered opposite the primary content (e.g Shortcut text)\n */\n secondaryContent?: Slot<'span'>;\n};\n\nexport type MenuItemProps = ComponentProps<Partial<MenuItemSlots>> & {\n /**\n * If the menu item is a trigger for a submenu\n *\n * @default false\n */\n hasSubmenu?: boolean;\n\n /**\n * Clicking on the menu item will not dismiss an open menu\n *\n * @default false\n */\n persistOnClick?: boolean;\n};\n\nexport type MenuItemState = ComponentState<MenuItemSlots> &\n Required<Pick<MenuItemProps, 'disabled' | 'hasSubmenu' | 'persistOnClick'>> & {\n isNativeButton: boolean;\n };\n"]}
1
+ {"version":3,"file":"MenuItem.types.js","sourceRoot":"","sources":["../../../../../../../../../packages/react-components/react-menu/src/components/MenuItem/MenuItem.types.ts"],"names":[],"mappings":"","sourcesContent":["import type { ComponentProps, ComponentState, Slot } from '@fluentui/react-utilities';\n\nexport type MenuItemSlots = {\n root: Slot<'div'>;\n\n /**\n * Icon slot rendered before children content\n */\n icon?: Slot<'span'>;\n\n /**\n * A helper slot for alignment when a menu item is used with selectable menuitems\n * Avoid using this slot as a replacement for MenuItemCheckbox and MenuItemRadio components\n */\n checkmark?: Slot<'span'>;\n\n /**\n * Icon slot that shows the indicator for a submenu\n */\n submenuIndicator?: Slot<'span'>;\n\n /**\n * Component children are placed in this slot\n * Avoid using the `children` property in this slot in favour of Component children whenever possible\n */\n content?: Slot<'span'>;\n\n /**\n * Secondary content rendered opposite the primary content (e.g Shortcut text)\n */\n secondaryContent?: Slot<'span'>;\n};\n\nexport type MenuItemProps = ComponentProps<Partial<MenuItemSlots>> & {\n /**\n * If the menu item is a trigger for a submenu\n *\n * @default false\n */\n hasSubmenu?: boolean;\n\n /**\n * Clicking on the menu item will not dismiss an open menu\n *\n * @default false\n */\n persistOnClick?: boolean;\n\n disabled?: boolean;\n /**\n * @deprecated this property does nothing.\n * disabled focusable is by default by simply using `disabled` property\n */\n disabledFocusable?: boolean;\n};\n\nexport type MenuItemState = ComponentState<MenuItemSlots> &\n Required<Pick<MenuItemProps, 'disabled' | 'hasSubmenu' | 'persistOnClick'>>;\n"]}
@@ -6,7 +6,7 @@ import { useMenuTriggerContext_unstable } from '../../contexts/menuTriggerContex
6
6
  import { ChevronRightFilled, ChevronRightRegular, ChevronLeftFilled, ChevronLeftRegular, bundleIcon } from '@fluentui/react-icons';
7
7
  import { useMenuListContext_unstable } from '../../contexts/menuListContext';
8
8
  import { useMenuContext_unstable } from '../../contexts/menuContext';
9
- import { useARIAButtonShorthand } from '@fluentui/react-aria';
9
+ import { useARIAButtonProps } from '@fluentui/react-aria';
10
10
  import { Enter, Space } from '@fluentui/keyboard-keys';
11
11
  const ChevronRightIcon = /*#__PURE__*/bundleIcon(ChevronRightFilled, ChevronRightRegular);
12
12
  const ChevronLeftIcon = /*#__PURE__*/bundleIcon(ChevronLeftFilled, ChevronLeftRegular);
@@ -18,8 +18,7 @@ export const useMenuItem_unstable = (props, ref) => {
18
18
  const persistOnClickContext = useMenuContext_unstable(context => context.persistOnItemClick);
19
19
  const {
20
20
  as = 'div',
21
- disabled,
22
- disabledFocusable,
21
+ disabled = false,
23
22
  hasSubmenu = isSubmenuTrigger,
24
23
  persistOnClick = persistOnClickContext
25
24
  } = props;
@@ -31,10 +30,9 @@ export const useMenuItem_unstable = (props, ref) => {
31
30
  } = useFluent();
32
31
  const innerRef = React.useRef(null);
33
32
  const dismissedWithKeyboardRef = React.useRef(false);
34
- const isDisabled = Boolean(disabled || disabledFocusable);
35
33
  const state = {
36
34
  hasSubmenu,
37
- disabled: isDisabled,
35
+ disabled,
38
36
  persistOnClick,
39
37
  components: {
40
38
  root: 'div',
@@ -44,44 +42,38 @@ export const useMenuItem_unstable = (props, ref) => {
44
42
  content: 'span',
45
43
  secondaryContent: 'span'
46
44
  },
47
- isNativeButton: as === 'button',
48
- root: getNativeElementProps(as, useARIAButtonShorthand({
45
+ root: getNativeElementProps(as, useARIAButtonProps(as, {
46
+ role: 'menuitem',
47
+ ...props,
49
48
  disabled: false,
50
- disabledFocusable: isDisabled,
51
- as
52
- }, {
53
- required: true,
54
- defaultProps: {
55
- role: 'menuitem',
56
- ...props,
57
- ref: useMergedRefs(ref, innerRef),
58
- onKeyDown: useEventCallback(event => {
59
- var _a;
60
- (_a = props.onKeyDown) === null || _a === void 0 ? void 0 : _a.call(props, event);
61
- if (!event.isDefaultPrevented() && (event.key === Space || event.key === Enter)) {
62
- dismissedWithKeyboardRef.current = true;
63
- }
64
- }),
65
- onMouseEnter: useEventCallback(event => {
66
- var _a, _b;
67
- (_a = innerRef.current) === null || _a === void 0 ? void 0 : _a.focus();
68
- (_b = props.onMouseEnter) === null || _b === void 0 ? void 0 : _b.call(props, event);
69
- }),
70
- onClick: useEventCallback(event => {
71
- var _a;
72
- if (!hasSubmenu && !persistOnClick) {
73
- setOpen(event, {
74
- open: false,
75
- keyboard: dismissedWithKeyboardRef.current,
76
- bubble: true,
77
- type: 'menuItemClick',
78
- event
79
- });
80
- dismissedWithKeyboardRef.current = false;
81
- }
82
- (_a = props.onClick) === null || _a === void 0 ? void 0 : _a.call(props, event);
83
- })
84
- }
49
+ disabledFocusable: disabled,
50
+ ref: useMergedRefs(ref, innerRef),
51
+ onKeyDown: useEventCallback(event => {
52
+ var _a;
53
+ (_a = props.onKeyDown) === null || _a === void 0 ? void 0 : _a.call(props, event);
54
+ if (!event.isDefaultPrevented() && (event.key === Space || event.key === Enter)) {
55
+ dismissedWithKeyboardRef.current = true;
56
+ }
57
+ }),
58
+ onMouseEnter: useEventCallback(event => {
59
+ var _a, _b;
60
+ (_a = innerRef.current) === null || _a === void 0 ? void 0 : _a.focus();
61
+ (_b = props.onMouseEnter) === null || _b === void 0 ? void 0 : _b.call(props, event);
62
+ }),
63
+ onClick: useEventCallback(event => {
64
+ var _a;
65
+ if (!hasSubmenu && !persistOnClick) {
66
+ setOpen(event, {
67
+ open: false,
68
+ keyboard: dismissedWithKeyboardRef.current,
69
+ bubble: true,
70
+ type: 'menuItemClick',
71
+ event
72
+ });
73
+ dismissedWithKeyboardRef.current = false;
74
+ }
75
+ (_a = props.onClick) === null || _a === void 0 ? void 0 : _a.call(props, event);
76
+ })
85
77
  })),
86
78
  icon: resolveShorthand(props.icon, {
87
79
  required: hasIcons