Skip to content

Commit

Permalink
frontend: Adding Vertical Orientation to Stepper and adjusting Wizard…
Browse files Browse the repository at this point in the history
… to account for it (#2932)
  • Loading branch information
jdslaugh authored Feb 13, 2024
1 parent f2c0d02 commit 97de041
Show file tree
Hide file tree
Showing 12 changed files with 1,134 additions and 806 deletions.
163 changes: 92 additions & 71 deletions frontend/packages/core/src/stepper.tsx
Original file line number Diff line number Diff line change
@@ -1,7 +1,10 @@
import * as React from "react";
import styled from "@emotion/styled";
import MuiCheckIcon from "@mui/icons-material/Check";
import PriorityHighIcon from "@mui/icons-material/PriorityHigh";
import type {
Orientation as StepperOrientation,
StepperProps as MuiStepperProps,
} from "@mui/material";
import {
alpha,
Step as MuiStep,
Expand All @@ -12,78 +15,91 @@ import {
useTheme,
} from "@mui/material";

const StepContainer = styled.div(({ theme }: { theme: Theme }) => ({
margin: "0px 2px 30px 2px",
".MuiStepLabel-label": {
fontWeight: 500,
fontSize: "14px",
color: alpha(theme.palette.secondary[900], 0.38),
},
".MuiStepLabel-label.Mui-active": {
color: theme.palette.secondary[900],
},
".MuiStepLabel-label.Mui-completed": {
color: alpha(theme.palette.secondary[900], 0.38),
},
".MuiStepper-root": {
background: "transparent",
padding: "0",
},
".MuiGrid-container": {
padding: "16px 0",
},
".MuiStepLabel-labelContainer": {
width: "unset",
},
".MuiStepConnector-alternativeLabel": {
top: "10px",
right: "calc(50% + 8px)",
left: "calc(-50% + 8px)",
zIndex: 10,
},
".MuiStepLabel-iconContainer": {
zIndex: 20,
},
".MuiStep-root": {
padding: "0",
},
".MuiStep-root:first-of-type": {
".MuiStepLabel-root": {
alignItems: "flex-start",
import styled from "./styled";

const StepContainer = styled("div")<{ $orientation: StepperOrientation }>(
{
".MuiStepper-root": {
background: "transparent",
padding: "0",
},
},
".MuiStep-root:nth-of-type(2)": {
".MuiStepConnector-alternativeLabel": {
left: "calc(-100%)",
".MuiGrid-container": {
padding: "16px 0",
},
},
".MuiStep-root:last-of-type": {
".MuiStepLabel-root": {
alignItems: "flex-end",
".MuiStepLabel-labelContainer": {
width: "unset",
},

".MuiStepConnector-alternativeLabel": {
right: "0px",
top: "10px",
right: "calc(50% + 8px)",
left: "calc(-50% + 8px)",
zIndex: 10,
},
".MuiStepLabel-iconContainer": {
zIndex: 20,
},
".MuiStep-root": {
padding: "0",
},
".MuiStep-root:nth-of-type(2)": {
".MuiStepConnector-alternativeLabel": {
left: "calc(-100%)",
},
},
".MuiStep-root:last-of-type": {
".MuiStepConnector-alternativeLabel": {
right: "0px",
},
},
},
props => ({ theme }: { theme: Theme }) => ({
".MuiStepLabel-label": {
fontWeight: 500,
fontSize: "14px",
color: alpha(theme.palette.secondary[900], 0.38),
},
".MuiStepLabel-label.Mui-active": {
color: theme.palette.secondary[900],
},
".MuiStepLabel-label.Mui-completed": {
color: alpha(theme.palette.secondary[900], 0.38),
},
".Mui-active .MuiStepConnector-line": {
backgroundColor: theme.palette.primary[600],
},
".Mui-completed .MuiStepConnector-line": {
backgroundColor: theme.palette.primary[600],
},
...(props.$orientation === "horizontal"
? {
margin: "0px 2px 30px 2px",
".MuiStep-root:first-of-type": {
".MuiStepLabel-root": {
alignItems: "flex-start",
},
},
".MuiStep-root:last-of-type": {
".MuiStepLabel-root": {
alignItems: "flex-end",
},
},
".MuiStepConnector-line": {
height: "5px",
border: 0,
backgroundColor: theme.palette.secondary[200],
borderRadius: "4px",
},
}
: {
margin: "0px 2px 8px 2px",
".MuiStepConnector-line": {
borderColor: theme.palette.secondary[300],
},
}),
})
);

".MuiStepConnector-line": {
height: "5px",
border: 0,
backgroundColor: theme.palette.secondary[200],
borderRadius: "4px",
},

".Mui-active .MuiStepConnector-line": {
backgroundColor: theme.palette.primary[600],
},

".Mui-completed .MuiStepConnector-line": {
backgroundColor: theme.palette.primary[600],
},
}));

const Circle = styled.div((props: { background: string; border: string }) => ({
const Circle = styled("div")((props: { background: string; border: string }) => ({
backgroundColor: props.background,
border: props.border,
boxSizing: "border-box",
Expand All @@ -93,7 +109,7 @@ const Circle = styled.div((props: { background: string; border: string }) => ({
top: "24px",
}));

const DefaultIcon = styled.div((props: { font: string }) => ({
const DefaultIcon = styled("div")((props: { font: string }) => ({
height: "100%",
width: "100%",
color: props.font,
Expand Down Expand Up @@ -166,14 +182,19 @@ export interface StepProps {

const Step: React.FC<StepProps> = ({ children }) => <>{children}</>;

export interface StepperProps {
export interface StepperProps extends Pick<MuiStepperProps, "orientation"> {
activeStep: number;
children?: React.ReactElement<StepProps>[] | React.ReactElement<StepProps>;
}

const Stepper = ({ activeStep, children }: StepperProps) => (
<StepContainer>
<MuiStepper activeStep={activeStep} connector={<MuiStepConnector />} alternativeLabel>
const Stepper = ({ activeStep, orientation = "horizontal", children }: StepperProps) => (
<StepContainer $orientation={orientation}>
<MuiStepper
activeStep={activeStep}
connector={<MuiStepConnector />}
alternativeLabel={orientation === "horizontal"}
orientation={orientation}
>
{React.Children.map(children, (step: any, idx: number) => {
const stepProps = {
index: idx + 1,
Expand Down
104 changes: 63 additions & 41 deletions frontend/packages/core/src/stories/stepper.stories.tsx
Original file line number Diff line number Diff line change
@@ -1,21 +1,31 @@
import * as React from "react";
import styled from "@emotion/styled";
import type { Meta } from "@storybook/react";

import { Button, ButtonGroup } from "../button";
import Grid from "../grid";
import type { StepperProps } from "../stepper";
import { Step, Stepper } from "../stepper";

const Text = styled.div({
textAlign: "center",
});
import { Typography } from "../typography";

export default {
title: "Core/Stepper",
component: Stepper,
argTypes: {
orientation: {
options: ["horizontal", "vertical"],
defaultValue: "horizontal",
control: {
type: "select",
},
},
},
} as Meta;

const PrimaryTemplate = ({ stepCount, activeStep }: StepperProps & { stepCount: number }) => {
const PrimaryTemplate = ({
stepCount,
activeStep,
orientation,
}: StepperProps & { stepCount: number }) => {
const [curStep, setCurStep] = React.useState(activeStep || 0);

const handleNext = () => {
Expand All @@ -32,31 +42,40 @@ const PrimaryTemplate = ({ stepCount, activeStep }: StepperProps & { stepCount:

return (
<>
<Stepper activeStep={curStep}>
{Array(stepCount)
.fill(null)
.map((_, index: number) => (
// eslint-disable-next-line react/no-array-index-key
<Step key={index} label={`Step ${index + 1}`} />
))}
</Stepper>
<div>
<Text>Step{curStep + 1} content</Text>

<Grid container direction={orientation === "horizontal" ? "column" : "row"}>
<Grid item xs={1}>
<Stepper activeStep={curStep} orientation={orientation}>
{Array(stepCount)
.fill(null)
.map((_, index: number) => (
// eslint-disable-next-line react/no-array-index-key
<Step key={index} label={`Step ${index + 1}`} />
))}
</Stepper>
</Grid>
<Grid container item xs={11} alignContent="center" justifyContent="center">
<Typography variant="body3">Step{curStep + 1} content</Typography>
</Grid>
</Grid>
<ButtonGroup justify="flex-start">
{curStep === stepCount - 1 ? (
<Button onClick={handleReset} text="Reset" variant="neutral" />
) : (
<div>
<>
<Button disabled={curStep === 0} onClick={handleBack} text="Back" variant="neutral" />
<Button onClick={handleNext} text={curStep === stepCount ? "Finish" : "Next"} />
</div>
</>
)}
</div>
</ButtonGroup>
</>
);
};

const FailureTemplate = ({ failedStep = 2, activeStep }: StepperProps & { failedStep: number }) => {
const FailureTemplate = ({
failedStep = 2,
activeStep,
orientation,
}: StepperProps & { failedStep: number }) => {
const [curStep, setCurStep] = React.useState(activeStep || 0);
const stepCount = 4;

Expand All @@ -74,31 +93,34 @@ const FailureTemplate = ({ failedStep = 2, activeStep }: StepperProps & { failed

return (
<>
<Stepper activeStep={curStep}>
{Array(stepCount)
.fill(null)
.map((_, index: number) => (
<Step
error={curStep === failedStep && index === failedStep}
key={index} // eslint-disable-line react/no-array-index-key
label={`Step ${index + 1}`}
/>
))}
</Stepper>
<div>
<Text>Step{curStep + 1} content</Text>

<Grid container direction={orientation === "horizontal" ? "column" : "row"}>
<Grid item xs={1}>
<Stepper activeStep={curStep} orientation={orientation}>
{Array(stepCount)
.fill(null)
.map((_, index: number) => (
<Step
error={curStep === failedStep && index === failedStep}
key={index} // eslint-disable-line react/no-array-index-key
label={`Step ${index + 1}`}
/>
))}
</Stepper>
</Grid>
<Grid container item xs={11} alignContent="center" justifyContent="center">
<Typography variant="body3">Step{curStep + 1} content</Typography>
</Grid>
</Grid>
<ButtonGroup justify="flex-start">
{curStep === stepCount - 1 || curStep === failedStep ? (
<ButtonGroup justify="flex-start">
<Button onClick={handleReset} text="Reset" variant="neutral" />
</ButtonGroup>
<Button onClick={handleReset} text="Reset" variant="neutral" />
) : (
<ButtonGroup justify="flex-start">
<>
<Button disabled={curStep === 0} onClick={handleBack} text="Back" variant="neutral" />
<Button onClick={handleNext} text={curStep === stepCount ? "Finish" : "Next"} />
</ButtonGroup>
</>
)}
</div>
</ButtonGroup>
</>
);
};
Expand Down
1 change: 1 addition & 0 deletions frontend/packages/tools/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
"@babel/eslint-parser": "^7.18.2",
"@babel/plugin-proposal-nullish-coalescing-operator": "^7.16.0",
"@babel/plugin-proposal-optional-chaining": "^7.16.0",
"@babel/plugin-proposal-private-property-in-object": "^7.16.0",
"@babel/plugin-transform-runtime": "^7.16.4",
"@babel/preset-env": "^7.16.4",
"@babel/preset-react": "^7.16.0",
Expand Down
Loading

0 comments on commit 97de041

Please sign in to comment.