Media Temple Hosting

CSS3 Radial Gradient Syntax Breakdown

A short time ago I wrote an article that broke down the syntax for coding CSS3 linear gradients from scratch.

Once you get the hang of them, linear gradients are pretty simple to code. Radial gradients, on the other hand, are a little more complex.

So let’s finish off what I started in that earlier post and go through the syntax for radial gradients.

The Complete Syntax

First things first — for those who will inevitably find this page via search, below is the full syntax that will make the gradient work in all supporting browsers, along with a few additions to cover any future support:

#element {
	background: #000000; /* fallback for non-supporting browsers */
	background-image: -webkit-gradient(radial, center center, 0, center center, 141, from(black), to(white), color-stop(25%, blue), color-stop(40%, green), color-stop(60%, red), color-stop(80%, purple)); /* old WebKit Syntax */
	background-image: -webkit-radial-gradient(center center, circle contain, black 0%, blue 25%, green 40%, red 60%, purple 80%, white 100%); /* New WebKit syntax */
	background-image: -moz-radial-gradient(center center, circle contain, black 0%, blue 25%, green 40%, red 60%, purple 80%, white 100%);
	background-image: -ms-radial-gradient(center center, circle contain, black 0%, blue 25%, green 40%, red 60%, purple 80%, white 100%); /* IE10+ */
	background-image: -o-radial-gradient(center center, circle contain, black 0%, blue 25%, green 40%, red 60%, purple 80%, white 100%); /* Opera (13?) */
}
Update: (June 30, 2012) The syntax for radial gradients has changed. IE10 is the first browser to support them unprefixed. This means that the unprefixed declarations using the old syntax will be invalid, so I’ve removed that line from the code above. I will update this article accordingly in time, but in the meantime here are some links:

Unprefixed CSS3 Gradients in IE10 (IEBlog)

The new radial gradient syntax (Peter Gasston)

Wow, that’s a lot of code. I’ve explicitly included extra color stops along with positions for all the colors (all of which will be discussed in this article), to give the copy-and-pasters something to work with.

The last two lines in the above code are not necessary because Opera, as of this writing, doesn’t have support yet, and the standard syntax is not supported by anyone. But it’s good practice to leave those in, as this will ensure your code is as future-proof as possible. I’ve also included the old WebKit syntax with code that creates an identical gradient in older versions of Chrome and Safari (more on this later).

So, using only the proposed standard syntax for brevity, let’s break down the code using a simplified example:

#element {
	background-image: radial-gradient(center center, circle cover, black, blue, green, red, purple, white);	
}

Defining the Gradient Center

The first argument that’s passed into the gradient function (yes, it’s a function — that’s why it has parentheses) defines the position of the center of the ellipse that’s created when the gradient is complete. I’ve used a value pair of center center in the example above.

The word radial means “going from the center outward… along a radius”. So the first argument defines where the outward action begins.

Basically, this argument accepts any value that you can put in the background-position property. This is basic CSS, so for details on how to define these, see this article on SitePoint’s CSS reference. The default, or initial value, for the position of the center of the gradient is center center.

Defining the Shape and Size

The next argument in the function defines the shape and size of the gradient.

The first part of the second argument can either be circle or ellipse. The difference is basically that an ellipse is not a perfect circle, but it could be. So, depending on the size and center position of the gradient, the value ellipse could make the gradient oval-shaped. But a value of circle means the gradient will always be a perfect circle.

The next part of the second argument (the size) can take one of six values. The values are:

  • closest-side
  • closest-corner
  • farthest-side
  • farthest-corner
  • contain
  • cover

At first glance, these values might be a little difficult to grasp, so let’s break each one down visually. Let’s use a basic black-to-white gradient so we can illustrate what each value does. Here’s the code:

#element {
	background-image: radial-gradient(50px 50px, circle closest-side, black, white);
}

