diff --git a/packages/amount-selectors/src/components/AmountSelectors.js b/packages/amount-selectors/src/components/AmountSelectors.js index fbb7f9230..ebd8df124 100644 --- a/packages/amount-selectors/src/components/AmountSelectors.js +++ b/packages/amount-selectors/src/components/AmountSelectors.js @@ -20,12 +20,22 @@ const selectorSizeToFontSize = { class AmountSelectors extends React.Component { state = { - value: this.props.value, + value: 0, disableBoth: false, tooltipText: "", - displayValue: this.props.value + displayValue: "" }; + componentDidMount() { + this.updateStateWithNewValue(this.props.value); + } + + componentDidUpdate(prevProps, prevState) { + if (prevProps.value !== this.props.value) { + this.updateStateWithNewValue(this.props.value); + } + } + // Conditions to disable both buttons, // see https://developer.mozilla.org/en-US/docs/Web/Guide/HTML/HTML5/Constraint_validation disableBoth = validity => @@ -49,21 +59,6 @@ class AmountSelectors extends React.Component { return this.props.onChange(validValue); }; - validValue = value => { - const parsedValue = parseFloat(value) || 0; - return Math.min(this.props.max, Math.max(this.props.min, parsedValue)); - }; - - updateDisplayValue = () => { - const validValue = this.validValue(this.state.value); - this.setState({ - value: validValue, - displayValue: validValue.toFixed(2) - }); - - return this.props.onChange(validValue); - }; - decrement = () => { const value = this.state.value - this.props.step; @@ -76,15 +71,31 @@ class AmountSelectors extends React.Component { this.onChange(Math.min(value, this.props.max), this.updateDisplayValue); }; - componentDidUpdate(prevProps, prevState) { - if (prevProps.value !== this.props.value) { - const validValue = this.validValue(this.props.value); - this.setState({ - value: validValue, - displayValue: validValue.toFixed(2) - }); - } - } + updateDisplayValue = () => { + const validValue = this.updateStateWithNewValue(this.state.value); + + return this.props.onChange(validValue); + }; + + getValidValue = value => { + const parsedValue = parseFloat(value) || 0; + const validValue = Math.min( + this.props.max, + Math.max(this.props.min, parsedValue) + ); + + return Number(validValue.toFixed(2)); + }; + + updateStateWithNewValue = value => { + const validValue = this.getValidValue(value); + this.setState({ + value: validValue, + displayValue: validValue.toFixed(2) + }); + + return validValue; + }; render() { return ( diff --git a/packages/amount-selectors/src/components/AmountSelectors.test.js b/packages/amount-selectors/src/components/AmountSelectors.test.js index 7cb27344d..dea3dc009 100644 --- a/packages/amount-selectors/src/components/AmountSelectors.test.js +++ b/packages/amount-selectors/src/components/AmountSelectors.test.js @@ -147,4 +147,16 @@ describe("Amount selectors", () => { expect(component.state().displayValue).toBe(expectedDisplayValue); }); }); + + test("getValidValue should return a valid value with 2 decimal places", () => { + const component = shallow(); + const { getValidValue } = component.instance(); + + const value = 3.345678; + const validValue = getValidValue(value); + + const expectedValue = Number(value.toFixed(2)); + + expect(validValue).toBe(expectedValue); + }); }); diff --git a/packages/amount-selectors/src/components/__snapshots__/AmountSelectors.story.storyshot b/packages/amount-selectors/src/components/__snapshots__/AmountSelectors.story.storyshot index b28146092..397e785e3 100644 --- a/packages/amount-selectors/src/components/__snapshots__/AmountSelectors.story.storyshot +++ b/packages/amount-selectors/src/components/__snapshots__/AmountSelectors.story.storyshot @@ -357,7 +357,7 @@ exports[`Storyshots Amount selectors Default 1`] = ` size={4} step={1} type="number" - value={0} + value="0.00" /> @@ -757,7 +757,7 @@ exports[`Storyshots Amount selectors Disabled typing 1`] = ` size={4} step={1} type="number" - value={0} + value="0.00" /> @@ -1157,7 +1157,7 @@ exports[`Storyshots Amount selectors Small size 1`] = ` size={4} step={1} type="number" - value={0} + value="0.00" /> @@ -1552,7 +1552,7 @@ exports[`Storyshots Amount selectors With 0.5 steps 1`] = ` size={4} step={0.5} type="number" - value={2} + value="2.00" /> @@ -1947,7 +1947,7 @@ exports[`Storyshots Amount selectors With 0.5 steps and step mismatch validation size={4} step={0.5} type="number" - value={2} + value="2.00" /> @@ -2342,7 +2342,7 @@ exports[`Storyshots Amount selectors With a max value of 3 1`] = ` size={4} step={0.5} type="number" - value={2} + value="2.00" /> @@ -2742,7 +2742,7 @@ exports[`Storyshots Amount selectors With onChange function 1`] = ` size={4} step={1} type="number" - value={0} + value="0.00" /> @@ -3137,7 +3137,7 @@ exports[`Storyshots Amount selectors With value set 1`] = ` size={4} step={1} type="number" - value={2} + value="2.00" /> @@ -3533,7 +3533,7 @@ exports[`Storyshots Amount selectors With value set after mount 1`] = ` size={4} step={1} type="number" - value={10} + value="10.00" />