diff --git a/src/components/CurrencyInput.tsx b/src/components/CurrencyInput.tsx index acdb275..24a2854 100644 --- a/src/components/CurrencyInput.tsx +++ b/src/components/CurrencyInput.tsx @@ -103,14 +103,13 @@ export const CurrencyInput: FC = forwardRef< transformRawValue, }; - const formattedStateValue = - defaultValue !== undefined && defaultValue !== null + const [stateValue, setStateValue] = useState(() => + defaultValue != null ? formatValue({ ...formatValueOptions, decimalScale, value: String(defaultValue) }) - : userValue !== undefined && userValue !== null + : userValue != null ? formatValue({ ...formatValueOptions, decimalScale, value: String(userValue) }) - : ''; - - const [stateValue, setStateValue] = useState(formattedStateValue); + : '' + ); const [dirty, setDirty] = useState(false); const [cursor, setCursor] = useState(0); const [changeCount, setChangeCount] = useState(0); @@ -157,7 +156,7 @@ export const CurrencyInput: FC = forwardRef< ...formatValueOptions, }); - if (cursorPosition !== undefined && cursorPosition !== null) { + if (cursorPosition != null) { // Prevent cursor jumping let newCursor = cursorPosition + (formattedValue.length - value.length); newCursor = newCursor <= 0 ? (prefix ? prefix.length : 0) : newCursor; @@ -261,7 +260,7 @@ export const CurrencyInput: FC = forwardRef< const currentValue = parseFloat( - userValue !== undefined && userValue !== null + userValue != null ? String(userValue).replace(decimalSeparator, '.') : cleanValue({ value: stateValue, ...cleanValueOptions }) ) || 0; @@ -315,6 +314,13 @@ export const CurrencyInput: FC = forwardRef< onKeyUp && onKeyUp(event); }; + // Update state if userValue changes to undefined + useEffect(() => { + if (userValue == null && defaultValue == null) { + setStateValue(''); + } + }, [defaultValue, userValue]); + useEffect(() => { // prevent cursor jumping if editing value if ( @@ -333,8 +339,7 @@ export const CurrencyInput: FC = forwardRef< */ const getRenderValue = () => { if ( - userValue !== undefined && - userValue !== null && + userValue != null && stateValue !== '-' && (!decimalSeparator || stateValue !== decimalSeparator) ) { diff --git a/src/components/__tests__/CurrencyInput.spec.tsx b/src/components/__tests__/CurrencyInput.spec.tsx index 5b723dd..01942e4 100644 --- a/src/components/__tests__/CurrencyInput.spec.tsx +++ b/src/components/__tests__/CurrencyInput.spec.tsx @@ -3,6 +3,7 @@ import '@testing-library/jest-dom'; import { render, fireEvent, screen } from '@testing-library/react'; import userEvent from '@testing-library/user-event'; import CurrencyInput from '../CurrencyInput'; +import { act } from 'react-dom/test-utils'; describe('', () => { const onValueChangeSpy = jest.fn(); @@ -260,4 +261,32 @@ describe('', () => { expect(onKeyUpSpy).toBeCalledTimes(1); }); + + it('should update the input when prop value changes to another number', () => { + const { rerender } = render( + + ); + + const field = screen.getByRole('textbox'); + expect(field).toHaveValue('£1'); + + act(() => { + rerender(); + }); + + expect(field).toHaveValue('£2'); + }); + + it('should update the input when prop value changes to undefined', () => { + const { rerender } = render(); + + const field = screen.getByRole('textbox'); + expect(field).toHaveValue('£1'); + + act(() => { + rerender(); + }); + + expect(field).toHaveValue(''); + }); });