Easy rounded corners — playing nice with borders in IE6

When a graphic designer gives you a mockup full of rounded corners, you just know you’re in for some pain. Why can’t they be satisifed with Comic Sans fonts instead of delving into techniques that haven’t quite penetrated the user-agent landscape yet. Ah… just jokes of course!

Andrew has published a technique dubbed “cornerise” over at irama, that neatly wraps up what we discovered when implementing rounded corners. As noted, border-radius does all the magic in newer builds of gecko and webkit, but that leaves us with a good chunk of Internet Explorer users needing some love—cornerise is such a technique.

It works by using javascript to insert some tactically placed tags into a document. These spans are positioned in the corners, and background images provide the corners. The overall footprint can be kept lean by utilising css sprites (like this one).

If you happen to be using borders with corners, you have a bit more to do. Firstly, the background images must include a border strip the same size as the border — pixel widths only here. Secondly, the corners need to be positioned on top of the border which means moving them slightly beyond the bounds of the containing box. Thirdly, you will enounter a quirk in IE6 that results in a 1 pixel border on the right or bottom of the box. Try as you might you won’t get rid of it — without compromising the corners in IE7 and IE8 that is! Actually, this quirk presents even without borders.

To solve this quirk, we need to understand it. It is caused by a rounding issue (measurements are rounded to the nearest pixel when a layout is drawn on the screen). It only occurs when the width or height of the box is an odd number of pixels. And it only affects the right or bottom edge, the top and left are always ok. Because this only occurs on an odd number of pixels, you might not even be aware of the issue straightaway. Ah, these are the challenges that web designers live for!

You could specify the dimensions of boxes so that they are always an even number of pixels, but that’s a poor compromise. Here’s a simple solution we discovered that allows you to have any size box, and support resizing on the fly (due to viewport or text size changes). It requires a css expression. Yes, expressions only work when javascript is enabled. Since the cornerise technique itself utilises javascript, this is completely suitable. (And it’s not like corners need to be accessible, this is just sugar.)

For corners on the right edge:
_margin-right: expression(this.parentNode.offsetWidth%2==0 ? '0' : '-1px');
For corners on the bottom edge:
_margin-bottom: expression(this.parentNode.offsetHeight%2==0 ? '0' : '-1px');

What does it mean? Well, this will set the right/bottom margin to either 0 or -1px depending on whether the width/height is an odd number of pixels. That’s what the %2 is for. Yes, another use for modulus arithmatic!

Now, as stated, this problem only occurs in IE6. We don’t want this expression interfering with the nice positioning in IE7 and IE8, so we need to hide it from those browsers. You can do this with conditional comments if you like, but if you don’t want to maintain separate stylesheets for individual versions of IE, you have another option: prefix the property name with an underscore. Yep, it is that simple to hide a rule from IE7 and IE8.

True, it’s a bit hacky, but you can’t argue with the results!