-
Notifications
You must be signed in to change notification settings - Fork 8
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #22 from securityscorecard/ajkl2533@implement-full…
…screen-modal feat(FullscreenModal): add component
- Loading branch information
Showing
36 changed files
with
812 additions
and
4 deletions.
There are no files selected for viewing
Binary file added
BIN
+47.2 KB
...apshots/expected/components_FullscreenModal_Single Column (layout single-6).png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added
BIN
+42.8 KB
...apshots/expected/components_FullscreenModal_Single Column (layout single-8).png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added
BIN
+53.6 KB
...ed/components_FullscreenModal_Two Columns with sidebar (layout sidebar-4-6).png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added
BIN
+49.8 KB
...ed/components_FullscreenModal_Two Columns with sidebar (layout sidebar-4-8).png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added
BIN
+91.7 KB
...ybook/image-snapshots/expected/components_FullscreenModal_With Long Content.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,85 @@ | ||
import React, { useRef } from 'react'; | ||
import PropTypes from 'prop-types'; | ||
import styled from 'styled-components'; | ||
|
||
import { getColor, pxToRem } from '../../../utils/helpers'; | ||
import { FlexContainer } from '../../FlexContainer'; | ||
import { ScrollToTopButton } from '../ScrollToTopButton'; | ||
import { useStickyFooter } from '../hooks/useStickyFooter'; | ||
import { Col, Container, Row } from '../../layout'; | ||
import { FooterProps } from './Footer.types'; | ||
|
||
const BaseStickyFooter = styled.footer` | ||
position: fixed; | ||
bottom: 0; | ||
left: 0; | ||
width: 100%; | ||
padding: ${pxToRem(10, 0)}; | ||
background-color: ${getColor('graphite5H')}; | ||
border-top: 1px solid ${getColor('graphiteHB')}; | ||
`; | ||
const BaseFooter = styled.footer` | ||
border-top: 1px solid ${getColor('graphiteHB')}; | ||
padding-top: ${pxToRem(24)}; | ||
margin-top: ${pxToRem(40)}; | ||
`; | ||
|
||
const Footer: React.FC<FooterProps> = ({ | ||
children, | ||
width, | ||
offset, | ||
modalRef, | ||
scrollToTopButtonLabel, | ||
}) => { | ||
const modalFooterRef = useRef(null); | ||
const { isFixed, shouldShowScrollToTopButton } = useStickyFooter( | ||
modalRef, | ||
modalFooterRef, | ||
); | ||
|
||
const scrollToTop = () => { | ||
modalRef.current.scrollTo(0, 0); | ||
}; | ||
|
||
return ( | ||
<> | ||
{isFixed && ( | ||
<BaseStickyFooter as="div"> | ||
<Container> | ||
<Row> | ||
<Col cols={width} offset={offset}> | ||
{children} | ||
</Col> | ||
</Row> | ||
</Container> | ||
</BaseStickyFooter> | ||
)} | ||
<BaseFooter ref={modalFooterRef}> | ||
{children} | ||
{shouldShowScrollToTopButton && ( | ||
<FlexContainer | ||
alignItems="center" | ||
justifyContent="center" | ||
margin={{ vertical: 1.2 }} | ||
> | ||
<ScrollToTopButton | ||
label={scrollToTopButtonLabel} | ||
onClick={scrollToTop} | ||
/> | ||
</FlexContainer> | ||
)} | ||
</BaseFooter> | ||
</> | ||
); | ||
}; | ||
|
||
Footer.propTypes = { | ||
width: PropTypes.number.isRequired, | ||
offset: PropTypes.number.isRequired, | ||
modalRef: PropTypes.exact({ | ||
current: PropTypes.instanceOf(HTMLElement), | ||
}).isRequired, | ||
scrollToTopButtonLabel: PropTypes.string, | ||
}; | ||
|
||
export default Footer; |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,6 @@ | ||
export interface FooterProps { | ||
width: number; | ||
offset: number; | ||
modalRef: React.MutableRefObject<HTMLElement>; | ||
scrollToTopButtonLabel: string; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,12 @@ | ||
export const FullscreenModalSizes = { | ||
lg: 'lg', | ||
md: 'md', | ||
sm: 'sm', | ||
} as const; | ||
|
||
export const FullscreenModalLayouts = { | ||
single6: 'single-6', | ||
single8: 'single-8', | ||
sidebar46: 'sidebar-4-6', | ||
sidebar48: 'sidebar-4-8', | ||
} as const; |
173 changes: 173 additions & 0 deletions
173
src/components/FullscreenModal/FullscreenModal.stories.tsx
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,173 @@ | ||
import React from 'react'; | ||
import { Meta, Story } from '@storybook/react/types-6-0'; | ||
import { action } from '@storybook/addon-actions'; | ||
|
||
import { FlexContainer } from '../FlexContainer'; | ||
import { Button } from '../Button'; | ||
import { ButtonVariants } from '../Button/Button.enums'; | ||
import { Link, Paragraph } from '../typography'; | ||
import FullscreenModal from './FullscreenModal'; | ||
import { FullscreenModalLayouts } from './FullscreenModal.enums'; | ||
|
||
export default { | ||
title: 'components/FullscreenModal', | ||
component: FullscreenModal, | ||
parameters: { | ||
docs: { | ||
inlineStories: false, | ||
iframeHeight: 500, | ||
source: { type: 'code' }, | ||
}, | ||
screenshot: { | ||
viewport: { | ||
width: 1280, | ||
height: 720, | ||
}, | ||
}, | ||
}, | ||
} as Meta; | ||
|
||
const header = 'Invite vendor to SecurityScorecard'; | ||
const Content = () => ( | ||
<Paragraph> | ||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Nam volutpat velit | ||
vel urna molestie, vitae sodales sem hendrerit. Nunc risus nibh, rhoncus ut | ||
massa id, eleifend lacinia orci. Morbi porta, urna ut tincidunt efficitur, | ||
lorem nulla facilisis orci, sit amet rutrum augue elit ut elit. Interdum et | ||
malesuada fames ac ante ipsum primis in faucibus. Suspendisse consectetur | ||
lectus finibus diam posuere, elementum vehicula sapien placerat. In sed | ||
ornare ex, quis lacinia lorem. Nunc rhoncus lorem a laoreet posuere. Nam | ||
cursus lorem vestibulum semper pulvinar. Nunc tempus ornare urna, sit amet | ||
varius nisl fringilla et. Fusce volutpat urna et aliquet dictum. In nec | ||
cursus elit. Vivamus congue ac elit placerat suscipit. Nulla facilisi. | ||
Praesent fringilla, quam sit amet blandit tempor, risus leo bibendum leo, ut | ||
aliquet metus leo non neque. Etiam in ante arcu. | ||
</Paragraph> | ||
); | ||
const LongContent = () => ( | ||
<> | ||
<Content /> | ||
<Content /> | ||
<Content /> | ||
<Content /> | ||
<Content /> | ||
<Content /> | ||
</> | ||
); | ||
const Footer = () => ( | ||
<FlexContainer justifyContent="space-between"> | ||
<Button variant={ButtonVariants.outline}>Email me preview</Button> | ||
<FlexContainer> | ||
<Button margin={{ right: 0.5 }} variant={ButtonVariants.outline}> | ||
Cancel | ||
</Button> | ||
<Button variant={ButtonVariants.solid}>Submit</Button> | ||
</FlexContainer> | ||
</FlexContainer> | ||
); | ||
const Sidebar = () => ( | ||
<nav> | ||
<ul> | ||
<li> | ||
<Link href="#">Sidebar link 1</Link> | ||
</li> | ||
<li> | ||
<Link href="#">Sidebar link 2</Link> | ||
</li> | ||
<li> | ||
<Link href="#">Sidebar link 3</Link> | ||
</li> | ||
<li> | ||
<Link href="#">Sidebar link 4</Link> | ||
</li> | ||
</ul> | ||
</nav> | ||
); | ||
|
||
export const SingleColumn6: Story = () => ( | ||
<FullscreenModal | ||
content={Content()} | ||
footer={Footer()} | ||
header={header} | ||
layout={FullscreenModalLayouts.single6} | ||
onClose={action('close modal')} | ||
/> | ||
); | ||
SingleColumn6.storyName = 'Single Column (layout: single-6)'; | ||
SingleColumn6.argTypes = { | ||
header: { | ||
control: { disable: true }, | ||
description: 'Content of the header wrapper', | ||
table: { type: { summary: 'React.node' } }, | ||
}, | ||
content: { | ||
control: { disable: true }, | ||
description: 'Content of the content wrapper', | ||
table: { type: { summary: 'React.node' } }, | ||
}, | ||
footer: { | ||
control: { disable: true }, | ||
description: 'Content of the footer wrapper', | ||
table: { type: { summary: 'React.node' } }, | ||
}, | ||
sidebar: { | ||
control: { disable: true }, | ||
description: 'Content of the sidebar wrapper', | ||
table: { type: { summary: 'React.node' } }, | ||
}, | ||
scrollToTopButtonLabel: { | ||
control: { disable: true }, | ||
description: 'Label of the scroll to top button', | ||
table: { defaultValue: { summary: '"Scroll to top"' } }, | ||
}, | ||
onClose: { | ||
control: { disable: true }, | ||
description: 'Modal window close handler', | ||
}, | ||
}; | ||
|
||
export const SingleColumn8: Story = () => ( | ||
<FullscreenModal | ||
content={Content()} | ||
footer={Footer()} | ||
header={header} | ||
layout={FullscreenModalLayouts.single8} | ||
onClose={action('close modal')} | ||
/> | ||
); | ||
|
||
SingleColumn8.storyName = 'Single Column (layout: single-8)'; | ||
|
||
export const Sidebar4Column6: Story = () => ( | ||
<FullscreenModal | ||
content={Content()} | ||
footer={Footer()} | ||
header={header} | ||
layout={FullscreenModalLayouts.sidebar46} | ||
sidebar={Sidebar()} | ||
onClose={action('close modal')} | ||
/> | ||
); | ||
Sidebar4Column6.storyName = 'Two Columns with sidebar (layout: sidebar-4-6)'; | ||
|
||
export const Sidebar4Column8: Story = () => ( | ||
<FullscreenModal | ||
content={Content()} | ||
footer={Footer()} | ||
header={header} | ||
layout={FullscreenModalLayouts.sidebar48} | ||
sidebar={Sidebar()} | ||
onClose={action('close modal')} | ||
/> | ||
); | ||
Sidebar4Column8.storyName = 'Two Columns with sidebar (layout: sidebar-4-8)'; | ||
|
||
export const WithLongContent: Story = () => ( | ||
<FullscreenModal | ||
content={LongContent()} | ||
footer={Footer()} | ||
header={header} | ||
layout={FullscreenModalLayouts.single6} | ||
onClose={action('close modal')} | ||
/> | ||
); |
Oops, something went wrong.