From d5c43662a7848cac44e1771d3c33a08a2de4d715 Mon Sep 17 00:00:00 2001 From: Giuseppe Ciotola <30926550+gciotola@users.noreply.github.com> Date: Mon, 11 Nov 2024 16:36:30 +0100 Subject: [PATCH] fix: add `displayMode` to Progress to display percentage details --- .../src/ui/atoms/Progress.test.tsx | 28 +++++++++++++++ .../app-elements/src/ui/atoms/Progress.tsx | 34 +++++++++++++++---- .../src/stories/atoms/Progress.stories.tsx | 20 +++++++++++ 3 files changed, 75 insertions(+), 7 deletions(-) diff --git a/packages/app-elements/src/ui/atoms/Progress.test.tsx b/packages/app-elements/src/ui/atoms/Progress.test.tsx index 3a9c3f3e0..1b3628f14 100644 --- a/packages/app-elements/src/ui/atoms/Progress.test.tsx +++ b/packages/app-elements/src/ui/atoms/Progress.test.tsx @@ -26,4 +26,32 @@ describe('Progress', () => { '20%' ) }) + + test('Should display the completion status as fraction by default', () => { + const { getByText } = render( + + sample label + + ) + expect(getByText('12/20')).toBeVisible() + }) + + test('Should display the completion status as percentage', () => { + const { getByText } = render( + + sample label + + ) + expect(getByText('60%')).toBeVisible() + }) + + test('Should render hidden text `max/max` to keep right space and alignments', () => { + const { getByText } = render( + + sample label + + ) + expect(getByText('1/20')).toBeVisible() + expect(getByText('20/20')).toHaveClass('invisible') + }) }) diff --git a/packages/app-elements/src/ui/atoms/Progress.tsx b/packages/app-elements/src/ui/atoms/Progress.tsx index 2ee546df1..f93034cb0 100644 --- a/packages/app-elements/src/ui/atoms/Progress.tsx +++ b/packages/app-elements/src/ui/atoms/Progress.tsx @@ -15,7 +15,13 @@ export interface ProgressProps * this indicates that an activity is ongoing with no indication of how long it is expected to take. */ value?: number - + /** + * The display mode of the progress bar. + * - `fraction` - Display the completion status as a fraction (default) + * - `percentage` - Display the completion status as a percentage + * - `none` - Do not display the completion + */ + displayMode?: 'fraction' | 'percentage' | 'none' children: React.ReactNode } @@ -30,6 +36,7 @@ export const Progress: React.FC = ({ value, children, className, + displayMode = 'fraction', ...rest }) => { return ( @@ -45,12 +52,25 @@ export const Progress: React.FC = ({ {value != null && ( - - {value}/{max} - - + {displayMode === 'fraction' ? ( + <> + + {value}/{max} + + + + ) : displayMode === 'percentage' ? ( + <> + + {Math.round((value / max) * 100)}% + + + + ) : null} )} diff --git a/packages/docs/src/stories/atoms/Progress.stories.tsx b/packages/docs/src/stories/atoms/Progress.stories.tsx index 4d99131e7..cde3f21b9 100644 --- a/packages/docs/src/stories/atoms/Progress.stories.tsx +++ b/packages/docs/src/stories/atoms/Progress.stories.tsx @@ -23,3 +23,23 @@ export const Indeterminate: StoryFn = (args) => ( Loading... ) Indeterminate.args = {} + +/** Display completion percentage using `displayMode` prop */ +export const WithPercentage: StoryFn = (args) => ( + 40% +) +WithPercentage.args = { + max: 100, + value: 40, + displayMode: 'percentage' +} + +/** Only show the progress bar, without completion details */ +export const OnlyBar: StoryFn = (args) => ( + 40% +) +OnlyBar.args = { + max: 100, + value: 40, + displayMode: 'none' +}