Animate the drawing of line

The following snippet is a CSS animation to draw a line. The line is a SVG path.

CSS
path {
  /* Use the same value as pathLength attribute of the path. */
  --length: 1;

  stroke-dasharray: var(--length);
  stroke-dashoffset: var(--length);

  animation: draw 2s;
  animation-iteration-count:infinite;
}

@keyframes draw {
  to {
    stroke-dashoffset: 0;
  }
}

The problem

HTML does not have the concept of a line! SVG has the line element but it does not have a length CSS property.

Demo

Solution

SVG has the line and path elements that can create lines. These elements have a length represented by the pathLength attribute, but it does not have a corresponding CSS property! You can imitate animating the length of the element to “draw” it via the 2 CSS properties: stroke-dasharray and stroke-dashoffset.

The process to animate a line is as follows:

  1. Create a line in a SVG with the line or path element. Any SVG element that has the pathLength attribute should work in theory.
  2. Add a pathLength attribute with a value of 1 to the element.
  3. In the stylesheet, set the stroke-dasharray and stroke-dashoffset properties to 1.
  4. Create a @keyframes that animates the stroke-dashoffset property to zero.
  5. Use the above keyframes in an animation.

Explanation

The key to this trick is to set the stroke-dasharray and stroke-dashoffset to the same length of the path we want to draw.

If we take this path:

We can make it into a dashed line through the stroke-dasharray property.

CSS
/* This gives us dashes with a length of 30 units. */
.path {
  stroke-dasharray: 30;
}

Through stroke-dashoffset, we can reposition the dashes relative to their original position. This is what it looks like to use a value of 20:

Now imagine making a dash that covers the entire length of the path. It will look like the path is not dashed at all! Then, if we offset the dash by the same amount as the length of the path, we push the dash just outside the visible area. Now, we see nothing!

You can visualize this by playing with the values below. If you drag both sliders to their maximum, then slowly decrease the stroke-dashoffset, you can see the line being “drawn”! What you are doing is bringing the single dash into the visible area incrementally.

You’re probably wondering how do you get the length of the path. You can use the following JavaScript to get the exact figure:

Javascript
let path = document.querySelector('path');
let length = path.getTotalLength(); // 560.9810180664062

The nice thing is that we dont have to measure the length of the path, we can set it through the pathLength attribute! So, if we set the pathLength to 1, we can use that value in our CSS. This simplifies things!

Attribution

Jake Archibald pioneered the technique in 2013.