Skip to content
Snippets Groups Projects
Commit 668a34ad authored by Alexandru Munteanu's avatar Alexandru Munteanu
Browse files

feat(styleguide): add contextual box container

parent 45986b98
No related branches found
No related tags found
1 merge request!43Sprint #19
import React from 'react'
import { Icon, H3 } from '@pubsweet/ui'
import styled from 'styled-components'
import { override, th } from '@pubsweet/ui-toolkit'
import Accordion from './pending/Accordion'
const CustomHeader = ({
label,
toggle,
expanded,
transparent,
rightChildren,
...props
}) => (
<Header
expanded={expanded}
hasChildren={rightChildren}
onClick={toggle}
transparent={transparent}
>
<div>
<Icon secondary size={2}>
{expanded ? 'minus' : 'plus'}
</Icon>
<H3>{label}</H3>
</div>
{typeof rightChildren === 'function'
? rightChildren({ ...props, expanded, transparent })
: rightChildren}
</Header>
)
const ContextualBox = ({
label,
children,
transparent,
rightChildren,
...props
}) => (
<Accordion
header={CustomHeader}
label={label}
rightChildren={rightChildren}
transparent={transparent}
{...props}
>
{children}
</Accordion>
)
export default ContextualBox
// #region styles
const Header = styled.div.attrs({
'data-test-id': props => props['data-test-id'] || 'accordion-header',
})`
align-items: center;
cursor: pointer;
display: flex;
justify-content: ${props =>
props.hasChildren ? 'space-between' : 'flex-start'};
${override('ui.Accordion.Header')};
${H3} {
margin: ${th('gridUnit')} 0;
}
& div {
align-items: center;
display: flex;
}
`
// #endregion
A collapseable contextual box.
```js
<ContextualBox label="Reviewer reports">
<div
style={{
padding: 16,
backgroundColor: 'lavenderblush',
}}
>
What is Lorem Ipsum? Lorem Ipsum is simply dummy text of the printing and
typesetting industry. Lorem Ipsum has been the industry's standard dummy
text ever since the 1500s, when an unknown printer took a galley of type and
scrambled it to make a type specimen book. It has survived not only five
centuries, but also the leap into electronic typesetting, remaining
essentially unchanged. It was popularised in the 1960s with the release of
Letraset sheets containing Lorem Ipsum passages, and more recently with
desktop publishing software like Aldus PageMaker including versions of Lorem
Ipsum. Why do we use it? It is a long established fact that a reader will be
distracted by the readable content of a page when looking at its layout. The
point of using Lorem Ipsum is that it has a more-or-less normal distribution
of letters, as opposed to using 'Content here, content here', making it look
like readable English. Many desktop publishing packages and web page editors
now use Lorem Ipsum as their default model text, and a search for 'lorem
ipsum' will uncover many web sites still in their infancy. Various versions
have evolved over the years, sometimes by accident, sometimes on purpose
(injected humour and the like).
</div>
</ContextualBox>
```
A contextual box without border, shadow and no backgrounds.
```js
<ContextualBox label="Files" transparent>
<div>
<FileItem file={{ id: '1', name: 'myfile.pdf', size: 123123 }} />
<FileItem file={{ id: '2', name: 'myfile2.pdf', size: 1123 }} />
</div>
</ContextualBox>
```
Render custom components on the right side of the header.
```js
<ContextualBox
label="Plain html on the right side"
rightChildren={<div>1 invited, 0 accepted</div>}
>
<div
style={{
padding: 16,
backgroundColor: 'lavenderblush',
}}
>
What is Lorem Ipsum? Lorem Ipsum is simply dummy text of the printing and
typesetting industry. Lorem Ipsum has been the industry's standard dummy
text ever since the 1500s, when an unknown printer took a galley of type and
scrambled it to make a type specimen book. It has survived not only five
centuries, but also the leap into electronic typesetting, remaining
essentially unchanged. It was popularised in the 1960s with the release of
Letraset sheets containing Lorem Ipsum passages, and more recently with
desktop publishing software like Aldus PageMaker including versions of Lorem
Ipsum. Why do we use it? It is a long established fact that a reader will be
distracted by the readable content of a page when looking at its layout. The
point of using Lorem Ipsum is that it has a more-or-less normal distribution
of letters, as opposed to using 'Content here, content here', making it look
like readable English. Many desktop publishing packages and web page editors
now use Lorem Ipsum as their default model text, and a search for 'lorem
ipsum' will uncover many web sites still in their infancy. Various versions
have evolved over the years, sometimes by accident, sometimes on purpose
(injected humour and the like).
</div>
</ContextualBox>
```
React components can be passed as right children too. All the props provided to the contextual box are also passed to the right header children.
```js
const MyRightComponent = ({headLabel}) => <div>{headLabel}: 1 accepted, 4 denied</div>;
<ContextualBox
headLabel="I am the right header * "
label="React component to the right"
rightChildren={MyRightComponent}
>
<div
style={{
padding: 16,
backgroundColor: 'lavenderblush',
}}
>
What is Lorem Ipsum? Lorem Ipsum is simply dummy text of the printing and
typesetting industry. Lorem Ipsum has been the industry's standard dummy
text ever since the 1500s, when an unknown printer took a galley of type and
scrambled it to make a type specimen book. It has survived not only five
centuries, but also the leap into electronic typesetting, remaining
essentially unchanged. It was popularised in the 1960s with the release of
Letraset sheets containing Lorem Ipsum passages, and more recently with
desktop publishing software like Aldus PageMaker including versions of Lorem
Ipsum. Why do we use it? It is a long established fact that a reader will be
distracted by the readable content of a page when looking at its layout. The
point of using Lorem Ipsum is that it has a more-or-less normal distribution
of letters, as opposed to using 'Content here, content here', making it look
like readable English. Many desktop publishing packages and web page editors
now use Lorem Ipsum as their default model text, and a search for 'lorem
ipsum' will uncover many web sites still in their infancy. Various versions
have evolved over the years, sometimes by accident, sometimes on purpose
(injected humour and the like).
</div>
</ContextualBox>
```
/* eslint-disable react/require-default-props */
import React from 'react'
import PropTypes from 'prop-types'
import { Icon } from '@pubsweet/ui'
import styled from 'styled-components'
import { th, override } from '@pubsweet/ui-toolkit'
import { withState, withHandlers, compose } from 'recompose'
// #region styles
const Root = styled.div`
cursor: pointer;
display: flex;
flex-direction: column;
transition: all ${th('transitionDuration')};
${override('ui.Accordion')};
`
const Header = styled.div.attrs({
'data-test-id': props => props['data-test-id'] || 'accordion-header',
})`
align-items: center;
cursor: pointer;
display: flex;
justify-content: flex-start;
${override('ui.Accordion.Header')};
`
const HeaderLabel = styled.span`
color: ${th('colorPrimary')};
font-family: ${th('fontHeading')};
font-size: ${th('fontSizeBase')};
${override('ui.Accordion.Header.Label')};
`
const HeaderIcon = styled.div`
align-items: center;
display: flex;
justify-content: center;
transform: ${({ expanded }) => `rotateZ(${expanded ? 0 : 180}deg)`};
transition: transform ${th('transitionDuration')};
${override('ui.Accordion.Header.Icon')};
`
// #endregion
const HeaderComponent = ({ icon, label, toggle, expanded, ...props }) => (
<Header expanded={expanded} onClick={toggle} {...props}>
<HeaderIcon expanded={expanded}>
<Icon primary size={3}>
{icon}
</Icon>
</HeaderIcon>
<HeaderLabel>{label}</HeaderLabel>
</Header>
)
const Accordion = ({
toggle,
expanded,
children,
icon = 'chevron_up',
header: Header = HeaderComponent,
...props
}) => (
<Root expanded={expanded} {...props}>
<Header expanded={expanded} icon={icon} toggle={toggle} {...props} />
{expanded && children}
</Root>
)
Accordion.propTypes = {
/** Header icon, from the [Feather](https://feathericons.com/) icon set. */
icon: PropTypes.string,
/** Initial state of the accordion. */
startExpanded: PropTypes.bool,
/** Function called when toggling the accordion. The new state is passed as a paremeter. */
onToggle: PropTypes.func,
}
Accordion.defaultProps = {
onToggle: null,
startExpanded: false,
}
export default compose(
withState('expanded', 'setExpanded', ({ startExpanded }) => startExpanded),
withHandlers({
toggle: ({ expanded, setExpanded, onToggle }) => () => {
setExpanded(!expanded)
if (typeof onToggle === 'function') {
onToggle(!expanded)
}
},
}),
)(Accordion)
......@@ -9,7 +9,7 @@
"dist"
],
"dependencies": {
"@pubsweet/ui": "8.2.0",
"@pubsweet/ui": "^8.3.0",
"@pubsweet/styleguide": "3.1.4",
"@pubsweet/ui-toolkit": "latest",
"moment": "^2.20.1",
......
......@@ -4,7 +4,7 @@
"main": "src",
"license": "MIT",
"dependencies": {
"@pubsweet/ui": "8.2.0",
"@pubsweet/ui": "^8.3.0",
"@pubsweet/ui-toolkit": "latest",
"@pubsweet/styleguide": "3.1.4",
"moment": "^2.22.1",
......
......@@ -3,14 +3,20 @@ import { th } from '@pubsweet/ui-toolkit'
export default {
Root: css`
background-color: ${th('accordion.backgroundColor')};
background-color: ${props =>
props.transparent ? 'transparent' : th('accordion.backgroundColor')};
border-radius: ${th('borderRadius')};
box-shadow: ${th('boxShadow')};
box-shadow: ${props =>
props.transparent ? 'transparent' : th('boxShadow')};
`,
Header: {
Root: css`
background-color: ${th('accordion.headerBackgroundColor')};
border-radius: ${props => (props.expanded ? 0 : th('borderRadius'))};
borde-border-top-left-radius: ${th('borderRadius')};
border-top-right-radius: ${th('borderRadius')};
border-bottom: ${props =>
props.expanded ? th('accordion.border') : 'none'};
props.expanded && !props.transparent ? th('accordion.border') : 'none'};
`,
Label: css`
color: ${th('colorText')};
......
......@@ -10,4 +10,5 @@ export default css`
stroke: ${props => darken(props.color, 0.2)};
}
}
display: initial;
`
......@@ -39,7 +39,8 @@ const hindawiTheme = {
colorWarning: '#FC6A4B',
accordion: {
backgroundColor: '#ffffff',
headerBackgroundColor: '#ffffff',
backgroundColor: '#f6f6f6',
headerFontSize: '16px',
headerFontFamily: "'Myriad Pro'",
border: '1px solid #dbdbdb',
......
......@@ -19,7 +19,7 @@
"webpack-node-externals": "^1.6.0"
},
"dependencies": {
"@pubsweet/ui": "8.2.0",
"@pubsweet/ui": "^8.3.0",
"@pubsweet/ui-toolkit": "^1.2.0",
"hindawi-theme": "^1.0.1",
"react": "^16.4.2",
......
......@@ -8,7 +8,7 @@
"url": "https://gitlab.coko.foundation/xpub/xpub-faraday"
},
"dependencies": {
"@pubsweet/ui": "8.2.0",
"@pubsweet/ui": "^8.3.0",
"@pubsweet/styleguide": "3.1.4",
"@pubsweet/ui-toolkit": "latest",
"@pubsweet/component-aws-s3": "^1.2.0",
......
......@@ -183,30 +183,6 @@
lodash "^4.17.4"
styled-components "^3.2.5"
"@pubsweet/ui@8.2.0":
version "8.2.0"
resolved "https://registry.yarnpkg.com/@pubsweet/ui/-/ui-8.2.0.tgz#fbd4b5eb08ceee430c5bfb4287d4c5f0883e31e6"
dependencies:
"@pubsweet/ui-toolkit" "^1.1.3"
babel-jest "^21.2.0"
classnames "^2.2.5"
enzyme "^3.2.0"
enzyme-adapter-react-16 "^1.1.1"
invariant "^2.2.3"
lodash "^4.17.4"
moment "^2.22.1"
prop-types "^15.5.10"
react "^16.2.0"
react-dom "^16.2.0"
react-feather "^1.0.8"
react-redux "^5.0.2"
react-router-dom "^4.2.2"
react-tag-autocomplete "^5.5.0"
recompose "^0.26.0"
redux "^3.6.0"
redux-form "^7.0.3"
styled-components "^3.2.5"
"@pubsweet/ui@^8.2.0", "@pubsweet/ui@^8.3.0":
version "8.3.0"
resolved "https://registry.yarnpkg.com/@pubsweet/ui/-/ui-8.3.0.tgz#b8da7be8d9110594abdd18476e3808c9606a74b4"
......
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment