Cross-browser CSS gradient buttons

Recently I talked about CSS cross-browser gradients and last week I wrote again about CSS3 gradients. So what I’m going to do today? I will show you how to put the CSS gradient feature in practical use.

In this article you will see how you can create a set of gradient buttons just with CSS (no images).


Oh no! Not another CSS3 buttons!

That’s what you may say but, oh yes :) … This is another buttons set, powered by almighty CSS3 (and IE gradient filters).

Features

  • Scalability – Scale the buttons using font-size.
  • Adjustability – Change padding and font-size and there you go.
  • Flexibility – Apply the styles to any HTML elements.
  • Fallback styles – Graceful degradation for other browsers.
  • Usability – Normal, hover and active states are available.

“How it’s made”

View demo

HTML structure

Let’s see how the HTML looks for the blue button for example:

<a href="#" class="button button-blue">
    <span>Button</span>
</a>

Multiple classes are used in order to have minimal HTML and CSS files.

The top border could have been achieved with an inset box-shadow but, this way the CSS3 buttons will degrade graceful, as you will see later in this article.

The CSS

.button
{
    margin: 10px;
    text-decoration: none;
    font: bold 1.5em 'Trebuchet MS',Arial, Helvetica; /*Change the em value to scale the button*/
    display: inline-block;
    text-align: center;
    color: #fff;
    
    border: 1px solid #9c9c9c; /* Fallback style */
    border: 1px solid rgba(0, 0, 0, 0.3);            
    
    text-shadow: 0 1px 0 rgba(0,0,0,0.4);
    
    box-shadow: 0 0 .05em rgba(0,0,0,0.4);
    -moz-box-shadow: 0 0 .05em rgba(0,0,0,0.4);
    -webkit-box-shadow: 0 0 .05em rgba(0,0,0,0.4);
    
}

.button, .button span
{
    -moz-border-radius: .3em;
    border-radius: .3em;
}

.button span
{
    border-top: 1px solid #fff; /* Fallback style */
    border-top: 1px solid rgba(255, 255, 255, 0.5);
    display: block;
    padding: 0.5em 2.5em;
    
    /* The background pattern */
    
    background-image: -webkit-gradient(linear, 0 0, 100% 100%, color-stop(.25, rgba(0, 0, 0, 0.05)), color-stop(.25, transparent), to(transparent)),
                      -webkit-gradient(linear, 0 100%, 100% 0, color-stop(.25, rgba(0, 0, 0, 0.05)), color-stop(.25, transparent), to(transparent)),
                      -webkit-gradient(linear, 0 0, 100% 100%, color-stop(.75, transparent), color-stop(.75, rgba(0, 0, 0, 0.05))),
                      -webkit-gradient(linear, 0 100%, 100% 0, color-stop(.75, transparent), color-stop(.75, rgba(0, 0, 0, 0.05)));
    background-image: -moz-linear-gradient(45deg, rgba(0, 0, 0, 0.05) 25%, transparent 25%, transparent),
                      -moz-linear-gradient(-45deg, rgba(0, 0, 0, 0.05) 25%, transparent 25%, transparent),
                      -moz-linear-gradient(45deg, transparent 75%, rgba(0, 0, 0, 0.05) 75%),
                      -moz-linear-gradient(-45deg, transparent 75%, rgba(0, 0, 0, 0.05) 75%);

    /* Pattern settings */
    
    -moz-background-size: 3px 3px;
    -webkit-background-size: 3px 3px;
    background-size: 3px 3px;            
}

.button:hover
{
    box-shadow: 0 0 .1em rgba(0,0,0,0.4);
    -moz-box-shadow: 0 0 .1em rgba(0,0,0,0.4);
    -webkit-box-shadow: 0 0 .1em rgba(0,0,0,0.4);
}

.button:active
{
    /* When pressed, move it down 1px */
    position: relative;
    top: 1px;
}

Blue button:

