@@ -60,10 +60,10 @@ type KeyHandlerConfig = {
6060} ;
6161
6262/**
63- * Creates a keyboard event handler for lookup components
63+ * Custom hook for keyboard event handling in lookup components
6464 */
65- const createKeyHandler = ( config : KeyHandlerConfig ) => {
66- return ( e : KeyboardEvent ) => {
65+ const useKeyHandler = ( config : KeyHandlerConfig ) => {
66+ return useEventCallback ( ( e : KeyboardEvent ) => {
6767 const {
6868 opened,
6969 onOpen,
@@ -114,7 +114,7 @@ const createKeyHandler = (config: KeyHandlerConfig) => {
114114 }
115115 break ;
116116 }
117- } ;
117+ } ) ;
118118} ;
119119
120120/**
@@ -958,83 +958,81 @@ export const Lookup = createFC<LookupProps, { isFormElement: boolean }>(
958958 } , 10 ) ;
959959 } ) ;
960960
961- const onInputKeyDown = useEventCallback (
962- createKeyHandler ( {
963- type : 'search' ,
964- opened,
965- onOpen : ( ) => {
961+ const onInputKeyDown = useKeyHandler ( {
962+ type : 'search' ,
963+ opened,
964+ onOpen : ( ) => {
965+ setOpened ( true ) ;
966+ onLookupRequest_ ?.( searchText ) ;
967+ } ,
968+ onClose : ( ) => {
969+ setOpened ( false ) ;
970+ onComplete ?.( true ) ;
971+ } ,
972+ onNavigateDown : ( ) => {
973+ const nextValue = getNextValue ( focusedValue ) ;
974+ setFocusedValue ( nextValue ) ;
975+ scrollFocusedElementIntoView ( nextValue ) ;
976+ } ,
977+ onNavigateUp : ( ) => {
978+ const prevValue = getPrevValue ( focusedValue ) ;
979+ setFocusedValue ( prevValue ) ;
980+ scrollFocusedElementIntoView ( prevValue ) ;
981+ } ,
982+ onSelect : ( ) => {
983+ if ( opened && focusedValue ) {
984+ const selectedEntry = data . find (
985+ ( entry ) => entry . value === focusedValue
986+ ) ;
987+ if ( selectedEntry ) {
988+ onSelect ( selectedEntry ) ;
989+ setOpened ( false ) ;
990+ onComplete ?.( ) ;
991+ }
992+ } else if ( searchText ) {
966993 setOpened ( true ) ;
967994 onLookupRequest_ ?.( searchText ) ;
968- } ,
969- onClose : ( ) => {
970- setOpened ( false ) ;
971- onComplete ?. ( true ) ;
972- } ,
973- onNavigateDown : ( ) => {
974- const nextValue = getNextValue ( focusedValue ) ;
975- setFocusedValue ( nextValue ) ;
976- scrollFocusedElementIntoView ( nextValue ) ;
977- } ,
978- onNavigateUp : ( ) => {
979- const prevValue = getPrevValue ( focusedValue ) ;
980- setFocusedValue ( prevValue ) ;
981- scrollFocusedElementIntoView ( prevValue ) ;
982- } ,
983- onSelect : ( ) => {
984- if ( opened && focusedValue ) {
985- const selectedEntry = data . find (
986- ( entry ) => entry . value === focusedValue
987- ) ;
988- if ( selectedEntry ) {
989- onSelect ( selectedEntry ) ;
990- setOpened ( false ) ;
991- onComplete ?.( ) ;
992- }
993- } else if ( searchText ) {
994- setOpened ( true ) ;
995- onLookupRequest_ ?. ( searchText ) ;
995+ }
996+ } ,
997+ isTabNavigationIgnored : ( direction ) => {
998+ const optionValues = getOptionValues ( ) ;
999+ const currentIndex = focusedValue
1000+ ? optionValues . indexOf ( focusedValue )
1001+ : - 1 ;
1002+
1003+ return (
1004+ currentIndex === - 1 ||
1005+ ( direction === 'backward' && currentIndex <= 0 ) ||
1006+ ( direction === 'forward' && currentIndex >= optionValues . length - 1 )
1007+ ) ;
1008+ } ,
1009+ onTabNavigation : ( direction ) => {
1010+ const optionValues = getOptionValues ( ) ;
1011+ const currentIndex = focusedValue
1012+ ? optionValues . indexOf ( focusedValue )
1013+ : - 1 ;
1014+
1015+ if ( direction === 'backward' ) {
1016+ if ( currentIndex <= 0 ) {
1017+ setOpened ( false ) ;
1018+ onComplete ?.( ) ;
1019+ } else {
1020+ const prevValue = getPrevValue ( focusedValue ) ;
1021+ setFocusedValue ( prevValue ) ;
1022+ scrollFocusedElementIntoView ( prevValue ) ;
9961023 }
997- } ,
998- isTabNavigationIgnored : ( direction ) => {
999- const optionValues = getOptionValues ( ) ;
1000- const currentIndex = focusedValue
1001- ? optionValues . indexOf ( focusedValue )
1002- : - 1 ;
1003-
1004- return (
1005- currentIndex === - 1 ||
1006- ( direction === 'backward' && currentIndex <= 0 ) ||
1007- ( direction === 'forward' && currentIndex >= optionValues . length - 1 )
1008- ) ;
1009- } ,
1010- onTabNavigation : ( direction ) => {
1011- const optionValues = getOptionValues ( ) ;
1012- const currentIndex = focusedValue
1013- ? optionValues . indexOf ( focusedValue )
1014- : - 1 ;
1015-
1016- if ( direction === 'backward' ) {
1017- if ( currentIndex <= 0 ) {
1018- setOpened ( false ) ;
1019- onComplete ?.( ) ;
1020- } else {
1021- const prevValue = getPrevValue ( focusedValue ) ;
1022- setFocusedValue ( prevValue ) ;
1023- scrollFocusedElementIntoView ( prevValue ) ;
1024- }
1024+ } else {
1025+ if ( currentIndex >= optionValues . length - 1 ) {
1026+ setOpened ( false ) ;
1027+ onComplete ?.( ) ;
10251028 } else {
1026- if ( currentIndex >= optionValues . length - 1 ) {
1027- setOpened ( false ) ;
1028- onComplete ?.( ) ;
1029- } else {
1030- const nextValue = getNextValue ( focusedValue ) ;
1031- setFocusedValue ( nextValue ) ;
1032- scrollFocusedElementIntoView ( nextValue ) ;
1033- }
1029+ const nextValue = getNextValue ( focusedValue ) ;
1030+ setFocusedValue ( nextValue ) ;
1031+ scrollFocusedElementIntoView ( nextValue ) ;
10341032 }
1035- } ,
1036- } )
1037- ) ;
1033+ }
1034+ } ,
1035+ } ) ;
10381036
10391037 const onOptionClick = useEventCallback ( ( entry : LookupEntry ) => {
10401038 onSelect ( entry ) ;
@@ -1068,82 +1066,80 @@ export const Lookup = createFC<LookupProps, { isFormElement: boolean }>(
10681066 onScopeMenuClick_ ?.( ) ;
10691067 } ) ;
10701068
1071- const onScopeKeyDown = useEventCallback (
1072- createKeyHandler ( {
1073- type : 'scope' ,
1074- opened : scopeOpened ,
1075- onOpen : ( ) => {
1076- if ( ! scopes ) return ;
1077- setScopeOpened ( true ) ;
1078- setScopeFocusedIndex ( 0 ) ;
1079- } ,
1080- onClose : ( ) => {
1081- setScopeOpened ( false ) ;
1082- setScopeFocusedIndex ( - 1 ) ;
1083- } ,
1084- onNavigateDown : ( ) => {
1085- if ( ! scopes ) return ;
1086- const nextIndex = Math . min ( scopeFocusedIndex + 1 , scopes . length - 1 ) ;
1087- setScopeFocusedIndex ( nextIndex ) ;
1088- scrollFocusedScopeIntoView ( nextIndex ) ;
1089- } ,
1090- onNavigateUp : ( ) => {
1091- if ( ! scopes ) return ;
1092- const prevIndex = Math . max ( scopeFocusedIndex - 1 , 0 ) ;
1093- setScopeFocusedIndex ( prevIndex ) ;
1094- scrollFocusedScopeIntoView ( prevIndex ) ;
1095- } ,
1096- onSelect : ( ) => {
1097- if ( ! scopes ) return ;
1098- if ( scopeOpened && scopeFocusedIndex >= 0 ) {
1099- const selectedScope = scopes [ scopeFocusedIndex ] ;
1100- if ( selectedScope ) {
1101- onScopeSelect ( selectedScope . label ) ;
1102- setScopeOpened ( false ) ;
1103- setScopeFocusedIndex ( - 1 ) ;
1104- }
1105- } else {
1106- setScopeOpened ( ! scopeOpened ) ;
1107- }
1108- } ,
1109- isTabNavigationIgnored : ( direction ) => {
1110- if ( ! scopes ) {
1111- return false ;
1069+ const onScopeKeyDown = useKeyHandler ( {
1070+ type : 'scope' ,
1071+ opened : scopeOpened ,
1072+ onOpen : ( ) => {
1073+ if ( ! scopes ) return ;
1074+ setScopeOpened ( true ) ;
1075+ setScopeFocusedIndex ( 0 ) ;
1076+ } ,
1077+ onClose : ( ) => {
1078+ setScopeOpened ( false ) ;
1079+ setScopeFocusedIndex ( - 1 ) ;
1080+ } ,
1081+ onNavigateDown : ( ) => {
1082+ if ( ! scopes ) return ;
1083+ const nextIndex = Math . min ( scopeFocusedIndex + 1 , scopes . length - 1 ) ;
1084+ setScopeFocusedIndex ( nextIndex ) ;
1085+ scrollFocusedScopeIntoView ( nextIndex ) ;
1086+ } ,
1087+ onNavigateUp : ( ) => {
1088+ if ( ! scopes ) return ;
1089+ const prevIndex = Math . max ( scopeFocusedIndex - 1 , 0 ) ;
1090+ setScopeFocusedIndex ( prevIndex ) ;
1091+ scrollFocusedScopeIntoView ( prevIndex ) ;
1092+ } ,
1093+ onSelect : ( ) => {
1094+ if ( ! scopes ) return ;
1095+ if ( scopeOpened && scopeFocusedIndex >= 0 ) {
1096+ const selectedScope = scopes [ scopeFocusedIndex ] ;
1097+ if ( selectedScope ) {
1098+ onScopeSelect ( selectedScope . label ) ;
1099+ setScopeOpened ( false ) ;
1100+ setScopeFocusedIndex ( - 1 ) ;
11121101 }
1102+ } else {
1103+ setScopeOpened ( ! scopeOpened ) ;
1104+ }
1105+ } ,
1106+ isTabNavigationIgnored : ( direction ) => {
1107+ if ( ! scopes ) {
1108+ return false ;
1109+ }
11131110
1114- return (
1115- scopeFocusedIndex === - 1 ||
1116- ( direction === 'backward' && scopeFocusedIndex <= 0 ) ||
1117- ( direction === 'forward' && scopeFocusedIndex >= scopes . length - 1 )
1118- ) ;
1119- } ,
1120- onTabNavigation : ( direction ) => {
1121- if ( ! scopes ) return ;
1122- if ( direction === 'backward' ) {
1123- if ( scopeFocusedIndex <= 0 ) {
1124- setScopeOpened ( false ) ;
1125- setScopeFocusedIndex ( - 1 ) ;
1126- } else {
1127- const prevIndex = Math . max ( scopeFocusedIndex - 1 , 0 ) ;
1128- setScopeFocusedIndex ( prevIndex ) ;
1129- scrollFocusedScopeIntoView ( prevIndex ) ;
1130- }
1111+ return (
1112+ scopeFocusedIndex === - 1 ||
1113+ ( direction === 'backward' && scopeFocusedIndex <= 0 ) ||
1114+ ( direction === 'forward' && scopeFocusedIndex >= scopes . length - 1 )
1115+ ) ;
1116+ } ,
1117+ onTabNavigation : ( direction ) => {
1118+ if ( ! scopes ) return ;
1119+ if ( direction === 'backward' ) {
1120+ if ( scopeFocusedIndex <= 0 ) {
1121+ setScopeOpened ( false ) ;
1122+ setScopeFocusedIndex ( - 1 ) ;
11311123 } else {
1132- if ( scopeFocusedIndex >= scopes . length - 1 ) {
1133- setScopeOpened ( false ) ;
1134- setScopeFocusedIndex ( - 1 ) ;
1135- } else {
1136- const nextIndex = Math . min (
1137- scopeFocusedIndex + 1 ,
1138- scopes . length - 1
1139- ) ;
1140- setScopeFocusedIndex ( nextIndex ) ;
1141- scrollFocusedScopeIntoView ( nextIndex ) ;
1142- }
1124+ const prevIndex = Math . max ( scopeFocusedIndex - 1 , 0 ) ;
1125+ setScopeFocusedIndex ( prevIndex ) ;
1126+ scrollFocusedScopeIntoView ( prevIndex ) ;
11431127 }
1144- } ,
1145- } )
1146- ) ;
1128+ } else {
1129+ if ( scopeFocusedIndex >= scopes . length - 1 ) {
1130+ setScopeOpened ( false ) ;
1131+ setScopeFocusedIndex ( - 1 ) ;
1132+ } else {
1133+ const nextIndex = Math . min (
1134+ scopeFocusedIndex + 1 ,
1135+ scopes . length - 1
1136+ ) ;
1137+ setScopeFocusedIndex ( nextIndex ) ;
1138+ scrollFocusedScopeIntoView ( nextIndex ) ;
1139+ }
1140+ }
1141+ } ,
1142+ } ) ;
11471143
11481144 const onScopeBlur = useEventCallback ( ( e : FocusEvent ) => {
11491145 if ( e . relatedTarget !== null ) {
0 commit comments