Skip to content

Commit 9fc4833

Browse files
committed
feat(menu): add openMenuOnArrows option to allow disabling arrow keys to open the menu
1 parent 28251dc commit 9fc4833

File tree

5 files changed

+60
-7
lines changed

5 files changed

+60
-7
lines changed

.changeset/openMenuOnArrows.md

+5
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
---
2+
'react-select': minor
3+
---
4+
5+
Add `openMenuOnArrows` option, to disable opening menu on arrow up/down keys

package.json

+1-1
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,7 @@
2828
"@testing-library/dom": "8.19.0",
2929
"@testing-library/jest-dom": "5.1.1",
3030
"@testing-library/react": "12.1.4",
31-
"@testing-library/user-event": "^10.0.0",
31+
"@testing-library/user-event": "^13.0.0",
3232
"@types/copy-webpack-plugin": "^5.0.2",
3333
"@types/html-webpack-plugin": "^3.2.4",
3434
"@types/jest-in-case": "^1.0.6",

packages/react-select/src/Select.tsx

+8
Original file line numberDiff line numberDiff line change
@@ -248,6 +248,8 @@ export interface Props<
248248
openMenuOnFocus: boolean;
249249
/** Allows control of whether the menu is opened when the Select is clicked */
250250
openMenuOnClick: boolean;
251+
/** Allows control of whether the menu is opened on up and down arrows */
252+
openMenuOnArrows: boolean;
251253
/** Array of options that populate the select menu */
252254
options: OptionsOrGroups<Option, Group>;
253255
/** Number of options to jump in menu when page{up|down} keys are used */
@@ -310,6 +312,7 @@ export const defaultProps = {
310312
noOptionsMessage: () => 'No options',
311313
openMenuOnFocus: false,
312314
openMenuOnClick: true,
315+
openMenuOnArrows: true,
313316
options: [],
314317
pageSize: 5,
315318
placeholder: 'Select...',
@@ -1565,6 +1568,7 @@ export default class Select<
15651568
onKeyDown,
15661569
tabSelectsValue,
15671570
openMenuOnFocus,
1571+
openMenuOnArrows,
15681572
} = this.props;
15691573
const { focusedOption, focusedValue, selectValue } = this.state;
15701574

@@ -1659,13 +1663,17 @@ export default class Select<
16591663
case 'ArrowUp':
16601664
if (menuIsOpen) {
16611665
this.focusOption('up');
1666+
} else if (!openMenuOnArrows) {
1667+
return;
16621668
} else {
16631669
this.openMenu('last');
16641670
}
16651671
break;
16661672
case 'ArrowDown':
16671673
if (menuIsOpen) {
16681674
this.focusOption('down');
1675+
} else if (!openMenuOnArrows) {
1676+
return;
16691677
} else {
16701678
this.openMenu('first');
16711679
}

packages/react-select/src/__tests__/Select.test.tsx

+40
Original file line numberDiff line numberDiff line change
@@ -969,6 +969,46 @@ test('clicking when focused does not open select when openMenuOnClick=false', ()
969969
expect(spy).not.toHaveBeenCalled();
970970
});
971971

