Copy to Clipboard
/* eslint-disable no-prototype-builtins */
/* eslint react/prop-types: 0 */
import React from 'react'
import {
BarGraph,
Body,
Caption,
Card,
CircleIconButton,
Currency,
Flex,
FlexItem,
Gauge,
IconStatValue,
Layout,
ProgressSimple,
SectionSeparator,
Title,
} from 'playbook-ui'
////////////////////////////////////////////////////
//
// Props for the components
//
////////////////////////////////////////////////////
const pipelineData = {
title: 'Pipeline Chart',
chartData: [
{ label: 'Add to Cart', percent: 100.0, value: 2577 },
{ label: 'Shopping Cart', percent: 79.0, value: 2023 },
{ label: 'Payment Methods', percent: 59.0, value: 1567 },
{ label: 'Delivery Methods', percent: 56.0, value: 1252 },
{ label: 'Confirm', percent: 49.0, value: 1182 },
{ label: 'Delivery', percent: 46.0, value: 1098 },
],
}
const ticketData = {
gridData: [
{ icon: 'ticket-alt', variant: 'green', size: 'lg', text: 'Tickets (YTD)', value: '1426.0' },
{ icon: 'times-square', variant: 'red', size: 'lg', text: 'Overdue', value: '25.0' },
{ icon: 'tasks', variant: 'teal', size: 'lg', text: 'Closed Without Action (YTD)', value: '97.0' },
{ icon: 'exclamation-triangle', variant: 'yellow', size: 'lg', text: 'Escalated (YTD)', value: '896.0' },
],
}
const totalRevenue = {
title: 'Total Revenue',
data: [{
name: 'Total Sales',
value: 80,
}],
legendData: [
{ value: '1000', label: 'Target' },
{ value: '224', label: 'Last Week' },
{ value: '965', label: 'Last Month' },
],
}
const salesReport = {
title: 'Total Revenue',
legendData: [
{ value: '1000', label: 'Target' },
{ value: '543', label: 'Last Week' },
],
data: [{
name: 'Sales Report',
data: [343, 135, 665, 903, 571, 191, 173, 520, 917],
}],
}
const clientData = {
title: 'Client Data',
data: [
{ title: 'New Clients', value: 35, percent: 11.0, status: 'negative' },
{ title: 'Returning Clients', value: 8, percent: 5.0, status: 'positive' },
{ title: 'VIP Clients', value: 1, percent: 11.0, status: 'negative' },
{ title: 'Orders on Clients', value: 1.44, percent: 5.0, status: 'positive' },
{ title: 'Bounce on Clients', value: 30.77, unit: '%', percent: 5.0, status: 'positive' },
{ title: 'Days Between Orders', value: 3, percent: 0.0, unit: 'days' },
{ title: 'New Orders', value: 26, percent: 11.0, status: 'negative' },
{ title: 'Confirmed Orders', value: 15, percent: 11.0, status: 'negative' },
],
}
////////////////////////////////////////////////////
//
// Components
//
////////////////////////////////////////////////////
const FulfillmentChart = ({ chartData, title }) => (
<Card
borderNone
margin="sm"
padding="none"
shadow="deeper"
>
<Flex
spacing="between"
vertical="center"
>
<Title
padding="sm"
size="4"
text={title}
/>
<CircleIconButton
icon="ellipsis-h"
variant="link"
/>
</Flex>
<SectionSeparator />
{chartData.map((row, i) => (
<Flex
key={i}
padding="sm"
spacing="between"
vertical="center"
>
<FlexItem fixedSize="100px">
<Caption
size="xs"
text={row.label}
/>
</FlexItem>
<FlexItem grow>
<Flex
spacing="around"
vertical="center"
>
<ProgressSimple
percent={row.percent}
width="100px"
/>
<FlexItem fixedSize="50px">
<Caption
marginX="xs"
size="xs"
text={`${row.percent}%`}
/>
</FlexItem>
</Flex>
</FlexItem>
<FlexItem>
<Flex vertical="right">
<Body
text={`${row.value}`}
/>
</Flex>
</FlexItem>
</Flex>
))}
</Card>
)
const GridRowFill = ({ data }) => (
<Card.Body padding="none">
<Flex
horizontal="center"
spacing="evenly"
wrap
>
{
data.map((line, i) => (
<FlexItem
fixedSize="215px"
key={`grid-row-item-${line.icon}-${i}`}
margin="md"
>
<IconStatValue {...line} />
</FlexItem>
)
)
}
</Flex>
</Card.Body>
)
const IconGrid = ({ gridData }) => (
<Card
borderNone
margin="sm"
padding="none"
shadow="deeper"
>
<GridRowFill data={gridData.slice(0, 2)} />
<GridRowFill data={gridData.slice(2)} />
</Card>
)
const Legend = ({ name, data }) => {
name = name.toLowerCase().replace(/\s/g, '-')
return (
<Flex
className="flex-container"
horizontal="center"
margin="xs"
spacing="between"
wrap
>
{
data.map((point, i) => (
<FlexItem
key={`legend-${name}-${i}`}
marginX="sm"
marginY="sm"
>
<Currency
amount={point.value}
emphasized
label={point.label}
marginBottom="md"
size="md"
symbol="$"
variant="light"
/>
</FlexItem>
)
)
}
</Flex>
)
}
const GaugeLegend = ({ title, data, legendData }) => (
<Card
borderNone
margin="sm"
padding="none"
shadow="deeper"
>
<Flex
spacing="between"
vertical="center"
>
<Title
padding="sm"
size="4"
text={title}
/>
<CircleIconButton
icon="ellipsis-h"
variant="link"
/>
</Flex>
<SectionSeparator />
<Card.Body>
<Flex
horizontal="center"
orientation="column"
vertical="center"
>
<Gauge
chartData={data}
fullCircle
id="full-circle"
/>
<Caption text="Total Sales made Today" />
</Flex>
</Card.Body>
<SectionSeparator />
<Card.Body padding="none">
<Legend
data={legendData}
name={title}
/>
</Card.Body>
</Card>
)
const BarGraphLegend = ({ title, data, legendData }) => (
<Card
borderNone
margin="sm"
padding="none"
shadow="deeper"
>
<Flex
spacing="between"
vertical="center"
>
<Title
padding="sm"
size="4"
text={title}
/>
<CircleIconButton
icon="ellipsis-h"
variant="link"
/>
</Flex>
<SectionSeparator />
<Card.Body>
<BarGraph
chartData={data}
height="75%"
id="bar-default"
xAxisCategories={[]}
yAxisCategories="0"
/>
</Card.Body>
<SectionSeparator />
<Legend
data={legendData}
name={title}
/>
</Card>
)
const GridBlock = ({ data }) => {
const unit = data.hasOwnProperty('unit') ? `${data.unit}` : ''
const status = data.hasOwnProperty('status') ? (data.status === 'positive' ? '+' : '-') : ''
return (
<Flex
orientation="column"
wrap
>
<FlexItem
marginY="md"
>
<FlexItem>
<Body
color="light"
text={data.title}
/>
</FlexItem>
<FlexItem>
<Flex>
<FlexItem>
<Title
size="3"
tag="h3"
text={`${data.value} ${unit}`}
/>
</FlexItem>
<FlexItem>
<Body
marginLeft="xs"
status={data.status}
text={`${status}${data.percent}%`}
value={data.percent}
/>
</FlexItem>
</Flex>
</FlexItem>
</FlexItem>
</Flex>
)
}
const NumberGrid = ({ data }) => {
return (
<Card
borderNone
margin="sm"
shadow="deeper"
>
<Layout layout="collection">
<Layout.Body>
{
data.map((block, i) => (
<GridBlock
data={block}
key={i}
/>
)
)
}
</Layout.Body>
</Layout>
</Card>
)
}
////////////////////////////////////////////////////
//
// Layout
//
////////////////////////////////////////////////////
// remove flex from here and use the stylesheet
const CardDashboard = () => {
return (
<div id="main-dashboard-content">
<FulfillmentChart {...pipelineData} />
<IconGrid {...ticketData} />
<BarGraphLegend {...salesReport} />
<NumberGrid {...clientData} />
<GaugeLegend {...totalRevenue} />
</div>
)
}
export default CardDashboard
/* eslint-disable no-prototype-builtins */
/* eslint react/prop-types: 0 */
import React from 'react'
import {
BarGraph,
Body,
Caption,
Card,
CircleIconButton,
Currency,
Flex,
FlexItem,
Gauge,
IconStatValue,
Layout,
ProgressSimple,
SectionSeparator,
Title,
} from 'playbook-ui'
////////////////////////////////////////////////////
//
// Props for the components
//
////////////////////////////////////////////////////
const pipelineData = {
title: 'Pipeline Chart',
chartData: [
{ label: 'Add to Cart', percent: 100.0, value: 2577 },
{ label: 'Shopping Cart', percent: 79.0, value: 2023 },
{ label: 'Payment Methods', percent: 59.0, value: 1567 },
{ label: 'Delivery Methods', percent: 56.0, value: 1252 },
{ label: 'Confirm', percent: 49.0, value: 1182 },
{ label: 'Delivery', percent: 46.0, value: 1098 },
],
}
const ticketData = {
gridData: [
{ icon: 'ticket-alt', variant: 'green', size: 'lg', text: 'Tickets (YTD)', value: '1426.0' },
{ icon: 'times-square', variant: 'red', size: 'lg', text: 'Overdue', value: '25.0' },
{ icon: 'tasks', variant: 'teal', size: 'lg', text: 'Closed Without Action (YTD)', value: '97.0' },
{ icon: 'exclamation-triangle', variant: 'yellow', size: 'lg', text: 'Escalated (YTD)', value: '896.0' },
],
}
const totalRevenue = {
title: 'Total Revenue',
data: [{
name: 'Total Sales',
value: 80,
}],
legendData: [
{ value: '1000', label: 'Target' },
{ value: '224', label: 'Last Week' },
{ value: '965', label: 'Last Month' },
],
}
const salesReport = {
title: 'Total Revenue',
legendData: [
{ value: '1000', label: 'Target' },
{ value: '543', label: 'Last Week' },
],
data: [{
name: 'Sales Report',
data: [343, 135, 665, 903, 571, 191, 173, 520, 917],
}],
}
const clientData = {
title: 'Client Data',
data: [
{ title: 'New Clients', value: 35, percent: 11.0, status: 'negative' },
{ title: 'Returning Clients', value: 8, percent: 5.0, status: 'positive' },
{ title: 'VIP Clients', value: 1, percent: 11.0, status: 'negative' },
{ title: 'Orders on Clients', value: 1.44, percent: 5.0, status: 'positive' },
{ title: 'Bounce on Clients', value: 30.77, unit: '%', percent: 5.0, status: 'positive' },
{ title: 'Days Between Orders', value: 3, percent: 0.0, unit: 'days' },
{ title: 'New Orders', value: 26, percent: 11.0, status: 'negative' },
{ title: 'Confirmed Orders', value: 15, percent: 11.0, status: 'negative' },
],
}
////////////////////////////////////////////////////
//
// Components
//
////////////////////////////////////////////////////
const FulfillmentChart = ({ chartData, title }) => (
<Card
borderNone
margin="sm"
padding="none"
shadow="deeper"
>
<Flex
spacing="between"
vertical="center"
>
<Title
padding="sm"
size="4"
text={title}
/>
<CircleIconButton
icon="ellipsis-h"
variant="link"
/>
</Flex>
<SectionSeparator />
{chartData.map((row, i) => (
<Flex
key={i}
padding="sm"
spacing="between"
vertical="center"
>
<FlexItem fixedSize="100px">
<Caption
size="xs"
text={row.label}
/>
</FlexItem>
<FlexItem grow>
<Flex
spacing="around"
vertical="center"
>
<ProgressSimple
percent={row.percent}
width="100px"
/>
<FlexItem fixedSize="50px">
<Caption
marginX="xs"
size="xs"
text={`${row.percent}%`}
/>
</FlexItem>
</Flex>
</FlexItem>
<FlexItem>
<Flex vertical="right">
<Body
text={`${row.value}`}
/>
</Flex>
</FlexItem>
</Flex>
))}
</Card>
)
const GridRowFill = ({ data }) => (
<Card.Body padding="none">
<Flex
horizontal="center"
spacing="evenly"
wrap
>
{
data.map((line, i) => (
<FlexItem
fixedSize="215px"
key={`grid-row-item-${line.icon}-${i}`}
margin="md"
>
<IconStatValue {...line} />
</FlexItem>
)
)
}
</Flex>
</Card.Body>
)
const IconGrid = ({ gridData }) => (
<Card
borderNone
margin="sm"
padding="none"
shadow="deeper"
>
<GridRowFill data={gridData.slice(0, 2)} />
<GridRowFill data={gridData.slice(2)} />
</Card>
)
const Legend = ({ name, data }) => {
name = name.toLowerCase().replace(/\s/g, '-')
return (
<Flex
className="flex-container"
horizontal="center"
margin="xs"
spacing="between"
wrap
>
{
data.map((point, i) => (
<FlexItem
key={`legend-${name}-${i}`}
marginX="sm"
marginY="sm"
>
<Currency
amount={point.value}
emphasized
label={point.label}
marginBottom="md"
size="md"
symbol="$"
variant="light"
/>
</FlexItem>
)
)
}
</Flex>
)
}
const GaugeLegend = ({ title, data, legendData }) => (
<Card
borderNone
margin="sm"
padding="none"
shadow="deeper"
>
<Flex
spacing="between"
vertical="center"
>
<Title
padding="sm"
size="4"
text={title}
/>
<CircleIconButton
icon="ellipsis-h"
variant="link"
/>
</Flex>
<SectionSeparator />
<Card.Body>
<Flex
horizontal="center"
orientation="column"
vertical="center"
>
<Gauge
chartData={data}
fullCircle
id="full-circle"
/>
<Caption text="Total Sales made Today" />
</Flex>
</Card.Body>
<SectionSeparator />
<Card.Body padding="none">
<Legend
data={legendData}
name={title}
/>
</Card.Body>
</Card>
)
const BarGraphLegend = ({ title, data, legendData }) => (
<Card
borderNone
margin="sm"
padding="none"
shadow="deeper"
>
<Flex
spacing="between"
vertical="center"
>
<Title
padding="sm"
size="4"
text={title}
/>
<CircleIconButton
icon="ellipsis-h"
variant="link"
/>
</Flex>
<SectionSeparator />
<Card.Body>
<BarGraph
chartData={data}
height="75%"
id="bar-default"
xAxisCategories={[]}
yAxisCategories="0"
/>
</Card.Body>
<SectionSeparator />
<Legend
data={legendData}
name={title}
/>
</Card>
)
const GridBlock = ({ data }) => {
const unit = data.hasOwnProperty('unit') ? `${data.unit}` : ''
const status = data.hasOwnProperty('status') ? (data.status === 'positive' ? '+' : '-') : ''
return (
<Flex
orientation="column"
wrap
>
<FlexItem
marginY="md"
>
<FlexItem>
<Body
color="light"
text={data.title}
/>
</FlexItem>
<FlexItem>
<Flex>
<FlexItem>
<Title
size="3"
tag="h3"
text={`${data.value} ${unit}`}
/>
</FlexItem>
<FlexItem>
<Body
marginLeft="xs"
status={data.status}
text={`${status}${data.percent}%`}
value={data.percent}
/>
</FlexItem>
</Flex>
</FlexItem>
</FlexItem>
</Flex>
)
}
const NumberGrid = ({ data }) => {
return (
<Card
borderNone
margin="sm"
shadow="deeper"
>
<Layout layout="collection">
<Layout.Body>
{
data.map((block, i) => (
<GridBlock
data={block}
key={i}
/>
)
)
}
</Layout.Body>
</Layout>
</Card>
)
}
////////////////////////////////////////////////////
//
// Layout
//
////////////////////////////////////////////////////
// remove flex from here and use the stylesheet
const CardDashboard = () => {
return (
<div id="main-dashboard-content">
<FulfillmentChart {...pipelineData} />
<IconGrid {...ticketData} />
<BarGraphLegend {...salesReport} />
<NumberGrid {...clientData} />
<GaugeLegend {...totalRevenue} />
</div>
)
}
export default CardDashboard