@font-face in Depth

September 20th, 2009 by admin · 68 Comments


  • (Aug 11, 2012): This article has been given a long overdue update to reflect the current state of browser support of @font-face.
  • (Oct 13, 2009): I have written a follow up article which explores SVG fonts,
    Opera 10 issues, and more
  • (Oct 28, 2010): This article has been translated into Belorussian by movavi.

Photo by marta.b (Source: Flickr)

When I told one of my co-workers how excited I was that almost all the major browser vendors now supported font-embedding in their products, I got the same reaction from her that Bert from Sesame Street got when he told Ernie how exciting he thought bottle cap collecting was (yes, gratuitous ridicule was involved).  Now, while I can somewhat understand her disinterest (she is not a front-end web developer, but a Java programmer), I defend my enthusiasm by stating here that fonts are a really important part of web design, and the fact that we can now theoretically choose any font to embed inside our web pages and applications is something to celebrate.

Sure, workarounds such as sIFR and Cufón have existed for quite a while now, but they have drawbacks (they both are best used only for headings, and Cufón  doesn’t do well at allowing copying and pasting its content).  If you really want to embed fonts in your webpages, I believe that @font-face is the safest, future-proof option.

Why care about fonts?

My Java developer colleague may not understand why fonts are important, but she is a regular reader of  The New Yorker.  Even though its website doesn’t use @font-face embedding (the standard New Yorker font is embedded in site using images), the developers of the site obviously know why fonts are important:

  • Fonts identify who the content belongs to. Just take a look at the content and without looking at the URL bar, you know exactly where you are – that font is highly integrated into that organization’s identity and branding.  Replace the New Yorker font with Arial and it’ll look like any old website.
  • Fonts given an emotional association to the content. The content has an air of authority because of the font it uses (after all, it looks like it was written by The New Yorker). It is the reason why phishing sites use the fonts, colours and logos of the banks they are posing as.
  • Fonts can help (or hinder) the legability of content. Scanning the content, you can tell where the article titles are, where the navigation is, and what section each of the articles belong to.  This is all because of the way fonts are used on the site.


The New Yorker's website is a great example of how to use fonts effectively on the web.

The New Yorker uses images in order to display fonts.  Using font embedding effectively would save on bandwidth, since one font download could be used for all the headings on the page.

Font formats supported

Firefox 3.5+ , Safari 3.1+, Opera 10+, Chrome 4.0+ and Internet Explorer 4.0+ all support @font-face embedding (Google’s Chrome 3.0 beta does as well, but users will have to start it up in a special mode to make it work). They all support the use of TrueType (.ttf) and OpenType (.otf) fonts … except for Internet Explorer which only supports the proprietary Embedded Open Type (.eot) format. There aren’t as many fonts available in this format and the tool Microsoft gives out that converts .ttf fonts to .eot, called WEFT, is quite frustrating to use, and even crashes on Vista. There is, however, an excellent command-line tool, ttf2eot, that does a much better job. Both WEFT and ttf2eot only convert TrueType to Embedded Open Type – if you want to convert an OpenType font to Embedded Open Type, it is necessary to use FontForge, a free font-editing tool, to convert the font to TrueType first, and then use ttf2eot to convert the resultant font to .eot format. Although this method is roundabout and results in loss of detail due to the way the font formats store information, it is the only way I know to do this conversion.

For more detail on how to perform .eot font conversions using ttf2eot and FontForge, check out Edward O’Connor’s great article How to create EOT files without Microsoft WEFT

Update: Since I have originally written this article, I have created a command-line tool that will convert TTF or OTF font into all font formats supported by all the browsers, along with an embedded stylesheet. Font Squirrel also has an excellent on-line tool that you can use to do this as well. In addition, all modern browsers now support WOFF fonts, and quite a few also support SVG fonts as well. To keep up with what works with what, take a look at CanIUse.com’s excellent compatibility chart.

Where to get fonts you can legally use in web pages.

Although it is now technically possible to embed almost any font inside a web page, it is important to remember that if you use a commercial font for this purpose, you must have a license to do this. Since putting a font on a website will allow anyone on the Web to download it, a lot of font foundries currently do not allow their fonts to be used for web page embedding. It is for this reason that the browser vendors have been reluctant to implement this technology into their products until recently (font embedding is part of the CSS2 specification, which has been around since 1998).

Luckily, there are a few sites that are sprouting up that have done the initial work for you by listing fonts that allow font embedding on web pages legally.  The ones that I have visited include:

