import React from 'react' ; export type TrashBinState < T > = { current : T ; trash : T ; } ; export enum TrashBinActionType { /**
     * Sets the current state, a payload containing the new state must be provided. The payload must
     * be either the value of the new state or a function with the signature
     * `(state: TrashBinState<T>) => T`.
     */ Set , /**
     * Moves the current state into the trash state and sets it to the empty value.
     */ Clear , /**
     * Moves the trash state to the current state and sets it to the empty value.
     */ Restore } export type TrashBinAction < T > = { type : TrashBinActionType ; payload ? : T | ( ( state : TrashBinState < T > ) => T ) ; } ; export type TrashBinReducer < T > = React . Reducer < TrashBinState < T > , TrashBinAction < T > > ; export type TrashBinMergeFunc < T > = ( current : T , trash : T ) => T ; function makeTrashBinReducer < T > ( emptyValue , restoreFunc ? , clearFunc ? ) { return ( state , action ) => { switch ( action . type ) { case TrashBinActionType . Clear : if ( clearFunc === undefined ) { return { current : emptyValue , trash : state . current , } ; } return { current : emptyValue , trash : clearFunc ( state . current , state . trash ) , } ; case TrashBinActionType . Restore : if ( restoreFunc === undefined ) { return { current : state . trash , trash : emptyValue , } ; } return { current : restoreFunc ( state . current , state . trash ) , trash : emptyValue , } ; case TrashBinActionType . Set : if ( action . payload === undefined ) { throw new Error ( 'Expected a payload' ) ; } if ( typeof action . payload === 'function' ) { return { current : ( action . payload as ( state : TrashBinState < T > ) => T ) ( state ) , trash : state . trash , } ; } else { return { current : action . payload , trash : state . trash , } ; } default : console . error ( 'Unexpected action on the trashbin reducer' , action ) ; return state ; } } ; } param initialValues param emptyValue param restoreFunc param clearFunc export function useTrashBinReducer < T > ( initialValues , emptyValue , restoreFunc ? , clearFunc ? ) { return React . useReducer ( makeTrashBinReducer ( emptyValue , restoreFunc , clearFunc ) , { current : initialValues , trash : emptyValue , } ) ; }