maxvoltar

RSS

by Tim Van Damme

Follow me on Twitter

Rounded corners on images, CSS-only

Note: The latest version of Safari does support rounded corners on images, but Firefox and Opera still don’t. Depending on which browsers you want to support, this article might be useless, and I wasted an hour of sleep on it.


Admit it, even though rounded corners are widely seen as overused, you love playing with border-radius. A common complaint is that you can’t use that CSS3 property on images. Define any value, and the images will still display as nature intended: straight corners.

For a project I’m working on, it would’ve been really nice having certain images displayed with rounded corners, so I started looking at the options:

  • Cropping the corners off of the images manually, which is impossible on a large scale or with users uploading their own avatars, photos…
  • Adding an extra element with a background image that would be positioned over the image. The background image would cut off the corners.
  • To save ourself from elements without a real purpose, you could also do the same with img:after and content: url(youroverlay.png); (like I did on Adii’s website)
  • Set the image as a background image, which does inherit the rounded corners.

These options all have downsides. You can’t right click to save the image or drag it into another app or onto your desktop, it’s impossible to be prepared for all the different image sizes (gets even worse when you want to add a shadow), you can’t use a random background behind the image because the corners would be fixed…

So after some tinkering, I think I came up with what I think is a bulletproof solution. Bulletproof as in it will render great in browsers which support rounded corners and drop shadows, and won’t break on older browsers. Here’s a screenshot of the final result:

Result

The HTML isn’t too different from what you’d usually write:

<p style="background-image: url(bluesbrothers.jpg)">
    <img src="bluesbrothers.jpg" alt="Blues Brothers" />
</p>

It felt a bit dirty using inline-CSS, but I think the result has more value than that. As it’s twice the same image we’re loading, there are no performance issues. The actual CSS is pretty straightforward, except for this bit:

p img {
    opacity: 0;
}

The magic part about this is that the wrapping element respects the size of the image (even though I had to “hack” it with float: left; for the width), and you can right click or drag the image all you want. You can even use any background image or color (if you’re not using Safari, try resizing the browser window).

Just because you can’t see something doesn’t mean it’s not there ;)

  • Bram Van Damme (not related to me, just a kick-ass last name) made a Javascript version of this technique, automatically adding all the necessary code. He also solves my float: left; hack by using a <span>, which is more semantic (as pointed out by Thomas Horster).
  • Jason Long explains how you can do this serverside, clearing the markup from the extra code.