Get "PHP 8 in a Nuthshell" (Soon includes PHP 8.4)
Amit Merchant

Amit Merchant

A blog on PHP, JavaScript, and more

Building Dynamic Progress Bars using only CSS

Here’s a full disclaimer upfront: This isn’t something I’ve come up with. Jeffery Way from Laracasts has come up with this technique in one of the videos and I’m just sharing it here for my reference.

Essentially, the video explains how you can create a dynamic progress bar purely using conic gradients in CSS. Yep! No JavaScript is needed at all.

The end result will look something like this.

Dynamic Progress Bar

As you can tell, the blue line around the circle shows the progress of the video which is denoted by the number in the middle.

Let’s see how you can create this.

First, let’s create a simple HTML structure for our progress bar.

<div class="progress">01</div>

Now, let’s style it using CSS.

.progress {
    width: 100px;
    height: 100px;
    border-radius: calc(infinity * 1px);
    font-family: sans-serif;
    display: flex;
    align-items: center;
    justify-content: center;
    background-color: red;
}

This will create a simple red circle with the text “01” in the middle.

Now, we need to change the background color to a conic gradient. Here’s how you can do it.

.progress {
    /* code commented for brevity */
    background: conic-gradient(
        red 50%,
        transparent 50%,
    );
}

This will create a conic gradient that is 50% red and 50% transparent. This will create a half-filled circle with the red color.

See the Pen Progress Bars with Conic Gradients by Amit Merchant (@amit_merchant) on CodePen.

To make it how we want, we need to put a child element inside the .progress element which will be a circle but with a slightly smaller size (than the parent) and a gray background. This will create an illusion of a progress bar around the circle.

Here’s how you can do it.

<div class="progress">
    <div class="number">01</div>
</div>

And here’s the CSS for the same.

.progress .number {
  background: #e3e3e3;
  width: 93%;
  height: 93%;
  color: var(--color, 'red');
  border-radius: inherit;
  margin: auto;
  display: flex;
  align-items: center;
  justify-content: center;
}

As you can tell, we moved the centering styles to the .number class and also added a --color variable which will be used to change the color of the progress bar dynamically.

See the Pen Progress Bars with Conic Gradients - Part 2 by Amit Merchant (@amit_merchant) on CodePen.

We will also make the percentage dynamic using CSS variables. Here’s how you can do it.

.progress {
    /* code commented for brevity */
    background: conic-gradient(
        var(--color, 'red') calc(var(--percentage, 1) * 1%), 
        transparent calc(var(--percentage, 1)* 1%)
    );
}

Finally, to make the percentage and the progress color dynamic, you can change the --percentage and --color variables in the .progress element using inline styles.

<div class="progress" style="--percentage: 75;--color: blue;">
    <div class="number">01</div>
</div>

The percentages (and the color) can easily be changed in the HTML or dynamically using JavaScript or server-side rendering techniques.

The ability to change the progress bar color can help maintain a consistent color scheme throughout your application.

And that’s it! You’ve created a dynamic progress bar using only CSS.

Here’s the final code for the same. Go ahead and change the --percentage and --color variables to see the progress bar in action.

See the Pen Progress Bars with Conic Gradients by Amit Merchant (@amit_merchant) on CodePen.

If you prefer to watch the video, here’s the original video by Jeffery Way.

Like this article?

Buy me a coffee

👋 Hi there! I'm Amit. I write articles about all things web development. You can become a sponsor on my blog to help me continue my writing journey and get your brand in front of thousands of eyes.

Comments?