Old browser

This article shows off HTML5 features, don't you think it would be a good idea to read it with a browser that supports these features so you can see them?

Circular progress bars for HTML5

Radial progress indicators are one of the most pretentious things you could possibly put on your website.
It's like saying "Bars are not good enough for me! Let's have a huge circle, and waste space to show how good I am with web technologies!"

Well, if you're looking for something lightweight, animated and customizable that will do the job on IE9+, look no further.

I will be using the Roboto font a lot, so you might want to download it. The code will use whatever your current font is.
You are free to copy, modify and use this code as you wish.

All the bars shown here can scale accordingly to the font-size attribute and can be used in a responsive layout.

Javascript

First, download the JS code.
Less than 4kb, and no frameworks required. Just the way I like it. It's basically a couple of calls to the Canvas.arc method, glorified with a bunch of settings and some really trivial animations, as you can see here:

Loading...

How to use it

First, import the .js file. Add this to your head tag.

<script type="text/javascript" src="radialprogress.js"></div>

Then, create an element for the bar in your body, such as a div.

<div id="bar"></div>

Finally, create the progress bar with javascript.
Make sure to store it in a variable so you can control it later.

var bar=new RadialProgress(document.getElementById("bar"), ...optional config goes here... );

When created, the bar takes up 10em in both width and height. The font-size of the element can be changed to scale it.
The default style mimics the look of the Windows 10 upgrade progress indicator.

Optional parameters can be passed as an Object (not a JSON string!):

  • colorBg: color of the part that's not filled. Accepts hex codes, rgba, etc. (Default: #404040)
  • colorFg: color of the part that's filled. Accepts hex codes, rgba, etc. (Default: #007FFF)
  • colorText: color of the text inside the circle. Accepts hex codes, rgba, etc. (Default: #FFFFFF)
  • indeterminate: if set to true, displays an indeterminate loading animation, otherwise it shows the progress. (Default: false)
  • progress: progress as float 0-1 (Default: 0)
  • round: if set to true, it rounds the corners of the filled part (Default: false)
  • thick: thickness of the circle as float 0-50 (Default: 2)
  • fixedTextSize: by default, the font size is picked automatically to stay within the circle. You can override this with this parameter. Text size is expressed as a float >0 (usually <0.5). (Default: undefined)
  • noPercentage: if set to true, it will not show the percentage in the middle of the circle, allowing text to be set manually with the setText function. (Default: false)
  • spin: if set to true, the circle rotates while showing progress (similar to the image loading animation of Telegram). See example 3. (Default: false)
  • animationSpeed: speeds up/down the animations. (Default: 1)
  • noAnimations: if set to true, disables all animations except the indeterminate spinning animation. (Default: false)
  • noInitAnimation: if set to true, when the bar is created, the bar will not gradually fill up to reach the indicated progreess. (Default: false)

The main functions to control the progress bars are:

  • setValue(v): sets the new progress as a float 0-1
  • setIndeterminate(i): when set to true, it will show an indeterminate loading animation, otherwise it will show the progress
  • setText(text): when the bar is set to not show the percentage (from config, not with the setIndeterminate function), it sets the string shown in the center of the bar

By default, the text inside the progress bar uses the current font. You can customize the text with CSS like this:

#bar .rp_text{ //replace #bar with the id of your bar
  ...custom style...
}
Example:
var bar=new RadialProgress(document.getElementById("bar"),{indeterminate:true,colorFg:"#FFFFFF",thick:2.5,fixedTextSize:0.3});
...
bar.setIndeterminate(false);
bar.setValue(0.3);

Style can be changed at any time, with instructions like:

bar.colorFg="#40FFFF"; bar.draw(true); //this forces the bar to be redrawn

This allows the creation of effects like the one shown in Example 8.

Example 1

{thick:5}

Example 2

{indeterminate:true,colorBg:"rgba(0,0,0,0)",colorFg:"#FFFFFF",thick:5}

Example 3

{colorBg:"#DDDDDD",colorFg:"#202020",colorText:"#202020",thick:12,fixedTextSize:0.25,round:true,spin:true,animationSpeed:0.5}

Example 4: custom text style

HTML
<div>
  <style type="text/css" scoped="scoped">
    #example4 .rp_text{
      text-shadow: 0.05em 0.05em rgba(0,0,0,0.4);
      font-weight:700;
    }
  </style>
  <div id="example4"></div>
</div>
Config
{progress:0.7,colorFg:"#D0D020",thick:50,fixedTextSize:0.35}

Example 5: Custom text

JS
bar.setText("Proud");
Config
{progress:0.85,colorBg:"rgba(0,0,0,0)",colorFg:"#FFFFFF",thick:1.8,noPercentage:true,fixedTextSize:0.3}

Example 6: Centered and Scalable

HTML
<div style="text-align:center">
  <div id="example6" style="font-size:1.5vw; display:inline-block;"></div>
</div>
Config
{progress:0.9,colorFg:"#FF5858",thick:2.5,fixedTextSize:0.3}

Example 7: transparency

{progress:0.7,colorBg:"rgba(255,255,255,0.4)",colorFg:"rgba(255,255,255,0.8)",colorText:"rgba(255,255,255,0.9)",thick:6}

Example 8: changing style at runtime

JS
setInterval(function(){
  bar8.colorFg="hsl("+(Math.random()*360)+",100%,65%)";
  bar8.draw(true);
},500);
Config
{progress:0.65,colorBg:"rgba(128,128,128,0.4)",thick:7}

Limitations

No fallback for IE8-

Browsers that don't support the canvas element will show nothing, or show only the text.
A fallback implementation using a linear progress bar or SVG could be implemented.

Don't use too many animated bars at the same time

You may have noticed that this page disables the usual animated background. This is because I had to display several progress bars, some of which are animated.
These animations will redraw the bar at 60 frames per second, and that can be quite heavy on mobile devices, so you don't want to show too many bars at the same time, especially if they're big.
Using faster animations (or disabling them) will reduce the amount of work.

Could use more settings

The current implementation will cover most modern scenarios, as it's perfect for a flat looking website, however it could use a few more settings to allow more effects to be applied so it can be used in other contexts as well.

Share this article

Comments