UNPKG

react-dynamic-stepper

Version:

Advanced and multi-feature react stepper component designed to be incredibly versatile for a variety of workflows and use cases.

271 lines (222 loc) 13.4 kB
[![Storybook][badge_storybook]][package_link] [![Npm version][badge_npm-version]][package_link] [![Npm downloads][badge_npm-downloads]][package_link] [![Npm minified][badge_npm-minified]][package_link] [![Npm CICD][badge_npm-cicd]][package_link] # Table of Contents: - [Overview](#overview) - [Demo](#demo) - [Installation](#installation) - [Usage](#usage) - [Stepper props](#stepper-props) - [Features and Methods](#features-and-methods) - [Resources](#resources) ## Overview: Advanced and multi-feature stepper component designed to be incredibly versatile for a variety of workflows and use cases. It supports the following: - Horizontal stepper UI. - Vertical stepper UI. - Inline stepper UI. - Sequence stepper. - Right to left languages. - Custom pallet. - Custom header. - Custom footer. - Navigate to the required step programmatically. <p dir="rtl"><a href="#table-of-contents">Back to top</a></p> ## Demo: Checkout the demo of this package on [codepen][package_demo-link] <p dir="rtl"><a href="#table-of-contents">Back to top</a></p> ## Installation: - Via npm: ```shell npm install react-dynamic-stepper ``` - Via yarn: ```shell yarn add react-dynamic-stepper ``` - Via pnpm: ```shell pnpm add react-dynamic-stepper ``` <p dir="rtl"><a href="#table-of-contents">Back to top</a></p> ## Usage: ```jsx import { Stepper } from 'react-dynamic-stepper'; const App = () => { const steps = [ { header: { label: 'Step 1', }, content: <div>First step content</div>, isError: false, isWarning: false, isComplete: true, }, { header: { label: 'Step 2', }, content: <div>Second step content</div>, onClickHandler: () => console.log('clicked on second step next button'), isLoading: false, isError: false, isComplete: true, }, { header: { label: 'Step 3', }, content: <div>Third step content</div>, isError: false, isComplete: true, }, ]; const submitStepper = () => { console.log('submitted'); }; return ( <Stepper steps={steps} footerData={{ submitHandler: submitStepper, }} /> ); }; ``` <p dir="rtl"><a href="#table-of-contents">Back to top</a></p> ## Stepper props: | Prop | Type | Default | Required | Description | |------------------------------|--------------------------------|---------| --- |------------------------------------------------------------------------------------------------------| | isRightToLeftLanguage | Boolean | `false` | No | If true, sets the direction of the stepper to **rtl** | | isVertical | Boolean | `false` | No | If true, sets the orientation of the stepper to vertical | | isInline | Boolean | `false` | No | If true, sets the header display of the stepper to inline | | isSequenceStepper | Boolean | `false` | No | If true, sets the stepper to sequence mode (forces the user to complete steps in sequence) | | isStepConnector | Boolean | `true` | No | If false, removes the step connector | | [ref](#features-and-methods) | `useRef<NavigateToStepHandler>` | `null` | No | It exposes `navigateToStep` function, that can programmatically navigate the user to a specific step | | steps | [StepInterface[]](#StepInterface) | - | Yes | Array of steps | | footerData | [FooterDataInterface[]](#FooterDataInterface) | - | Yes | Footer data | | pallet | [PalletInterface[]](#PalletInterface) | - | No | Pallet for custom color codes | <p dir="rtl"><a href="#table-of-contents">Back to top</a></p> ### StepInterface: | Prop | Type | Default | Required | Description | |--------------------------------------------|-------------------------------------------------|--------------------------------------------|----------|--------------------------------------------------------------------------------------------------------------------------| | header.label | String | - | Yes | The label to display on the step header | | header.indicator | ReactNode | Step number | No | Custom indicator for the step | | header.indicator.isKeepIndicatorOnComplete | Boolean | `false` | No | Keep header indicator when step is completed | | footer.nextButtonLabel | String | `Continue to ${nextStepLabel}` or `Submit` | No | Set next button label of the current step | | footer.prevButtonLabel | String | `Back to ${prevStepLabel}` | No | Set prev button label of the current step | | footer.isPreventNextClick | Boolean | `false` | No | If true, clicking the ‘Next’ or ‘Submit’ button for the current step will not trigger any action unless its set to false | | footer.onClickHandler | Function: `() => void` or `() => Promise<void>` | - | No | Invoked when the next button of the current step is clicked | | content | ReactNode | - | Yes | The content to display for the step | | isLoading | Boolean | `false` | No | If true, the 'Next' button will be disabled | | isError | Boolean | `false` | No | If true, will display the step with error UI | | isWarning | Boolean | `false` | No | If true, will display the step with warning UI | | isComplete | Boolean | `false` | Yes | If true, will display the step with completed UI and enables 'Next' button | <p dir="rtl"><a href="#table-of-contents">Back to top</a></p> ### FooterDataInterface: | Prop | Type | Default | Required | Description | | --- | --- |--------------------------------|--- |----------------------------------------------------------------------| | prevBtnLabel | String | `Back to ${prevStepLabel}` | No | Label for the prev button | | prevBtnClassName | String | `undefined` | No | CSS classname(s) to be applied to prev button | | nextBtnLabel | String | `Continue to ${nextStepLabel}` | No | Label for the next button | | nextBtnClassName | String | `undefined` | No | CSS classname(s) to be applied to next button | | submitBtnLabel | String | `Submit` | No | Label for submit button in the last step | | submitBtnClassName | String | `undefined` | No | CSS classname(s) to be applied to the submit button in the last step | | submitHandler | Function: `() => void` or `() => Promise<void>` | - | Yes | Invoked when the submit button is clicked | <p dir="rtl"><a href="#table-of-contents">Back to top</a></p> ### PalletInterface: | Prop | Type | Default | Required | Description | |----------| --- | --- | --- |----------------------------| | default | String | `#627c90` | Yes | Default color code | | warning | String | `#f1c40f` | Yes | Color code for warning UI | | danger | String | `#e95a4b` | Yes | Color code for error UI | | success | String | `#4caf50` | Yes | Color code for success UI | | disabled | String | `#e3e8ec` | Yes | Color code for disabled UI | <p dir="rtl"><a href="#table-of-contents">Back to top</a></p> ## Features and Methods ### Navigate to step programmatically: The **ref** passed to the Stepper component exposes a **navigateToStep** function, that can programmatically navigate the user to a specific step. It can be useful in scenarios when controlling step navigation from outside the Stepper component is required. > ### ***Important Note***: > > Make sure to mark the required steps as **completed** if you want to **navigate programmatically** so that you can submit your stepper. This ensures that all necessary steps have been taken before the finish line. <details> <summary>JavaScript</summary> ```jsx import { useRef } from 'react'; import { Stepper } from 'react-dynamic-stepper'; const App = () => { const stepperRef = useRef(null); return ( <> <button onClick={() => { stepperRef.current?.navigateToStep(1); }} > Navigate to step 2 programmatically </button> <Stepper ref={stepperRef} /* OTHER PROPS */ /> </> ); }; ``` </details> <details> <summary>TypeScript</summary> ```typescript jsx import { useRef } from 'react'; import { Stepper, NavigateToStepHandler } from 'react-dynamic-stepper'; const App = () => { const stepperRef = useRef<NavigateToStepHandler>(null); return ( <> <button onClick={() => { stepperRef.current?.navigateToStep(1); }} > Navigate to step 2 programmatically </button> <Stepper ref={stepperRef} /* OTHER PROPS */ /> </> ); }; ``` </details> <p dir="rtl"><a href="#table-of-contents">Back to top</a></p> ### Invoke a function on Next button click of current step - `step.onClickHandler` => This is invoked when the 'Next' button of the current step is clicked. - If your `onClickHandler` returns a Promise and you want to navigate to the next step only if the Promise resolves successfully, you need to `throw error` inside the **catch** block: ```typescript const submitCurrentStep = async () => { try { /* Your business logic here */ } catch (error) { throw error; } finally { /* Cleanup code here */ } }; ``` <p dir="rtl"><a href="#table-of-contents">Back to top</a></p> ## Resources - [Changelog][changelog] <p dir="rtl"><a href="#table-of-contents">Back to top</a></p> [changelog]: https://github.com/DonAdam2/react-dynamic-stepper/blob/main/CHANGELOG.md [badge_npm-version]: https://img.shields.io/npm/v/react-dynamic-stepper.svg [badge_npm-downloads]: https://img.shields.io/npm/dm/react-dynamic-stepper.svg [badge_npm-minified]: https://img.shields.io/bundlejs/size/react-dynamic-stepper [badge_npm-cicd]: https://github.com/DonAdam2/react-dynamic-stepper/actions/workflows/publish.yml/badge.svg [badge_storybook]: https://cdn.jsdelivr.net/gh/storybookjs/brand@master/badge/badge-storybook.svg [package_link]: https://npmjs.org/package/react-dynamic-stepper [package_demo-link]: https://codepen.io/AdamMorsi/pen/qBRazPM