Skip to content

Import

import { ProgressIndicator } from '@dnb/eufemia'

Description

Use a ProgressIndicator whenever the user has to wait for more than 150ms. This component is also known as:

  • Indicator (Activity-Indicator)
  • Loader (Pre-loader)
  • Spinner

Demos

Default ProgressIndicator is Circular

Code Editor
<ProgressIndicator />

Default Circular ProgressIndicator

Code Editor
<ProgressIndicator type="circular" />

Circular ProgressIndicator with a label in a horizontal direction

Vennligst vent ...
Code Editor
<ProgressIndicator
  // label="Custom label ..."
  type="circular"
  showDefaultLabel={true}
  labelDirection="horizontal"
/>

Circular ProgressIndicator with a label in a vertical direction

Vennligst vent ...
Code Editor
<ProgressIndicator
  // label="Custom label ..."
  type="circular"
  showDefaultLabel={true}
  labelDirection="vertical"
/>

Circular ProgressIndicator with a label inside

Inside labels must be carefully sized, and are generally meant for just an icon or a number.

72%
Code Editor
<ProgressIndicator
  right
  label={<IconPrimary icon="save" />}
  type="circular"
  labelDirection="inside"
/>
<ProgressIndicator
  progress={72}
  size="large"
  type="circular"
  labelDirection="inside"
>
  <span className="dnb-p dnb-t__weight--bold dnb-t__size--small">
    {72}%
  </span>
</ProgressIndicator>

Shows a large Circular ProgressIndicator with a static 50% in progress

Code Editor
<ProgressIndicator
  type="circular"
  progress="50"
  size="large"
  noAnimation
/>

Circular ProgressIndicator with random value

Vennligst vent ...
Code Editor
const ChangeValue = () => {
  const [value, setValue] = React.useState(50)
  return (
    <Flex.Horizontal align="center">
      <ProgressIndicator
        type="circular"
        progress={value}
        showDefaultLabel
        noAnimation
      />
      <Button
        left
        size="small"
        variant="secondary"
        onClick={() => setValue(Math.random() * 100)}
      >
        Change
      </Button>
    </Flex.Horizontal>
  )
}
render(<ChangeValue />)

Circular ProgressIndicator with random progress value to show the transition

Code Editor
const Example = () => {
  const random = (min, max) =>
    Math.floor(Math.random() * (max - min + 1)) + min
  const [progress, setProgressIndicator] = React.useState(random(1, 100))
  React.useEffect(() => {
    const timer = setInterval(
      () => setProgressIndicator(random(1, 100)),
      1e3,
    )
    return () => clearInterval(timer)
  })
  return (
    <ProgressIndicator type="circular" size="large" progress={progress} />
  )
}
render(<Example />)

Circular ProgressIndicator with random on_complete callback

Code Editor
const Example = () => {
  const random = (min, max) =>
    Math.floor(Math.random() * (max - min + 1)) + min
  const [visible, setVisible] = React.useState(true)
  React.useEffect(() => {
    const timer = setInterval(
      () => setVisible(!visible),
      random(2400, 4200),
    )
    return () => clearTimeout(timer)
  })
  return (
    <ProgressIndicator
      type="circular"
      size="large"
      visible={visible}
      onComplete={() => {
        console.log('on_complete_circular')
      }}
    />
  )
}
render(<Example />)

Circular ProgressIndicator inside a Dialog

Code Editor
<Dialog
  spacing={false}
  maxWidth="12rem"
  fullscreen={false}
  alignContent="centered"
  hideCloseButton
  triggerAttributes={{
    text: 'Show',
  }}
  preventClose={false}
>
  <ProgressIndicator
    type="circular"
    showDefaultLabel
    labelDirection="vertical"
    top="large"
    bottom="large"
    size="large"
  />
</Dialog>

Default Linear ProgressIndicator

Code Editor
<ProgressIndicator type="linear" />

Small Linear ProgressIndicator

Code Editor
<ProgressIndicator type="linear" size="small" />

Linear ProgressIndicator with a label in a horizontal direction

Vennligst vent ...
Code Editor
<ProgressIndicator
  type="linear"
  // label="Custom label ..."
  showDefaultLabel={true}
  labelDirection="horizontal"
/>

Linear ProgressIndicator with a label in a vertical direction

Vennligst vent ...
Code Editor
<ProgressIndicator
  type="linear"
  // label="Custom label ..."
  showDefaultLabel={true}
  labelDirection="vertical"
/>

Shows a large Linear ProgressIndicator with a static 50% in progress

Code Editor
<ProgressIndicator type="linear" progress="50" size="large" noAnimation />

Linear ProgressIndicator with random value

Code Editor
const ChangeValue = () => {
  const [value, setValue] = React.useState(50)
  return (
    <FormRow centered>
      <ProgressIndicator type="linear" progress={value} noAnimation />
      <Button
        left
        size="small"
        variant="secondary"
        onClick={() => setValue(Math.random() * 100)}
      >
        Change
      </Button>
    </FormRow>
  )
}
render(<ChangeValue />)

Linear ProgressIndicator with random progress value to show the transition

Code Editor
const Example = () => {
  const random = (min, max) =>
    Math.floor(Math.random() * (max - min + 1)) + min
  const [progress, setProgressIndicator] = React.useState(random(1, 100))
  React.useEffect(() => {
    const timer = setInterval(
      () => setProgressIndicator(random(1, 100)),
      1e3,
    )
    return () => clearInterval(timer)
  })
  return <ProgressIndicator type="linear" progress={progress} />
}
render(<Example />)

Linear ProgressIndicator with random on_complete callback

Code Editor
const Example = () => {
  const random = (min, max) =>
    Math.floor(Math.random() * (max - min + 1)) + min
  const [visible, setVisible] = React.useState(true)
  React.useEffect(() => {
    const timer = setInterval(
      () => setVisible(!visible),
      random(2400, 4200),
    )
    return () => clearTimeout(timer)
  })
  return (
    <ProgressIndicator
      type="linear"
      size="large"
      visible={visible}
      onComplete={() => {
        console.log('on_complete_linear')
      }}
    />
  )
}
render(<Example />)

Linear ProgressIndicator inside a Dialog

Code Editor
<Dialog
  spacing={false}
  maxWidth="12rem"
  fullscreen={false}
  alignContent="centered"
  hideCloseButton
  triggerAttributes={{
    text: 'Show',
  }}
  preventClose={false}
>
  <ProgressIndicator
    type="linear"
    showDefaultLabel
    labelDirection="vertical"
    top="large"
    bottom="large"
  />
</Dialog>

Countdown indicator

Code Editor
const ChangeValue = () => {
  const max = 60
  const [current, setCurrent] = React.useState(10)
  React.useEffect(() => {
    const timer = setInterval(() => {
      setCurrent(current === 0 ? max - 1 : current - 1)
    }, 1000)
    return () => clearTimeout(timer)
  })
  return (
    <ProgressIndicator
      type="countdown"
      progress={(current / max) * 100}
      title={current + ' av ' + max}
      size="large"
      labelDirection="inside"
    >
      <MyCustomLabel aria-hidden>{current}</MyCustomLabel>
    </ProgressIndicator>
  )
}
render(<ChangeValue />)

Style customization

The sizes and colors can be customized with the properties size, customColors, and customCircleWidth if needed. The types circular and countdown has a few more options than linear.

20 dleft
done