@sparkpost/matchbox
Version:
A React UI component library
128 lines (109 loc) • 3.03 kB
JavaScript
import React, { Component } from 'react';
import PropTypes from 'prop-types';
import { buttonFrom } from '../Button';
import { ChevronLeft } from '@sparkpost/matchbox-icons';
import { EmptyState } from '../EmptyState';
import { UnstyledLink, linkFrom } from '../UnstyledLink';
import { filterByVisible } from '../../helpers/array';
import styles from './Page.module.scss';
const Breadcrumb = ({ content, ...rest }) => (
<UnstyledLink {...rest}>
<ChevronLeft size={27} />
{content}
</UnstyledLink>
);
class Page extends Component {
static displayName = 'Page';
static defaultProps = {
empty: {}
}
static propTypes = {
/**
* The Page display title
*/
title: PropTypes.string,
/**
* Main cta. Most button props will work in here.
* e.g. { content: 'button label', onClick: callback() }
*/
primaryAction: PropTypes.shape({
content: PropTypes.node.isRequired
}),
/**
* Actions that appear below title
* e.g. { content: 'button label', onClick: callback() }
*/
secondaryActions: PropTypes.arrayOf(PropTypes.shape({
content: PropTypes.node.isRequired
})),
/**
* The back link action
*/
breadcrumbAction: PropTypes.shape({
content: PropTypes.node.isRequired
}),
/**
* Optional empty state object
*/
empty: PropTypes.shape({
show: PropTypes.bool,
content: PropTypes.node
}),
/**
* Page Children
*/
children: PropTypes.node
};
render() {
const {
title,
primaryAction,
secondaryActions,
breadcrumbAction,
empty,
children
} = this.props;
const { show, content, ...emptyOptions } = empty;
if (show) {
return (
<EmptyState
title={title}
primaryAction={primaryAction}
{...emptyOptions}>
{content}
</EmptyState>
);
}
const primaryActionMarkup = primaryAction
? buttonFrom(primaryAction, {
size: 'large',
...(!primaryAction.color ? { color: 'orange' } : {})
})
: null;
const secondaryActionsMarkup = secondaryActions
? filterByVisible(secondaryActions).map((action, i) => linkFrom({ ...action, className: styles.SecondaryAction }, i))
: null;
const breadcrumbMarkup = breadcrumbAction
? <div><Breadcrumb {...breadcrumbAction} className={styles.Breadcrumb}/></div>
: null;
const titleMarkup = title ? <h1 className={styles.Title}>{title}</h1> : null;
return (
<div>
<div className={styles.Page}>
{breadcrumbMarkup}
<div className={styles.MainContent}>
{titleMarkup}
<div className={styles.PrimaryAction}>
{primaryActionMarkup}
</div>
</div>
<div className={styles.SecondaryActions}>
{secondaryActionsMarkup}
</div>
</div>
{children}
</div>
);
}
}
export default Page;