All the other values will remain the same, but we’ll change the size value (currently shown as closest-side) so you can see the effect each one has on the look of the gradient.

Take note also that I’ve set the center position at 50px 50px to help make the shape and size values more clear.

closest-side
This value causes the gradient’s edge to meet the side of the element that is closest to the gradient’s center. Here’s how it looks:

closest-corner
This value causes the gradient’s edge to meet the corner of the element that’s closest to the center position of the gradient. Here it is:

Notice that part of the gradient’s full shape is cut off. This is because it’s being pushed into the corner of the element so that its edge meets the element’s corner.

farthest-side
This one does the opposite of the first value, causing the gradient’s edge to meet the side of the element that is farthest from the gradient’s center:

Notice that the size of the gradient in this example is different from the other two values because the gradient is forced to stretch to touch the farthest edge of the element.

farthest-corner
This value causes the gradient to stretch to the corner of the element that’s farthest away from the gradient’s center position:

Now the gradient covers much more of the element.

contain
This value causes the element to enlarge the gradient until it’s fully contained without any of the gradient being cut off by the element’s boundaries:

Look familiar? Well, it should, because this value is equivalent to closest-side, discussed above.

cover
Finally, this value causes the gradient to enlarge until it covers the entire area of the element:

Again, this should look familiar because this value is equivalent to farthest-corner.

I’m really not sure why the specification has different keywords defining identical results, but let’s not forget that the CSS3 spec is still in flux, so this could change.

Explicit Shape and Size

In addition to defining a size implicitly using the keywords just discussed, you have the option to define the gradient’s size explicitly using length or percentage values, like this:

#element {
	background-image: radial-gradient(center center, 60px 70px, black, white);
}

And here’s the result:

(Note: Firefox doesn’t yet support an explicitly-defined size for the gradient, so you won’t see the gradient in that browser)

Notice two things here: First, to make the shape more clear, I’ve moved the position of the gradient’s center to the center of the element. Second, I’ve removed both the size and the shape values that we used earlier (e.g. circle cover).

This is because you can’t combine explicit size values with any of the size and shape keywords; you need to use either one or the other method.

The explicit values define the lengths of the horizontal and vertical axes of the radial’s shape. So if we double the values from the previous example (using 120px 140px), then the new gradient would look like this:

(Note: Same as above; Firefox won’t render this gradient.)

Colors and Color Stops

Finally, the last part of the syntax lets you define which colors begin and end the gradient, along with any intermediary colors.

Naturally, the color values can be any valid CSS colors, and you also have the option to add positions for each color.

Here’s an example with four colors placed at specific intervals using percentages:

#element {
	background-image: radial-gradient(center center, 30px 40px, red 10%, orange 40%, yellow 65%, brown 90%);
}

Here are some things to note on the color values:

  • You have the option to omit the position of any of the colors, which will cause the browser to calculate the location on its own.
  • You can use negative values, which will cause the color to begin unseen, but you’ll still see the results (the gradual change from one color to the next), depending on the value.
  • The positions for the color stops define where each respective color is at its full state; everything in between is where the gradual changes (i.e. the gradient) occur
  • Since we’re dealing with radial gradients, then naturally the color stops are defining the boundaries and colors of nested ellipses

The Old Syntax

Because older versions of WebKit-based browsers supported a different syntax, it can be challenging to create a gradient that looks the same across all supporting browsers. Fortunately, for the most part, the browsers using the old syntax are not in very high use.

Nonetheless, here’s the old syntax, with a quick breakdown of the code:

#element {
	background-image: -webkit-gradient(radial, center center, 0, center center, 141, from(black), to(white), color-stop(25%, blue), color-stop(40%, green), color-stop(60%, red), color-stop(80%, purple)); /* old WebKit Syntax */
}

Instead of the fairly specific -webkit-radial-gradient function, the old syntax uses the more general -webkit-gradient. The first argument in the function defines the type of gradient (in this case radial).

