@font-face tip: define font-weight and font-style to keep your CSS simple

When using @font-face to embed a typeface that has several weights and styles, your CSS can become a bit of a mess unless you define those weights and styles in the @font-face declarations. Unfortunately some tutorials and font embedding services do not do this.

Declaring multiple font-family names for the same typeface makes your CSS complex

So let’s take a look at what the problem is. As an example, let’s say you want to use the Droid Serif typeface and host it on your own server. An easy option is to get a ready-to-go @font-face kit from Font Squirrel. The CSS in that kit looks like this (multiple src declarations removed to save space):

@font-face {
    font-family: 'DroidSerifRegular';
    src: url('DroidSerif-Regular-webfont.ttf') format('truetype');
    font-weight: normal;
    font-style: normal;
}
@font-face {
    font-family: 'DroidSerifItalic';
    src: url('DroidSerif-Italic-webfont.ttf') format('truetype');
    font-weight: normal;
    font-style: normal;
}
@font-face {
    font-family: 'DroidSerifBold';
    src: url('DroidSerif-Bold-webfont.ttf') format('truetype');
    font-weight: normal;
    font-style: normal;
}
@font-face {
    font-family: 'DroidSerifBoldItalic';
    src: url('DroidSerif-BoldItalic-webfont.ttf') format('truetype');
    font-weight: normal;
    font-style: normal;
}

With the above CSS a separate font name is declared for each font weight and style, forcing you to write CSS like this:

body { font-family:"DroidSerifRegular", Georgia, serif; }
h1 {
    font-family:"DroidSerifBold", Georgia, serif;
    font-weight:normal;
}
em {
    font-family:"DroidSerifItalic", Georgia, serif;
    font-weight:normal;
    font-style:normal;
}
strong em {
    font-family:"DroidSerifBoldItalic", Georgia, serif;
    font-weight:normal;
    font-style:normal;
}

Each time you need a different style you basically have to reset the default styling to normal to stop browsers from applying their own fake bold or italic style on top of the downloaded font. Doing this not only makes your CSS unwieldy – it also removes bold and italics in browsers that do not support @font-face or in the case of the font files not being downloaded properly.

Using the same font-family name keeps things simple and provides a fallback

By changing the font-weight and font-style declarations of each @font-face rule to match each font’s properties, and using the same font-family name for each rule, we will no longer need to be overly specific in our CSS:

@font-face {
    font-family: 'DroidSerif';
    src: url('DroidSerif-Regular-webfont.ttf') format('truetype');
    font-weight: normal;
    font-style: normal;
}
@font-face {
    font-family: 'DroidSerif';
    src: url('DroidSerif-Italic-webfont.ttf') format('truetype');
    font-weight: normal;
    font-style: italic;
}
@font-face {
    font-family: 'DroidSerif';
    src: url('DroidSerif-Bold-webfont.ttf') format('truetype');
    font-weight: bold;
    font-style: normal;
}
@font-face {
    font-family: 'DroidSerif';
    src: url('DroidSerif-BoldItalic-webfont.ttf') format('truetype');
    font-weight: bold;
    font-style: italic;
}

You can now specify font-weight:bold or font-style:italic to any element you like without having to specify the font-family or overriding font-weight and font-style.

body { font-family:"DroidSerif", Georgia, serif; }
h1 { font-weight:bold; }
em { font-style:italic; }
strong em {
    font-weight:bold;
    font-style:italic;
}

An additional benefit is that in the case of @font-face not being supported or the font files not being downloaded, browsers will fall back to faking it.

It should be noted that using the same font-family name like this may crash Safari for older versions of iOS (older than version 4.2, if I am correct) due to a bug. There are some workarounds:

  • Don’t link to SVG versions of the fonts. Obviously this way older iOS devices (and old versions of Chrome and Opera) won’t render your nice fonts, but Safari for iOS won’t crash either.
  • Use browser sniffing (eugh) to avoid sending SVG fonts to old versions Safari for iOS.
  • Define separate font-family names for each weight and style and accept the drawbacks to doing that (as described above).

My personal preference is to drop SVG fonts. There are other formats that are supported by the most recent versions of all major browsers (including Safari for iOS), so only a small (and shrinking) subset of users will be missing out on the downloadable fonts. Keeping the CSS maintainable and allowing for a fallback for browsers that do not support @font-face is more important to me. YMMV.

Posted on December 22, 2010 in CSS, Typography

Comments are disabled for this post (read why), but if you have spotted an error or have additional info that you think should be in this post, feel free to contact me.