@@ -21,15 +21,16 @@ import {
2121 FUNCTIONS ,
2222 EMPTY_ARRAY ,
2323 DEFAULT_THEME ,
24- SELECT_WRAPPER_ATTRS ,
2524 PAGE_SIZE_DEFAULT ,
2625 PLACEHOLDER_DEFAULT ,
2726 LOADING_MSG_DEFAULT ,
27+ SELECT_CONTAINER_CLS ,
2828 CONTROL_CONTAINER_CLS ,
2929 FOCUSED_OPTION_DEFAULT ,
3030 NO_OPTIONS_MSG_DEFAULT ,
3131 MENU_ITEM_SIZE_DEFAULT ,
3232 MENU_MAX_HEIGHT_DEFAULT ,
33+ SELECT_CONTAINER_TESTID ,
3334 CONTROL_CONTAINER_TESTID
3435} from './constants' ;
3536import type {
@@ -56,9 +57,10 @@ import { isBoolean, isFunction, isPlainObject, mergeDeep, suppressEvent, normali
5657
5758type SelectProps = Readonly < {
5859 async ?: boolean ;
60+ menuId ?: string ;
5961 inputId ?: string ;
60- pageSize ?: number ;
6162 selectId ?: string ;
63+ pageSize ?: number ;
6264 isMulti ?: boolean ;
6365 ariaLabel ?: string ;
6466 required ?: boolean ;
@@ -127,7 +129,7 @@ interface ControlWrapperProps extends Pick<SelectProps, 'isInvalid' | 'isDisable
127129 isFocused : boolean ;
128130}
129131
130- const SelectWrapper = styled . div . attrs ( SELECT_WRAPPER_ATTRS ) `
132+ const SelectWrapper = styled . div `
131133 position : relative;
132134 box-sizing : border-box;
133135 ${ ( { theme } ) => theme . select . css }
@@ -180,6 +182,7 @@ const ControlWrapper = styled.div<ControlWrapperProps>`
180182const Select = forwardRef < SelectRef , SelectProps > ( (
181183 {
182184 async,
185+ menuId,
183186 isMulti,
184187 inputId,
185188 selectId,
@@ -374,7 +377,8 @@ const Select = forwardRef<SelectRef, SelectProps>((
374377 } , [ isMulti , closeMenuOnSelect , blurInputOnSelect , removeSelectedOption ] ) ;
375378
376379 /**
377- * useImperativeHandle.
380+ * `React.useImperativeHandle`
381+ *
378382 * Exposed API methods/properties available on a ref instance of this Select.tsx component.
379383 * Dependency list passed as the third param to re-create the handle when one of them updates.
380384 */
@@ -406,15 +410,19 @@ const Select = forwardRef<SelectRef, SelectProps>((
406410 ) ;
407411
408412 /**
409- * useMountEffect
410- * If autoFocus = true, focus the control following initial mount.
413+ * `useMountEffect`
414+ *
415+ * If 'autoFocus' true, focus the control following initial mount
411416 */
412417 useMountEffect ( ( ) => {
413- autoFocus && focusInput ( ) ;
418+ if ( autoFocus ) {
419+ focusInput ( ) ;
420+ }
414421 } ) ;
415422
416423 /**
417- * useEffect
424+ * `React.useEffect`
425+ *
418426 * If 'onSearchChange' function is defined, run as callback when the stateful debouncedInputValue
419427 * updates check if onChangeEvtValue ref is set true, which indicates the inputValue change was triggered by input change event
420428 */
@@ -426,7 +434,8 @@ const Select = forwardRef<SelectRef, SelectProps>((
426434 } , [ onSearchChangeFn , onSearchChangeIsFn , debouncedInputValue ] ) ;
427435
428436 /**
429- * useUpdateEffect
437+ * `useUpdateEffect`
438+ *
430439 * Handle passing 'selectedOption' value(s) to onOptionChange callback function prop (if defined)
431440 */
432441 useUpdateEffect ( ( ) => {
@@ -442,7 +451,8 @@ const Select = forwardRef<SelectRef, SelectProps>((
442451 } , [ onOptionChangeFn , onOptionChangeIsFn , isMulti , selectedOption ] ) ;
443452
444453 /**
445- * useUpdateEffect
454+ * `useUpdateEffect`
455+ *
446456 * Handle clearing focused option if menuOptions array has 0 length;
447457 * Handle menuOptions changes - conditionally focus first option and do scroll to first option;
448458 * Handle reseting scroll pos to first item after the previous search returned zero results (use prevMenuOptionsLen)
@@ -472,7 +482,7 @@ const Select = forwardRef<SelectRef, SelectProps>((
472482 }
473483 } ;
474484
475- // Only Multiselect mode supports value focusing (ArrowRight || ArrowLeft)
485+ // only Multiselect mode supports value focusing (ArrowRight || ArrowLeft)
476486 const focusValueOnArrowKey = ( key : string ) : void => {
477487 if ( ! hasSelectedOptions ) return ;
478488
@@ -492,7 +502,7 @@ const Select = forwardRef<SelectRef, SelectProps>((
492502 : 0 ;
493503 }
494504
495- const nextFocusedVal = focusedIdx >= 0
505+ const nextFocusedVal = focusedIdx > - 1
496506 ? selectedOption [ focusedIdx ] . value !
497507 : null ;
498508
@@ -533,8 +543,8 @@ const Select = forwardRef<SelectRef, SelectProps>((
533543 const handleOnKeyDown = ( e : KeyboardEvent < HTMLElement > ) : void => {
534544 if ( isDisabled ) return ;
535545
536- if ( isFunction ( onKeyDown ) ) {
537- onKeyDown ( e . key , inputValue , focusedOption ) ;
546+ if ( onKeyDown ) {
547+ onKeyDown ( e , inputValue , focusedOption ) ;
538548 if ( e . defaultPrevented ) return ;
539549 }
540550
@@ -563,7 +573,7 @@ const Select = forwardRef<SelectRef, SelectProps>((
563573 focusOptionOnArrowKey ( OptionIndexEnum . PAGEDOWN ) ;
564574 break ;
565575 }
566- // Handle spacebar keydown events
576+ // handle spacebar keydown events
567577 case ' ' : {
568578 if ( inputValue ) return ;
569579
@@ -685,15 +695,14 @@ const Select = forwardRef<SelectRef, SelectProps>((
685695
686696 const flexValueWrapper = ! ! isMulti && hasSelectedOptions ;
687697 const showClear = ! ! isClearable && ! isDisabled && hasSelectedOptions ;
688- const inputReadOnly = isDisabled || ! isSearchable || ! ! focusedMultiValue ;
689698
690699 return (
691700 < ThemeProvider theme = { theme } >
692701 < SelectWrapper
693702 id = { selectId }
694- aria-controls = { inputId }
695- aria-expanded = { menuOpen }
696703 onKeyDown = { handleOnKeyDown }
704+ className = { SELECT_CONTAINER_CLS }
705+ data-testid = { SELECT_CONTAINER_TESTID }
697706 >
698707 < ControlWrapper
699708 ref = { controlRef }
@@ -719,15 +728,18 @@ const Select = forwardRef<SelectRef, SelectProps>((
719728 < AutosizeInput
720729 id = { inputId }
721730 ref = { inputRef }
731+ menuId = { menuId }
732+ menuOpen = { menuOpen }
722733 required = { required }
723734 ariaLabel = { ariaLabel }
735+ isInvalid = { isInvalid }
724736 inputValue = { inputValue }
725- readOnly = { inputReadOnly }
726737 onBlur = { handleOnInputBlur }
727738 onFocus = { handleOnInputFocus }
728739 onChange = { handleOnInputChange }
729740 ariaLabelledBy = { ariaLabelledBy }
730741 hasSelectedOptions = { hasSelectedOptions }
742+ readOnly = { ! isSearchable || ! ! focusedMultiValue }
731743 />
732744 </ ValueWrapper >
733745 < IndicatorIcons
@@ -744,6 +756,7 @@ const Select = forwardRef<SelectRef, SelectProps>((
744756 />
745757 </ ControlWrapper >
746758 < Menu
759+ id = { menuId }
747760 menuRef = { menuRef }
748761 menuOpen = { menuOpen }
749762 isLoading = { isLoading }
0 commit comments