diff --git a/package.json b/package.json index acad3e2..1558a16 100644 --- a/package.json +++ b/package.json @@ -60,6 +60,7 @@ "scripts": { "watch": "babel src --verbose --watch --out-dir dist --ignore '**/__tests__' --source-maps inline", "build": "rm -rf dist; babel src --out-dir dist --ignore '**/__tests__' --source-maps inline", + "build:watch": "babel src --verbose --watch --out-dir dist --ignore '**/__tests__' --source-maps inline", "prepare": "rm -rf ./dist && npm run build", "lint": "eslint src", "test": "jest", diff --git a/src/bootstrap/NumberInput.js b/src/bootstrap/NumberInput.js index 6715690..d3e1e14 100644 --- a/src/bootstrap/NumberInput.js +++ b/src/bootstrap/NumberInput.js @@ -10,8 +10,6 @@ import React from "react"; import PropTypes from "prop-types"; import { Input } from "./Input"; -export const NumberInput = ({ ...props }) => ; - NumberInput.propTypes = { /** Field label. */ label: PropTypes.string.isRequired, @@ -24,4 +22,38 @@ NumberInput.propTypes = { PropTypes.string, PropTypes.number, ]), + /** Function called when value changes. */ + onChange: PropTypes.func.isRequired, + /** Additional description dispaled to the right of input value. */ + inlineText: PropTypes.string, }; + +NumberInput.defaultProps = { + value: 0, +}; + +export function NumberInput({ onChange, inlineText, ...props }) { + return ( + +
+ {inlineText &&

{inlineText}

} + + +
+ + ); +} diff --git a/src/bootstrap/__tests__/NumberInput.test.js b/src/bootstrap/__tests__/NumberInput.test.js index e328940..d26e2e4 100644 --- a/src/bootstrap/__tests__/NumberInput.test.js +++ b/src/bootstrap/__tests__/NumberInput.test.js @@ -7,23 +7,39 @@ import React from "react"; -import { render } from "customTestRender"; +import { render, fireEvent } from "customTestRender"; import { NumberInput } from "../NumberInput"; - describe("", () => { - it("Render number input", () => { - const { container } = render( + const onChangeMock = jest.fn(); + let container; + let getByLabelText; + + beforeEach(() => { + ({ container, getByLabelText } = render( { - }} + value={1} + onChange={onChangeMock} /> - ); - expect(container.firstChild) - .toMatchSnapshot(); + )); + }); + + it("Render number input", () => { + expect(container.firstChild).toMatchSnapshot(); + }); + + it("Increase number with button", () => { + const increaseButton = getByLabelText("Increase"); + fireEvent.click(increaseButton); + expect(onChangeMock).toHaveBeenCalledWith({"target": {"value": 2}}); + }); + + it("Decrease number with button", () => { + const decreaseButton = getByLabelText("Decrease"); + fireEvent.click(decreaseButton); + expect(onChangeMock).toHaveBeenCalledWith({"target": {"value": 0}}); }); }); diff --git a/src/bootstrap/__tests__/__snapshots__/NumberInput.test.js.snap b/src/bootstrap/__tests__/__snapshots__/NumberInput.test.js.snap index ecc3104..67cf590 100644 --- a/src/bootstrap/__tests__/__snapshots__/NumberInput.test.js.snap +++ b/src/bootstrap/__tests__/__snapshots__/NumberInput.test.js.snap @@ -19,8 +19,30 @@ exports[` Render number input 1`] = ` class="form-control" id="1" type="number" - value="1123" + value="1" /> +
+ + +
0) { + return instance; + } + return undefined; +} + +/** Return object without keys that have undefined value. */ +export function withoutUndefinedKeys(instance) { + return Object.keys(instance).reduce( + (accumulator, key) => { + if (instance[key] !== undefined) { + accumulator[key] = instance[key]; + } + return accumulator; + }, + {}, + ); +}