@centreon/ui 23.10.24 → 23.10.25-feature-MON-19319.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +8 -1
- package/src/Dashboard/DashboardLayout.stories.tsx +3 -5
- package/src/Dashboard/Layout.tsx +4 -4
- package/src/Dashboard/utils.ts +28 -28
- package/src/ThemeProvider/index.tsx +6 -5
- package/src/ThemeProvider/palettes.ts +234 -208
- package/src/components/Button/Button.styles.ts +7 -2
- package/src/components/Header/Header.styles.ts +0 -27
- package/src/components/Header/PageHeader/PageHeader.stories.tsx +83 -0
- package/src/components/Header/PageHeader/PageHeader.styles.ts +105 -0
- package/src/components/Header/PageHeader/PageHeader.tsx +15 -0
- package/src/components/Header/PageHeader/PageHeaderActions.tsx +17 -0
- package/src/components/Header/PageHeader/PageHeaderMain.tsx +15 -0
- package/src/components/Header/PageHeader/PageHeaderMenu.tsx +15 -0
- package/src/components/Header/PageHeader/PageHeaderTitle.tsx +44 -0
- package/src/components/Header/PageHeader/index.ts +12 -0
- package/src/components/Header/index.ts +1 -1
- package/src/components/Layout/AreaIndicator.styles.ts +33 -0
- package/src/components/Layout/AreaIndicator.tsx +35 -0
- package/src/components/Layout/PageLayout/PageLayout.stories.tsx +81 -0
- package/src/components/Layout/PageLayout/PageLayout.styles.ts +30 -0
- package/src/components/Layout/PageLayout/PageLayout.tsx +21 -0
- package/src/components/Layout/PageLayout/PageLayoutActions.tsx +15 -0
- package/src/components/Layout/PageLayout/PageLayoutBody.tsx +24 -0
- package/src/components/Layout/PageLayout/PageLayoutHeader.tsx +15 -0
- package/src/components/Layout/PageLayout/index.ts +10 -0
- package/src/components/Layout/index.ts +1 -0
- package/src/components/Menu/Menu.tsx +0 -0
- package/src/components/Tooltip/TextOverflowTooltip/TextOverflowTooltip.stories.tsx +71 -0
- package/src/components/Tooltip/TextOverflowTooltip/TextOverflowTooltip.styles.ts +5 -0
- package/src/components/Tooltip/TextOverflowTooltip/TextOverflowTooltip.tsx +115 -0
- package/src/components/Tooltip/TextOverflowTooltip/index.tsx +1 -0
- package/src/components/Tooltip/Tooltip.stories.tsx +41 -0
- package/src/components/Tooltip/Tooltip.styles.ts +5 -0
- package/src/components/Tooltip/Tooltip.tsx +46 -0
- package/src/components/Tooltip/index.ts +1 -0
- package/src/components/index.ts +2 -0
- package/src/index.ts +0 -2
- package/src/screens/dashboard/DashboardsOverview.stories.tsx +109 -101
- package/src/utils/useResizeObserver.ts +6 -0
- package/test/setupTests.js +23 -20
- package/src/components/Header/Header.stories.tsx +0 -27
- package/src/components/Header/Header.tsx +0 -23
- package/src/layout/TiledListingPage/TiledListingActions.tsx +0 -15
- package/src/layout/TiledListingPage/TiledListingContent.tsx +0 -21
- package/src/layout/TiledListingPage/TiledListingList.tsx +0 -11
- package/src/layout/TiledListingPage/TiledListingPage.styles.ts +0 -16
- package/src/layout/TiledListingPage/TiledListingPage.tsx +0 -15
- package/src/layout/TiledListingPage/index.ts +0 -4
|
@@ -1,27 +0,0 @@
|
|
|
1
|
-
import { makeStyles } from 'tss-react/mui';
|
|
2
|
-
|
|
3
|
-
const useStyles = makeStyles()((theme) => ({
|
|
4
|
-
header: {
|
|
5
|
-
alignItems: 'flex-start',
|
|
6
|
-
borderBottom: `1px solid ${theme.palette.primary.main}`,
|
|
7
|
-
display: 'flex',
|
|
8
|
-
flexDirection: 'row',
|
|
9
|
-
h1: {
|
|
10
|
-
font: 'normal normal 600 24px/24px Roboto',
|
|
11
|
-
letterSpacing: '0.18px',
|
|
12
|
-
margin: theme.spacing(0, 0, 1.5, 0)
|
|
13
|
-
},
|
|
14
|
-
justifyContent: 'space-between',
|
|
15
|
-
marginBottom: theme.spacing(2.5),
|
|
16
|
-
|
|
17
|
-
nav: {
|
|
18
|
-
display: 'flex',
|
|
19
|
-
gap: theme.spacing(1),
|
|
20
|
-
justifyContent: 'flex-end'
|
|
21
|
-
},
|
|
22
|
-
|
|
23
|
-
padding: theme.spacing(0, 0, 1.5, 0)
|
|
24
|
-
}
|
|
25
|
-
}));
|
|
26
|
-
|
|
27
|
-
export { useStyles };
|
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
import { Meta, StoryObj } from '@storybook/react';
|
|
2
|
+
|
|
3
|
+
import {
|
|
4
|
+
ArrowDropDown as ArrowDropDownIcon,
|
|
5
|
+
Menu as MenuIcon,
|
|
6
|
+
Settings as SettingsIcon,
|
|
7
|
+
StarOutline as StarOutlineIcon
|
|
8
|
+
} from '@mui/icons-material';
|
|
9
|
+
|
|
10
|
+
import { Button, IconButton } from '../../Button';
|
|
11
|
+
|
|
12
|
+
import { PageHeader } from './index';
|
|
13
|
+
|
|
14
|
+
type PageHeaderComponent = typeof PageHeader & typeof PageHeader.Title;
|
|
15
|
+
|
|
16
|
+
const meta: Meta<typeof PageHeader> = {
|
|
17
|
+
component: PageHeader
|
|
18
|
+
};
|
|
19
|
+
|
|
20
|
+
export default meta;
|
|
21
|
+
type Story = StoryObj<PageHeaderComponent>;
|
|
22
|
+
|
|
23
|
+
export const Default: Story = {
|
|
24
|
+
args: {
|
|
25
|
+
title: 'Page header'
|
|
26
|
+
},
|
|
27
|
+
render: (args) => (
|
|
28
|
+
<PageHeader>
|
|
29
|
+
<PageHeader.Main>
|
|
30
|
+
<PageHeader.Title {...args} />
|
|
31
|
+
</PageHeader.Main>
|
|
32
|
+
<PageHeader.Actions>
|
|
33
|
+
<Button
|
|
34
|
+
icon={<SettingsIcon />}
|
|
35
|
+
iconVariant="start"
|
|
36
|
+
size="small"
|
|
37
|
+
variant="ghost"
|
|
38
|
+
>
|
|
39
|
+
Manage
|
|
40
|
+
</Button>
|
|
41
|
+
</PageHeader.Actions>
|
|
42
|
+
</PageHeader>
|
|
43
|
+
)
|
|
44
|
+
};
|
|
45
|
+
|
|
46
|
+
export const WithDescription: Story = {
|
|
47
|
+
args: {
|
|
48
|
+
description:
|
|
49
|
+
'Eu aliquip quis in minim laboris occaecat quis nostrud occaecat. Cupidatat consectetur non Lorem eiusmod ut cupidatat dolor enim cillum ex enim irure velit. ',
|
|
50
|
+
title: 'Nulla ex dolore tempor magna ex'
|
|
51
|
+
},
|
|
52
|
+
render: Default.render
|
|
53
|
+
};
|
|
54
|
+
|
|
55
|
+
export const WithMenu: Story = {
|
|
56
|
+
args: {
|
|
57
|
+
...WithDescription.args,
|
|
58
|
+
actions: (
|
|
59
|
+
<IconButton icon={<StarOutlineIcon />} size="small" variant="ghost" />
|
|
60
|
+
)
|
|
61
|
+
},
|
|
62
|
+
render: (args) => (
|
|
63
|
+
<PageHeader>
|
|
64
|
+
<PageHeader.Main>
|
|
65
|
+
<PageHeader.Menu>
|
|
66
|
+
<MenuIcon />
|
|
67
|
+
<ArrowDropDownIcon data-size="small" />
|
|
68
|
+
</PageHeader.Menu>
|
|
69
|
+
<PageHeader.Title {...args} />
|
|
70
|
+
</PageHeader.Main>
|
|
71
|
+
<PageHeader.Actions>
|
|
72
|
+
<Button
|
|
73
|
+
icon={<SettingsIcon />}
|
|
74
|
+
iconVariant="start"
|
|
75
|
+
size="small"
|
|
76
|
+
variant="ghost"
|
|
77
|
+
>
|
|
78
|
+
Manage
|
|
79
|
+
</Button>
|
|
80
|
+
</PageHeader.Actions>
|
|
81
|
+
</PageHeader>
|
|
82
|
+
)
|
|
83
|
+
};
|
|
@@ -0,0 +1,105 @@
|
|
|
1
|
+
import { makeStyles } from 'tss-react/mui';
|
|
2
|
+
|
|
3
|
+
const useStyles = makeStyles()((theme) => ({
|
|
4
|
+
header: {
|
|
5
|
+
alignItems: 'flex-start',
|
|
6
|
+
borderBottom: `1px solid ${theme.palette.primary.main}`,
|
|
7
|
+
display: 'flex',
|
|
8
|
+
flexDirection: 'row',
|
|
9
|
+
h1: {
|
|
10
|
+
font: 'normal normal 600 24px/24px Roboto',
|
|
11
|
+
letterSpacing: '0.18px',
|
|
12
|
+
margin: theme.spacing(0, 0, 1.5, 0)
|
|
13
|
+
},
|
|
14
|
+
justifyContent: 'space-between',
|
|
15
|
+
|
|
16
|
+
nav: {
|
|
17
|
+
display: 'flex',
|
|
18
|
+
gap: theme.spacing(1),
|
|
19
|
+
justifyContent: 'flex-end'
|
|
20
|
+
},
|
|
21
|
+
|
|
22
|
+
padding: theme.spacing(0, 0, 1.5, 0)
|
|
23
|
+
},
|
|
24
|
+
pageHeader: {
|
|
25
|
+
alignItems: 'flex-start',
|
|
26
|
+
borderBottom: `1px solid ${theme.palette.header.page.border}`,
|
|
27
|
+
display: 'flex',
|
|
28
|
+
gap: theme.spacing(4),
|
|
29
|
+
paddingBottom: theme.spacing(2)
|
|
30
|
+
},
|
|
31
|
+
pageHeaderActions: {
|
|
32
|
+
'& > button': {
|
|
33
|
+
'&:hover': {
|
|
34
|
+
backgroundColor: theme.palette.header.page.action.background.active,
|
|
35
|
+
color: theme.palette.header.page.action.color.active
|
|
36
|
+
},
|
|
37
|
+
backgroundColor: theme.palette.header.page.action.background.default,
|
|
38
|
+
|
|
39
|
+
color: theme.palette.header.page.action.color.default
|
|
40
|
+
},
|
|
41
|
+
display: 'flex',
|
|
42
|
+
|
|
43
|
+
gap: theme.spacing(2)
|
|
44
|
+
},
|
|
45
|
+
pageHeaderMain: {
|
|
46
|
+
display: 'flex',
|
|
47
|
+
flexGrow: 1,
|
|
48
|
+
gap: theme.spacing(1.5)
|
|
49
|
+
},
|
|
50
|
+
pageHeaderMenu: {
|
|
51
|
+
// TEMP
|
|
52
|
+
'& [data-size="small"]': {
|
|
53
|
+
height: '20px',
|
|
54
|
+
marginTop: theme.spacing(0.25),
|
|
55
|
+
width: '20px'
|
|
56
|
+
},
|
|
57
|
+
alignItems: 'top',
|
|
58
|
+
display: 'flex',
|
|
59
|
+
opacity: 0.5,
|
|
60
|
+
padding: theme.spacing(0.25, 0)
|
|
61
|
+
},
|
|
62
|
+
pageHeaderTitle: {
|
|
63
|
+
'& > *': {
|
|
64
|
+
display: 'grid'
|
|
65
|
+
},
|
|
66
|
+
'& > span': {
|
|
67
|
+
display: 'flex',
|
|
68
|
+
flexDirection: 'row',
|
|
69
|
+
|
|
70
|
+
gap: theme.spacing(2)
|
|
71
|
+
},
|
|
72
|
+
display: 'flex',
|
|
73
|
+
|
|
74
|
+
flexDirection: 'column',
|
|
75
|
+
|
|
76
|
+
gap: theme.spacing(1),
|
|
77
|
+
|
|
78
|
+
h1: {
|
|
79
|
+
color: theme.palette.header.page.title,
|
|
80
|
+
font: 'normal normal 700 24px/100% Roboto',
|
|
81
|
+
letterSpacing: '0.15px',
|
|
82
|
+
margin: theme.spacing(0)
|
|
83
|
+
}
|
|
84
|
+
},
|
|
85
|
+
pageHeaderTitleActions: {
|
|
86
|
+
'& > button': {
|
|
87
|
+
opacity: 0.2,
|
|
88
|
+
padding: 0
|
|
89
|
+
},
|
|
90
|
+
alignItems: 'bottom',
|
|
91
|
+
display: 'flex',
|
|
92
|
+
gap: theme.spacing(1)
|
|
93
|
+
},
|
|
94
|
+
pageHeaderTitleDescription: {
|
|
95
|
+
color: theme.palette.header.page.description,
|
|
96
|
+
font: 'normal normal 400 12px/16px Roboto',
|
|
97
|
+
letterSpacing: '0.15px',
|
|
98
|
+
maxWidth: '560px',
|
|
99
|
+
overflow: 'hidden',
|
|
100
|
+
textOverflow: 'ellipsis',
|
|
101
|
+
whiteSpace: 'nowrap'
|
|
102
|
+
}
|
|
103
|
+
}));
|
|
104
|
+
|
|
105
|
+
export { useStyles };
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import React, { ReactElement, ReactNode } from 'react';
|
|
2
|
+
|
|
3
|
+
import { useStyles } from './PageHeader.styles';
|
|
4
|
+
|
|
5
|
+
type PageHeaderProps = {
|
|
6
|
+
children?: ReactNode;
|
|
7
|
+
};
|
|
8
|
+
|
|
9
|
+
const PageHeader = ({ children }: PageHeaderProps): ReactElement => {
|
|
10
|
+
const { classes } = useStyles();
|
|
11
|
+
|
|
12
|
+
return <section className={classes.pageHeader}>{children}</section>;
|
|
13
|
+
};
|
|
14
|
+
|
|
15
|
+
export { PageHeader };
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import React, { ReactElement, ReactNode } from 'react';
|
|
2
|
+
|
|
3
|
+
import { useStyles } from './PageHeader.styles';
|
|
4
|
+
|
|
5
|
+
type PageHeaderActionsProps = {
|
|
6
|
+
children?: ReactNode;
|
|
7
|
+
};
|
|
8
|
+
|
|
9
|
+
const PageHeaderActions = ({
|
|
10
|
+
children
|
|
11
|
+
}: PageHeaderActionsProps): ReactElement => {
|
|
12
|
+
const { classes } = useStyles();
|
|
13
|
+
|
|
14
|
+
return <header className={classes.pageHeaderActions}>{children}</header>;
|
|
15
|
+
};
|
|
16
|
+
|
|
17
|
+
export { PageHeaderActions };
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import React, { ReactElement, ReactNode } from 'react';
|
|
2
|
+
|
|
3
|
+
import { useStyles } from './PageHeader.styles';
|
|
4
|
+
|
|
5
|
+
type PageHeaderMainProps = {
|
|
6
|
+
children?: ReactNode;
|
|
7
|
+
};
|
|
8
|
+
|
|
9
|
+
const PageHeaderMain = ({ children }: PageHeaderMainProps): ReactElement => {
|
|
10
|
+
const { classes } = useStyles();
|
|
11
|
+
|
|
12
|
+
return <div className={classes.pageHeaderMain}>{children}</div>;
|
|
13
|
+
};
|
|
14
|
+
|
|
15
|
+
export { PageHeaderMain };
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import React, { ReactElement, ReactNode } from 'react';
|
|
2
|
+
|
|
3
|
+
import { useStyles } from './PageHeader.styles';
|
|
4
|
+
|
|
5
|
+
type PageHeaderMenuProps = {
|
|
6
|
+
children?: ReactNode;
|
|
7
|
+
};
|
|
8
|
+
|
|
9
|
+
const PageHeaderMenu = ({ children }: PageHeaderMenuProps): ReactElement => {
|
|
10
|
+
const { classes } = useStyles();
|
|
11
|
+
|
|
12
|
+
return <nav className={classes.pageHeaderMenu}>{children}</nav>;
|
|
13
|
+
};
|
|
14
|
+
|
|
15
|
+
export { PageHeaderMenu };
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
import React, { ReactElement, ReactNode } from 'react';
|
|
2
|
+
|
|
3
|
+
import { Typography as MuiTypography } from '@mui/material';
|
|
4
|
+
|
|
5
|
+
import { TextOverflowTooltip } from '../../Tooltip/TextOverflowTooltip';
|
|
6
|
+
|
|
7
|
+
import { useStyles } from './PageHeader.styles';
|
|
8
|
+
|
|
9
|
+
type PageHeaderTitleProps = {
|
|
10
|
+
actions?: ReactNode;
|
|
11
|
+
description?: string;
|
|
12
|
+
title: string;
|
|
13
|
+
};
|
|
14
|
+
|
|
15
|
+
const PageHeaderTitle = ({
|
|
16
|
+
actions,
|
|
17
|
+
title,
|
|
18
|
+
description
|
|
19
|
+
}: PageHeaderTitleProps): ReactElement => {
|
|
20
|
+
const { classes } = useStyles();
|
|
21
|
+
|
|
22
|
+
return (
|
|
23
|
+
<div className={classes.pageHeaderTitle}>
|
|
24
|
+
<span>
|
|
25
|
+
<MuiTypography variant="h1">{title}</MuiTypography>
|
|
26
|
+
{actions && (
|
|
27
|
+
<div className={classes.pageHeaderTitleActions}>{actions}</div>
|
|
28
|
+
)}
|
|
29
|
+
</span>
|
|
30
|
+
{description && (
|
|
31
|
+
<TextOverflowTooltip label={description}>
|
|
32
|
+
<MuiTypography
|
|
33
|
+
className={classes.pageHeaderTitleDescription}
|
|
34
|
+
variant="body2"
|
|
35
|
+
>
|
|
36
|
+
{description}
|
|
37
|
+
</MuiTypography>
|
|
38
|
+
</TextOverflowTooltip>
|
|
39
|
+
)}
|
|
40
|
+
</div>
|
|
41
|
+
);
|
|
42
|
+
};
|
|
43
|
+
|
|
44
|
+
export { PageHeaderTitle };
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import { PageHeader as PageHeaderRoot } from './PageHeader';
|
|
2
|
+
import { PageHeaderMain } from './PageHeaderMain';
|
|
3
|
+
import { PageHeaderMenu } from './PageHeaderMenu';
|
|
4
|
+
import { PageHeaderTitle } from './PageHeaderTitle';
|
|
5
|
+
import { PageHeaderActions } from './PageHeaderActions';
|
|
6
|
+
|
|
7
|
+
export const PageHeader = Object.assign(PageHeaderRoot, {
|
|
8
|
+
Actions: PageHeaderActions,
|
|
9
|
+
Main: PageHeaderMain,
|
|
10
|
+
Menu: PageHeaderMenu,
|
|
11
|
+
Title: PageHeaderTitle
|
|
12
|
+
});
|
|
@@ -1 +1 @@
|
|
|
1
|
-
export * from './
|
|
1
|
+
export * from './PageHeader';
|
|
@@ -0,0 +1,33 @@
|
|
|
1
|
+
import { makeStyles } from 'tss-react/mui';
|
|
2
|
+
|
|
3
|
+
export const useStyles = makeStyles()((theme) => ({
|
|
4
|
+
areaIndicator: {
|
|
5
|
+
'& .areaIndicator': {
|
|
6
|
+
left: theme.spacing(10)
|
|
7
|
+
},
|
|
8
|
+
'& label:first-of-type': {
|
|
9
|
+
border: '1px dashed #9747FF7F',
|
|
10
|
+
borderRadius: '4px',
|
|
11
|
+
color: '#9747FFFF',
|
|
12
|
+
fontSize: '0.75rem',
|
|
13
|
+
fontWeight: 500,
|
|
14
|
+
left: theme.spacing(1),
|
|
15
|
+
padding: theme.spacing(0.125, 1),
|
|
16
|
+
position: 'absolute',
|
|
17
|
+
top: theme.spacing(0.75)
|
|
18
|
+
},
|
|
19
|
+
'&[data-depth="1"]': {
|
|
20
|
+
'& label:first-of-type': {
|
|
21
|
+
'&:before': {
|
|
22
|
+
content: '"+ "'
|
|
23
|
+
},
|
|
24
|
+
left: theme.spacing(10)
|
|
25
|
+
}
|
|
26
|
+
},
|
|
27
|
+
|
|
28
|
+
backgroundColor: '#9747FF19',
|
|
29
|
+
minHeight: theme.spacing(4),
|
|
30
|
+
|
|
31
|
+
position: 'relative'
|
|
32
|
+
}
|
|
33
|
+
}));
|
|
@@ -0,0 +1,35 @@
|
|
|
1
|
+
import { ReactElement, ReactNode } from 'react';
|
|
2
|
+
|
|
3
|
+
import { useStyles } from './AreaIndicator.styles';
|
|
4
|
+
|
|
5
|
+
type AreaIndicatorProps = {
|
|
6
|
+
children?: ReactNode | Array<ReactNode>;
|
|
7
|
+
depth?: number;
|
|
8
|
+
height?: number | string;
|
|
9
|
+
name: string;
|
|
10
|
+
width?: number | string;
|
|
11
|
+
};
|
|
12
|
+
|
|
13
|
+
const AreaIndicator = ({
|
|
14
|
+
children,
|
|
15
|
+
name = 'area',
|
|
16
|
+
width = '100%',
|
|
17
|
+
height = '100%',
|
|
18
|
+
depth = 0
|
|
19
|
+
}: AreaIndicatorProps): ReactElement => {
|
|
20
|
+
const { classes } = useStyles();
|
|
21
|
+
|
|
22
|
+
return (
|
|
23
|
+
<div
|
|
24
|
+
className={classes.areaIndicator}
|
|
25
|
+
data-depth={depth}
|
|
26
|
+
style={{ height, width }}
|
|
27
|
+
>
|
|
28
|
+
{/* eslint-disable-next-line jsx-a11y/label-has-associated-control */}
|
|
29
|
+
<label>{name}</label>
|
|
30
|
+
{children}
|
|
31
|
+
</div>
|
|
32
|
+
);
|
|
33
|
+
};
|
|
34
|
+
|
|
35
|
+
export { AreaIndicator };
|
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
import { Meta, StoryObj } from '@storybook/react';
|
|
2
|
+
|
|
3
|
+
import { AreaIndicator } from '../AreaIndicator';
|
|
4
|
+
import { Default as DefaultPageHeaderStory } from '../../Header/PageHeader/PageHeader.stories';
|
|
5
|
+
|
|
6
|
+
import { PageLayout } from './index';
|
|
7
|
+
|
|
8
|
+
const meta: Meta<typeof PageLayout> = {
|
|
9
|
+
argTypes: {
|
|
10
|
+
variant: {
|
|
11
|
+
control: {
|
|
12
|
+
options: ['default', 'fixed-header']
|
|
13
|
+
}
|
|
14
|
+
}
|
|
15
|
+
},
|
|
16
|
+
component: PageLayout,
|
|
17
|
+
parameters: {
|
|
18
|
+
layout: 'fullscreen'
|
|
19
|
+
}
|
|
20
|
+
};
|
|
21
|
+
|
|
22
|
+
export default meta;
|
|
23
|
+
type Story = StoryObj<typeof PageLayout>;
|
|
24
|
+
|
|
25
|
+
export const Default: Story = {
|
|
26
|
+
args: {
|
|
27
|
+
children: (
|
|
28
|
+
<>
|
|
29
|
+
<PageLayout.Header>
|
|
30
|
+
<AreaIndicator name="header" />
|
|
31
|
+
</PageLayout.Header>
|
|
32
|
+
<PageLayout.Body>
|
|
33
|
+
<AreaIndicator height="100vh" name="body">
|
|
34
|
+
<PageLayout.Actions>
|
|
35
|
+
<AreaIndicator depth={1} name="actions" />
|
|
36
|
+
</PageLayout.Actions>
|
|
37
|
+
</AreaIndicator>
|
|
38
|
+
</PageLayout.Body>
|
|
39
|
+
</>
|
|
40
|
+
),
|
|
41
|
+
variant: 'default'
|
|
42
|
+
}
|
|
43
|
+
};
|
|
44
|
+
|
|
45
|
+
export const FixedHeader: Story = {
|
|
46
|
+
args: {
|
|
47
|
+
children: (
|
|
48
|
+
<>
|
|
49
|
+
<PageLayout.Header>
|
|
50
|
+
<AreaIndicator name="header" />
|
|
51
|
+
</PageLayout.Header>
|
|
52
|
+
<PageLayout.Body hasBackground>
|
|
53
|
+
<AreaIndicator height="100vh" name="body">
|
|
54
|
+
<PageLayout.Actions>
|
|
55
|
+
<AreaIndicator depth={1} name="actions" />
|
|
56
|
+
</PageLayout.Actions>
|
|
57
|
+
</AreaIndicator>
|
|
58
|
+
</PageLayout.Body>
|
|
59
|
+
</>
|
|
60
|
+
),
|
|
61
|
+
variant: 'fixed-header'
|
|
62
|
+
}
|
|
63
|
+
};
|
|
64
|
+
|
|
65
|
+
export const DefaultWithPageHeader: Story = {
|
|
66
|
+
args: {
|
|
67
|
+
children: (
|
|
68
|
+
<>
|
|
69
|
+
<PageLayout.Header>
|
|
70
|
+
{/* eslint-disable react/jsx-pascal-case */}
|
|
71
|
+
{/* @ts-expect-error storybook story render method not being recognised */}
|
|
72
|
+
<DefaultPageHeaderStory.render {...DefaultPageHeaderStory.args} />
|
|
73
|
+
</PageLayout.Header>
|
|
74
|
+
<PageLayout.Body>
|
|
75
|
+
<AreaIndicator height="100vh" name="body" />
|
|
76
|
+
</PageLayout.Body>
|
|
77
|
+
</>
|
|
78
|
+
),
|
|
79
|
+
variant: 'default'
|
|
80
|
+
}
|
|
81
|
+
};
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
import { makeStyles } from 'tss-react/mui';
|
|
2
|
+
|
|
3
|
+
export const useStyles = makeStyles()((theme) => ({
|
|
4
|
+
pageLayout: {
|
|
5
|
+
display: 'flex',
|
|
6
|
+
flexDirection: 'column',
|
|
7
|
+
height: '100%'
|
|
8
|
+
},
|
|
9
|
+
pageLayoutActions: {
|
|
10
|
+
paddingBottom: theme.spacing(2.5)
|
|
11
|
+
},
|
|
12
|
+
pageLayoutBody: {
|
|
13
|
+
'&[data-has-background="true"]': {
|
|
14
|
+
backgroundColor: theme.palette.layout.body.background
|
|
15
|
+
},
|
|
16
|
+
padding: theme.spacing(3, 4, 5)
|
|
17
|
+
},
|
|
18
|
+
pageLayoutHeader: {
|
|
19
|
+
'[data-variant="fixed-header"] &': {
|
|
20
|
+
backgroundColor: theme.palette.layout.header.background,
|
|
21
|
+
borderBottom: `1px solid ${theme.palette.layout.header.border}`,
|
|
22
|
+
padding: theme.spacing(5, 4, 2),
|
|
23
|
+
position: 'sticky',
|
|
24
|
+
top: 0,
|
|
25
|
+
zIndex: `calc(${theme.zIndex.mobileStepper} - 100)`
|
|
26
|
+
},
|
|
27
|
+
|
|
28
|
+
padding: theme.spacing(5, 4, 0)
|
|
29
|
+
}
|
|
30
|
+
}));
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
import { ReactElement, ReactNode } from 'react';
|
|
2
|
+
|
|
3
|
+
import { useStyles } from './PageLayout.styles';
|
|
4
|
+
|
|
5
|
+
type PageLayoutProps = {
|
|
6
|
+
children: Array<ReactNode> | ReactNode;
|
|
7
|
+
variant?: 'default' | 'fixed-header';
|
|
8
|
+
};
|
|
9
|
+
|
|
10
|
+
export const PageLayout = ({
|
|
11
|
+
children,
|
|
12
|
+
variant = 'default'
|
|
13
|
+
}: PageLayoutProps): ReactElement => {
|
|
14
|
+
const { classes } = useStyles();
|
|
15
|
+
|
|
16
|
+
return (
|
|
17
|
+
<section className={classes.pageLayout} data-variant={variant}>
|
|
18
|
+
{children}
|
|
19
|
+
</section>
|
|
20
|
+
);
|
|
21
|
+
};
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import { ReactElement, ReactNode } from 'react';
|
|
2
|
+
|
|
3
|
+
import { useStyles } from './PageLayout.styles';
|
|
4
|
+
|
|
5
|
+
type PageLayoutActionsProps = {
|
|
6
|
+
children: Array<ReactNode> | ReactNode;
|
|
7
|
+
};
|
|
8
|
+
|
|
9
|
+
export const PageLayoutActions = ({
|
|
10
|
+
children
|
|
11
|
+
}: PageLayoutActionsProps): ReactElement => {
|
|
12
|
+
const { classes } = useStyles();
|
|
13
|
+
|
|
14
|
+
return <section className={classes.pageLayoutActions}>{children}</section>;
|
|
15
|
+
};
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
import { ReactElement, ReactNode } from 'react';
|
|
2
|
+
|
|
3
|
+
import { useStyles } from './PageLayout.styles';
|
|
4
|
+
|
|
5
|
+
type PageLayoutBodyProps = {
|
|
6
|
+
children: Array<ReactNode> | ReactNode;
|
|
7
|
+
hasBackground?: boolean;
|
|
8
|
+
};
|
|
9
|
+
|
|
10
|
+
export const PageLayoutBody = ({
|
|
11
|
+
children,
|
|
12
|
+
hasBackground = false
|
|
13
|
+
}: PageLayoutBodyProps): ReactElement => {
|
|
14
|
+
const { classes } = useStyles();
|
|
15
|
+
|
|
16
|
+
return (
|
|
17
|
+
<section
|
|
18
|
+
className={classes.pageLayoutBody}
|
|
19
|
+
data-has-background={hasBackground}
|
|
20
|
+
>
|
|
21
|
+
{children}
|
|
22
|
+
</section>
|
|
23
|
+
);
|
|
24
|
+
};
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import { ReactNode } from 'react';
|
|
2
|
+
|
|
3
|
+
import { useStyles } from './PageLayout.styles';
|
|
4
|
+
|
|
5
|
+
type PageLayoutHeaderProps = {
|
|
6
|
+
children: Array<ReactNode> | ReactNode;
|
|
7
|
+
};
|
|
8
|
+
|
|
9
|
+
export const PageLayoutHeader = ({
|
|
10
|
+
children
|
|
11
|
+
}: PageLayoutHeaderProps): JSX.Element => {
|
|
12
|
+
const { classes } = useStyles();
|
|
13
|
+
|
|
14
|
+
return <header className={classes.pageLayoutHeader}>{children}</header>;
|
|
15
|
+
};
|
|
@@ -0,0 +1,10 @@
|
|
|
1
|
+
import { PageLayout as PageLayoutRoot } from './PageLayout';
|
|
2
|
+
import { PageLayoutHeader } from './PageLayoutHeader';
|
|
3
|
+
import { PageLayoutBody } from './PageLayoutBody';
|
|
4
|
+
import { PageLayoutActions } from './PageLayoutActions';
|
|
5
|
+
|
|
6
|
+
export const PageLayout = Object.assign(PageLayoutRoot, {
|
|
7
|
+
Actions: PageLayoutActions,
|
|
8
|
+
Body: PageLayoutBody,
|
|
9
|
+
Header: PageLayoutHeader
|
|
10
|
+
});
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export * from './PageLayout';
|
|
File without changes
|