Little Details: Subpixel vs Greyscale Antialiasing
by Matthew Crist Friday, May 18th, 2012There are two methods of antialiasing used in web browsers, greyscale and subpixel. Type rendered using subpixel antialiasing tends to look heavier than when rendered with greyscale. Most browsers will consistently use one or the other and in some cases it’s possible change your settings. Webkit on the other hand uses both at the same time depending on what styles are applied to the element.
By default, WebKit browsers will render type using the subpixel method. This usually ends up looking something like this:
![]()
The problem with WebKit’s handling of type is that you might end up with inconsistent type rendering or even flickering type if you are using any CSS animations. You’ll be able to tell the difference during the animation like so:
![]()
When you animate an element in WebKit, the element will change from subpixel to greyscale and then back to subpixel when the animation is complete. You can play with a couple different examples on this demo.
This is one of those little details that front end developers need to work around. The way to resolve this issue is to start out with greyscale antialiasing on the element. This can be acheived by placing this little snippet of CSS on the animated element:
By doing this, you will have two separate types of type on the same page. Depending on your site’s design, this may not be an issue. If it is though, you might want to consider enabling greyscale on all elements on a page for consistency. The downside of doing so might affect the overall performance of your site.
This isn’t front-end ‘development’. It’s front-end ‘design’.
It has to do with how it looks, not how it is performing/populating, whether dynamically or from a feed.
As long as you are tweaking the way something ‘looks’ you’re dealing with ‘design presentation’, not ‘development’.
Congratulations Jodo, that’s the most pedantic and useless comment I’ll read all day and it’s before noon.
Thanks for the helpful tip, Matthew. Good developers will gladly appreciate this knowledge.
The ironic thing is that the font on this website is very difficult for me to read.
That’s sound advice. It’s also an option to apply an opaque background to the text element (or even text-shadow, if I recall correctly).
For subpixel calculation, the rendering engine needs the text and the background color—but, under hardware acceleration, the type with an alpha channel is cached as a texture. Knowing this, you can elect to force the element to always be grayscale AA, or you can ensure that your cached elements are opaque.
It’s been said that in Opera, even 0,0 transform will distort the text. Another way I’ve gotten past this issue is to keep a text-shadow on the text (forcing it to anti-aliased) that is transparent or the same color as the background. Also be sure to utilize text-rendering:optimizeLegibility;
On Chrome 19.0.1084.46 under Lion 10.7.4, the middle example renders with subpixel anti-aliasing no matter which state the red box is in.
Have you considered just using -webkit-font-smoothing: antialiased?
@evan – yes, though I don’t think of it as the best solution. as one of the commenters on HN mentioned, this issue is really a bug in webkit. Once they solve that (which it appears the latest Chrome has), the font will render consistently using the transform method. Unless you apply -webkit-font-smoothing: antialiased to the entire document it will still render inconsistently after the fix.
I’ve been using this for a while, but instead I add text-shadow to the body like this
text-shadow: 0 0 0 rgba(0,0,0,0);
And I get the same effect. I’ve not noticed any performance issues thus far.
There’s no difference on Chrome (18 OSX, 19 W7) or Safari on Mac.
This isn’t a bug, it’s a technical limitation. Subpixel anti-aliasing is equivalent to having a separate alpha value for the R, G and B channel. GPUs do not support this natively.