Merge pull request #11344 from leschaller1/controls
[storybook] Enable controls in Storybook
This commit is contained in:
@@ -0,0 +1,5 @@
|
||||
---
|
||||
'@backstage/core-components': patch
|
||||
---
|
||||
|
||||
Add controls to Storybook stories
|
||||
@@ -15,29 +15,51 @@
|
||||
*/
|
||||
|
||||
import React from 'react';
|
||||
import Chip from '@material-ui/core/Chip';
|
||||
import AddIcon from '@material-ui/icons/Add';
|
||||
import WarningIcon from '@material-ui/icons/Warning';
|
||||
import EditIcon from '@material-ui/icons/Edit';
|
||||
import Chip, { ChipProps } from '@material-ui/core/Chip';
|
||||
|
||||
const icons = {
|
||||
AddIcon: <AddIcon />,
|
||||
WarningIcon: <WarningIcon />,
|
||||
EditIcon: <EditIcon />,
|
||||
None: null,
|
||||
};
|
||||
|
||||
const defaultArgs = {
|
||||
label: 'Label',
|
||||
size: 'medium',
|
||||
variant: 'default',
|
||||
icon: 'None',
|
||||
};
|
||||
|
||||
export default {
|
||||
title: 'Data Display/Chip',
|
||||
component: Chip,
|
||||
argTypes: {
|
||||
size: {
|
||||
options: ['small', 'medium'],
|
||||
control: { type: 'select' },
|
||||
},
|
||||
variant: {
|
||||
options: ['default', 'outlined'],
|
||||
control: { type: 'select' },
|
||||
},
|
||||
icon: {
|
||||
options: Object.keys(icons),
|
||||
mapping: icons,
|
||||
control: {
|
||||
type: 'select',
|
||||
},
|
||||
},
|
||||
},
|
||||
};
|
||||
|
||||
export const Default = () => <Chip label="Default" />;
|
||||
export const Default = (args: ChipProps) => <Chip {...args} />;
|
||||
Default.args = defaultArgs;
|
||||
|
||||
export const LargeDeletable = () => (
|
||||
<Chip label="Large deletable" size="medium" onDelete={() => ({})} />
|
||||
export const Deleteable = (args: ChipProps) => (
|
||||
<Chip {...args} onDelete={() => ({})} />
|
||||
);
|
||||
|
||||
export const LargeNotDeletable = () => (
|
||||
<Chip label="Large not deletable" size="medium" />
|
||||
);
|
||||
|
||||
export const SmallDeletable = () => (
|
||||
<Chip label="Small deletable" size="small" onDelete={() => ({})} />
|
||||
);
|
||||
|
||||
export const SmallNotDeletable = () => (
|
||||
<Chip label="Small not deletable" size="small" />
|
||||
);
|
||||
|
||||
export const Outline = () => <Chip label="Outline" variant="outlined" />;
|
||||
Deleteable.args = defaultArgs;
|
||||
|
||||
+18
-56
@@ -15,7 +15,7 @@
|
||||
*/
|
||||
|
||||
import React from 'react';
|
||||
import { DismissableBanner } from './DismissableBanner';
|
||||
import { DismissableBanner, Props } from './DismissableBanner';
|
||||
import Typography from '@material-ui/core/Typography';
|
||||
import { WebStorage } from '@backstage/core-app-api';
|
||||
import {
|
||||
@@ -29,6 +29,12 @@ import { Link } from '../Link';
|
||||
export default {
|
||||
title: 'Feedback/DismissableBanner',
|
||||
component: DismissableBanner,
|
||||
argTypes: {
|
||||
variant: {
|
||||
options: ['info', 'error', 'warning'],
|
||||
control: { type: 'select' },
|
||||
},
|
||||
},
|
||||
};
|
||||
|
||||
let errorApi: ErrorApi;
|
||||
@@ -39,47 +45,27 @@ const createWebStorage = (): StorageApi => {
|
||||
};
|
||||
|
||||
const apis = [[storageApiRef, createWebStorage()] as const];
|
||||
const defaultArgs = {
|
||||
message: 'This is a dismissable banner',
|
||||
variant: 'info',
|
||||
fixed: false,
|
||||
};
|
||||
|
||||
export const Default = () => (
|
||||
export const Default = (args: Props) => (
|
||||
<div style={containerStyle}>
|
||||
<TestApiProvider apis={apis}>
|
||||
<DismissableBanner
|
||||
message="This is a dismissable banner"
|
||||
variant="info"
|
||||
id="default_dismissable"
|
||||
/>
|
||||
<DismissableBanner {...args} id="default_dismissable" />
|
||||
</TestApiProvider>
|
||||
</div>
|
||||
);
|
||||
|
||||
export const Error = () => (
|
||||
<div style={containerStyle}>
|
||||
<TestApiProvider apis={apis}>
|
||||
<DismissableBanner
|
||||
message="This is a dismissable banner with an error message"
|
||||
variant="error"
|
||||
id="error_dismissable"
|
||||
/>
|
||||
</TestApiProvider>
|
||||
</div>
|
||||
);
|
||||
Default.args = defaultArgs;
|
||||
|
||||
export const EmojisIncluded = () => (
|
||||
<div style={containerStyle}>
|
||||
<TestApiProvider apis={apis}>
|
||||
<DismissableBanner
|
||||
message="This is a dismissable banner with emojis: 🚀 💚 😆 "
|
||||
variant="info"
|
||||
id="emojis_dismissable"
|
||||
/>
|
||||
</TestApiProvider>
|
||||
</div>
|
||||
);
|
||||
|
||||
export const WithLink = () => (
|
||||
export const WithLink = (args: Props) => (
|
||||
<div style={containerStyle}>
|
||||
<TestApiProvider apis={apis}>
|
||||
<DismissableBanner
|
||||
{...args}
|
||||
message={
|
||||
<Typography>
|
||||
This is a dismissable banner with a link:{' '}
|
||||
@@ -88,34 +74,10 @@ export const WithLink = () => (
|
||||
</Link>
|
||||
</Typography>
|
||||
}
|
||||
variant="info"
|
||||
id="linked_dismissable"
|
||||
/>
|
||||
</TestApiProvider>
|
||||
</div>
|
||||
);
|
||||
|
||||
export const Fixed = () => (
|
||||
<div style={containerStyle}>
|
||||
<TestApiProvider apis={apis}>
|
||||
<DismissableBanner
|
||||
message="This is a dismissable banner with a fixed position fixed at the bottom of the page"
|
||||
variant="info"
|
||||
id="fixed_dismissable"
|
||||
fixed
|
||||
/>
|
||||
</TestApiProvider>
|
||||
</div>
|
||||
);
|
||||
|
||||
export const Warning = () => (
|
||||
<div style={containerStyle}>
|
||||
<TestApiProvider apis={apis}>
|
||||
<DismissableBanner
|
||||
message="This is a dismissable banner with a warning message"
|
||||
variant="warning"
|
||||
id="warning_dismissable"
|
||||
/>
|
||||
</TestApiProvider>
|
||||
</div>
|
||||
);
|
||||
WithLink.args = defaultArgs;
|
||||
|
||||
@@ -87,7 +87,7 @@ const useStyles = makeStyles(
|
||||
{ name: 'BackstageDismissableBanner' },
|
||||
);
|
||||
|
||||
type Props = {
|
||||
export type Props = {
|
||||
variant: 'info' | 'error' | 'warning';
|
||||
message: ReactNode;
|
||||
id: string;
|
||||
|
||||
@@ -16,7 +16,7 @@
|
||||
|
||||
import TextField from '@material-ui/core/TextField';
|
||||
import React, { useState } from 'react';
|
||||
import { SimpleStepper } from './SimpleStepper';
|
||||
import { SimpleStepper, StepperProps } from './SimpleStepper';
|
||||
import { SimpleStepperStep } from './SimpleStepperStep';
|
||||
|
||||
export default {
|
||||
@@ -24,8 +24,13 @@ export default {
|
||||
component: SimpleStepper,
|
||||
};
|
||||
|
||||
export const Default = () => (
|
||||
<SimpleStepper>
|
||||
const defaultArgs = {
|
||||
elevated: false,
|
||||
activeStep: 0,
|
||||
};
|
||||
|
||||
export const Default = (args: StepperProps) => (
|
||||
<SimpleStepper {...args}>
|
||||
<SimpleStepperStep title="Step 1">
|
||||
<div>This is the content for step 1</div>
|
||||
</SimpleStepperStep>
|
||||
@@ -38,11 +43,13 @@ export const Default = () => (
|
||||
</SimpleStepper>
|
||||
);
|
||||
|
||||
export const ConditionalButtons = () => {
|
||||
Default.args = defaultArgs;
|
||||
|
||||
export const ConditionalButtons = (args: StepperProps) => {
|
||||
const [required, setRequired] = useState(false);
|
||||
|
||||
return (
|
||||
<SimpleStepper>
|
||||
<SimpleStepper {...args}>
|
||||
<SimpleStepperStep
|
||||
title="Step 1 with required field"
|
||||
actions={{
|
||||
@@ -65,9 +72,11 @@ export const ConditionalButtons = () => {
|
||||
);
|
||||
};
|
||||
|
||||
export const CompletionStep = () => {
|
||||
ConditionalButtons.args = defaultArgs;
|
||||
|
||||
export const CompletionStep = (args: StepperProps) => {
|
||||
return (
|
||||
<SimpleStepper>
|
||||
<SimpleStepper {...args}>
|
||||
<SimpleStepperStep title="Step 1">
|
||||
<div>This is the content for step 1</div>
|
||||
</SimpleStepperStep>
|
||||
@@ -80,3 +89,5 @@ export const CompletionStep = () => {
|
||||
</SimpleStepper>
|
||||
);
|
||||
};
|
||||
|
||||
CompletionStep.args = defaultArgs;
|
||||
|
||||
@@ -21,6 +21,22 @@ import { Header } from './Header';
|
||||
export default {
|
||||
title: 'Layout/Header',
|
||||
component: Header,
|
||||
argTypes: {
|
||||
type: {
|
||||
options: [
|
||||
'home',
|
||||
'tool',
|
||||
'service',
|
||||
'website',
|
||||
'library',
|
||||
'app',
|
||||
'apis',
|
||||
'documentation',
|
||||
'other',
|
||||
],
|
||||
control: { type: 'select' },
|
||||
},
|
||||
},
|
||||
};
|
||||
|
||||
const labels = (
|
||||
@@ -31,80 +47,21 @@ const labels = (
|
||||
</>
|
||||
);
|
||||
|
||||
export const Home = () => (
|
||||
<Page themeId="home">
|
||||
<Header title="Start/Home Page" type="home">
|
||||
{labels}
|
||||
</Header>
|
||||
</Page>
|
||||
);
|
||||
export const Default = (args: {
|
||||
type: string;
|
||||
title: string;
|
||||
subtitle: string;
|
||||
}) => {
|
||||
const { type } = args;
|
||||
return (
|
||||
<Page themeId={type}>
|
||||
<Header {...args}>{labels}</Header>
|
||||
</Page>
|
||||
);
|
||||
};
|
||||
|
||||
export const HomeWithSubtitle = () => (
|
||||
<Header title="Start/Home Page" subtitle="This is a subtitle">
|
||||
{labels}
|
||||
</Header>
|
||||
);
|
||||
|
||||
export const Apis = () => (
|
||||
<Page themeId="apis">
|
||||
<Header title="API catalogue" type="tool">
|
||||
{labels}
|
||||
</Header>
|
||||
</Page>
|
||||
);
|
||||
|
||||
export const Tool = () => (
|
||||
<Page themeId="tool">
|
||||
<Header title="Stand-alone tool" type="tool">
|
||||
{labels}
|
||||
</Header>
|
||||
</Page>
|
||||
);
|
||||
|
||||
export const Service = () => (
|
||||
<Page themeId="service">
|
||||
<Header title="Service component page" type="service">
|
||||
{labels}
|
||||
</Header>
|
||||
</Page>
|
||||
);
|
||||
|
||||
export const Website = () => (
|
||||
<Page themeId="website">
|
||||
<Header title="Website component page" type="website">
|
||||
{labels}
|
||||
</Header>
|
||||
</Page>
|
||||
);
|
||||
|
||||
export const Library = () => (
|
||||
<Page themeId="library">
|
||||
<Header title="Library component page" type="library">
|
||||
{labels}
|
||||
</Header>
|
||||
</Page>
|
||||
);
|
||||
|
||||
export const App = () => (
|
||||
<Page themeId="app">
|
||||
<Header title="App component page" type="app">
|
||||
{labels}
|
||||
</Header>
|
||||
</Page>
|
||||
);
|
||||
|
||||
export const Documentation = () => (
|
||||
<Page themeId="documentation">
|
||||
<Header title="Documentation component page" type="documentation">
|
||||
{labels}
|
||||
</Header>
|
||||
</Page>
|
||||
);
|
||||
|
||||
export const Other = () => (
|
||||
<Page themeId="other">
|
||||
<Header title="Other/generic component page" type="other">
|
||||
{labels}
|
||||
</Header>
|
||||
</Page>
|
||||
);
|
||||
Default.args = {
|
||||
type: 'home',
|
||||
title: 'This is a title',
|
||||
subtitle: 'This is a subtitle',
|
||||
};
|
||||
|
||||
@@ -18,9 +18,7 @@ import Grid from '@material-ui/core/Grid';
|
||||
import Typography from '@material-ui/core/Typography';
|
||||
import React, { PropsWithChildren } from 'react';
|
||||
import { MemoryRouter } from 'react-router';
|
||||
import { InfoCard } from './InfoCard';
|
||||
|
||||
const linkInfo = { title: 'Go to XYZ Location', link: '#' };
|
||||
import { InfoCard, Props } from './InfoCard';
|
||||
|
||||
export default {
|
||||
title: 'Layout/Information Card',
|
||||
@@ -38,6 +36,11 @@ const text = (
|
||||
</Typography>
|
||||
);
|
||||
|
||||
const defaultProps = {
|
||||
title: 'Information Card',
|
||||
subheader: 'Subheader',
|
||||
};
|
||||
|
||||
const Wrapper = ({ children }: PropsWithChildren<{}>) => (
|
||||
<MemoryRouter>
|
||||
<Grid container spacing={4}>
|
||||
@@ -48,24 +51,21 @@ const Wrapper = ({ children }: PropsWithChildren<{}>) => (
|
||||
</MemoryRouter>
|
||||
);
|
||||
|
||||
export const Default = () => (
|
||||
export const Default = (args: Props) => (
|
||||
<Wrapper>
|
||||
<InfoCard title="Information Card">{text}</InfoCard>
|
||||
<InfoCard {...args}>{text}</InfoCard>
|
||||
</Wrapper>
|
||||
);
|
||||
|
||||
export const Subhead = () => (
|
||||
Default.args = defaultProps;
|
||||
|
||||
export const LinkInFooter = (args: Props) => (
|
||||
<Wrapper>
|
||||
<InfoCard title="Information Card" subheader="Subheader">
|
||||
{text}
|
||||
</InfoCard>
|
||||
<InfoCard {...args}>{text}</InfoCard>
|
||||
</Wrapper>
|
||||
);
|
||||
|
||||
export const LinkInFooter = () => (
|
||||
<Wrapper>
|
||||
<InfoCard title="Information Card" deepLink={linkInfo}>
|
||||
{text}
|
||||
</InfoCard>
|
||||
</Wrapper>
|
||||
);
|
||||
LinkInFooter.args = {
|
||||
...defaultProps,
|
||||
deepLink: { title: 'Go to XYZ Location', link: '#' },
|
||||
};
|
||||
|
||||
@@ -125,7 +125,7 @@ export type InfoCardVariants = 'flex' | 'fullHeight' | 'gridItem';
|
||||
*
|
||||
* `<InfoCard variant="gridItem">...</InfoCard>`
|
||||
*/
|
||||
type Props = {
|
||||
export type Props = {
|
||||
title?: ReactNode;
|
||||
subheader?: ReactNode;
|
||||
divider?: boolean;
|
||||
|
||||
@@ -32,6 +32,7 @@ module.exports = ({ args }) => {
|
||||
return {
|
||||
stories,
|
||||
addons: [
|
||||
'@storybook/addon-controls',
|
||||
'@storybook/addon-a11y',
|
||||
'@storybook/addon-actions',
|
||||
'@storybook/addon-links',
|
||||
|
||||
@@ -9,14 +9,15 @@
|
||||
},
|
||||
"dependencies": {
|
||||
"@sucrase/webpack-loader": "^2.0.0",
|
||||
"sucrase": "^3.21.0",
|
||||
"react": "^17.0.2",
|
||||
"react-dom": "^17.0.2",
|
||||
"react-hot-loader": "^4.13.0",
|
||||
"react-dom": "^17.0.2"
|
||||
"sucrase": "^3.21.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@storybook/addon-a11y": "^6.4.21",
|
||||
"@storybook/addon-actions": "^6.4.21",
|
||||
"@storybook/addon-controls": "^6.4.22",
|
||||
"@storybook/addon-links": "^6.4.21",
|
||||
"@storybook/addon-storysource": "^6.4.21",
|
||||
"@storybook/addons": "^6.4.21",
|
||||
@@ -24,9 +25,9 @@
|
||||
"storybook-dark-mode": "^1.0.9"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"@backstage/theme": "link:../packages/theme",
|
||||
"@backstage/test-utils": "link:../packages/test-utils",
|
||||
"@backstage/core-app-api": "link:../packages/core-app-api",
|
||||
"@backstage/core-plugin-api": "link:../packages/core-plugin-api"
|
||||
"@backstage/core-plugin-api": "link:../packages/core-plugin-api",
|
||||
"@backstage/test-utils": "link:../packages/test-utils",
|
||||
"@backstage/theme": "link:../packages/theme"
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1381,6 +1381,24 @@
|
||||
util-deprecate "^1.0.2"
|
||||
uuid-browser "^3.1.0"
|
||||
|
||||
"@storybook/addon-controls@^6.4.22":
|
||||
version "6.4.22"
|
||||
resolved "https://registry.npmjs.org/@storybook/addon-controls/-/addon-controls-6.4.22.tgz#42c7f426eb7ba6d335e8e14369d6d13401878665"
|
||||
integrity sha512-f/M/W+7UTEUnr/L6scBMvksq+ZA8GTfh3bomE5FtWyOyaFppq9k8daKAvdYNlzXAOrUUsoZVJDgpb20Z2VBiSQ==
|
||||
dependencies:
|
||||
"@storybook/addons" "6.4.22"
|
||||
"@storybook/api" "6.4.22"
|
||||
"@storybook/client-logger" "6.4.22"
|
||||
"@storybook/components" "6.4.22"
|
||||
"@storybook/core-common" "6.4.22"
|
||||
"@storybook/csf" "0.0.2--canary.87bc651.0"
|
||||
"@storybook/node-logger" "6.4.22"
|
||||
"@storybook/store" "6.4.22"
|
||||
"@storybook/theming" "6.4.22"
|
||||
core-js "^3.8.2"
|
||||
lodash "^4.17.21"
|
||||
ts-dedent "^2.0.0"
|
||||
|
||||
"@storybook/addon-links@^6.4.21":
|
||||
version "6.4.22"
|
||||
resolved "https://registry.npmjs.org/@storybook/addon-links/-/addon-links-6.4.22.tgz#c0ed9e9ef6505cf1562e1476bbc5064c82dadbe2"
|
||||
|
||||
Reference in New Issue
Block a user