1
- import React , { useCallback } from 'react' ;
1
+ import React , { useCallback , useEffect , useState } from 'react' ;
2
+ import type { FC } from 'react' ;
2
3
import type { ChangeEvent } from 'react' ;
3
- import { useSelector } from 'react-redux' ;
4
+ import { useSelector , useDispatch } from 'react-redux' ;
4
5
5
6
import { UISearchBox } from '@sap-ux/ui-components' ;
6
7
7
- import type { AppState } from '../../../../types' ;
8
- import { actions } from '../../../../state' ;
8
+ import { fetchTreesData } from '../../../../features/Trees/Trees.utils' ;
9
+ import { useAppSelector } from '../../../../state/hooks' ;
10
+ import { actions } from '../../../../state/store' ;
11
+ import {
12
+ getSearchQuery ,
13
+ getNetworkStatus ,
14
+ getActiveScreen ,
15
+ getProductFilters ,
16
+ getComponentFilters
17
+ } from '../../../../state/reducers' ;
9
18
import { Filters } from '../Filters' ;
10
19
11
20
const SEARCH_TIMEOUT = 250 ;
@@ -14,57 +23,71 @@ const SEARCH_TIMEOUT = 250;
14
23
*
15
24
* @returns An input field
16
25
*/
17
- export function SearchField ( ) {
18
- const appState = useSelector < AppState , AppState > ( ( state ) => state ) ;
26
+ export const SearchField : FC = ( ) : JSX . Element => {
27
+ const dispatch = useDispatch ( ) ;
19
28
20
- const debounce = ( fn : Function , delay = SEARCH_TIMEOUT ) => {
21
- let timeoutId : ReturnType < typeof setTimeout > ;
22
- return function ( this : any , ...args : any [ ] ) {
23
- clearTimeout ( timeoutId ) ;
24
- timeoutId = setTimeout ( ( ) => fn . apply ( this , args ) , delay ) ;
25
- } ;
26
- } ;
29
+ const networkStatus : string = useAppSelector ( getNetworkStatus ) ;
30
+ const productFilters : string [ ] = useAppSelector ( getProductFilters ) ;
31
+ const componentFilters : string [ ] = useAppSelector ( getComponentFilters ) ;
32
+ const activeScreen : string = useAppSelector ( getActiveScreen ) ;
33
+ const activeSearch : string = useSelector ( getSearchQuery ) ;
27
34
28
- const debounceSearch = useCallback (
29
- debounce (
30
- ( newSearchTerm : string , productFilters : string [ ] , componentFilters : string [ ] ) =>
31
- actions . searchTree ( {
32
- query : newSearchTerm ,
33
- filters : {
34
- product : productFilters ,
35
- component : componentFilters
36
- } ,
37
- paging : {
38
- responseSize : appState . pageSize ,
39
- offset : 0
40
- }
41
- } ) ,
42
- SEARCH_TIMEOUT
43
- ) ,
44
- [ ]
45
- ) ;
35
+ const [ searchTerm , setSearchTerm ] = useState < string > ( activeSearch ) ;
36
+
37
+ const onClear = ( ) : void => {
38
+ if ( activeSearch !== '' ) {
39
+ actions . setQueryValue ( '' ) ;
40
+ }
41
+ } ;
46
42
47
- const onClearSearchTerm = ( ) : void => {
48
- actions . setQueryValue ( '' ) ;
49
- debounceSearch ( '' , [ ] , [ ] ) ;
43
+ const onChange = ( _ ?: ChangeEvent < HTMLInputElement > | undefined , newSearchTerm = '' ) : void => {
44
+ if ( ! / \S / . test ( newSearchTerm ) ) {
45
+ newSearchTerm = '' ;
46
+ }
47
+ if ( activeSearch !== newSearchTerm ) {
48
+ actions . setQueryValue ( newSearchTerm ) ;
49
+ }
50
50
} ;
51
51
52
- const onChangeSearchTerm = ( _ ?: ChangeEvent < HTMLInputElement > | undefined , newSearchTerm = '' ) : void => {
53
- actions . setQueryValue ( newSearchTerm ) ;
54
- debounceSearch ( newSearchTerm , appState . selectedProductFilters , appState . selectedComponentFilters ) ;
52
+ const onSearch = ( searchItem : string ) : void => {
53
+ if ( ! / \S / . test ( searchItem ) ) {
54
+ searchItem = '' ;
55
+ }
56
+ if ( activeSearch !== searchItem ) {
57
+ dispatch ( actions . setQueryValue ( searchItem ) ) ;
58
+ }
55
59
} ;
56
60
61
+ useEffect ( ( ) => {
62
+ if ( activeSearch !== searchTerm ) {
63
+ setSearchTerm ( activeSearch ) ;
64
+
65
+ fetchTreesData (
66
+ activeSearch ,
67
+ {
68
+ product : productFilters ,
69
+ component : componentFilters
70
+ } ,
71
+ {
72
+ responseSize : 20 , //appState.pageSize,
73
+ offset : 0
74
+ }
75
+ ) ;
76
+ }
77
+ } , [ activeSearch ] ) ;
78
+
57
79
return (
58
80
< div className = "guided-answer__header__searchField" >
59
81
< UISearchBox
60
82
className = "tree-search-field"
61
- value = { appState . query }
62
- readOnly = { appState . networkStatus === 'LOADING' }
83
+ defaultValue = { searchTerm }
84
+ readOnly = { networkStatus === 'LOADING' }
63
85
placeholder = "Search Guided Answers"
64
86
id = "search-field"
65
- onClear = { onClearSearchTerm }
66
- onChange = { onChangeSearchTerm } > </ UISearchBox >
67
- { appState . activeScreen === 'SEARCH' && < Filters /> }
87
+ onClear = { onClear }
88
+ onChange = { onChange }
89
+ onSearch = { onSearch } > </ UISearchBox >
90
+ { activeScreen === 'SEARCH' && < Filters /> }
68
91
</ div >
69
92
) ;
70
- }
93
+ } ;
0 commit comments