.button-blue
{
    background: #4477a1;
    background: -webkit-gradient(linear, left top, left bottom, from(#81a8cb), to(#4477a1) );
    background: -moz-linear-gradient(-90deg, #81a8cb, #4477a1);
    filter:  progid:DXImageTransform.Microsoft.gradient(GradientType=0,startColorstr='#81a8cb', endColorstr='#4477a1');
}

.button-blue:hover
{
    background: #81a8cb;
    background: -webkit-gradient(linear, left top, left bottom, from(#4477a1), to(#81a8cb) );
    background: -moz-linear-gradient(-90deg, #4477a1, #81a8cb);
    filter:  progid:DXImageTransform.Microsoft.gradient(GradientType=0,startColorstr='#4477a1', endColorstr='#81a8cb');            
}

.button-blue:active
{
    background: #4477a1;
}

And so on for the other buttons…

View demo

Browser support

Mozilla 3.6+

Full support, including CSS3 gradient patterns (though I noticed some performance issues when page is rendered).

Webkit (Safari, Chrome)

The buttons are rendered very nice on Webkit browsers.

Opera 11

Unfortunately, Opera lacks any support for CSS gradients, still the buttons render very nice as other CSS3 features are not missing here.

IE6, IE7, IE8

With filters, CSS gradients are possible also when talking about IE6 or IE7.

IE9

Besides the other IE browsers, IE9 supports rounded corners and box shadows, although the corners don’t look perfect as you can see below.

That’s all!

It would be recommended to use conditional comments when using filters. This way your CSS file will be cleaner and you will avoid performance issues.

Having said that, I hope you enjoyed this article and if you did don’t forget to follow me on Twitter or to leave a comment below!

43 thoughts on “Cross-browser CSS gradient buttons

  1. One thing I would change in the CSS would be to put the default declaration AFTER the vendor-specific declarations. For example box-shadow should come after -moz-box-shadow and -webkit-box-shadow. That way when full browser support arrives, your code will render according to the spec rather than specific to the vendor because the default declaration comes after the vendor declarations.

  2. The inner span is not required. You can have multiple backgrounds and the top border could be produced by an inset box shadow (box-shadow: 0 1px 0 rgba(255,255, 255, .5) inset;)

    Thanks for the mention!

    • Thanks for your comment Lea, much appreciated!

      I also mentioned above that alternatively, the top border could be produced by an inset box-shadow.

      When I wrote this article, I just wished to have that top border also for the browsers that doesn’t support the box-shadow property.

  3. Made my afternoon to find this. The white edge and the fallbacks are fantastic. As well, I played with where you marked off “pattern” and set it to “1px 1px” to get rid of the grid look that wasn’t my cup of tea. Also, I changed the font to simply “sans” because I personally don’t like Trebuchet. What’s also interesting was that I could merely add another class and style just the font-size (in pixels), and the whole button changed right along with it. Well done, and I tweeted this.

  4. Anyone having issues with these buttons on FF4? I’m noticing it’s much different than FF3, showing me harsher radial lines instead of a smooth, blended radial. Of course, I was running FF4 in a Windows VM on Ubuntu, however. Must test on a real Windows system….

    • It seems that FF4 does not use the background-size property with the -moz- prefix anymore.

      As a solution: add also the background-size property.

      I’ll also update the CSS for this, thanks for letting us know!

  5. Thank you SO much for the tutorial and clean-code in this. I was looking for how to properly do “rounded corners” on buttons but they have always stumped me. Adding gradients really makes them pop! Great job and your demo is appreciated! (side note: it seems IE always falls behind the curve of making things look nice. The round corners are … almost there on IE9, still disappointing though.)

  6. Can I make two styles – one. And if so, how is this possible? I tried and I made it! But does not display the color of links for browsing. What I do not do that? Sorry for some mistakes. Its google translate from russian language

  7. How do you define a button width so multiple buttons under each other can be the same width. Sorry if I’m missing something I don’t see this option anywhere… Thank You.

    • Hey Miklos, in the example above, all the anchors are set to inline-block and they contain the same text (Button – for demo purposes). That’s why they have the same size.

      Though, you can just define your own custom width for the buttons.

      Catalin

  8. It’s possible to have an IE9 gradient background that doesn’t bleed into the rounded corners by using a url reference to an SVG background. There are many generators available online. If you’d like a generator that creates the SVG code for all possible CSS linear and radial gradients then see http://www.visualcsstools.com. There’s are a free and a cheap version.

  9. Great tutorial! I’m writing an application using JQuery which will need to generate custom (pretty) buttons based on a single CSS color that the user specifies (in a SharePoint 2003 list, no less).

    In order to do that; I’d need a way of programmmatically creating an appropriate gradient featuring a given color. Would you recommend that I do this by applying a formula to the CSS color codes (which would require converting named colors into hex), or by layering on different gradients with transparency that lighten and darken the specified color?

  10. Hey, I’m glad you like this tutorial. Also, you may check my latest CSS3 buttons too.

    Now, to programmatically create gradient buttons based on a color, I’d go with the solution I’m talking about here.

    It’s about transitioning the background-color and apply a gradient image to it which fades to transparent value.

    Hope that helps, good luck!

    • Thank you for the prompt reply! While I’ve solved my original problem (with heavy use of your examples here), I’ll definitely check out that article. For someone as new to web design/development as me, however, each of your articles is a veritable Pandora’s Box filled with deep and mysterious teachings!

  11. I noticed that when you click near the top or bottom border of the button, the click event does not occur. This is because the CSS in the button:active, that uses top:1px. The only way I found to solve this is removing that part of the CSS (it loses the “animation” effect). Many thanks.

  12. Getting real serious lag on newest version of Firefox. Any way to make a backup for Firefox that looks similar but functions correctly?

Leave a Reply

Your email address will not be published. Required fields are marked *

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>