The next group of arguments (center center, 0) define the center position and radius of the inner circle of the gradient. Then the next group (center center, 141,) defines the center position and radius of the outer circle of the gradient. The radius value is set in pixels, but no unit is specified.

Then the next group of arguments define the start and end colors, and the color stops that are in between the start and end colors. So the colors marked as “to” and “from” define the start and end colors and the subsequent values are the color stops.

Again, since this is the old syntax, I won’t spend any more time on this. If you need to know more about this syntax, you can check out this article on the Safari Developer Library.

I think the most important thing to note here is that you should put the new syntax after the old, to ensure that newer browsers (which still support the old syntax) use the most up-to-date implementation.

Browser Support

Radial gradients are not quite as well supported as linear, but it’s pretty close. Here’s the breakdown, with some notes:

  • Chrome 2-9 (old syntax)
  • Chrome 10+ (old and new syntax)
  • Firefox 3.6+
  • Safari 4-5 (old syntax)
  • Safari 5.1+ (old and new syntax)
  • IE10+
  • iOS Safari 3.2+ (old syntax)
  • Android Browser 2.3+ (old syntax)

IE10 is still in Platform Preview so technically the most recent stable release of IE (version 9) does not support any kind of gradients except those created using IE filters (which don’t support radial or color stops).

Also, as mentioned, although Opera has added support for linear gradients in 11.1, radial gradients in that browser are still future.

Radial Gradient Generators

To make gradients easier to work with, there are a few good apps that generate the code for you. Here are some of the ones I’m familiar with:

From what I can see, there is no tool that creates a gradient with both the old and new code. Although the Westciv tool has an option to create the gradient using the old syntax, I couldn’t get the old syntax generator to work in either Chrome or Safari.

If you know of any other tool that produces radial gradients, especially one that adds an old syntax equivalent, please comment and I’ll add it to the list.

