import { useReducer , useEffect , useRef , useCallback } from 'react' ; import { SORT_ASC , SORT_DESC , } from '../reducer/admin/resource/list/queryReducer' ; import { SortPayload } from '../types' ; export interface SortProps { setSortField : ( field : string ) => void ; setSortOrder : ( order : string ) => void ; setSort : ( sort : SortPayload , order ? : string ) => void ; sort : SortPayload ; } interface Action { type : 'SET_SORT' | 'SET_SORT_FIELD' | 'SET_SORT_ORDER' ; payload : { sort ? : SortPayload ; field ? : string ; order ? : string ; } ; } const sortReducer = ( state , action ) : SortPayload => { switch ( action . type ) { case 'SET_SORT' : return action . payload . sort ; case 'SET_SORT_FIELD' : { const { field } = action . payload ; const order = state . field === field ? state . order === SORT_ASC ? SORT_DESC : SORT_ASC : SORT_ASC ; return { field , order } ; } case 'SET_SORT_ORDER' : { const { order } = action . payload ; return { ... state , order , } ; } default : return state ; } } ; export const defaultSort = { field : 'id' , order : 'DESC' } ; name function param { SortPayload } sort name function param { string } field name function param { string } order typedef SortProps property sort property { string } sort . field property { 'ASC' | 'DESC' } sort . order property { setSort } setSort property { setSortField } setSortField property { setSortOrder } setSortOrder example param initialSort param { string } initialSort . field param { string } initialSort . order returns { SortProps } const useSortState = ( initialSort = defaultSort ) : SortProps => { const [ sort , dispatch ] = useReducer ( sortReducer , initialSort ) ; const isFirstRender = useRef ( true ) ; useEffect ( ( ) => { if ( isFirstRender . current ) { isFirstRender . current = false ; return ; } dispatch ( { type : 'SET_SORT' , payload : { sort : initialSort } } ) ; } , [ initialSort . field , initialSort . order ] ) ; return { setSort : useCallback ( ( sort ) => dispatch ( { type : 'SET_SORT' , payload : { sort } } ) , [ dispatch ] ) , setSortField : useCallback ( ( field ) => dispatch ( { type : 'SET_SORT_FIELD' , payload : { field } } ) , [ dispatch ] ) , setSortOrder : useCallback ( ( order ) => dispatch ( { type : 'SET_SORT_ORDER' , payload : { order } } ) , [ dispatch ] ) , sort , } ; } ; export default useSortState ;