Note that whenever you use any font, make sure you check the license that comes with it. Some fonts, even if their license allows for font embedding, may not allow you to use it for commercial purposes. Others may, but only for a fee. To be safe, check the documentation that comes with the font.

How to insert a font into your webpage

Once you have a font that you’d like to insert into your webpage, you first have to declare it inside your CSS stylesheet:

@font-face {
    font-family: 'Droid Sans';
    src: url('DroidSans-webfont.eot?#iefix') format('embedded-opentype'),
         url('DroidSans-webfont.woff') format('woff'),
         url('DroidSans-webfont.ttf') format('truetype'),
         url('DroidSans-webfont.svg#DroidSansRegular') format('svg');
    font-weight: normal;
    font-style: normal;

It is very important to note here that order counts.  There are variations of this CSS syntax, but what I present above is from Ethan Dunham’s excellent article The New Bulletproof @Font-Face Syntax. It is the one that seems to be simplest and most bulletproof, even beating Paul Irish’s Bulletproof @font-face syntax, which is what I recommended in a previous iteration of this article.

The ?#iefix after the EOT font is there to avoid a bug in older versions of IE. See The New Bulletproof @Font-Face Syntax for more details. Also note the #DroidSansRegular in the svg url. If you open up an SVG font in a test editor, you’ll see something like this:

<?xml version="1.0" standalone="no"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd" >
<svg xmlns="http://www.w3.org/2000/svg">
This is a custom SVG webfont generated by Font Squirrel.
Copyright   : Digitized data copyright  2007 Google Corporation
Foundry     : Ascender Corporation
Foundry URL : http://www.ascendercorp.com
<font id="DroidSansRegular" horiz-adv-x="1128" >

The string after the # in the svg @font-face declaration (in this case #DroidSansRegular corresponds to the id in the svg file’s font tag.

After you declare the font, you can use it inside any of your selectors as you would use any other font:

body {
     font-family: "Droid Sans", "Arial", "Helvetica", sans-serif;

Note that it is still necessary to use alternative fonts – this is so that user agents that don’t support @font-face will still show an appropriate, similar looking font.

Some font families are contained in not just one file.  For example, Droid Sand has a bold variant that is stored in a separate TrueType file (the .eot file used by Internet Explorer in the above example contains both the regular and bold variants).  The bold variant of Droid Sans can be declared correctly in your stylesheet like this:

@font-face {
    font-family: 'Droid Sans';
    src: url('DroidSans-webfont.eot?#iefix') format('embedded-opentype'),
         url('DroidSans-webfont.woff') format('woff'),
         url('DroidSans-webfont.ttf') format('truetype'),
         url('DroidSans-webfont.svg#DroidSansRegular') format('svg');
    font-weight: normal;
    font-style: normal;


@font-face {
    font-family: 'Droid Sans Bold';
    src: url('DroidSans-Bold-webfont.eot?#iefix') format('embedded-opentype'),
         url('DroidSans-Bold-webfont.woff') format('woff'),
         url('DroidSans-Bold-webfont.ttf') format('truetype'),
         url('DroidSans-Bold-webfont.svg#DroidSansBold') format('svg');
    font-weight: normal;
    font-style: normal;


It will be necessary to use a different font name for the bold variant, but it is the easiest and safest cross-browser way to do this.

Browser Differences

To effectively illustrate how differently browsers render embedded fonts, let’s compare them side by side:

Safari 3


Firefox 3.5


Explorer 6


Title of this blog post Screenshot Detail 1 (Safari) Screenshot Detail 1 (Firefox) Screenshot Detail 1 (IE)
Close-up of the title of this blog post Screenshot Closeup 1a (Safari) Screenshot Closeup 1a (Firefox) Screenshot Closeup 1a (IE)
Subheading from this blog post Screenshot Detail 2 (Safari) Screenshot Detail 2 (Firefox) Screenshot Detail 2 (IE)
Close-up of subheading of this blog post Screenshot Closeup 2 (Safari) Screenshot Closeup 2 (Firefox) Screenshot Closeup 2 (IE)
Close-up of main text of this blog post Screenshot Closeup 3 (Safari) Screenshot Closeup 3 (Firefox) Screenshot Closeup 3 (IE)

As you may see, there are some slight differences in the way that fonts are rendered in the various browsers:

  • Fonts displayed on Safari for Windows (and all browsers on the Mac) in my opinion look the nicest: they are nicely smoothed out and the text is quite easily read at smaller sizes. This is due to the way Apple products render fonts. Apple has always differed in philosophy with Microsoft on how to render fonts, and this difference is quite obvious when testing pages under the Windows operating system.
  • I have found that Internet Explorer does a poor job when displaying fonts converted from OpenType — the glyphs tend to be more jagged and some elements tend to be rendered thinner than they should be. GrauBlau Web, the font used in the headings of  this page, is a converted OpenType font, and you can see this effect in the close-ups above. It does not occur in the main body of the text because Droid Sans is a TrueType font.  There seems to be two reasons for this:
    1. There was information loss when converting GrauBlau Web from OpenType to TrueType.
    2. In Explorer, ClearType renders this font using subpixel anti-aliasing quite more severely than Safari, while other Windows browsers use vanilla anti-aliasing to get the job done. A friend of mine pointed this out, and he said that it’s because ClearType renders TrueType (and, it seems, Embedded Open Type) fonts with subpixel anti-aliasing, but OpenType for some reason isn’t. I don’t know the reasons why, but in this example it looks like it is true – if you look at all of the Explorer closeups,you’ll see the coloured pixels on the edge of all the glyphs, while in Firefox only Droid Sans (which is a TrueType font) has them.
  • Firefox only allows you to embed fonts that come from the same server, unless some special headers appear in the HTTP server response. Also, unlike the other browsers, Firefox users first see the page without the embedded font until the font is loaded completely, at which time the fonts suddenly appear on the page. While it can be argued that this is a good thing (the user can read the content immediately without having to rely on the special font), this may not what a web designer would consider desirable.

There are a few more differences, which are better outlined at the Web Fonts Wiki, which seems to keep its information up-to-date.

How to choose which fonts to use

Not having gone to design school, I cannot claim to be an authority on this subject, but I think it is safe to say that when choosing the fonts that you are going to use, it should be in sync with the mood and message you want readers to experience.  Chuck Green’s article, Type palettes, goes into more depth on this subject, and Michael Martin of Smashing Magazine has a great article about Typographic Design Patterns and Best Practices.  Although both of these articles don’t go into font-embedding specifically, they are still relevant reading.

It took me a long time to decide on the fonts I have used here on my blog. When designing the layout, I was going for two things:

  1. I wanted the body text to be easy to read
  2. I wanted the feeling of the whole blog to be friendly and not look like an academic paper

In the end I decided to use:

  1. GrauBlau Web for the headers because it is narrow (which allows more text on a line), easy on the eyes, and since it is used on headers, the user notices it right away and thinks “Hey, this looks different!”.
  2. Droid Sans for the main text because it was designed to be easy to read even on low resolutions and, in combination with GrauBlau Web, gave the site a nice, pleasant and friendly look.
  3. Droid Sans Mono for the code listings since it was designed to compliment Droid Sans, and, I believe, looks a jillion times better than Courier (which everyone up to now has been forced to use due to a lack of nice looking monospace fonts installed on most computers today).

Again, I didn’t go to design school, but I think for the type of site this is (a blog about web technology), it suits its purpose rather well. I was tempted to choose more ornate fonts, but I didn’t think they suited the content.

Optimizing Font Files

Sometimes you may find that the font files are a little larger than you’d like.  If you open up the font file in FontForge, you may find that a lot of the glyphs inside are not necessary for what you are doing (for example, if your pages are all in English, you might not want all the accented characters that the font contains).  Use FontForge to delete the glyphs you don’t need and regenerate the font – you’ll see that you save quite a few kilobytes, especially in a Unicode font with lots of Japanese and Russian characters included.

Again, because of licensing issues, please ensure that the font license allows you to edit the font in this manner.


What is written here is just the tip of the iceberg.  In the next few years, I expect to be reading several articles on the best way to use embedded fonts, from technical, usability, internationalization and design perspectives. Unfortunately, I also expect to see a lot of MySpace pages looking uglier than ever. Imagine! Now, teenagers around the world can have animated backgrounds, Black Eyed Peas songs playing on load, and have that crazy typewriter font on the main copy.

My God, what have we done ….


Tags: @font-face · ClearType · converting · CSS · FontForge · Fonts · , , , , , , , ,

68 responses so far ↓
  • 1 Stewart McCoy // Sep 28, 2009 at 2:00 pm

    Thanks for the article!

  • 3 syber // Sep 29, 2009 at 10:17 pm

    I have long wanted to know how to embed custom web fonts – this is a fantastic article!

  • 4 admin // Sep 29, 2009 at 10:20 pm

    Thanks for the feedback! It seems it got a lot of attention on Twitter, so thanks to everyone there too!

  • 5 Brian Tao // Oct 2, 2009 at 10:21 am

    Any idea how well this works in HTML e-mail with the various MUA’s and webmail services? It would be great to have proper typeface support, without resorting to PDF links or embedding images.

  • 6 zoltan // Oct 3, 2009 at 12:12 pm

    I believe it may be a bit of a crapshoot, but I have no solid evidence to back me up. Sounds like a good topic for a future blog post.

  • 7 Catherine Azzarello // Oct 4, 2009 at 1:15 am

    Good article! I just wrestled with @font-face this week. For some reason, YanoneKaffeesatz would not work in IE–no matter what. I think something was wrong with the .eot files. I eventually tried Miso. IE liked that. But I still wanted to keep YK and Cuomotype (no .eot version) as my original fonts. So I included Miso.eot and Underwood-Champion-Regular.eot in my font stacks. Now FF, Safari and Opera get fed YK and Cuomotype, IE gets the similar Miso and UCR.

    All good!

  • 8 Catherine Azzarello // Oct 4, 2009 at 1:16 am

    OOps…visit the site…blog.franklyrealty.com to see @font-face in action!

  • 9 login // Oct 4, 2009 at 2:18 am

    I admire you on the willingness to share this info with others – good luck!

  • 12 dlv // Oct 4, 2009 at 1:06 pm

    excellent article !!! a really nice read, thanks for share this !!

  • 17 Mare // Oct 6, 2009 at 9:21 am

    I’m very interested in the way browsers render these fonts. In your table of browser differences Safari fonts look really the best, but my experience is totally different. On my machine (Vista Business x86), Safari 4.03 renders fonts dreadfully (see here: http://img11.imageshack.us/img11/6480/fontssafari.png ), while Firefox (3.7 alpha, but it’s the same on 3.5) renders them very good (see here: http://img7.imageshack.us/img7/5002/fontsff3.png ).

  • 18 David Duggins // Oct 6, 2009 at 10:02 am

    Wow. Totally awesome article. I have long been a font-fanatic. I feel kinda ashamed that I have not been using this. It is something I plan on correcting immediately!!

  • 19 zoltan // Oct 6, 2009 at 10:36 am

    Hey Mare.

    Thanks for the screenshots. That is quite interesting. It looks as though your screenshot of Firefox is pixel-perfect-identical to what I see, but your screenshot of Safari is quite different. In Safari, there is an option in the Preferences on how to render fonts (under the Appearance tab). What is yours set to?

  • 20 Steve Souders // Oct 6, 2009 at 12:04 pm

    How does this impact performance? Do font file downloads happen in parallel with other resources? Are they downloaded at declaration (“@font-face {}”), when used in a style (“body { font-family: }”), or when a DOM element uses a style that uses the font? Do they follow the normal HTTP caching behavior? Can they be gzipped?

    A ton of questions to answer before you should adopt custom fonts.

  • 21 zoltan // Oct 6, 2009 at 1:14 pm

    Steve: these are very good questions. A couple of things I have noted:

    - As mentioned before Firefox (and, from what I have seen, Opera as well) load the fonts after the document is loaded. You will see the document first without the fonts, and then as the fonts are loaded in, the font is inserted according to the style-sheet

    - It looks as if Safari and IE render the pages after the fonts are loaded. However, I haven’t done any real testing on that yet

    If anyone else can comment on these issues, I’d love to see replies to this. If not, I think they would all be excellent points to address in a follow-up article. :-)

  • 22 Paul Irish // Oct 6, 2009 at 1:57 pm

    Garrick at Kernest tipped me off that IE is very aggressive on download the font data. I’ve done some of my own testing, too:

    IE will download the .eot file immediately when it encounters the @font-face declaration.
    No browsers download the font file when they find a css rule that references the @font-face font.
    Gecko, Webkit, and Opera all wait until they encounter HTML that matches a CSS rule with a fontstack including the @font-face font.

    You can test this out on my load testing page here:

  • 23 zoltan // Oct 6, 2009 at 6:04 pm

    This is great info. Thank you Paul. My after assumption was slightly incorrect – I was just going by the visual evidence of the font replacement happening after the page was rendered.

    I bet you any money someone is going to find a method/series of hacks that will allow developers to control when this download occurs. I look forward to it.

    Anyone reading this want to take that on? :-)

  • 24 Matt Sandy // Oct 6, 2009 at 8:38 pm

    I will definitely give this a try for the new layout I am working on; right now I am using flir.

  • 25 dougwig // Oct 7, 2009 at 12:43 pm

    Very nice, this is the first web-font article I’ve seen where the information was presented so clearly that I had to give web-fonts a go myself.

    Note: I think you’ll want the .ttf and .eot files on a CDN so that downloads are optimized.

  • 27 Paul Irish // Oct 7, 2009 at 6:32 pm

    @Zoltan, here’s some code to accelerate the font download in other browsers.
    (html tags intentionally borked)

        /* chunk will load immediately in IE at this declaration*/
        @font-face {
        	font-family: 'ChunkFive Regular';
        	src: url('fonts/Chunkfive.eot');
        	src: local('ChunkFive Regular'), local('ChunkFive-Regular'), url('fonts/Chunkfive.otf') format('opentype');
        .chunk { font-family:'ChunkFive Regular'}
        // we're still in the head but we're going to get that font to download now.
        var dl = document.createElement('fontdl');
        dl.innerHTML = 'download the font asap';
        dl.className = 'chunk';
        dl.style.cssText = 'position:absolute; visibility:hidden'
        // it's still off-DOM so it doesn't download yet
        // document.body doesnt exist yet so we'll add it onto the HTML tag
        // font download initiated now.
        // let's clean up after ourselves (opera needs a timeout > 0)
        setTimeout(function(){dl.parentNode && dl.parentNode.removeChild(dl)},100)  

    I have a test page with this rolling here:

    I’ll write this up proper very very soon. :)

  • 29 Nacho // Oct 7, 2009 at 7:28 pm

    Nice article. Thank you :)

  • 31 Mare // Oct 8, 2009 at 7:50 am

    Ahhhh! Muuuch better! The setting in Safari was set to “Windows default”, and now I set it to “Light”. But why such a bad default? If I were Apple, and created a good rendering engine, I’d set that as a default. I don’t use Safari much (just to check some designs – I’m a QA person), and would have hard time finding out that this browser CAN display fonts better, and afterwards finding the correct setting…

  • 33 Steve Souders // Oct 8, 2009 at 2:50 pm

    Paul did a great write-up on @font-face performance: http://paulirish.com/2009/fighting-the-font-face-fout/

  • 34 Neil Osman // Oct 8, 2009 at 8:01 pm

    Thanks, well written

  • 38 Emma Smyth // Oct 12, 2009 at 11:57 am

    Thanks for the post and the screenshots, they always help, I really liked this article, cheers

  • 42 Marcel // Oct 16, 2009 at 1:33 pm


    You’re on Windows aren’t you? Safari on Windows gives you the choice on how to render Fonts, maybe you’ve choosen the Windows like way… see Prefs!

  • 43 kazi mohammad ekram // Oct 18, 2009 at 4:02 am

    thanks for the article. it helps lot. before i was using SIFR to embed any font in my website. which is using Flash. But it takes some time to load. Hope your article will help me lot.

  • 51 Vanrick // Nov 5, 2009 at 3:15 am

    Wow ! So interesting – Great Article thanks for taking the time to post this.

    Im a new Web Designer & want to try make this.

  • 52 Lavelle // Nov 5, 2009 at 6:02 pm

    Thanks for putting together this post, in particularly going through the various options available and how to actually implement each one. Cheers!

  • 60 Web Designer // Apr 6, 2010 at 3:59 pm

    Good post I always struggle with web fonts as I want to use nice typography but with the limited fonts available find it a nightmare!
    With the issues in different browsers I can envisage some difficulties with email HTML and spam settings. I have been playing around with flash replacement fonts but the usability and issues with load time has meant I have had to limit this.

  • 66 freelance seo manchester // Jan 11, 2011 at 8:07 am

    I have really started to use @font-face now – keep up the good work!

  • 67 Suraj Naik // Feb 6, 2011 at 4:12 am

    Thanks for such a great article. Its really gives an insight in this particular aspect of web design.

Give Feedback

Don't be shy! Give feedback and join the discussion.

Please Note: If you are asking for help using the information on this page or if you are reporting a bug with the code featured here, please include a URL that shows the problem you are experiencing along with the browser/version number/operating system combination where the issue manifests itself. Without this information, I may not be able to respond.

An orange star denotes a required field.