27 Responses

  1. Vitaly:

    Radial Gradient Support of all Browsers(since IE 5.5, Opera, FF, Moz): http://7synth.com/dev/gradients

  2. Michael Sherov:

    Correction: you can make radial gradients in IE through the use of a few crazy alpha filters.

    • You’re thinking of linear gradients. IE filters don’t let you create radial gradients.

      • Vitaly:

        The Alpha-filter got different styles beside the opacity. One style is a radial-alpha. Thats the trick.

        • Looks like you’re right:

          http://msdn.microsoft.com/en-us/library/ms532967(v=vs.85).aspx

          I’m going to have to look into that and see if some simple radial gradients can be mimicked for IE. Thanks.

          • On CSS: do not rely on that alone to feed smooene a ‘mobile’ version. The reason is the bandwidth — don’t force people to load HTML they can’t use. Sadly I think the mobile space is the place you need to have a different version of your site.Not sure what AUS telco’s do but in Canada the data plans are outrageously expensive. For that reason I doubt the mobile web will take off… at least not until the data plans drop in price.

          • nemo:

            In response to elliot…

            WRT using CSS to provide a mobile site (I can’t seem to reply to Elliot directly)

            If your site is done correctly, with a minimal number of tags and proper separation of semantics and formatting,
            the actual HTML should be very very light.
            Even a large HTML page does not use much bandwidth these days. Smartphones are quite capable of using Accept-Encoding: compress,gzip

            Take this page, which does have its problems (touch of divitis in the comments, quite a few embedded tracking, utility scripts and flash that aren’t that useful/used). Compressed size is 15KiB. And that’s for a rather long article. And CSS/Images/Javascript are cached, so should not be fetched that often by the phone. And of course the CSS/Javascript compresses well w/ Accept-Encoding too. A poorly designed mobile layout could easily end up being less adaptive to phone dimensions and using more bandwidth trying to dynamically generate some non-CSS layout.

            CSS is an excellent way to provide mobile phone or printable layouts if a site is built correctly.

        • From my testing, the IE radial gradients are pretty awful, and not very flexible or easy to manipulate.

          Here’s my JSBin:

          http://jsbin.com/uqizuj/edit#html,live

          Must view in any version of IE to see the ultra-weird gradients.

  3. Good article…………….

  4. nemo:

    2 Comments.

    1) It seems really poor form to use the prefixed version throughout your entire example.
    For one thing, the standard radial-gradient syntax was not a webkit creation, so why on earth give webkit preference on this one? Why not use -moz-? For another thing, using a prefixed version causes silly people to simply paste the prefixed version, see it working in their browser, and stop looking further. Better to use the unprefixed version, and remind people to include and test prefixes as needed.

    2) With regards to browsers, I just wanted to note there are still some bugs.
    http://m8y.org/tmp/testcase231.xhtml was an attempt to narrow down why
    http://m8y.org/tmp/testcase230.xhtml was failing in Chrome ( Safari worked fine ).
    Fortunately an angle was not needed here, but I’d say that browser support isn’t quite complete yet…

    • You’re absolutely right about the syntax thing. I’ve updated the post to use the proposed standard syntax for the brief examples.

      Thank you for pointing that out, I’ve been meaning to be more browser-neutral in my code samples.

    • Sebas:

      The angle in radial-gradient is innecesary and is wrong.
      The complete support shouldn’t have angle. Support angle in radial-gradient syntax isn’t “complete support” is a incorrect support.

      • nemo:

        https://developer.mozilla.org/en-US/docs/CSS/radial-gradient#Values
        I did say it was unnecessary.
        Should not have blown up tho.

        • nemo:

          And. Yeah, can’t think of any situation it would be useful in, which is probably why it was dropped from the final spec. Even if a radial gradient is stretched from one corner to the farthest one, having an angle as well to, say, further distort it off that path from corner to corner by a certain angle seems. well. nutty.

          Anyway. That’s how it was documented when prefixed, given it was originally a Moz spec.

  5. No other article might even get close to this one, for explaining CSS3 radial gradient that clearly and easily. I really enjoyed it. Thanks.

  6. Sathya:

    I was trying to follow your tutorial to create radial gradient on IE9. But i cant figure it out. Even your example radial gradient is not loading in my brower. could you help me out as to what would be the problem.

  7. Scott R. Godin:

    Lea Verou’s prefixfree does a fairly decent job of letting you eliminate vendor prefixes with these. see also http://lea.verou.me/2012/07/important-prefix-free-update/

  8. Scott R. Godin:

    also just found http://www.visualcsstools.com/ for radial and linear gradient creation that generates css, svg and canvas values automagically.

  9. I’m confused. This method actually creates a background colour, nothing to do with an image – correct?

    I’ve managed to get it working as above, but what I needto do now is apply it to a real background image, cropping the corners showing the colour undernneath.

    Is this possible?

    Regards
    Pete

    • Technically, a CSS3 gradient is actually an image, not a color. The browser produces the image automatically, so it works the same way that a regular background image does, except it’s a gradient with custom colors.

      For what you are asking, Yes, that’s possible, if your image has transparency (using PNG or GIF) so you can see through the corners, and then show the background gradient behind the image.

      • Thanks Louis, it’s good to know that what I want to do is possible.

        I now have to work out how to showthe gradient behind the image.

        Regards
        Pete

  10. Excelente… BuenĂ­simo.

Leave a Reply

Comment Rules: Please use a real name or alias. Keywords are not allowed in the "name" field. If you use keywords, your comment will be deleted, or your name will be replaced with the alias from your email address. No foul language, please. Thank you for cooperating.

Instructions for code snippets: Wrap inline code in <code> tags; wrap blocks of code in <pre> and <code> tags. When you want your HTML to display on the page in a code snippet inside of <code> tags, make sure you use &lt; and &gt; instead of < and >, otherwise your code will be eaten by pink unicorns.