Tuesday, March 10th, 2009
fontAvailable: Test to see if a font is usable
Howard Rauscher has wrapped up a little script to test the users browser for a particular font support. fontAvailable is a jQuery plugin, but can easily be tweaked to be independent:
-
-
/* fontAvailable jQuery Plugin, v1.0
-
*
-
* Copyright (c) 2009, Howard Rauscher
-
* Licensed under the MIT License
-
*/
-
-
(function($) {
-
$.fontAvailable = function(fontName) {
-
var element, width;
-
-
// prepare element, and append to DOM
-
element = $(document.createElement('span'))
-
.css('visibility', 'hidden')
-
.html('abcdefghijklmnopqrstuvwxyz')
-
.appendTo(document.body);
-
-
// get the width of element after applying a fake font
-
width = element
-
.css('font-family', '__FAKEFONT__')
-
.width();
-
-
element.css('font-family', fontName);
-
-
return (width !== element.width());
-
}
-
})(jQuery);
-
Howard told us about the library:
The company I work for has been using Tahoma as the default font for about two years now. A couple of months ago I wanted to figure out approximately how many users actually support this font. I decided to convert this code into a jQuery plugin. It is a pretty simple solution and does not require any swf files like other methods I found. I attach an invisible span to the bottom of a document and apply a fake font to the element. I get the width of the element and then compare it to the width of the element after I apply the given font name. If the widths are different, then the font is available.












un-removed element a part, is this method that reliable? As example, times new roman returns false on windows … and I wonder how many fonts with the same character size could return false as well.
Sounds good for most cases, but the concept is based on an assumption that could be wrong which is important to note:
.
If my browser’s default font is set to the font you are trying to test for, then the test will be incorrect. You apply the fake font and it falls back to the browser default. Then you test the new font and it doesn’t change, returning false as the result when it should be true:
font test
yep, that’s what I meant when I talked about times new roman but generally speaking, if charater width is the same of the default font, even if the height is different this function will return false.
Finally, as I already said, that element should be removed before the return ;-)
This will fail when the default font is the same as the one you’re querying.
Yeah, testing for the default font is definitely a case where it breaks. I a couple of different revisions where I try to handle that case, and they all pretty much fail. The reason I submitted it to Ajaxian is so I could get ideas and some feedback.
@WebReflection
I never thought about checking for the height of the test element. Thanks
I think it would be better to set the font family to “monospace” and then to “__FAKEFONT__, monospace”. Then comapre the widths. This will of course not work for monospaced fonts, but use of monospaced font is a very rare case.
Sooooooo, spill the beans Howard – How many of your users had Tahoma installed?
As for those worried about a few edge cases – this test could probably be beefed up by testing against a few different faces rather then just a fake font — for example test against “fake font” but also the monospace, serif and sans-serif generic families so you have a number of matrix to work off of. Even the most controlled environments [either by user preferences or by device type] will probably have different fonts set up for the different generics.
@ChrisCasciano
~85% of of home page views had tahoma. Even thought this number was a rough approximation and has to be taken with a grain of salt, I was hoping the number to be a lot lower so I would have a good reason to push for a wider used font like Arial.
I have been experimenting with a couple of different methods to make it more accurate. Testing against a matrix of generic families is a good idea.
I can’t believe this is hosted on Google Code. It seems more suited as a blog entry.
Should probably set the font-size as well. Don’t ya think?
You should probably do some cleaning up in the plugin. Multiple checks will mean a tonne of useless spans within the DOM.
Similar: http://ajaxian.com/archives/javascriptcss-font-detector
To handle the case where you’re checking the font it’s checked against, you can just check against two different fonts.
Here’s the implementation in Cappuccino: http://gist.github.com/280north/cappuccino/blob/89516d4a3817f0c098afa220486e36211ceab24d/AppKit/CPFontManager.j