diff --git a/.storybook/themes/index.js b/.storybook/themes/index.js index bad2d97..77e16af 100644 --- a/.storybook/themes/index.js +++ b/.storybook/themes/index.js @@ -7,7 +7,8 @@ const space = [0, 4, 8, 16, 32].map(value => `${value}px`) space.l = space[3] space.xl = space[4] -const lineHeights = [0.25, 1, 1.25, 1.75] +const lineHeights = [0.25, 1, 1.25, 1.75, 2] + lineHeights.header = lineHeights[4] lineHeights.heading = lineHeights[2] lineHeights.body = lineHeights[3] diff --git a/.storybook/themes/rg6-theme.js b/.storybook/themes/rg6-theme.js index 2d7ab12..13e379e 100644 --- a/.storybook/themes/rg6-theme.js +++ b/.storybook/themes/rg6-theme.js @@ -13,4 +13,5 @@ export const colors = { export const shadows = { m: '0 4px 16px rgba(0,0,0,.175)', + toolbar: '0 4px 4px 0px rgba(0, 0, 0, .175)', } diff --git a/src/Atoms/Button/Button.jsx b/src/Atoms/Button/Button.jsx index 1d0bcb4..d3b9af9 100644 --- a/src/Atoms/Button/Button.jsx +++ b/src/Atoms/Button/Button.jsx @@ -3,6 +3,7 @@ import css from '@styled-system/css' import Input from '../Input' const Button = styled(Input)` + cursor: pointer; &:hover { ${css({ bg: 'midgray', borderColor: 'lightgray' })}; } diff --git a/src/Atoms/Select/Select.jsx b/src/Atoms/Select/Select.jsx index 958fe35..9f29826 100644 --- a/src/Atoms/Select/Select.jsx +++ b/src/Atoms/Select/Select.jsx @@ -1,7 +1,12 @@ import React, { useState } from 'react' import styled from 'styled-components' import { - space, typography, border, color, shadow, + space, + typography, + border, + color, + shadow, + position, } from 'styled-system' import { useOnClickOutside } from '../../hooks' @@ -14,11 +19,11 @@ const Container = styled(Button)` const Options = styled.div` ${({ openOnTop }) => openOnTop ? 'bottom: 100%;' : 'top: 100%;'} + ${({ stickToLeft }) => stickToLeft ? 'left: 0;' : 'right: 0;'} display: ${({ open }) => open ? 'block' : 'none'}; position: absolute; border: 1px solid; min-width: 160px; - left: 0; text-align: left; z-index: 300; @@ -41,7 +46,12 @@ Options.defaultProps = { } const Select = ({ - label, options = [], openOnTop, onChange, ...props + label, + options = [], + openOnTop, + stickToLeft = true, + onChange, + ...props }) => { const [open, setOpen] = useState(false) const ref = useOnClickOutside(() => setOpen(false)) @@ -51,12 +61,12 @@ const Select = ({ } return ( - setOpen(!open)}> + options.length > 0 && setOpen(!open)}> {label} - - {options.map(option => ( - ) diff --git a/src/Atoms/Separator/README.md b/src/Atoms/Separator/README.md new file mode 100644 index 0000000..8988475 --- /dev/null +++ b/src/Atoms/Separator/README.md @@ -0,0 +1 @@ +## Separator diff --git a/src/Atoms/Separator/Separator.jsx b/src/Atoms/Separator/Separator.jsx new file mode 100644 index 0000000..edb61df --- /dev/null +++ b/src/Atoms/Separator/Separator.jsx @@ -0,0 +1,13 @@ +import styled from 'styled-components' + +import { Typo } from '../../Atoms' + +const Separator = styled(Typo)`` + +Separator.defaultProps = { + color: 'midgray', + lineHeight: 'header', + children: '|', +} + +export default Separator diff --git a/src/Atoms/Separator/Separator.stories.jsx b/src/Atoms/Separator/Separator.stories.jsx new file mode 100644 index 0000000..d12fa6b --- /dev/null +++ b/src/Atoms/Separator/Separator.stories.jsx @@ -0,0 +1,21 @@ +import React from 'react' +import { text } from '@storybook/addon-knobs' + +import Separator from './index' + +import markdown from './README.md' + +export default { + title: 'Atoms/Separator', +} + +export const separator = () => ( + +) + +separator.story = { + parameters: { + notes: { markdown }, + jest: ['Separator.test.jsx'], + }, +} diff --git a/src/Atoms/Separator/Separator.test.jsx b/src/Atoms/Separator/Separator.test.jsx new file mode 100644 index 0000000..7ce710a --- /dev/null +++ b/src/Atoms/Separator/Separator.test.jsx @@ -0,0 +1,9 @@ +import React from 'react' +import { render } from '@testing-library/react' +import '@testing-library/jest-dom/extend-expect' +import userEvent from '@testing-library/user-event' + +import Separator from './index' + +// TODO: implement test for Separator +it.todo('Separator should be tested') diff --git a/src/Atoms/Separator/index.js b/src/Atoms/Separator/index.js new file mode 100644 index 0000000..356ba2b --- /dev/null +++ b/src/Atoms/Separator/index.js @@ -0,0 +1,3 @@ +import Separator from './Separator' + +export default Separator diff --git a/src/Atoms/Typo/Typo.jsx b/src/Atoms/Typo/Typo.jsx index 786fe98..e80b5a7 100644 --- a/src/Atoms/Typo/Typo.jsx +++ b/src/Atoms/Typo/Typo.jsx @@ -1,9 +1,10 @@ import styled from 'styled-components' -import { typography, color } from 'styled-system' +import { typography, color, space } from 'styled-system' const Typo = styled.span` ${typography} ${color} + ${space} ` Typo.defaultProps = { diff --git a/src/Atoms/index.js b/src/Atoms/index.js index 7235cf1..e835fd0 100644 --- a/src/Atoms/index.js +++ b/src/Atoms/index.js @@ -5,3 +5,4 @@ export { default as Select } from './Select' export { default as Option } from './Select/Option' export { default as Typo } from './Typo' export { default as Banner } from './Banner' +export { default as Separator } from './Separator' diff --git a/src/Organisms/Header/Breadcrumbs/Breadcrumb/Breadcrumb.jsx b/src/Organisms/Header/Breadcrumbs/Breadcrumb/Breadcrumb.jsx new file mode 100644 index 0000000..bc07e6d --- /dev/null +++ b/src/Organisms/Header/Breadcrumbs/Breadcrumb/Breadcrumb.jsx @@ -0,0 +1,23 @@ +import React from 'react' +import styled from 'styled-components' +import { Select } from '../../../../Atoms' + +const StyledSelect = styled(Select)` + &:hover { + background-color: transparent; + } + + cursor: ${({ pointer }) => pointer ? 'pointer' : 'auto'} +` + +const Breadcrumb = ({ children, siblings = [], icon, onSiblingSelect = () => {} }) => + 0} + label={children} + onChange={onSiblingSelect} + options={siblings.map(({ id, name }) => ({ value: id, label: name }))} + /> + +export default Breadcrumb diff --git a/src/Organisms/Header/Breadcrumbs/Breadcrumb/Breadcrumb.stories.jsx b/src/Organisms/Header/Breadcrumbs/Breadcrumb/Breadcrumb.stories.jsx new file mode 100644 index 0000000..1a9a7c6 --- /dev/null +++ b/src/Organisms/Header/Breadcrumbs/Breadcrumb/Breadcrumb.stories.jsx @@ -0,0 +1,33 @@ +import React from 'react' +import { action } from '@storybook/addon-actions' +import { text, number } from '@storybook/addon-knobs' + +import Breadcrumb from './index' + +import markdown from './README.md' + +export default { + title: 'Organisms/Header/Breadcrumbs/Breadcrumb', +} + +const siblings = [ + { id: 9302, name: 'Node 1' }, + { id: 4302, name: 'Node 2' }, + { id: 8302, name: 'Node 3' }, +] + +export const breadcrumb = () => ( + + { text('Title', 'Node 24') } + +) + +breadcrumb.story = { + parameters: { + notes: { markdown }, + jest: ['Breadcrumb.test.jsx'], + }, +} diff --git a/src/Organisms/Header/Breadcrumbs/Breadcrumb/Breadcrumb.test.jsx b/src/Organisms/Header/Breadcrumbs/Breadcrumb/Breadcrumb.test.jsx new file mode 100644 index 0000000..eb87075 --- /dev/null +++ b/src/Organisms/Header/Breadcrumbs/Breadcrumb/Breadcrumb.test.jsx @@ -0,0 +1,9 @@ +import React from 'react' +import { render } from '@testing-library/react' +import '@testing-library/jest-dom/extend-expect' +import userEvent from '@testing-library/user-event' + +import Breadcrumb from './index' + +// TODO: implement test for Breadcrumb +it.todo('Header should be tested') diff --git a/src/Organisms/Header/Breadcrumbs/Breadcrumb/README.md b/src/Organisms/Header/Breadcrumbs/Breadcrumb/README.md new file mode 100644 index 0000000..33ee5e2 --- /dev/null +++ b/src/Organisms/Header/Breadcrumbs/Breadcrumb/README.md @@ -0,0 +1 @@ +## Breadcrumb diff --git a/src/Organisms/Header/Breadcrumbs/Breadcrumb/index.js b/src/Organisms/Header/Breadcrumbs/Breadcrumb/index.js new file mode 100644 index 0000000..268b7a1 --- /dev/null +++ b/src/Organisms/Header/Breadcrumbs/Breadcrumb/index.js @@ -0,0 +1,3 @@ +import Breadcrumb from './Breadcrumb' + +export default Breadcrumb diff --git a/src/Organisms/Header/Breadcrumbs/Breadcrumbs.jsx b/src/Organisms/Header/Breadcrumbs/Breadcrumbs.jsx new file mode 100644 index 0000000..ed8acfe --- /dev/null +++ b/src/Organisms/Header/Breadcrumbs/Breadcrumbs.jsx @@ -0,0 +1,46 @@ +import React from 'react' +import styled from 'styled-components' +import { Separator } from '../../../Atoms' + +const Container = styled.ol` + display: flex; + padding: 0; + margin: 0; + + & li { + list-style: none; + } +` + +const insertSeparators = (items, separator) => + items.reduce((acc, current, index) => { + if (index < items.length - 1) { + acc = acc.concat( + current, + + {separator} + + ) + } else { + acc.push(current) + } + + return acc + }, []) + +const Breadcrumbs = ({ children, separator = '>', collapse = 5 }) => ( + + {insertSeparators( + React.Children.toArray(children).map( + (child, index) => ( +
  • + {child} +
  • + ) + ), + separator + )} +
    +) + +export default Breadcrumbs diff --git a/src/Organisms/Header/Breadcrumbs/Breadcrumbs.stories.jsx b/src/Organisms/Header/Breadcrumbs/Breadcrumbs.stories.jsx new file mode 100644 index 0000000..ca8b948 --- /dev/null +++ b/src/Organisms/Header/Breadcrumbs/Breadcrumbs.stories.jsx @@ -0,0 +1,58 @@ +import React from 'react' +import { action } from '@storybook/addon-actions' +import { text, number } from '@storybook/addon-knobs' + +import Breadcrumbs from './index' +import Breadcrumb from './Breadcrumb' + +import markdown from './README.md' + +export default { + title: 'Organisms/Header/Breadcrumbs', +} + +const treePath = [ + { + id: 9302, + name: 'Node 1', + siblings: [ + { id: 918, name: 'Node 918' }, + { id: 915, name: 'Node 915' }, + ], + }, + { id: 4302, name: 'Node 2' }, + { + id: 8302, + name: 'Node 3', + siblings: [ + { id: 20, name: 'Node 20' }, + { id: 9107, name: 'Node 9107' }, + ], + }, +] + +export const breadcrumbs = () => ( + ({ id, name: text(`Node ${index}`, name) }))} + collapse={number('Collapse', 3)} + separator={text('Separator', '/')} + > + {treePath.map(({ id, name, siblings }, index) => ( + + {text(`Node ${index}`, name)} + + ))} + +) +breadcrumbs.story = { + parameters: { + notes: { markdown }, + jest: ['Breadcrumbs.test.jsx'], + }, +} diff --git a/src/Organisms/Header/Breadcrumbs/Breadcrumbs.test.jsx b/src/Organisms/Header/Breadcrumbs/Breadcrumbs.test.jsx new file mode 100644 index 0000000..90ab053 --- /dev/null +++ b/src/Organisms/Header/Breadcrumbs/Breadcrumbs.test.jsx @@ -0,0 +1,9 @@ +import React from 'react' +import { render } from '@testing-library/react' +import '@testing-library/jest-dom/extend-expect' +import userEvent from '@testing-library/user-event' + +import Breadcrumbs from './index' + +// TODO: implement test for Breadcrumbs +it.todo('Header should be tested') diff --git a/src/Organisms/Header/Breadcrumbs/README.md b/src/Organisms/Header/Breadcrumbs/README.md new file mode 100644 index 0000000..7053ecd --- /dev/null +++ b/src/Organisms/Header/Breadcrumbs/README.md @@ -0,0 +1 @@ +## Breadcrumbs diff --git a/src/Organisms/Header/Breadcrumbs/index.js b/src/Organisms/Header/Breadcrumbs/index.js new file mode 100644 index 0000000..c8c93df --- /dev/null +++ b/src/Organisms/Header/Breadcrumbs/index.js @@ -0,0 +1,3 @@ +import Breadcrumbs from './Breadcrumbs' + +export default Breadcrumbs diff --git a/src/Templates/Toolbar/README.md b/src/Templates/Toolbar/README.md new file mode 100644 index 0000000..cf3b1f6 --- /dev/null +++ b/src/Templates/Toolbar/README.md @@ -0,0 +1 @@ +## Toolbar diff --git a/src/Templates/Toolbar/Toolbar.jsx b/src/Templates/Toolbar/Toolbar.jsx new file mode 100644 index 0000000..7347c99 --- /dev/null +++ b/src/Templates/Toolbar/Toolbar.jsx @@ -0,0 +1,18 @@ +import styled from 'styled-components' +import { color, border, shadow } from 'styled-system' + +const Toolbar = styled.div` + display: flex; + justify-content: space-between; + padding: 10px 5px; + ${color} + ${border} + ${shadow} +` + +Toolbar.defaultProps = { + bg: 'lightgray', + boxShadow: 'toolbar', +} + +export default Toolbar diff --git a/src/Templates/Toolbar/Toolbar.stories.jsx b/src/Templates/Toolbar/Toolbar.stories.jsx new file mode 100644 index 0000000..2dbccd2 --- /dev/null +++ b/src/Templates/Toolbar/Toolbar.stories.jsx @@ -0,0 +1,44 @@ +import React from 'react' +import styled from 'styled-components' +import { text } from '@storybook/addon-knobs' + +import { Typo } from '../../Atoms' + +import Toolbar from './index' + +import markdown from './README.md' + +export default { + title: 'Templates/Toolbar', +} + +const Item = styled(Typo)` + padding: 0px 5px; +` + +export const toolbar = () => ( + +
    + + {text('Item 1', 'Item 1')} + + + {text('Item 2', 'Item 2')} + +
    +
    + + {text('Item 3', 'Item 3')} + + + {text('Item 4', 'Item 4')} + +
    +
    +) +toolbar.story = { + parameters: { + notes: { markdown }, + jest: ['Toolbar.test.jsx'], + }, +} diff --git a/src/Templates/Toolbar/Toolbar.test.jsx b/src/Templates/Toolbar/Toolbar.test.jsx new file mode 100644 index 0000000..c3dee33 --- /dev/null +++ b/src/Templates/Toolbar/Toolbar.test.jsx @@ -0,0 +1,9 @@ +import React from 'react' +import { render } from '@testing-library/react' +import '@testing-library/jest-dom/extend-expect' +import userEvent from '@testing-library/user-event' + +import Toolbar from './index' + +// TODO: implement test for Toolbar +it.todo('Toolbar should be tested') diff --git a/src/Templates/Toolbar/index.js b/src/Templates/Toolbar/index.js new file mode 100644 index 0000000..18b3050 --- /dev/null +++ b/src/Templates/Toolbar/index.js @@ -0,0 +1,3 @@ +import Toolbar from './Toolbar' + +export default Toolbar diff --git a/src/Templates/index.js b/src/Templates/index.js index e69de29..bf71a5d 100644 --- a/src/Templates/index.js +++ b/src/Templates/index.js @@ -0,0 +1 @@ +export { default as Toolbar } from './Toolbar' diff --git a/src/index.js b/src/index.js index 18868c9..b990213 100644 --- a/src/index.js +++ b/src/index.js @@ -6,3 +6,5 @@ export { Select } from './Atoms' export { Option } from './Atoms' export { Typo } from './Atoms' export { Banner } from './Atoms' +export { Toolbar } from './Templates' +export { Separator } from './Atoms'