How to Use CSS Variables for SVG Gradients

By: Monica Wheeler
Sunrise gradient background

I was recently presented with an SVG from our design team that included colors I needed to make flexible between different projects. Since the SVG contained a linearGradient with colors defined directly in the SVG, I knew I had to move those colors out of the SVG and into CSS. In this post, I walk you through my process of styling the SVG gradient stop-color attribute with CSS and Custom Variables. I also look at an interesting discovery that I made with browser support and documentation regarding styling the CSS property stop-color.

Using the Inline Stop-Color Attribute

To create a gradient within an SVG, you use the linearGradient or radialGradient element, with a nested stop element for each of the gradient “stops,” or gradient colors. Then you assign that gradient via an ID to the elements within the SVG that will get the gradient fill. stop-color is an attribute on the stop element and what I will be focusing on in this post. Let’s look at a simple example of a linear gradient for an SVG circle:

<svg width="72" height="72" viewBox="0 0 72 72" xmlns="http://www.w3.org/2000/svg">
  <linearGradient x1="0" y1="0" x2="100%" y2="100%" id="gradient">
    <stop stop-color="#c86dd7" offset="0"/>
    <stop stop-color="#3023ae" offset="100%"/>
  </linearGradient>
  <circle fill="url(#gradient)" cx="36" cy="36" r="20"/>
</svg>

The above shows that the linearGradient is created with a stop-color of #c86dd7 at offset 0 and a stop-color of #3023ae at offset 100%. Then that gradient is used as a fill in the circle.

CodePen example of the above.

Using CSS Variables

I can see that stop-color is each gradient color and the point at which it stops, or its offset. However, stop-color is inline with the SVG and I wanted to make it more flexible. I accomplished that by removing the stop-color attribute from the SVG, adding a class, then putting those into the CSS. Let’s look at an example:

HTML:

<svg width="72" height="72" viewBox="0 0 72 72" xmlns="http://www.w3.org/2000/svg">
  <linearGradient x1="0" y1="0" x2="100%" y2="100%" id="gradient">
    <stop class="gradient__brand-secondary" offset="0"/>
    <stop class="gradient__brand" offset="100%"/>
  </linearGradient>
  <circle fill="url(#gradient)" cx="36" cy="36" r="20"/>
</svg>

CSS:

:root {
  --color-brand: #3023ae;
  --color-brand-secondary: #c86dd7;
}

.gradient__brand-secondary {
  stop-color: var(--color-brand-secondary);
}

.gradient__brand {
  stop-color: var(--color-brand);
}

CodePen example of the above.

That’s exactly what I was looking for. This made the gradient flexible and if the brand colors change, the gradient changes as well.

Browser Support

Lastly, browser support. This is where things got weird. This was my first use of stop-color, so I wanted to make sure it was widely supported.

  • I checked caniuse but it found no results for a search of stop-color.

  • MDN discusses stop-color but only related to the SVG attribute.

  • An MDN sitewide search did not return any other documentation related to stop-color.

  • W3C does not list stop-color as a CSS property.

Finally, I found this W3C document related to styling SVGs with CSS. This document explains why stop-color works even though no one mentions it being a valid CSS property. The document says:

SVG user agents must support all of the CSS styling mechanisms described in this chapter.

And with that, I had my answer. It may not be an actual CSS property but it is a style mechanism described in the SVG styling documentation, so it must be supported if the browser supports SVGs.

IE11 Browser Exception

The last thing to note is that IE11 does not support CSS Variables (Custom Properties) but you can still use stop-color in the CSS like we did in the CodePen examples. If you do use CSS Variables, be sure that you have a fallback or use a plugin that converts the CSS Variables into actual color values for this technique to be supported in IE11.

A fallback might look like this:

.gradient__brand-secondary {
  stop-color: #c86dd7; /* fallback color */
  stop-color: var(--color-brand-secondary);
}

.gradient__brand {
  stop-color: #3023ae; /* fallback color */
  stop-color: var(--color-brand);
}

At DockYard, the digital design project I am working on uses PostCSS. For IE11 support we use a PostCSS plugin called postcss-custom-properties that converts CSS Variables into color values for you.

In Conclusion

You can use the stop-color property for your SVG gradients in CSS!

DockYard is a digital product agency offering exceptional user experience, design, full stack engineering, web app development, software, Ember, Elixir, and Phoenix services, consulting, and training.