972+
test('arrow keys does not open select when openMenuOnArrows=false', () => {
973+
let spy = jest.fn();
974+
let { container } = render(
975+
<Select
976+
{...BASIC_PROPS}
977+
openMenuOnArrows={false}
978+
openMenuOnFocus={false}
979+
openMenuOnClick={false}
980+
onMenuOpen={spy}
981+
/>
982+
);
983+
984+
// this will get updated on input click, though click on input is not bubbling up to control component
985+
userEvent.click(container.querySelector('input.react-select__input')!);
986+
expect(spy).not.toHaveBeenCalled();
987+
988+
userEvent.keyboard('[ArrowUp]');
989+
expect(spy).not.toHaveBeenCalled();
990+
});
991+
992+
test('arrow keys does open select when openMenuOnArrows=true', () => {
993+
let spy = jest.fn();
994+
let { container } = render(
995+
<Select
996+
{...BASIC_PROPS}
997+
openMenuOnArrows
998+
openMenuOnFocus={false}
999+
openMenuOnClick={false}
1000+
onMenuOpen={spy}
1001+
/>
1002+
);
1003+
1004+
// this will get updated on input click, though click on input is not bubbling up to control component
1005+
userEvent.click(container.querySelector('input.react-select__input')!);
1006+
expect(spy).not.toHaveBeenCalled();
1007+
1008+
userEvent.keyboard('[ArrowUp]');
1009+
expect(spy).toHaveBeenCalled();
1010+
});
1011+
9721012
cases(
9731013
'focus on options > keyboard interaction with Menu',
9741014
({ props, selectedOption, nextFocusOption, keyEvent = [] }) => {

yarn.lock

+6-6
Original file line numberDiff line numberDiff line change
@@ -1266,7 +1266,7 @@
12661266
pirates "^4.0.5"
12671267
source-map-support "^0.5.16"
12681268

1269-
"@babel/runtime@^7.0.0", "@babel/runtime@^7.1.2", "@babel/runtime@^7.10.2", "@babel/runtime@^7.10.4", "@babel/runtime@^7.12.0", "@babel/runtime@^7.12.13", "@babel/runtime@^7.12.5", "@babel/runtime@^7.13.10", "@babel/runtime@^7.17.8", "@babel/runtime@^7.18.3", "@babel/runtime@^7.2.0", "@babel/runtime@^7.5.0", "@babel/runtime@^7.5.5", "@babel/runtime@^7.7.2", "@babel/runtime@^7.7.6", "@babel/runtime@^7.7.7", "@babel/runtime@^7.8.3", "@babel/runtime@^7.8.4", "@babel/runtime@^7.8.7":
1269+
"@babel/runtime@^7.0.0", "@babel/runtime@^7.1.2", "@babel/runtime@^7.10.4", "@babel/runtime@^7.12.0", "@babel/runtime@^7.12.13", "@babel/runtime@^7.12.5", "@babel/runtime@^7.13.10", "@babel/runtime@^7.17.8", "@babel/runtime@^7.18.3", "@babel/runtime@^7.2.0", "@babel/runtime@^7.5.0", "@babel/runtime@^7.5.5", "@babel/runtime@^7.7.2", "@babel/runtime@^7.7.6", "@babel/runtime@^7.7.7", "@babel/runtime@^7.8.3", "@babel/runtime@^7.8.4", "@babel/runtime@^7.8.7":
12701270
version "7.19.4"
12711271
resolved "https://registry.yarnpkg.com/@babel/runtime/-/runtime-7.19.4.tgz#a42f814502ee467d55b38dd1c256f53a7b885c78"
12721272
integrity sha512-EXpLCrk55f+cYqmHsSR+yD/0gAIMxxA9QK9lnQWzhMCvt+YmoBN7Zx94s++Kv0+unHk39vxNO8t+CMA2WSS3wA==
@@ -3315,12 +3315,12 @@
33153315
"@testing-library/dom" "^8.0.0"
33163316
"@types/react-dom" "*"
33173317

3318-
"@testing-library/user-event@^10.0.0":
3319-
version "10.4.1"
3320-
resolved "https://registry.yarnpkg.com/@testing-library/user-event/-/user-event-10.4.1.tgz#f62adeae45681484dc24e6ca4f0b8f8a09321429"
3321-
integrity sha512-3sdJAfjT0i4aNvo0Gqod5MvZXutMXarVsLtb+r1t65AaRJY7BgMIzWgOtfM5dxRvZsc7IdXnCt9+gcWhiXk1xg==
3318+
"@testing-library/user-event@^13.0.0":
3319+
version "13.5.0"
3320+
resolved "https://registry.yarnpkg.com/@testing-library/user-event/-/user-event-13.5.0.tgz#69d77007f1e124d55314a2b73fd204b333b13295"
3321+
integrity sha512-5Kwtbo3Y/NowpkbRuSepbyMFkZmHgD+vPzYB/RJ4oxt5Gj/avFFBYjhw27cqSVPVw/3a67NK1PbiIr9k4Gwmdg==
33223322
dependencies:
3323-
"@babel/runtime" "^7.10.2"
3323+
"@babel/runtime" "^7.12.5"
33243324

33253325
"@ts-morph/common@~0.5.2":
33263326
version "0.5.2"

0 commit comments

Comments
 (0)