From 1d409a44a2ef7b5979a054dc2d9c28bfee06662c Mon Sep 17 00:00:00 2001 From: Jupp Mueller Date: Fri, 15 Apr 2022 15:01:17 -0700 Subject: [PATCH] feat: add HasManyFields2 This change adds HasManyfields2, a successor to HasManyFields that is more composable and easier to integrate with state management libraries like mobx and easier to adopt to server-side rendering and dynamic hydration (compared to HasManyfields). --- .storybook/main.js | 1 + .vscode/settings.json | 8 +- package.json | 25 +- src/components/Button/Button.stories.js | 111 ++- .../HasManyFields2/HasManyFields2.spec.tsx | 499 +++++++++++ .../HasManyFields2/HasManyFields2.stories.tsx | 188 +++++ .../HasManyFields2/HasManyFields2.tsx | 179 ++++ .../HasManyFields2/HasManyFields2Row.tsx | 82 ++ .../HasManyFields2/components/DragHandle.tsx | 27 + .../components/HasManyFields2Add.tsx | 35 + .../components/HasManyFields2Context.ts | 13 + src/components/Icon/FontAwesomeAPM.tsx | 5 +- src/index.ts | 1 + yarn.lock | 788 ++++++++++-------- 14 files changed, 1557 insertions(+), 405 deletions(-) create mode 100644 src/components/HasManyFields2/HasManyFields2.spec.tsx create mode 100644 src/components/HasManyFields2/HasManyFields2.stories.tsx create mode 100644 src/components/HasManyFields2/HasManyFields2.tsx create mode 100644 src/components/HasManyFields2/HasManyFields2Row.tsx create mode 100644 src/components/HasManyFields2/components/DragHandle.tsx create mode 100644 src/components/HasManyFields2/components/HasManyFields2Add.tsx create mode 100644 src/components/HasManyFields2/components/HasManyFields2Context.ts diff --git a/.storybook/main.js b/.storybook/main.js index 298a46362..eb1b687cb 100644 --- a/.storybook/main.js +++ b/.storybook/main.js @@ -13,6 +13,7 @@ module.exports = { docs: false, }, }, + '@storybook/addon-controls', '@storybook/addon-knobs', '@storybook/addon-actions', { diff --git a/.vscode/settings.json b/.vscode/settings.json index 3662b3700..1f8bef0a0 100644 --- a/.vscode/settings.json +++ b/.vscode/settings.json @@ -1,3 +1,9 @@ { - "typescript.tsdk": "node_modules/typescript/lib" + "typescript.tsdk": "node_modules/typescript/lib", + "prettier.configPath": ".prettierrc.json", + "eslint.format.enable": true, + "editor.defaultFormatter": "esbenp.prettier-vscode", + "[typescriptreact]": { + "editor.defaultFormatter": "esbenp.prettier-vscode" + } } \ No newline at end of file diff --git a/package.json b/package.json index 5f7eecb23..448b12958 100644 --- a/package.json +++ b/package.json @@ -43,6 +43,10 @@ "react-dom": ">= 16.8" }, "dependencies": { + "@dnd-kit/core": "^6.0.0", + "@dnd-kit/modifiers": "^6.0.0", + "@dnd-kit/sortable": "^7.0.0", + "@dnd-kit/utilities": "^3.1.0", "@fortawesome/fontawesome-free": "^6.2.0", "@fortawesome/fontawesome-svg-core": "^6.2.0", "@popperjs/core": "^2.10.1", @@ -90,15 +94,16 @@ "@babel/preset-react": "^7.16.7", "@babel/preset-typescript": "^7.16.7", "@jest/types": "^27.5.1", - "@storybook/addon-a11y": "^6.3.11", - "@storybook/addon-actions": "^6.3.11", - "@storybook/addon-essentials": "^6.3.11", - "@storybook/addon-knobs": "^6.3.1", - "@storybook/addon-links": "^6.3.11", - "@storybook/addon-storysource": "^6.3.11", - "@storybook/addon-viewport": "^6.3.11", - "@storybook/addons": "^6.3.11", - "@storybook/react": "^6.3.11", + "@storybook/addon-a11y": "^6.4.22", + "@storybook/addon-actions": "^6.4.22", + "@storybook/addon-controls": "^6.5.8", + "@storybook/addon-essentials": "^6.4.22", + "@storybook/addon-knobs": "^6.4.0", + "@storybook/addon-links": "^6.4.22", + "@storybook/addon-storysource": "^6.4.22", + "@storybook/addon-viewport": "^6.4.22", + "@storybook/addons": "^6.4.22", + "@storybook/react": "^6.4.22", "@testing-library/dom": "^8.13.0", "@testing-library/jest-dom": "^5.16.3", "@testing-library/react": "^11.2.6", @@ -144,6 +149,8 @@ "jest": "^27.5.1", "jsdom": "^11.12.0", "jsdom-global": "^3.0.2", + "mobx": "^6.5.0", + "mobx-react-lite": "^3.3.0", "prettier": "^2.5.1", "raf-stub": "^3.0.0", "react": "^16.14.0", diff --git a/src/components/Button/Button.stories.js b/src/components/Button/Button.stories.js index f8dbbbf0b..6d1a3976b 100644 --- a/src/components/Button/Button.stories.js +++ b/src/components/Button/Button.stories.js @@ -1,6 +1,6 @@ import { action } from '@storybook/addon-actions'; import { text, boolean, select } from '@storybook/addon-knobs'; -import React from 'react'; +import React, { useRef, useCallback, useState } from 'react'; import { buttonColors } from '../../tooling/colors'; import DropdownItem from '../Dropdown/DropdownItem'; import DropdownMenu from '../Dropdown/DropdownMenu'; @@ -11,24 +11,41 @@ import ButtonDropdown from './ButtonDropdown'; import ButtonGroup from './ButtonGroup'; import ButtonToolbar from './ButtonToolbar'; import ConfirmationButton from './ConfirmationButton'; +import Tooltip from '../Tooltip/Tooltip'; export default { title: 'Buttons', component: Button, }; -export const LiveExample = () => ( - -); +export const LiveExample = () => { + // const ref = useRef(null); + const [tooltipTarget, setTooltipTarget] = useState(); + const callbackRef = useCallback(node => { + if (node) { + setTooltipTarget(node); + } + }, []); + return ( + + { + tooltipTarget && + some tooltip stuff + + } + + + ); +}; export const Colors = () => ( @@ -45,38 +62,42 @@ export const Colors = () => ( ); -export const Disabled = () => ( - - - - - - - - - - - - -); +export const Disabled = () => { + // const ref = useRef(null); + return ( + + Some thing here + + + + + + + + + + + + ); +}; export const Outline = () => ( diff --git a/src/components/HasManyFields2/HasManyFields2.spec.tsx b/src/components/HasManyFields2/HasManyFields2.spec.tsx new file mode 100644 index 000000000..2ec92ec1d --- /dev/null +++ b/src/components/HasManyFields2/HasManyFields2.spec.tsx @@ -0,0 +1,499 @@ +import assert from 'assert'; +import { fireEvent, render, screen, act } from '@testing-library/react'; +import React from 'react'; +import { HasManyFields2, HasManyFields2Row } from './HasManyFields2'; + +const tick = async () => + new Promise((resolve) => { + setTimeout(resolve, 0); + }); + +describe(`<${HasManyFields2.name} />`, () => { + it('should render', async () => { + const props = { + addButtonLabel: 'Add a row', + disabled: false, + onOrderChanged: jest.fn(), + onAdd: jest.fn(), + reorderable: false, + maximumRows: 5, + minimumRows: 0, + }; + render( + + +
row_0 Content
+
+ +
row_1 Content
+
+
+ ); + + assert(screen.queryByText('row_0 Content')); + assert(screen.queryByText('row_1 Content')); + }); + + describe('add function', () => { + it('should not have add buttons when no add function supplied', async () => { + const props = { + addButtonLabel: 'add', + disabled: false, + onOrderChanged: jest.fn(), + onAdd: undefined, + reorderable: false, + maximumRows: 5, + minimumRows: 0, + }; + render( + + +
row_0 Content
+
+ +
row_1 Content
+
+
+ ); + + expect(() => screen.getByText('add')).toThrow(); + }); + + it('should have add buttons when add function supplied', async () => { + const props = { + addButtonLabel: 'add', + disabled: false, + onOrderChanged: jest.fn(), + onAdd: jest.fn(), + reorderable: false, + maximumRows: 5, + minimumRows: 0, + }; + render( + + +
row_0 Content
+
+ +
row_1 Content
+
+
+ ); + + expect(screen.getByText('add')).toBeTruthy(); + }); + + it('should call add function when add button clicked', async () => { + const addFunction = jest.fn(); + const props = { + addButtonLabel: 'add', + disabled: false, + onOrderChanged: jest.fn(), + onAdd: addFunction, + reorderable: false, + maximumRows: 5, + minimumRows: 0, + }; + render( + + +
row_0 Content
+
+ +
row_1 Content
+
+
+ ); + + const addButton = screen.getByText('add'); + addButton.click(); + expect(addFunction).toBeCalledTimes(1); + }); + + it('should allow setting of add button label', () => { + const addFunction = jest.fn(); + const addButtonLabel = '8b5776ff-cdcf-411c-8925-476d03c0be40'; + const props = { + addButtonLabel, + disabled: false, + onOrderChanged: jest.fn(), + onAdd: addFunction, + reorderable: false, + maximumRows: 5, + minimumRows: 0, + }; + render( + + +
row_0 Content
+
+ +
row_1 Content
+
+
+ ); + + const addButton = screen.getByText(addButtonLabel); + expect(addButton).toBeValid(); + }); + }); + + describe('reorderable', () => { + // setup to test ordering is difficult in `dnd-kit`. This solution was inspired by + // https://github.com/clauderic/dnd-kit/issues/261#issuecomment-923242587 + const height = 20; + const width = 100; + const offsetHeight = 'offsetHeight'; + const offsetWidth = 'offsetWidth'; + + const mockGetBoundingClientRect = (element: any, index: number) => + jest.spyOn(element, 'getBoundingClientRect').mockImplementation(() => { + return { + bottom: 0, + height, + left: 0, + right: 0, + top: index * height, + width, + x: 0, + y: index * height, + }; + }); + + const originalOffsetHeight = Object.getOwnPropertyDescriptor( + HTMLElement.prototype, + offsetHeight + ); + const originalOffsetWidth = Object.getOwnPropertyDescriptor(HTMLElement.prototype, offsetWidth); + + beforeAll(() => { + Object.defineProperty(HTMLElement.prototype, offsetHeight, { + configurable: true, + value: height, + }); + Object.defineProperty(HTMLElement.prototype, offsetWidth, { + configurable: true, + value: width, + }); + }); + + afterAll(() => { + Object.defineProperty(HTMLElement.prototype, offsetHeight, originalOffsetHeight!); + Object.defineProperty(HTMLElement.prototype, offsetWidth, originalOffsetWidth!); + }); + + it('should have grab handle when reorderable', async () => { + const props = { + addButtonLabel: 'add', + disabled: false, + onOrderChanged: jest.fn(), + onAdd: undefined, + reorderable: true, + maximumRows: 5, + minimumRows: 0, + }; + const { container } = render( + + +
row_0 Content
+
+ +
row_1 Content
+
+
+ ); + + expect(container.getElementsByClassName('fa-grip-vertical').length).toBeGreaterThan(0); + }); + + it('should not have grab handle when not reorderable', async () => { + const props = { + addButtonLabel: 'add', + disabled: false, + onOrderChanged: jest.fn(), + onAdd: undefined, + reorderable: false, + maximumRows: 5, + minimumRows: 0, + }; + const { container } = render( + + +
row_0 Content
+
+ +
row_1 Content
+
+
+ ); + + expect(container.getElementsByClassName('fa-grip-vertical').length).toBeLessThanOrEqual(0); + }); + + it('should call onOrderChanged when order changed', async () => { + Object.setPrototypeOf(window, Window.prototype); + + const orderChangedFunction = jest.fn(); + const props = { + addButtonLabel: 'add', + disabled: false, + onOrderChanged: orderChangedFunction, + onAdd: undefined, + reorderable: true, + maximumRows: 5, + minimumRows: 0, + }; + const { container } = render( + + +
row_0 Content
+
+ +
row_1 Content
+
+
+ ); + + const dragHandles = screen.getAllByTitle('drag-handle'); + const draggables = container.querySelectorAll('[aria-roledescription="sortable"]'); + + assert(draggables.length > 0); + + draggables.forEach((draggable: Element, index: number) => { + mockGetBoundingClientRect(draggable, index); + }); + + dragHandles.forEach((draggable: Element, index: number) => { + mockGetBoundingClientRect(draggable, index); + }); + + const dragHandleRow0 = dragHandles[0]; + assert(dragHandleRow0); + + await act(async () => { + await tick(); + fireEvent.focus(dragHandleRow0); + await tick(); + + fireEvent.keyDown(dragHandleRow0, { + code: 'Space', + }); + + await tick(); + fireEvent.keyUp(dragHandleRow0, { + code: 'Space', + }); + + await tick(); + fireEvent.keyDown(dragHandleRow0, { + code: 'ArrowDown', + }); + + await tick(); + fireEvent.keyUp(dragHandleRow0, { + code: 'ArrowDown', + }); + + await tick(); + fireEvent.keyDown(dragHandleRow0, { + code: 'Space', + }); + + await tick(); + fireEvent.keyUp(dragHandleRow0, { + code: 'Space', + }); + + await tick(); + }); + + expect(orderChangedFunction).toBeCalledWith(['row_1', 'row_0']); + }); + }); + + describe('disabled', () => { + it('should show disabledReason popup', async () => { + const props = { + addButtonLabel: 'add', + onOrderChanged: jest.fn(), + onAdd: undefined, + reorderable: true, + maximumRows: 5, + minimumRows: 0, + }; + const { container } = render( + + +
row_0 Content
+
+ +
row_1 Content
+
+
+ ); + + const row0 = container.querySelector('#test-row-0'); + assert(row0); + act(() => { + fireEvent.mouseOver(row0); + }); + + expect(Array.from(await screen.findAllByRole('tooltip')).length).toBeGreaterThan(0); + }); + }); + + describe('minimumRows', () => { + it('should allow deletion when minimumRows not reached', async () => { + const props = { + addButtonLabel: 'add', + disabled: false, + onOrderChanged: jest.fn(), + onAdd: undefined, + reorderable: false, + maximumRows: 5, + minimumRows: 0, + }; + render( + + +
row_0 Content
+
+ +
row_1 Content
+
+
+ ); + + expect(screen.getAllByRole('button', { name: 'Delete' }).length).toBe(2); + }); + + it('should not allow deletion when minimumRows reached', async () => { + const props = { + addButtonLabel: 'add', + disabled: false, + onOrderChanged: jest.fn(), + onAdd: undefined, + reorderable: false, + maximumRows: 5, + minimumRows: 2, + }; + render( + + +
row_0 Content
+
+ +
row_1 Content
+
+
+ ); + + expect(() => screen.getAllByRole('button', { name: 'Delete' })).toThrow(); + }); + }); + + describe('maximumRows', () => { + it('should allow add when maximumRows not reached', async () => { + const props = { + addButtonLabel: 'add', + disabled: false, + onOrderChanged: jest.fn(), + onAdd: jest.fn(), + reorderable: false, + maximumRows: 5, + minimumRows: 0, + }; + render( + + +
row_0 Content
+
+ +
row_1 Content
+
+
+ ); + + expect(screen.getByText('add')).toBeTruthy(); + }); + + it('should not allow add when maximumRows reached', async () => { + const props = { + addButtonLabel: 'add', + disabled: false, + onOrderChanged: jest.fn(), + onAdd: jest.fn(), + reorderable: false, + maximumRows: 2, + minimumRows: 0, + }; + render( + + +
row_0 Content
+
+ +
row_1 Content
+
+
+ ); + + expect(() => screen.getByText('add')).toThrow(); + }); + }); + + describe('deletable', () => { + it('should allow deletion', async () => { + const props = { + addButtonLabel: 'add', + disabled: false, + onOrderChanged: jest.fn(), + onAdd: jest.fn(), + reorderable: false, + maximumRows: 5, + minimumRows: 0, + }; + render( + + +
row_0 Content
+
+ +
row_1 Content
+
+
+ ); + + expect(screen.getAllByRole('button', { name: 'Delete' }).length).toBe(2); + }); + + it('should not allow delete when row is marked as not deletable', async () => { + const props = { + addButtonLabel: 'add', + disabled: false, + onOrderChanged: jest.fn(), + onAdd: jest.fn(), + reorderable: false, + maximumRows: 2, + minimumRows: 0, + }; + render( + + +
row_0 Content
+
+ +
row_1 Content
+
+
+ ); + + expect(screen.getAllByRole('button', { name: 'Delete' }).length).toBe(1); + }); + }); +}); diff --git a/src/components/HasManyFields2/HasManyFields2.stories.tsx b/src/components/HasManyFields2/HasManyFields2.stories.tsx new file mode 100644 index 000000000..aedb704b2 --- /dev/null +++ b/src/components/HasManyFields2/HasManyFields2.stories.tsx @@ -0,0 +1,188 @@ +import { Placement } from '@popperjs/core'; +import { action } from '@storybook/addon-actions'; +import { action as mobxAction, makeObservable, observable, runInAction } from 'mobx'; +import { observer } from 'mobx-react-lite'; +import React from 'react'; +import AddressInput from '../Address/AddressInput'; +import { HasManyFields2 } from './HasManyFields2'; +import { HasManyFields2Row } from './HasManyFields2Row'; + +export default { + title: 'HasManyFields2', + component: HasManyFields2, + argTypes: { + minimumRows: { control: { type: 'number', min: 0, max: 10 } }, + maxiumRows: { control: { type: 'number', min: 0, max: 10 } }, + reorderable: { control: 'boolean' }, + disabled: { control: 'boolean' }, + disabledReasonPlacement: { + options: [ + 'auto', + 'top', + 'bottom', + 'right', + 'left' + ], + control: { type: 'select' } + } + }, + subcomponents: { HasManyFields2Row } +}; + +type Address = { + address1: string; + address2: string; + city: string; + state: string; + postal: string; + countryCode: string; + rowId: string; +}; +class AddressStore { + addresses: Address[] = [ + { + address1: '90 Castilian Dr.', + address2: '', + city: 'Goleta', + state: 'CA', + postal: '93117', + countryCode: 'US', + rowId: crypto.randomUUID(), + }, + { + address1: '70 Castilian Dr.', + address2: '', + city: 'Goleta', + state: 'CA', + postal: '93117', + countryCode: 'US', + rowId: crypto.randomUUID(), + }, + ]; + + disabled = false; + + disabledReason: string | undefined; + + disabledReasonPlacement: Placement = 'auto'; + + maximumRows = 5; + + minimumRows = 1; + + reorderable = true; + + addButtonLabel = 'Add an Address'; + + constructor() { + makeObservable(this, { + addresses: observable, + addAddress: mobxAction, + disabled: observable, + disabledReason: observable, + disabledReasonPlacement: observable, + maximumRows: observable, + minimumRows: observable, + reorderable: observable, + addButtonLabel: observable, + orderChanged: mobxAction, + rowDeleted: mobxAction, + }); + } + + addAddress() { + const defaultAddress = { + address1: `${Math.floor(Math.random() * 1000)} Castilian Dr.`, + address2: '', + city: 'Goleta', + state: 'CA', + postal: '93117', + countryCode: 'US', + rowId: crypto.randomUUID(), + }; + this.addresses.push(defaultAddress); + } + + orderChanged(order: string[]) { + // TODO: make this not O(n^2) + const newAddresses = order + .map((rowId) => this.addresses.find((address) => address.rowId === rowId)) + .filter((address) => address !== undefined) as Address[]; + + this.addresses = newAddresses; + } + + rowDeleted(rowId: string) { + this.addresses = this.addresses.filter((address) => address.rowId !== rowId); + } +} +const addressStore = new AddressStore(); + +const HasManyAddresses: React.FC<{ store: AddressStore }> = observer(({ store }) => ( + { + store.addAddress(); + action('hasManyFields onAdd')(); + }} + onOrderChanged={(order) => { + store.orderChanged(order); + action('order changed')(order); + }} + maximumRows={store.maximumRows} + minimumRows={store.minimumRows} + reorderable={store.reorderable} + > + {store.addresses.map((address) => ( + { + store.rowDeleted(address.rowId); + action(`hasManyFieldsRow onDelete: rowId=${address.rowId}`)(); + }} + > + + + ))} + +)); + +interface Controls { + minimumRows: number; + maximumRows: number; + reorderable: boolean; + disabled: boolean; + disabledReason: string; + disabledReasonPlacement: Placement; + addButtonLabel: string; +} + +export const LiveExample = (args: Controls) => { + runInAction(() => { + addressStore.minimumRows = args.minimumRows; + addressStore.maximumRows = args.maximumRows; + addressStore.reorderable = args.reorderable; + addressStore.disabled = args.disabled; + addressStore.disabledReason = args.disabledReason; + addressStore.disabledReasonPlacement = args.disabledReasonPlacement; + addressStore.addButtonLabel = args.addButtonLabel; + }); + + return (); +} + +LiveExample.args = { + minimumRows: 1, + maximumRows: 5, + reorderable: true, + disabled: false, + disabledReason: 'You clicked disabled', + disabledReasonPlacement: 'auto', + addButtonLabel: 'Add an Address', +} diff --git a/src/components/HasManyFields2/HasManyFields2.tsx b/src/components/HasManyFields2/HasManyFields2.tsx new file mode 100644 index 000000000..9e5a9c834 --- /dev/null +++ b/src/components/HasManyFields2/HasManyFields2.tsx @@ -0,0 +1,179 @@ +import { + DndContext, + DragEndEvent, + DragStartEvent, + useSensors, + useSensor, + KeyboardSensor, + PointerSensor, +} from '@dnd-kit/core'; +import { restrictToVerticalAxis, restrictToWindowEdges } from '@dnd-kit/modifiers'; +import { + SortableContext, + verticalListSortingStrategy, + sortableKeyboardCoordinates, +} from '@dnd-kit/sortable'; +import React, { useEffect, useMemo, useState } from 'react'; +import HasManyFields2Add from './components/HasManyFields2Add'; +import HasManyFields2Context, { defaultContext } from './components/HasManyFields2Context'; +import { HasManyFields2Child } from './HasManyFields2Row'; + +export { HasManyFields2Row } from './HasManyFields2Row'; + +interface HasManyFields2Props { + children?: HasManyFields2Child | HasManyFields2Child[]; + addButtonLabel?: string; + disabled?: boolean; + onAdd?: () => void; + onOrderChanged?: (newOrderIds: string[]) => void; + maximumRows?: number | undefined; + minimumRows?: number | undefined; + reorderable?: boolean; +} + +export const HasManyFields2: React.FC = ({ + children, + onOrderChanged, + disabled, + addButtonLabel, + onAdd, + reorderable, + maximumRows, + minimumRows, +}) => { + const [activeId, setActiveId] = useState(null); + const [itemIds, setItemIds] = useState([]); + const [componentLookupMap, setComponentLookupMap] = useState>( + {} + ); + + useEffect(() => { + const newComponentLookupMap: Record = {}; + const newItemIds: string[] = []; + React.Children.forEach(children, (child) => { + if (!React.isValidElement(child)) { + return undefined; + } + newItemIds.push(child.props.rowId); + newComponentLookupMap[child.props.rowId] = child; + return undefined; + }); + setComponentLookupMap(newComponentLookupMap); + setItemIds(newItemIds); + }, [children]); + + const onDragStart = ({ active }: DragStartEvent) => { + if (disabled) { + return; + } + + if (!active) { + return; + } + + setActiveId(String(active.id)); + }; + + const swapItemIdPositions = (id1: string, id2: string) => { + const newItemIds = [...itemIds]; + const idx1 = newItemIds.indexOf(id1); + const idx2 = newItemIds.indexOf(id2); + const temp = newItemIds[idx1]; + newItemIds[idx1] = newItemIds[idx2]; + newItemIds[idx2] = temp; + return newItemIds; + }; + + const onDragEnd = ({ over }: DragEndEvent) => { + if (disabled) { + return; + } + + setActiveId(null); + + if (!over) { + return; + } + + if (!activeId) { + return; + } + + if (activeId === over.id) { + return; + } + + const newItemIds = swapItemIdPositions(activeId, String(over.id)); + setItemIds(newItemIds); + + if (onOrderChanged) { + onOrderChanged(newItemIds); + } + }; + + const onDragCancel = () => setActiveId(null); + + const contextCached = useMemo(() => { + return { + reorderable: reorderable === undefined ? defaultContext.reorderable : reorderable, + minimumRowsReached: minimumRows !== undefined && itemIds.length <= minimumRows, + }; + }, [reorderable, minimumRows, itemIds.length]); + + const shouldDisplayAddButton = Boolean(onAdd) && (!maximumRows || itemIds.length < maximumRows); + + const renderRows = useMemo( + () => ( + + {itemIds.map((itemId) => { + const child = componentLookupMap[itemId]; + if (child) { + const childDisabled = child.props.disabled === undefined + ? disabled + : child.props.disabled; + return React.cloneElement(child, { disabled: childDisabled }); + } + return child; + })} + + ), + [itemIds, contextCached, componentLookupMap, disabled] + ); + + const sensors = useSensors( + useSensor(PointerSensor, {}), + useSensor(KeyboardSensor, { + coordinateGetter: sortableKeyboardCoordinates, + }) + ); + + const isDraggable = reorderable && !disabled; + + return ( + <> + {isDraggable ? ( + + + {renderRows} + + + ) : ( + renderRows + )} + + {onAdd && ( + + {addButtonLabel || 'Add'} + + )} + + ); +}; + +export default HasManyFields2; diff --git a/src/components/HasManyFields2/HasManyFields2Row.tsx b/src/components/HasManyFields2/HasManyFields2Row.tsx new file mode 100644 index 000000000..24735c289 --- /dev/null +++ b/src/components/HasManyFields2/HasManyFields2Row.tsx @@ -0,0 +1,82 @@ +import { useSortable } from '@dnd-kit/sortable'; +import { CSS } from '@dnd-kit/utilities'; +import { Placement } from '@popperjs/core'; +import React, { useContext } from 'react'; +import ConfirmationButton from '../Button/ConfirmationButton'; +import Icon from '../Icon/Icon'; +import Tooltip from '../Tooltip/Tooltip'; +import DragHandle from './components/DragHandle'; +import HasManyFields2Context from './components/HasManyFields2Context'; + +export interface HasManyFields2RowProps { + deleteable?: boolean; + disabled?: boolean; + disabledReason?: string | undefined; + disabledReasonPlacement?: Placement | undefined; + onDelete?: (rowId?: string) => any; + rowId: string; +} + +export const HasManyFields2Row: React.FC = ({ + children, + rowId, + deleteable, + disabled, + disabledReason, + disabledReasonPlacement, + onDelete, +}) => { + const { attributes, listeners, setNodeRef, transform, transition } = useSortable({ id: rowId }); + + const { reorderable, minimumRowsReached } = useContext(HasManyFields2Context); + + const style = { + transform: CSS.Transform.toString(transform), + transition, + }; + + const showDeleteButton = !minimumRowsReached && deleteable; + + const showTooltip = disabled && disabledReason && disabledReasonPlacement; + const tooltipId = `rowId-${rowId}`; + const isDraggable = reorderable && !disabled; + + return ( +
+ {isDraggable ? : null} +
{children}
+ {showDeleteButton ? ( + { + e.preventDefault(); + onDelete?.(rowId); + }} + className="p-2 col-auto" + disabled={disabled} + > + + + ) : null} + {showTooltip && ( + + {disabledReason} + + )} +
+ ); +}; + +export type HasManyFields2Child = ReturnType; + +export default HasManyFields2Row; diff --git a/src/components/HasManyFields2/components/DragHandle.tsx b/src/components/HasManyFields2/components/DragHandle.tsx new file mode 100644 index 000000000..b46e864f2 --- /dev/null +++ b/src/components/HasManyFields2/components/DragHandle.tsx @@ -0,0 +1,27 @@ +import React from 'react'; +import Icon from '../../Icon/Icon'; + +const DragHandle = (props: any) => ( + <> +
+ + + +
+ {/* + // @ts-ignore */} + + + ) + + export default DragHandle; diff --git a/src/components/HasManyFields2/components/HasManyFields2Add.tsx b/src/components/HasManyFields2/components/HasManyFields2Add.tsx new file mode 100644 index 000000000..1cae402a7 --- /dev/null +++ b/src/components/HasManyFields2/components/HasManyFields2Add.tsx @@ -0,0 +1,35 @@ +import classNames from 'classnames'; +import PropTypes from 'prop-types'; +import React, { ReactChild } from 'react'; +import Button from '../../Button/Button'; +import Icon from '../../Icon/Icon'; + +export interface HasManyFields2AddProps { + children: ReactChild[] | ReactChild; + className?: string; + disabled: boolean | 0 | undefined; + onClick: (...args: any[]) => any; + visible?: boolean; +} + +const HasManyFields2Add = ({ children, className, visible, disabled, ...props }: HasManyFields2AddProps) => { + const classes = classNames('border-0', className); + + return ( + visible ? + : null + ); +}; + +HasManyFields2Add.propTypes = { + className: PropTypes.string, + children: PropTypes.node.isRequired, + disabled: PropTypes.bool, +}; + +HasManyFields2Add.displayName = 'HasManyFields2Add'; + +export default HasManyFields2Add; diff --git a/src/components/HasManyFields2/components/HasManyFields2Context.ts b/src/components/HasManyFields2/components/HasManyFields2Context.ts new file mode 100644 index 000000000..c125219a6 --- /dev/null +++ b/src/components/HasManyFields2/components/HasManyFields2Context.ts @@ -0,0 +1,13 @@ +import React from 'react'; + +export const defaultContext: { + reorderable: boolean; + minimumRowsReached: boolean; +} = { + reorderable: true, + minimumRowsReached: false, +}; + +const HasManyFields2Context = React.createContext(defaultContext); + +export default HasManyFields2Context; diff --git a/src/components/Icon/FontAwesomeAPM.tsx b/src/components/Icon/FontAwesomeAPM.tsx index 9d9d96234..7ef3ceabd 100644 --- a/src/components/Icon/FontAwesomeAPM.tsx +++ b/src/components/Icon/FontAwesomeAPM.tsx @@ -27,6 +27,7 @@ export interface FontAwesomeAPMProps extends React.HTMLAttributes { size?: 'xs' | 'sm' | 'lg' | '2x' | '3x' | '4x' | '5x'; spin?: boolean; stack?: '1x' | '2x'; + tabIndex?: number; tag?: keyof JSX.IntrinsicElements; iconStyle?: 'regular' | 'solid' | 'thin' | 'light' | 'duotone'; } @@ -50,6 +51,7 @@ export interface FontAwesomeAPMProps extends React.HTMLAttributes { * @param {String} [stack] Stack an icon on top of another * @param {String} [tag=span] The HTML tag to use as a string (eg 'i' or 'em') * @param {String} [iconStyle] Font Awesome classic family with multiple icon styles to choose from + * @param {Number} [tabIndex] Tab index as per HTML Spec * @module FontAwesome * @type {ReactClass} */ @@ -71,6 +73,7 @@ export default class FontAwesomeAPM extends React.Component tag: Tag = 'i', iconStyle, ariaLabel, + tabIndex, ...props } = this.props; @@ -110,7 +113,7 @@ export default class FontAwesomeAPM extends React.Component className && classNames.push(className); return ( - + {ariaLabel && {ariaLabel}} ); diff --git a/src/index.ts b/src/index.ts index a865f1dac..1020a2531 100755 --- a/src/index.ts +++ b/src/index.ts @@ -85,6 +85,7 @@ export { default as FormText } from './components/Form/FormText'; export { default as HasManyFields } from './components/HasManyFields/HasManyFields'; export { default as HasManyFieldsAdd } from './components/HasManyFields/HasManyFieldsAdd'; export { default as HasManyFieldsRow } from './components/HasManyFields/HasManyFieldsRow'; +export { default as HasManyFields2 } from './components/HasManyFields2/HasManyFields2'; export { default as HelpBubble } from './components/HelpBubble/HelpBubble'; export { default as Highlight } from './components/Highlight/Highlight'; export { default as Icon } from './components/Icon/Icon'; diff --git a/yarn.lock b/yarn.lock index 64bad7c95..07997811a 100644 --- a/yarn.lock +++ b/yarn.lock @@ -57,19 +57,24 @@ __metadata: "@babel/preset-env": ^7.16.11 "@babel/preset-react": ^7.16.7 "@babel/preset-typescript": ^7.16.7 + "@dnd-kit/core": ^6.0.0 + "@dnd-kit/modifiers": ^6.0.0 + "@dnd-kit/sortable": ^7.0.0 + "@dnd-kit/utilities": ^3.1.0 "@fortawesome/fontawesome-free": ^6.2.0 "@fortawesome/fontawesome-svg-core": ^6.2.0 "@jest/types": ^27.5.1 "@popperjs/core": ^2.10.1 - "@storybook/addon-a11y": ^6.3.11 - "@storybook/addon-actions": ^6.3.11 - "@storybook/addon-essentials": ^6.3.11 - "@storybook/addon-knobs": ^6.3.1 - "@storybook/addon-links": ^6.3.11 - "@storybook/addon-storysource": ^6.3.11 - "@storybook/addon-viewport": ^6.3.11 - "@storybook/addons": ^6.3.11 - "@storybook/react": ^6.3.11 + "@storybook/addon-a11y": ^6.4.22 + "@storybook/addon-actions": ^6.4.22 + "@storybook/addon-controls": ^6.5.8 + "@storybook/addon-essentials": ^6.4.22 + "@storybook/addon-knobs": ^6.4.0 + "@storybook/addon-links": ^6.4.22 + "@storybook/addon-storysource": ^6.4.22 + "@storybook/addon-viewport": ^6.4.22 + "@storybook/addons": ^6.4.22 + "@storybook/react": ^6.4.22 "@testing-library/dom": ^8.13.0 "@testing-library/jest-dom": ^5.16.3 "@testing-library/react": ^11.2.6 @@ -135,6 +140,8 @@ __metadata: lodash.uniqueid: ^4.0.1 lodash.without: ^4.4.0 memoize-one: ^5.1.1 + mobx: ^6.5.0 + mobx-react-lite: ^3.3.0 prettier: ^2.5.1 prop-types: ^15.7.2 raf-stub: ^3.0.0 @@ -1808,6 +1815,67 @@ __metadata: languageName: node linkType: hard +"@dnd-kit/accessibility@npm:^3.0.0": + version: 3.0.1 + resolution: "@dnd-kit/accessibility@npm:3.0.1" + dependencies: + tslib: ^2.0.0 + peerDependencies: + react: ">=16.8.0" + checksum: 0afc2c0fce9a1c107453620ca0da1778f182d340e74ffbc6e369ef0ac8943cafb929d3a6c0891d9b915aa23b2b92137ff4fad958f43118466586d8129a3359d5 + languageName: node + linkType: hard + +"@dnd-kit/core@npm:^6.0.0": + version: 6.0.5 + resolution: "@dnd-kit/core@npm:6.0.5" + dependencies: + "@dnd-kit/accessibility": ^3.0.0 + "@dnd-kit/utilities": ^3.2.0 + tslib: ^2.0.0 + peerDependencies: + react: ">=16.8.0" + react-dom: ">=16.8.0" + checksum: 09061e741bea9d2ba3987d01bb760c354fe29ca27996e74da3774e68c4783cf09ad21087703b5ffb036d3c2f86d16bea3c9f24466c2f266c8698f1e76c29d386 + languageName: node + linkType: hard + +"@dnd-kit/modifiers@npm:^6.0.0": + version: 6.0.0 + resolution: "@dnd-kit/modifiers@npm:6.0.0" + dependencies: + "@dnd-kit/utilities": ^3.2.0 + tslib: ^2.0.0 + peerDependencies: + "@dnd-kit/core": ^6.0.0 + checksum: 82c2640627aa9d04641fce2a48e8a374d2c6be6f96d75a110eaf69c043cce84685914e58453d54254b9bfc6041668ee3c34f8c4294b1ce367435900b210336e6 + languageName: node + linkType: hard + +"@dnd-kit/sortable@npm:^7.0.0": + version: 7.0.1 + resolution: "@dnd-kit/sortable@npm:7.0.1" + dependencies: + "@dnd-kit/utilities": ^3.2.0 + tslib: ^2.0.0 + peerDependencies: + "@dnd-kit/core": ^6.0.4 + react: ">=16.8.0" + checksum: b8b5ae504d57d6afb847c3ac8a865a3623c5915f4f0dd767017a17e6d1d36e144b74f6f90a17c07d5f8ddc83395a2db8bb90c420f017aee15bd88538b6f3f226 + languageName: node + linkType: hard + +"@dnd-kit/utilities@npm:^3.1.0, @dnd-kit/utilities@npm:^3.2.0": + version: 3.2.0 + resolution: "@dnd-kit/utilities@npm:3.2.0" + dependencies: + tslib: ^2.0.0 + peerDependencies: + react: ">=16.8.0" + checksum: 575e554992c5ff26622854b889b6288580f308e1125620a4aae55d0a113d47f05fdb7c6e2023ce51c58d5a206091fc1deac868222dd5f9c35c80c3e2f99db9af + languageName: node + linkType: hard + "@emotion/cache@npm:^10.0.27, @emotion/cache@npm:^10.0.9": version: 10.0.29 resolution: "@emotion/cache@npm:10.0.29" @@ -2551,18 +2619,18 @@ __metadata: languageName: node linkType: hard -"@storybook/addon-a11y@npm:^6.3.11": - version: 6.5.10 - resolution: "@storybook/addon-a11y@npm:6.5.10" +"@storybook/addon-a11y@npm:^6.4.22": + version: 6.5.13 + resolution: "@storybook/addon-a11y@npm:6.5.13" dependencies: - "@storybook/addons": 6.5.10 - "@storybook/api": 6.5.10 - "@storybook/channels": 6.5.10 - "@storybook/client-logger": 6.5.10 - "@storybook/components": 6.5.10 - "@storybook/core-events": 6.5.10 + "@storybook/addons": 6.5.13 + "@storybook/api": 6.5.13 + "@storybook/channels": 6.5.13 + "@storybook/client-logger": 6.5.13 + "@storybook/components": 6.5.13 + "@storybook/core-events": 6.5.13 "@storybook/csf": 0.0.2--canary.4566f4d.1 - "@storybook/theming": 6.5.10 + "@storybook/theming": 6.5.13 axe-core: ^4.2.0 core-js: ^3.8.2 global: ^4.4.0 @@ -2579,21 +2647,21 @@ __metadata: optional: true react-dom: optional: true - checksum: 8264ea473b6c8d9be3dd0f6f62849043e2834dfc78030c886ed9e75d4f6bd2617dc8a80a4a223f5d4282e32c8e1614428ce78e6c8eb734f7834877c666a53048 + checksum: 6f1ba1f0d97d652a5346a33e051e1ff79aa07786532c6450c5c3dd677c2195e3ee8792cda756d4556e5fbaa2a72a0631843aec2880121b3439bad3e401c25359 languageName: node linkType: hard -"@storybook/addon-actions@npm:6.5.10, @storybook/addon-actions@npm:^6.3.11": - version: 6.5.10 - resolution: "@storybook/addon-actions@npm:6.5.10" +"@storybook/addon-actions@npm:6.5.13, @storybook/addon-actions@npm:^6.4.22": + version: 6.5.13 + resolution: "@storybook/addon-actions@npm:6.5.13" dependencies: - "@storybook/addons": 6.5.10 - "@storybook/api": 6.5.10 - "@storybook/client-logger": 6.5.10 - "@storybook/components": 6.5.10 - "@storybook/core-events": 6.5.10 + "@storybook/addons": 6.5.13 + "@storybook/api": 6.5.13 + "@storybook/client-logger": 6.5.13 + "@storybook/components": 6.5.13 + "@storybook/core-events": 6.5.13 "@storybook/csf": 0.0.2--canary.4566f4d.1 - "@storybook/theming": 6.5.10 + "@storybook/theming": 6.5.13 core-js: ^3.8.2 fast-deep-equal: ^3.1.3 global: ^4.4.0 @@ -2614,21 +2682,21 @@ __metadata: optional: true react-dom: optional: true - checksum: b864ceb0ec9aef76c438cfd55977946619954e07b2b822205e5209e3901cc9ae669babc9304026e48e3717e075212c9e5175d62fd63183cf696e3e196f1f6dd8 + checksum: 2679174b1467281860cd6f11fac5ba505e44629eb11ee90713d1c954569cfb54d80aa822a0ed1be2f92f11ca62889fec3dca96f61b89cf238503e0cea4b1db9a languageName: node linkType: hard -"@storybook/addon-backgrounds@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/addon-backgrounds@npm:6.5.10" +"@storybook/addon-backgrounds@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/addon-backgrounds@npm:6.5.13" dependencies: - "@storybook/addons": 6.5.10 - "@storybook/api": 6.5.10 - "@storybook/client-logger": 6.5.10 - "@storybook/components": 6.5.10 - "@storybook/core-events": 6.5.10 + "@storybook/addons": 6.5.13 + "@storybook/api": 6.5.13 + "@storybook/client-logger": 6.5.13 + "@storybook/components": 6.5.13 + "@storybook/core-events": 6.5.13 "@storybook/csf": 0.0.2--canary.4566f4d.1 - "@storybook/theming": 6.5.10 + "@storybook/theming": 6.5.13 core-js: ^3.8.2 global: ^4.4.0 memoizerific: ^1.11.3 @@ -2643,23 +2711,23 @@ __metadata: optional: true react-dom: optional: true - checksum: 665ff48ea7fcea2fd126218a6253171f222cc15290f18c0b84b1f2b6adfc333328b79db762d404ff9caf449776162e66532a5a39626b28bd168abff3b58afdd2 + checksum: 1b18255e0d8dceca56b8d6cf672506176eedad3809f11879d9754652538bf004f90637c0bf557de5e7bc24d5db5410da79e61f131493cb87b27340611cb31cf5 languageName: node linkType: hard -"@storybook/addon-controls@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/addon-controls@npm:6.5.10" +"@storybook/addon-controls@npm:6.5.13, @storybook/addon-controls@npm:^6.5.8": + version: 6.5.13 + resolution: "@storybook/addon-controls@npm:6.5.13" dependencies: - "@storybook/addons": 6.5.10 - "@storybook/api": 6.5.10 - "@storybook/client-logger": 6.5.10 - "@storybook/components": 6.5.10 - "@storybook/core-common": 6.5.10 + "@storybook/addons": 6.5.13 + "@storybook/api": 6.5.13 + "@storybook/client-logger": 6.5.13 + "@storybook/components": 6.5.13 + "@storybook/core-common": 6.5.13 "@storybook/csf": 0.0.2--canary.4566f4d.1 - "@storybook/node-logger": 6.5.10 - "@storybook/store": 6.5.10 - "@storybook/theming": 6.5.10 + "@storybook/node-logger": 6.5.13 + "@storybook/store": 6.5.13 + "@storybook/theming": 6.5.13 core-js: ^3.8.2 lodash: ^4.17.21 ts-dedent: ^2.0.0 @@ -2671,32 +2739,32 @@ __metadata: optional: true react-dom: optional: true - checksum: 3c8152e4a4be960a7376ab1b1dc405fb3b6eeab367684766330cfb260519420f693d19b46225fd66976b4fa16e2e888585bfa571436507b2bf10f9905dfa968e + checksum: a4f86332686b5681366ad1f1eebb50cb9939ce3424ade64c0043b94827df15a34da0190101c8dc9a2b4b9af67fafd9d3fb50a5b98ff7a24fed6a37a2f8f37f27 languageName: node linkType: hard -"@storybook/addon-docs@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/addon-docs@npm:6.5.10" +"@storybook/addon-docs@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/addon-docs@npm:6.5.13" dependencies: "@babel/plugin-transform-react-jsx": ^7.12.12 "@babel/preset-env": ^7.12.11 "@jest/transform": ^26.6.2 "@mdx-js/react": ^1.6.22 - "@storybook/addons": 6.5.10 - "@storybook/api": 6.5.10 - "@storybook/components": 6.5.10 - "@storybook/core-common": 6.5.10 - "@storybook/core-events": 6.5.10 + "@storybook/addons": 6.5.13 + "@storybook/api": 6.5.13 + "@storybook/components": 6.5.13 + "@storybook/core-common": 6.5.13 + "@storybook/core-events": 6.5.13 "@storybook/csf": 0.0.2--canary.4566f4d.1 - "@storybook/docs-tools": 6.5.10 + "@storybook/docs-tools": 6.5.13 "@storybook/mdx1-csf": ^0.0.1 - "@storybook/node-logger": 6.5.10 - "@storybook/postinstall": 6.5.10 - "@storybook/preview-web": 6.5.10 - "@storybook/source-loader": 6.5.10 - "@storybook/store": 6.5.10 - "@storybook/theming": 6.5.10 + "@storybook/node-logger": 6.5.13 + "@storybook/postinstall": 6.5.13 + "@storybook/preview-web": 6.5.13 + "@storybook/source-loader": 6.5.13 + "@storybook/store": 6.5.13 + "@storybook/theming": 6.5.13 babel-loader: ^8.0.0 core-js: ^3.8.2 fast-deep-equal: ^3.1.3 @@ -2718,26 +2786,26 @@ __metadata: optional: true react-dom: optional: true - checksum: 5fecd18ea3ddbe820c23c06f34a75e2f448315ee08e6ea0ae548db4705a8148ec57804916b2c571556282e507dd543f4538b189d0366da73a592c58caa89d3ab - languageName: node - linkType: hard - -"@storybook/addon-essentials@npm:^6.3.11": - version: 6.5.10 - resolution: "@storybook/addon-essentials@npm:6.5.10" - dependencies: - "@storybook/addon-actions": 6.5.10 - "@storybook/addon-backgrounds": 6.5.10 - "@storybook/addon-controls": 6.5.10 - "@storybook/addon-docs": 6.5.10 - "@storybook/addon-measure": 6.5.10 - "@storybook/addon-outline": 6.5.10 - "@storybook/addon-toolbars": 6.5.10 - "@storybook/addon-viewport": 6.5.10 - "@storybook/addons": 6.5.10 - "@storybook/api": 6.5.10 - "@storybook/core-common": 6.5.10 - "@storybook/node-logger": 6.5.10 + checksum: 41755593a28497172d18efa623d6dd3054d5fe867f2a4bf02be3875a0d22ca5cf10f5bf3946c4fa6b392f955952aaf8c90b4ae88d0622a1e236c7333b58902c3 + languageName: node + linkType: hard + +"@storybook/addon-essentials@npm:^6.4.22": + version: 6.5.13 + resolution: "@storybook/addon-essentials@npm:6.5.13" + dependencies: + "@storybook/addon-actions": 6.5.13 + "@storybook/addon-backgrounds": 6.5.13 + "@storybook/addon-controls": 6.5.13 + "@storybook/addon-docs": 6.5.13 + "@storybook/addon-measure": 6.5.13 + "@storybook/addon-outline": 6.5.13 + "@storybook/addon-toolbars": 6.5.13 + "@storybook/addon-viewport": 6.5.13 + "@storybook/addons": 6.5.13 + "@storybook/api": 6.5.13 + "@storybook/core-common": 6.5.13 + "@storybook/node-logger": 6.5.13 core-js: ^3.8.2 regenerator-runtime: ^0.13.7 ts-dedent: ^2.0.0 @@ -2778,11 +2846,11 @@ __metadata: optional: true webpack: optional: true - checksum: 968286922924840bd00221d17e0499b98c153677ea9e220e07ab2e34d17d76670d4549dbb517cc35326b890723cc08d7b138a22662aa508e51d864e1f7b6975b + checksum: a7b1b34c7fbf0d863cf8dab3160cc267516cbcbeb155c4f91aab2c1d6005b23d5662a9104be0d733476ba4a0c8328ea899ae46bf55a9bddda5ce41996737b358 languageName: node linkType: hard -"@storybook/addon-knobs@npm:^6.3.1": +"@storybook/addon-knobs@npm:^6.4.0": version: 6.4.0 resolution: "@storybook/addon-knobs@npm:6.4.0" dependencies: @@ -2814,15 +2882,15 @@ __metadata: languageName: node linkType: hard -"@storybook/addon-links@npm:^6.3.11": - version: 6.5.10 - resolution: "@storybook/addon-links@npm:6.5.10" +"@storybook/addon-links@npm:^6.4.22": + version: 6.5.13 + resolution: "@storybook/addon-links@npm:6.5.13" dependencies: - "@storybook/addons": 6.5.10 - "@storybook/client-logger": 6.5.10 - "@storybook/core-events": 6.5.10 + "@storybook/addons": 6.5.13 + "@storybook/client-logger": 6.5.13 + "@storybook/core-events": 6.5.13 "@storybook/csf": 0.0.2--canary.4566f4d.1 - "@storybook/router": 6.5.10 + "@storybook/router": 6.5.13 "@types/qs": ^6.9.5 core-js: ^3.8.2 global: ^4.4.0 @@ -2838,19 +2906,19 @@ __metadata: optional: true react-dom: optional: true - checksum: 5ffecdc7f1aac3d9f08ad443a05977da260f6cfbe9f9207bb9c6890dd797eb0304e41527cf70c6c9c68f69f98569ef89f5463bec57209814ff57471c1f0592d6 + checksum: 0bbe14652320c77dbcbcd0a6f45e4776de35475cca43b9825c36424e6ccc250fac4a172cdf01304debdc3c93d74ad2ea3bafb8a752e9a52a5e860f5bb9a397c2 languageName: node linkType: hard -"@storybook/addon-measure@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/addon-measure@npm:6.5.10" +"@storybook/addon-measure@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/addon-measure@npm:6.5.13" dependencies: - "@storybook/addons": 6.5.10 - "@storybook/api": 6.5.10 - "@storybook/client-logger": 6.5.10 - "@storybook/components": 6.5.10 - "@storybook/core-events": 6.5.10 + "@storybook/addons": 6.5.13 + "@storybook/api": 6.5.13 + "@storybook/client-logger": 6.5.13 + "@storybook/components": 6.5.13 + "@storybook/core-events": 6.5.13 "@storybook/csf": 0.0.2--canary.4566f4d.1 core-js: ^3.8.2 global: ^4.4.0 @@ -2862,19 +2930,19 @@ __metadata: optional: true react-dom: optional: true - checksum: 7a6be7fc80be358c329694ab5eb75a027210afaa8185c04774c741fdca4871b90937d46d3cd16f66d195dd78bb20d3f8734f3aa0863636119895f9c6253e834a + checksum: 4bf1823f83a51e773cb941329bd1e637fba7d84c238a2af442eba4ab9950bda2d199bfa18194c62d7e25891166d8c89bf130303fc6c94d5aafa2eb0aaaeafa27 languageName: node linkType: hard -"@storybook/addon-outline@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/addon-outline@npm:6.5.10" +"@storybook/addon-outline@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/addon-outline@npm:6.5.13" dependencies: - "@storybook/addons": 6.5.10 - "@storybook/api": 6.5.10 - "@storybook/client-logger": 6.5.10 - "@storybook/components": 6.5.10 - "@storybook/core-events": 6.5.10 + "@storybook/addons": 6.5.13 + "@storybook/api": 6.5.13 + "@storybook/client-logger": 6.5.13 + "@storybook/components": 6.5.13 + "@storybook/core-events": 6.5.13 "@storybook/csf": 0.0.2--canary.4566f4d.1 core-js: ^3.8.2 global: ^4.4.0 @@ -2888,21 +2956,21 @@ __metadata: optional: true react-dom: optional: true - checksum: 8d3e12a612fd51b3b8c49f6ff6ac145f510cfba85b00e08b0df625b99f9677c0532060bd8a132ea70e8052d9c09847bdba27caa1b69e51dd6d7845d38621dccf + checksum: f9ea9278ba7dd118b9db2dc8b695d661d2d289d4e52f5af02ba0e30f13245043f0c565a71925d8111694a3a02e6b8b459fbd42786fe794895cdb5c8345adf5f5 languageName: node linkType: hard -"@storybook/addon-storysource@npm:^6.3.11": - version: 6.5.10 - resolution: "@storybook/addon-storysource@npm:6.5.10" +"@storybook/addon-storysource@npm:^6.4.22": + version: 6.5.13 + resolution: "@storybook/addon-storysource@npm:6.5.13" dependencies: - "@storybook/addons": 6.5.10 - "@storybook/api": 6.5.10 - "@storybook/client-logger": 6.5.10 - "@storybook/components": 6.5.10 - "@storybook/router": 6.5.10 - "@storybook/source-loader": 6.5.10 - "@storybook/theming": 6.5.10 + "@storybook/addons": 6.5.13 + "@storybook/api": 6.5.13 + "@storybook/client-logger": 6.5.13 + "@storybook/components": 6.5.13 + "@storybook/router": 6.5.13 + "@storybook/source-loader": 6.5.13 + "@storybook/theming": 6.5.13 core-js: ^3.8.2 estraverse: ^5.2.0 loader-utils: ^2.0.0 @@ -2917,19 +2985,19 @@ __metadata: optional: true react-dom: optional: true - checksum: 20dde7aa87cb2255e5cbe4992be622610ae55e32032b6dddb490f490ed35e600f38b0de48de6556dad85e88963ce2a5513e5b09ac21d40a83e3cb5fae8952a90 + checksum: 35ad7b940df64b036c36edc1d203da8016203c2430ae98a380b33fef4ffbfe040651db61f54ef5a9e6edec298e58e660ddd933eb67a1563ce1e39faedbc56cba languageName: node linkType: hard -"@storybook/addon-toolbars@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/addon-toolbars@npm:6.5.10" +"@storybook/addon-toolbars@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/addon-toolbars@npm:6.5.13" dependencies: - "@storybook/addons": 6.5.10 - "@storybook/api": 6.5.10 - "@storybook/client-logger": 6.5.10 - "@storybook/components": 6.5.10 - "@storybook/theming": 6.5.10 + "@storybook/addons": 6.5.13 + "@storybook/api": 6.5.13 + "@storybook/client-logger": 6.5.13 + "@storybook/components": 6.5.13 + "@storybook/theming": 6.5.13 core-js: ^3.8.2 regenerator-runtime: ^0.13.7 peerDependencies: @@ -2940,20 +3008,20 @@ __metadata: optional: true react-dom: optional: true - checksum: 49c44596fdee713703ed69c47895a21151892d48af27d859f0c8c1b8be0b08be7e4945fadcb9053f6025c29dba93f0d5cd8ba34f090bd025e0d9ef5859e5bc75 + checksum: ec85023ffda5bdefe96cf6d6954c86fba67be190bb31cf3bb777d0a2493d606c78bed84d4bb19611d4114a35ba94f1efcc8331bc6032e0f9376a6fb797dc3ec2 languageName: node linkType: hard -"@storybook/addon-viewport@npm:6.5.10, @storybook/addon-viewport@npm:^6.3.11": - version: 6.5.10 - resolution: "@storybook/addon-viewport@npm:6.5.10" +"@storybook/addon-viewport@npm:6.5.13, @storybook/addon-viewport@npm:^6.4.22": + version: 6.5.13 + resolution: "@storybook/addon-viewport@npm:6.5.13" dependencies: - "@storybook/addons": 6.5.10 - "@storybook/api": 6.5.10 - "@storybook/client-logger": 6.5.10 - "@storybook/components": 6.5.10 - "@storybook/core-events": 6.5.10 - "@storybook/theming": 6.5.10 + "@storybook/addons": 6.5.13 + "@storybook/api": 6.5.13 + "@storybook/client-logger": 6.5.13 + "@storybook/components": 6.5.13 + "@storybook/core-events": 6.5.13 + "@storybook/theming": 6.5.13 core-js: ^3.8.2 global: ^4.4.0 memoizerific: ^1.11.3 @@ -2967,21 +3035,21 @@ __metadata: optional: true react-dom: optional: true - checksum: 6cbd32053d2b4947942b0bab0ab016817988192d52361b4f2e08420f6d94128174974a0ec9b7ee4167de8f7cb91b3a3a8c8336a398a21cb567ba633efbf9e2cf + checksum: ff602c8080c26a8513f76b9ba2cb2e287e31df598a5235aee8fa8c0337bb7e8e7d65620d03f2aa452801653c41d35ddf9dbfdb6a26d4f2b4d0cc7cff7b580915 languageName: node linkType: hard -"@storybook/addons@npm:6.5.10, @storybook/addons@npm:^6.3.11": - version: 6.5.10 - resolution: "@storybook/addons@npm:6.5.10" +"@storybook/addons@npm:6.5.13, @storybook/addons@npm:^6.4.22": + version: 6.5.13 + resolution: "@storybook/addons@npm:6.5.13" dependencies: - "@storybook/api": 6.5.10 - "@storybook/channels": 6.5.10 - "@storybook/client-logger": 6.5.10 - "@storybook/core-events": 6.5.10 + "@storybook/api": 6.5.13 + "@storybook/channels": 6.5.13 + "@storybook/client-logger": 6.5.13 + "@storybook/core-events": 6.5.13 "@storybook/csf": 0.0.2--canary.4566f4d.1 - "@storybook/router": 6.5.10 - "@storybook/theming": 6.5.10 + "@storybook/router": 6.5.13 + "@storybook/theming": 6.5.13 "@types/webpack-env": ^1.16.0 core-js: ^3.8.2 global: ^4.4.0 @@ -2989,21 +3057,21 @@ __metadata: peerDependencies: react: ^16.8.0 || ^17.0.0 || ^18.0.0 react-dom: ^16.8.0 || ^17.0.0 || ^18.0.0 - checksum: 9143908c77ab77064a5da3de1fcfb218e5f0e561f4b8a083e59b4104e442567c87fb571a752bb11c469317fc3bbcb9c2e42ebd9a5a41f825b3fd67a920d90621 + checksum: 28589da00e8a26b44d4ed8a1938fe934187a85b187e2a0dcd3e6d114460ed5a07fbfe0a89a4d899739767b379015cbabadd47c5c266457922a8c4255e3d769a4 languageName: node linkType: hard -"@storybook/api@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/api@npm:6.5.10" +"@storybook/api@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/api@npm:6.5.13" dependencies: - "@storybook/channels": 6.5.10 - "@storybook/client-logger": 6.5.10 - "@storybook/core-events": 6.5.10 + "@storybook/channels": 6.5.13 + "@storybook/client-logger": 6.5.13 + "@storybook/core-events": 6.5.13 "@storybook/csf": 0.0.2--canary.4566f4d.1 - "@storybook/router": 6.5.10 + "@storybook/router": 6.5.13 "@storybook/semver": ^7.3.2 - "@storybook/theming": 6.5.10 + "@storybook/theming": 6.5.13 core-js: ^3.8.2 fast-deep-equal: ^3.1.3 global: ^4.4.0 @@ -3017,31 +3085,31 @@ __metadata: peerDependencies: react: ^16.8.0 || ^17.0.0 || ^18.0.0 react-dom: ^16.8.0 || ^17.0.0 || ^18.0.0 - checksum: 49e01f35fa6de776329407533c0449aac84bbc9404bf717b1cebff5dc8961618956d7ba0003361c4e6cdc24e898619f778fea15db5a30eb320fc73a4b53adb40 + checksum: dd7c8db0cdea2a47ab835c02217f10f99c54bfbf6d826deadf0b160ece4c94b1cb2558cfbaff4e4244c5c776095028a164762bd8de19fcfe10ae318fe0a3fbb4 languageName: node linkType: hard -"@storybook/builder-webpack4@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/builder-webpack4@npm:6.5.10" +"@storybook/builder-webpack4@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/builder-webpack4@npm:6.5.13" dependencies: "@babel/core": ^7.12.10 - "@storybook/addons": 6.5.10 - "@storybook/api": 6.5.10 - "@storybook/channel-postmessage": 6.5.10 - "@storybook/channels": 6.5.10 - "@storybook/client-api": 6.5.10 - "@storybook/client-logger": 6.5.10 - "@storybook/components": 6.5.10 - "@storybook/core-common": 6.5.10 - "@storybook/core-events": 6.5.10 - "@storybook/node-logger": 6.5.10 - "@storybook/preview-web": 6.5.10 - "@storybook/router": 6.5.10 + "@storybook/addons": 6.5.13 + "@storybook/api": 6.5.13 + "@storybook/channel-postmessage": 6.5.13 + "@storybook/channels": 6.5.13 + "@storybook/client-api": 6.5.13 + "@storybook/client-logger": 6.5.13 + "@storybook/components": 6.5.13 + "@storybook/core-common": 6.5.13 + "@storybook/core-events": 6.5.13 + "@storybook/node-logger": 6.5.13 + "@storybook/preview-web": 6.5.13 + "@storybook/router": 6.5.13 "@storybook/semver": ^7.3.2 - "@storybook/store": 6.5.10 - "@storybook/theming": 6.5.10 - "@storybook/ui": 6.5.10 + "@storybook/store": 6.5.13 + "@storybook/theming": 6.5.13 + "@storybook/ui": 6.5.13 "@types/node": ^14.0.10 || ^16.0.0 "@types/webpack": ^4.41.26 autoprefixer: ^9.8.6 @@ -3078,60 +3146,60 @@ __metadata: peerDependenciesMeta: typescript: optional: true - checksum: 26921bbc477b8cc69a9515996f4e4a4b79ba43f783dab96930067c48ca6d127397ab7a461c25e3120468b99cad1cb641fbb85a0cd6ecf25661e2da2c182a97e6 + checksum: a95fea3951479d7724155a2ddbf2b04a8bfc0e7fddbf8415caed508b94ad71f7dc8d5d25464061ef26f3b4670f49f6ed40198b48b3f646d7af17d8daee5e89cb languageName: node linkType: hard -"@storybook/channel-postmessage@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/channel-postmessage@npm:6.5.10" +"@storybook/channel-postmessage@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/channel-postmessage@npm:6.5.13" dependencies: - "@storybook/channels": 6.5.10 - "@storybook/client-logger": 6.5.10 - "@storybook/core-events": 6.5.10 + "@storybook/channels": 6.5.13 + "@storybook/client-logger": 6.5.13 + "@storybook/core-events": 6.5.13 core-js: ^3.8.2 global: ^4.4.0 qs: ^6.10.0 telejson: ^6.0.8 - checksum: c0bb9cccb8071b6d68ba879f23a9eb52ee9da5563f93a235f2496838a691c7e3f7ed81e550f924bbdc305357e5a81d4b409254c7ce4d5bed53920f0ea357d4f6 + checksum: 8d6ccfff2aeafaae30b5fc1af856be8d06b3703b96841ecc0d70959e51542514901763e1a291e1d0278afe31b23cc5c0a5b351994f321e9bd03490be5b51e2d0 languageName: node linkType: hard -"@storybook/channel-websocket@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/channel-websocket@npm:6.5.10" +"@storybook/channel-websocket@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/channel-websocket@npm:6.5.13" dependencies: - "@storybook/channels": 6.5.10 - "@storybook/client-logger": 6.5.10 + "@storybook/channels": 6.5.13 + "@storybook/client-logger": 6.5.13 core-js: ^3.8.2 global: ^4.4.0 telejson: ^6.0.8 - checksum: e8c6df2ae02a7a257f0503cd489a2e787a419d23bc1c077868520db0ad61642001655543d594c4903f346112dc27698acfc9501c07d02bb2027d2fbb9f98f1eb + checksum: 16e3b1a51a1af093f6c78ab7ca9c4c69ed05b45fd9bbdefb3050809e92064ccbf7a46f6800d21df2555e5d110d64735dd8d35155e54c3118fa7b4efe6b3b0457 languageName: node linkType: hard -"@storybook/channels@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/channels@npm:6.5.10" +"@storybook/channels@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/channels@npm:6.5.13" dependencies: core-js: ^3.8.2 ts-dedent: ^2.0.0 util-deprecate: ^1.0.2 - checksum: 3837d2aff1575aa8d5af77162781b2824b909f18a7e7d3b961e6a14854b58011a56bd4f6c92bf065b8856fbcf7925a5849ffc56e42badac240701a560a26c627 + checksum: 5b8881a2799a4c5ceafea40bc2c8bad1a31649036341eec8da5a77acf79a9d610afeaa5b4ed5d06022ed3c74cb9562dcfc5046d62fd8d27cd65bcba09aa5e903 languageName: node linkType: hard -"@storybook/client-api@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/client-api@npm:6.5.10" +"@storybook/client-api@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/client-api@npm:6.5.13" dependencies: - "@storybook/addons": 6.5.10 - "@storybook/channel-postmessage": 6.5.10 - "@storybook/channels": 6.5.10 - "@storybook/client-logger": 6.5.10 - "@storybook/core-events": 6.5.10 + "@storybook/addons": 6.5.13 + "@storybook/channel-postmessage": 6.5.13 + "@storybook/channels": 6.5.13 + "@storybook/client-logger": 6.5.13 + "@storybook/core-events": 6.5.13 "@storybook/csf": 0.0.2--canary.4566f4d.1 - "@storybook/store": 6.5.10 + "@storybook/store": 6.5.13 "@types/qs": ^6.9.5 "@types/webpack-env": ^1.16.0 core-js: ^3.8.2 @@ -3148,27 +3216,27 @@ __metadata: peerDependencies: react: ^16.8.0 || ^17.0.0 || ^18.0.0 react-dom: ^16.8.0 || ^17.0.0 || ^18.0.0 - checksum: c939abed09fc71b91a2813b4d817a00f717dcef6c51444b091ad3676dd0e904673252dbb9e027192e87db72aeb950a76438c5ae5829471fe18c053887049f151 + checksum: b0af25786b9144a55ebaa7754dd1b3701f5f8796770eaf59e7bc6d21ada12911fcbe4bf0da037d01bdda2c46138f265a948befe1f3de356fdc0ae3af80973388 languageName: node linkType: hard -"@storybook/client-logger@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/client-logger@npm:6.5.10" +"@storybook/client-logger@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/client-logger@npm:6.5.13" dependencies: core-js: ^3.8.2 global: ^4.4.0 - checksum: 6aa15e27e1f805b34332f647545eb53277c87492044073daf31ac6151b274cb7da6d2c8b3831484bb0c4c410f8adc1bb13322c3b80ee2f88e30856721c7d9ab1 + checksum: 0252d9364a0b2a8faae588fdb29aaf458f660904c330ec7af790f63a668710926ece8f087f58f9b1bebb052e2fe517b8b74867e7500567499cc710ab71ccbbab languageName: node linkType: hard -"@storybook/components@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/components@npm:6.5.10" +"@storybook/components@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/components@npm:6.5.13" dependencies: - "@storybook/client-logger": 6.5.10 + "@storybook/client-logger": 6.5.13 "@storybook/csf": 0.0.2--canary.4566f4d.1 - "@storybook/theming": 6.5.10 + "@storybook/theming": 6.5.13 core-js: ^3.8.2 memoizerific: ^1.11.3 qs: ^6.10.0 @@ -3177,24 +3245,24 @@ __metadata: peerDependencies: react: ^16.8.0 || ^17.0.0 || ^18.0.0 react-dom: ^16.8.0 || ^17.0.0 || ^18.0.0 - checksum: ee0d520048296a4312b3018759a6b01fcc2c3fa867c64dd938e0c5ae6e4d907f599286323855128901420cd45955890e8cdb767c7b381be75d67729d89ca368a + checksum: 5d01c0f445f6574ccadcfa79afd99c078bd1f81d65e59186361100dc57bd73ccbb877e5a8bbc49dd6551bce1b32fbe6f135c2bea15c0126a83faf222cfaed878 languageName: node linkType: hard -"@storybook/core-client@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/core-client@npm:6.5.10" +"@storybook/core-client@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/core-client@npm:6.5.13" dependencies: - "@storybook/addons": 6.5.10 - "@storybook/channel-postmessage": 6.5.10 - "@storybook/channel-websocket": 6.5.10 - "@storybook/client-api": 6.5.10 - "@storybook/client-logger": 6.5.10 - "@storybook/core-events": 6.5.10 + "@storybook/addons": 6.5.13 + "@storybook/channel-postmessage": 6.5.13 + "@storybook/channel-websocket": 6.5.13 + "@storybook/client-api": 6.5.13 + "@storybook/client-logger": 6.5.13 + "@storybook/core-events": 6.5.13 "@storybook/csf": 0.0.2--canary.4566f4d.1 - "@storybook/preview-web": 6.5.10 - "@storybook/store": 6.5.10 - "@storybook/ui": 6.5.10 + "@storybook/preview-web": 6.5.13 + "@storybook/store": 6.5.13 + "@storybook/ui": 6.5.13 airbnb-js-shims: ^2.2.1 ansi-to-html: ^0.6.11 core-js: ^3.8.2 @@ -3212,13 +3280,13 @@ __metadata: peerDependenciesMeta: typescript: optional: true - checksum: c8bc4b41af51664461716dab87a176e7ac408f75568ff884b80435bbfce197ba7dd607ba83a2b36bdfbc90236e2e88848089a3ae27732a60b210fbd60ed3597c + checksum: c4350b1b579f0781a239fdede79f1d0975e297ecb61ba4096834d62bd553420615231dc9146c446d0178088e83863fd9dc720fbb4485b5779fac7d99ce3eeb9e languageName: node linkType: hard -"@storybook/core-common@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/core-common@npm:6.5.10" +"@storybook/core-common@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/core-common@npm:6.5.13" dependencies: "@babel/core": ^7.12.10 "@babel/plugin-proposal-class-properties": ^7.12.1 @@ -3242,7 +3310,7 @@ __metadata: "@babel/preset-react": ^7.12.10 "@babel/preset-typescript": ^7.12.7 "@babel/register": ^7.12.1 - "@storybook/node-logger": 6.5.10 + "@storybook/node-logger": 6.5.13 "@storybook/semver": ^7.3.2 "@types/node": ^14.0.10 || ^16.0.0 "@types/pretty-hrtime": ^1.0.0 @@ -3276,35 +3344,35 @@ __metadata: peerDependenciesMeta: typescript: optional: true - checksum: b3b95214a427c1ff34464c1638219fd34aa8a98b60541ec3e13d84b095be79773e5de64c958903da877e6ec52b88ff05dd9a8cd7ab0fde548ffa0db762a4ea4e + checksum: 369fbe41e9ac657410a8e7fb4668be0e77c50b84c29b352397cc26b72d79397a7e84dcbf7a94f2d02d819d395a66e30a3915de40e85936d7b7dc50bb426aeabb languageName: node linkType: hard -"@storybook/core-events@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/core-events@npm:6.5.10" +"@storybook/core-events@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/core-events@npm:6.5.13" dependencies: core-js: ^3.8.2 - checksum: 89139f3f34a4ea0f2bbc02ebaa2968664cdc17abd88cc2e0467a0dfb1c11577e85fa402e5804fe4d6a99edd696d365abf93d30c396fc177563478cdbb68bcb85 + checksum: 2afeaf5fd658a4e9eedb9ad458ba0bcc73ad4ae5ba0e9971434818258db01d9b48b604d4db396ebfc1e1571dace3f6659e9ed61ac35428a792a4e24bbc08b29c languageName: node linkType: hard -"@storybook/core-server@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/core-server@npm:6.5.10" +"@storybook/core-server@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/core-server@npm:6.5.13" dependencies: "@discoveryjs/json-ext": ^0.5.3 - "@storybook/builder-webpack4": 6.5.10 - "@storybook/core-client": 6.5.10 - "@storybook/core-common": 6.5.10 - "@storybook/core-events": 6.5.10 + "@storybook/builder-webpack4": 6.5.13 + "@storybook/core-client": 6.5.13 + "@storybook/core-common": 6.5.13 + "@storybook/core-events": 6.5.13 "@storybook/csf": 0.0.2--canary.4566f4d.1 - "@storybook/csf-tools": 6.5.10 - "@storybook/manager-webpack4": 6.5.10 - "@storybook/node-logger": 6.5.10 + "@storybook/csf-tools": 6.5.13 + "@storybook/manager-webpack4": 6.5.13 + "@storybook/node-logger": 6.5.13 "@storybook/semver": ^7.3.2 - "@storybook/store": 6.5.10 - "@storybook/telemetry": 6.5.10 + "@storybook/store": 6.5.13 + "@storybook/telemetry": 6.5.13 "@types/node": ^14.0.10 || ^16.0.0 "@types/node-fetch": ^2.5.7 "@types/pretty-hrtime": ^1.0.0 @@ -3348,16 +3416,16 @@ __metadata: optional: true typescript: optional: true - checksum: 0359f8cf68e2a207d07ec631d0615c30991c78bcbe3ebe50cb8df8dd5159ab939d52789b84a50e074c027c253f74f813f745b4a002a5cf945de50a0069e0e758 + checksum: 142b13ef4fef21a68c8255f35f42ca5c3b9f636b51986f61dc6ae95485788d0f581552604b8a4a796e7cd2ad9548b87317ac9647ea44be58f64b91c440bb71ea languageName: node linkType: hard -"@storybook/core@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/core@npm:6.5.10" +"@storybook/core@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/core@npm:6.5.13" dependencies: - "@storybook/core-client": 6.5.10 - "@storybook/core-server": 6.5.10 + "@storybook/core-client": 6.5.13 + "@storybook/core-server": 6.5.13 peerDependencies: react: ^16.8.0 || ^17.0.0 || ^18.0.0 react-dom: ^16.8.0 || ^17.0.0 || ^18.0.0 @@ -3369,13 +3437,13 @@ __metadata: optional: true typescript: optional: true - checksum: ee80fa596cfc305138089757b1f095a0b44ed403ff1db727e99190a5d04cca84614faa816ed881b60c7ed91a4d268ee91632cb7bcaa7f2a2127424acd66a2c96 + checksum: e0dbe5d8d52f2a12ab63db965d5d15ee671029a03b7204756954e2bc3253b560c8e430aaab5559ccbddcfd3e97d2bc1c0c58ed370aa593912724402aa86996b8 languageName: node linkType: hard -"@storybook/csf-tools@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/csf-tools@npm:6.5.10" +"@storybook/csf-tools@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/csf-tools@npm:6.5.13" dependencies: "@babel/core": ^7.12.10 "@babel/generator": ^7.12.11 @@ -3396,7 +3464,7 @@ __metadata: peerDependenciesMeta: "@storybook/mdx2-csf": optional: true - checksum: 9bb4b61822760520c91da78b734a05c1f5145ad2e91f73cfe03aa900a6f40fd455c1fc2c3b1529a97a5e33246efb44462c68ad72b8dbf8f0b1811b7491411267 + checksum: 2b8a5bed04ea89084334742e1095c4565b0b7367b5126e3a9b6648224b59c2136a9d57cbb9067264fc3951e9db58df40b23b975170180d171cce35dfabf2a090 languageName: node linkType: hard @@ -3409,34 +3477,34 @@ __metadata: languageName: node linkType: hard -"@storybook/docs-tools@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/docs-tools@npm:6.5.10" +"@storybook/docs-tools@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/docs-tools@npm:6.5.13" dependencies: "@babel/core": ^7.12.10 "@storybook/csf": 0.0.2--canary.4566f4d.1 - "@storybook/store": 6.5.10 + "@storybook/store": 6.5.13 core-js: ^3.8.2 doctrine: ^3.0.0 lodash: ^4.17.21 regenerator-runtime: ^0.13.7 - checksum: 7fe14992ba94c31879964001a192f338bd53399a9582c598ab1681a05efb30999059329b1f7a4cbd33947778f17e6929d0f983cf54c36cb9e371414044f5dd89 + checksum: d3ad4674922025aaf6e4e2b7c2ac6f4eaec8f5692dc9a792a15d2d5e38dcd2e1c138daffb31a3da04da1e04c645b3cd8d921890f9ba318bfee7b6a12f263b48a languageName: node linkType: hard -"@storybook/manager-webpack4@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/manager-webpack4@npm:6.5.10" +"@storybook/manager-webpack4@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/manager-webpack4@npm:6.5.13" dependencies: "@babel/core": ^7.12.10 "@babel/plugin-transform-template-literals": ^7.12.1 "@babel/preset-react": ^7.12.10 - "@storybook/addons": 6.5.10 - "@storybook/core-client": 6.5.10 - "@storybook/core-common": 6.5.10 - "@storybook/node-logger": 6.5.10 - "@storybook/theming": 6.5.10 - "@storybook/ui": 6.5.10 + "@storybook/addons": 6.5.13 + "@storybook/core-client": 6.5.13 + "@storybook/core-common": 6.5.13 + "@storybook/node-logger": 6.5.13 + "@storybook/theming": 6.5.13 + "@storybook/ui": 6.5.13 "@types/node": ^14.0.10 || ^16.0.0 "@types/webpack": ^4.41.26 babel-loader: ^8.0.0 @@ -3469,7 +3537,7 @@ __metadata: peerDependenciesMeta: typescript: optional: true - checksum: 954f93dded7a2294cdbd7c7df93fcf1addb34d5daf46d58d8bf64d0a7e83664e34f32cd905b2b2ec771a551869e497c12f8d659a358ac079d815ca02baede6e6 + checksum: 6645f30b6199d0badb2097aca16478e4d8bc88210b55e60c4da86962e8b0a3441128f1e696cddf8a535591920617a7abf5f1f9771dabc486479e76b8d4b20fbd languageName: node linkType: hard @@ -3492,38 +3560,38 @@ __metadata: languageName: node linkType: hard -"@storybook/node-logger@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/node-logger@npm:6.5.10" +"@storybook/node-logger@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/node-logger@npm:6.5.13" dependencies: "@types/npmlog": ^4.1.2 chalk: ^4.1.0 core-js: ^3.8.2 npmlog: ^5.0.1 pretty-hrtime: ^1.0.3 - checksum: 684eddeadccb632dd0aa7d2bca62a374f71a15f07037788ee82f4d57e18ce7616304e5d8084b96dff742fe2b810843c44f26d53d4ff8f7d0706cdd81d0060fee + checksum: bcd1d98822687580e39f27003e16c73e3c775cdfe6e9f8fd8fbe9f4626a82f3f63fe281f9c894f3917faa52202ccb8217916978032d27ba6dbfa9720064e7739 languageName: node linkType: hard -"@storybook/postinstall@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/postinstall@npm:6.5.10" +"@storybook/postinstall@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/postinstall@npm:6.5.13" dependencies: core-js: ^3.8.2 - checksum: ee6355953cb0d4c49392f59502465f967846253afed6df24c845d028e51c0a4b19dadc092a837b29ba8c7fea6529b1ca757b86e579deac7fc3decac2dd8d0247 + checksum: 87e57e55c7973ea5794b439484d6a99c078b816c0a865c989ae31979000abda6fcfe670671e999a36630b52a91d54e6c0d174b41410cf876e20db976e5a23f56 languageName: node linkType: hard -"@storybook/preview-web@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/preview-web@npm:6.5.10" +"@storybook/preview-web@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/preview-web@npm:6.5.13" dependencies: - "@storybook/addons": 6.5.10 - "@storybook/channel-postmessage": 6.5.10 - "@storybook/client-logger": 6.5.10 - "@storybook/core-events": 6.5.10 + "@storybook/addons": 6.5.13 + "@storybook/channel-postmessage": 6.5.13 + "@storybook/client-logger": 6.5.13 + "@storybook/core-events": 6.5.13 "@storybook/csf": 0.0.2--canary.4566f4d.1 - "@storybook/store": 6.5.10 + "@storybook/store": 6.5.13 ansi-to-html: ^0.6.11 core-js: ^3.8.2 global: ^4.4.0 @@ -3537,7 +3605,7 @@ __metadata: peerDependencies: react: ^16.8.0 || ^17.0.0 || ^18.0.0 react-dom: ^16.8.0 || ^17.0.0 || ^18.0.0 - checksum: ad4ee244101a5b9bac68373e99c95e86f3cf397d5e1093d871ad880a439dac737297bd85f4148a0b6dd3f7550e994125b4f434e113359ce9208c71cefaeab195 + checksum: d66d29667a936ee80d15de07bdeec0c6cb2a476fdaa59f262297f5c7dc774acb57e4779c2dd77e61f5a6d9974ac3359babe587a2cd9baf6aa7673ec949b3234d languageName: node linkType: hard @@ -3559,23 +3627,23 @@ __metadata: languageName: node linkType: hard -"@storybook/react@npm:^6.3.11": - version: 6.5.10 - resolution: "@storybook/react@npm:6.5.10" +"@storybook/react@npm:^6.4.22": + version: 6.5.13 + resolution: "@storybook/react@npm:6.5.13" dependencies: "@babel/preset-flow": ^7.12.1 "@babel/preset-react": ^7.12.10 "@pmmmwh/react-refresh-webpack-plugin": ^0.5.3 - "@storybook/addons": 6.5.10 - "@storybook/client-logger": 6.5.10 - "@storybook/core": 6.5.10 - "@storybook/core-common": 6.5.10 + "@storybook/addons": 6.5.13 + "@storybook/client-logger": 6.5.13 + "@storybook/core": 6.5.13 + "@storybook/core-common": 6.5.13 "@storybook/csf": 0.0.2--canary.4566f4d.1 - "@storybook/docs-tools": 6.5.10 - "@storybook/node-logger": 6.5.10 + "@storybook/docs-tools": 6.5.13 + "@storybook/node-logger": 6.5.13 "@storybook/react-docgen-typescript-plugin": 1.0.2-canary.6.9d540b91e815f8fc2f8829189deb00553559ff63.0 "@storybook/semver": ^7.3.2 - "@storybook/store": 6.5.10 + "@storybook/store": 6.5.13 "@types/estree": ^0.0.51 "@types/node": ^14.14.20 || ^16.0.0 "@types/webpack-env": ^1.16.0 @@ -3620,15 +3688,15 @@ __metadata: build-storybook: bin/build.js start-storybook: bin/index.js storybook-server: bin/index.js - checksum: 4459ee91ec8aa0159d51e9fae2d0a7bde1be4ff6fd84ae0c1a414feed2d1797e7c8b9f38b256177e3b451142ebbb64a26ac1960a15a5689ae25dbffd3fb1a7b2 + checksum: 5a21e4e49a0aba7376dbaef5408e03537cf937d3025e735b45848bce7c9f476a025ca9af4260aa32982a3da668e14a217f66a0ec465ed820369ff2fab49b2ab3 languageName: node linkType: hard -"@storybook/router@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/router@npm:6.5.10" +"@storybook/router@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/router@npm:6.5.13" dependencies: - "@storybook/client-logger": 6.5.10 + "@storybook/client-logger": 6.5.13 core-js: ^3.8.2 memoizerific: ^1.11.3 qs: ^6.10.0 @@ -3636,7 +3704,7 @@ __metadata: peerDependencies: react: ^16.8.0 || ^17.0.0 || ^18.0.0 react-dom: ^16.8.0 || ^17.0.0 || ^18.0.0 - checksum: 118598867067344607cff7ef6fdef7b7a18a3e08a53f75fc4beaa65013f435ae18d800d25eea52376662bc1d98a2822a143531e701d8cea7130d42dc48e2cce7 + checksum: ca144b2f6e3a46d5ac9d449b068d0905e9c72939c8574f095d8d7f7307b172a0c5c13f56ff08d5d5bff540292d9ed13eeecc3a4e600e282ea31e70ed763b735a languageName: node linkType: hard @@ -3652,12 +3720,12 @@ __metadata: languageName: node linkType: hard -"@storybook/source-loader@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/source-loader@npm:6.5.10" +"@storybook/source-loader@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/source-loader@npm:6.5.13" dependencies: - "@storybook/addons": 6.5.10 - "@storybook/client-logger": 6.5.10 + "@storybook/addons": 6.5.13 + "@storybook/client-logger": 6.5.13 "@storybook/csf": 0.0.2--canary.4566f4d.1 core-js: ^3.8.2 estraverse: ^5.2.0 @@ -3669,17 +3737,17 @@ __metadata: peerDependencies: react: ^16.8.0 || ^17.0.0 || ^18.0.0 react-dom: ^16.8.0 || ^17.0.0 || ^18.0.0 - checksum: 77d7a0255cace96fc9953518fe54162ce4b2167b53eb744f498cf2098ba4af8074d75f572940621675303043b69e2281e8a5479ce2d331d47aa86c189cdd53bb + checksum: 93da14a367a954f664d233f64bd9e7d983475e489b8fbe5c90b723ff793279ab899d86f967eb6882f7997296f4286f6f5c82c17ca83e9294c91f8e4aa0ec0a1d languageName: node linkType: hard -"@storybook/store@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/store@npm:6.5.10" +"@storybook/store@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/store@npm:6.5.13" dependencies: - "@storybook/addons": 6.5.10 - "@storybook/client-logger": 6.5.10 - "@storybook/core-events": 6.5.10 + "@storybook/addons": 6.5.13 + "@storybook/client-logger": 6.5.13 + "@storybook/core-events": 6.5.13 "@storybook/csf": 0.0.2--canary.4566f4d.1 core-js: ^3.8.2 fast-deep-equal: ^3.1.3 @@ -3695,16 +3763,16 @@ __metadata: peerDependencies: react: ^16.8.0 || ^17.0.0 || ^18.0.0 react-dom: ^16.8.0 || ^17.0.0 || ^18.0.0 - checksum: cd8628f9bca4fe021dbf915ac2fad02baccf6fb06568fbe8192d268d7eaaed0f96c5b42c43f9883a1528a9b46e98c7d1d06aa8c0fad4c103f5f99325979a6b89 + checksum: 69f55927bd3569ec9d87f4351879fd07654d51524a0f9da05c64c7f7f3b50e33024f1554fa59668997e47189e9838b85b691de422ab539bd71126b56922d9381 languageName: node linkType: hard -"@storybook/telemetry@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/telemetry@npm:6.5.10" +"@storybook/telemetry@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/telemetry@npm:6.5.13" dependencies: - "@storybook/client-logger": 6.5.10 - "@storybook/core-common": 6.5.10 + "@storybook/client-logger": 6.5.13 + "@storybook/core-common": 6.5.13 chalk: ^4.1.0 core-js: ^3.8.2 detect-package-manager: ^2.0.1 @@ -3715,38 +3783,38 @@ __metadata: nanoid: ^3.3.1 read-pkg-up: ^7.0.1 regenerator-runtime: ^0.13.7 - checksum: 774acc7f5d91b855be3ec1e2ae5a13b61e3eb9db2c2284ee54d788a701e637a86d4ca14597a027d32555f74392e4c99f47e886bc7729a7222e4e8159c492e054 + checksum: 94ad6fb58b09c8073600ad95b2a48f476524ea7bc6155aee8e9682966a99ac875a9923ee6512252238e8c56eeef725a712e94ba87e1060d7dca9ab196a9051a6 languageName: node linkType: hard -"@storybook/theming@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/theming@npm:6.5.10" +"@storybook/theming@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/theming@npm:6.5.13" dependencies: - "@storybook/client-logger": 6.5.10 + "@storybook/client-logger": 6.5.13 core-js: ^3.8.2 memoizerific: ^1.11.3 regenerator-runtime: ^0.13.7 peerDependencies: react: ^16.8.0 || ^17.0.0 || ^18.0.0 react-dom: ^16.8.0 || ^17.0.0 || ^18.0.0 - checksum: 2082d7847785a307a18eb605282468d844af01f57752916766a60047b5543cf6f0c6664b9c7a693809b4fdc121415989c2170833d3de7ca8b07fa056741787d0 + checksum: f7a59c7d81b87f3fbf65c5eb72f5db5a5c1707236c92350d46bc7e1dcf848d57522ca5dcdd4fe19336d4611bd20727e0d900c4b591d2e8e1dd8a754cb9c56aa3 languageName: node linkType: hard -"@storybook/ui@npm:6.5.10": - version: 6.5.10 - resolution: "@storybook/ui@npm:6.5.10" +"@storybook/ui@npm:6.5.13": + version: 6.5.13 + resolution: "@storybook/ui@npm:6.5.13" dependencies: - "@storybook/addons": 6.5.10 - "@storybook/api": 6.5.10 - "@storybook/channels": 6.5.10 - "@storybook/client-logger": 6.5.10 - "@storybook/components": 6.5.10 - "@storybook/core-events": 6.5.10 - "@storybook/router": 6.5.10 + "@storybook/addons": 6.5.13 + "@storybook/api": 6.5.13 + "@storybook/channels": 6.5.13 + "@storybook/client-logger": 6.5.13 + "@storybook/components": 6.5.13 + "@storybook/core-events": 6.5.13 + "@storybook/router": 6.5.13 "@storybook/semver": ^7.3.2 - "@storybook/theming": 6.5.10 + "@storybook/theming": 6.5.13 core-js: ^3.8.2 memoizerific: ^1.11.3 qs: ^6.10.0 @@ -3755,7 +3823,7 @@ __metadata: peerDependencies: react: ^16.8.0 || ^17.0.0 || ^18.0.0 react-dom: ^16.8.0 || ^17.0.0 || ^18.0.0 - checksum: fc0180fc183a41b5da5a530aa8e22fd84b1934602b01bdc90b3a9865794161ffaad520e7904daf603d9fd1797dca304c4df1c5360cc1894c4971dbbca463e5dd + checksum: d2866987f51d945246776d42628bc2b79e701f1e59fd511bb1e590c83c4b9d9adee5c7e1a11ecb2ef12b9192613e2d576694bbc9aeb1df5545567f2aa44c0145 languageName: node linkType: hard @@ -12949,6 +13017,28 @@ __metadata: languageName: node linkType: hard +"mobx-react-lite@npm:^3.3.0": + version: 3.4.0 + resolution: "mobx-react-lite@npm:3.4.0" + peerDependencies: + mobx: ^6.1.0 + react: ^16.8.0 || ^17 || ^18 + peerDependenciesMeta: + react-dom: + optional: true + react-native: + optional: true + checksum: 9294e127e281c8b37ec7bcaf17de479f50519e6ad485b58d7b991291900511541a5a718653759d3cf6503462c70325d025e1c2ed376d4584fb1b2d3aac9d9b48 + languageName: node + linkType: hard + +"mobx@npm:^6.5.0": + version: 6.6.2 + resolution: "mobx@npm:6.6.2" + checksum: b913abea51ed023d60c71eec0198e953c0b7faee93820be2e8f07037a789b3acf6fd89c340cb9d34e888532ebd34d34b10add7d129277a96026537e5ca48bda6 + languageName: node + linkType: hard + "moo@npm:^0.5.0": version: 0.5.1 resolution: "moo@npm:0.5.1"