543

I'm looking at the MDC page for the @font-face CSS rule, but I don't get one thing. I have separate files for bold, italic and bold + italic. How can I embed all three files in one @font-face rule? For example, if I have:

@font-face {
    font-family: "DejaVu Sans";
    src: url("./fonts/DejaVuSans.ttf") format("ttf");
}
strong {
    font-family: "DejaVu Sans";
    font-weight: bold;
}

The browser will not know which font to be used for bold (because that file is DejaVuSansBold.ttf), so it will default to something I probably don't want. How can I tell the browser all the different variants I have for a certain font?

Failed Scientist
  • 1,977
  • 3
  • 29
  • 48
Felix
  • 88,392
  • 43
  • 149
  • 167
  • As an extension to the question if we use these fonts in WYSIWYG editors like TinyMCE , do we still need the Bold Italics ? Despite the TinyMCE having buttongs to do Bold Italics ? My guess answer is a YES - because interally they look for these files ? – Nishant Nov 19 '13 at 14:40
  • possible duplicate of [How to merge fonts?](http://stackoverflow.com/questions/14603600/how-to-merge-fonts) – user2284570 Oct 26 '14 at 20:58

9 Answers9

883

The solution seems to be to add multiple @font-face rules, for example:

@font-face {
    font-family: "DejaVu Sans";
    src: url("fonts/DejaVuSans.ttf");
}
@font-face {
    font-family: "DejaVu Sans";
    src: url("fonts/DejaVuSans-Bold.ttf");
    font-weight: bold;
}
@font-face {
    font-family: "DejaVu Sans";
    src: url("fonts/DejaVuSans-Oblique.ttf");
    font-style: italic, oblique;
}
@font-face {
    font-family: "DejaVu Sans";
    src: url("fonts/DejaVuSans-BoldOblique.ttf");
    font-weight: bold;
    font-style: italic, oblique;
}

By the way, it would seem Google Chrome doesn't know about the format("ttf") argument, so you might want to skip that.

(This answer was correct for the CSS 2 specification. CSS3 only allows for one font-style rather than a comma-separated list.)

Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
Felix
  • 88,392
  • 43
  • 149
  • 167
  • @nvl according to [css3 spec](http://www.w3.org/TR/css3-fonts/#src), we should use `format()` to specify the format of the font. However, now I see that maybe I should've used `format("truetype")`, maybe Chrome would be able to handle that. – Felix Mar 13 '10 at 22:23
  • 157
    The order is important, the bold/italic style must come last. – The Who Jun 11 '10 at 12:40
  • 8
    Worth noting that this doesn't work in IE8 (and below), even if you use an EOT. IE will download the alternate typeface, but it won't use it, instead it will fake-bold/italic the regular typeface. Also, Chrome 11 seems to fail render a typeface that's both bold and italic – JaffaTheCake May 05 '11 at 18:46
  • 2
    This example works perfect for fonts that do have a separate TTF file for bold and italic. But what if the whole font is in one .ttf file and you want to use bold, how does that work? –  Jul 09 '11 at 11:42
  • 2
    [This article](https://www.fontspring.com/support/troubleshooting/style-linking) does a great job explaining why this works. Key excerpt: "Notice that the font-family property is the same name for all four fonts. Also, the font-style and font-weight match what the font is. Note: The normal weight must be at the top of the list! We haven’t found that the order after that matters." – JD Smith Jan 15 '13 at 20:30
  • * Style Linking is great way, but make sure to aware that IE will ignore it (no italic or bold at all), and also Opera will be messed up, read this [Style Linking](http://nicewebtype.com/notes/2009/10/30/how-to-use-css-font-face/) * PS : [Bulletproof Fontface from Paul Irish](http://www.paulirish.com/2009/bulletproof-font-face-implementation-syntax/) – phnah Jul 03 '13 at 03:40
  • IE works fine with that syntax. Opera makes regular fonts italic, but understands bold fonts. –  Sep 18 '13 at 11:30
  • 17
    I was having trouble with this snipped on the embedded browser Android 4.4. Ended changing `font-style: italic, oblique;` to just `font-style: italic;` seemed to fix everything. – Xavi Jan 10 '14 at 22:36
  • You might want to have a look at [Bartłomiej Mucha's answer](http://stackoverflow.com/a/12586279/1879895), as it's the correct one ^.^ – Bill Feb 26 '14 at 15:14
  • Does this also work with and does that get mapped to the right font-style , font-weight respectively ? We use WYSIWG editor and we wan't get these font's with Italic and Bold . – Nishant Sep 19 '14 at 11:25
  • you'll need the woff (and potentially) woff2 formats for some browsers. Eot is required for older versions of IE but not many places serve those anymore. (Burn IE!!) If you grab from google fonts you can paste the URL into the browser and it will actually show u a link to both woff and woff2 – dannio Aug 06 '15 at 08:24
  • 1
    @Xavi, that was super helpful. Everything was coming italics for us until we did that. @Felix, do you know if we really need `oblique` in the answer. – Anupam Dec 09 '19 at 08:50
  • What is the `oblique` for? I had to remove it, because everything was in italics! – Rodrigo Apr 25 '20 at 18:27
  • 1
    This answer will now make all fonts appear italic, please see Josiah's answer below for the updated way to do this properly. – JShorthouse May 31 '21 at 14:24
  • The order _didn't_ matter in Safari and Chrome in 2022. I was using [Sass `@each`](https://sass-lang.com/documentation/at-rules/control/each) to generate my font-face declarations. However, my issue was that I had included quotes around "normal", "italic", etc. in the list elements being iterated over by `@each`, such that the generated CSS said `font-style: "italic"` instead of `font-style: italic`. Removing the quotes fixed the issue. – nishanthshanmugham Jun 22 '22 at 12:52
86

As of CSS3, the spec has changed, allowing for only a single font-style. A comma-separated list (per CSS2) will be treated as if it were normal and override any earlier (default) entry. This will make fonts defined in this way appear italic permanently.

@font-face {
    font-family: "DejaVu Sans";
    src: url("fonts/DejaVuSans.ttf");
}
@font-face {
    font-family: "DejaVu Sans";
    src: url("fonts/DejaVuSans-Bold.ttf");
    font-weight: bold;
}
@font-face {
    font-family: "DejaVu Sans";
    src: url("fonts/DejaVuSans-Oblique.ttf");
    font-style: italic;
}
@font-face {
    font-family: "DejaVu Sans";
    src: url("fonts/DejaVuSans-BoldOblique.ttf");
    font-weight: bold;
    font-style: italic;
}
@font-face {
    font-family: "DejaVu Sans";
    src: url("fonts/DejaVuSans-Oblique.ttf");
    font-style: oblique;
}
@font-face {
    font-family: "DejaVu Sans";
    src: url("fonts/DejaVuSans-BoldOblique.ttf");
    font-weight: bold;
    font-style: oblique;
}

In most cases, italic will probably be sufficient and oblique rules won't be necessary if you take care to define whichever you will use and stick to it.

Josiah
  • 3,008
  • 1
  • 34
  • 45
  • I believe the third and fourth fonts are named wrong, they should have "Italic" instead of "Oblique". – Nathan Merrill Aug 01 '15 at 03:33
  • 5
    @NathanMerrill as by OP: `I have separate files for bold, italic and bold + italic` - so there's three different files. This answer corrects the accepted one in that `font-style: italic, oblique;` is no longer valid, but also that answer used the same file for italic and oblique. Still, worth pointing out that the file is shared in two cases. – Silly Freak Aug 01 '15 at 11:05
31

To have font variation working correctly, I had to reverse the order of @font-face in CSS.

@font-face {
    font-family: "DejaVuMono";
    src: url("styles/DejaVuSansMono-BoldOblique.ttf");
    font-weight: bold;
    font-style: italic, oblique;
}   
@font-face {
    font-family: "DejaVuMono";
    src: url("styles/DejaVuSansMono-Oblique.ttf");
    font-style: italic, oblique;
}
@font-face {
    font-family: "DejaVuMono";
    src: url("styles/DejaVuSansMono-Bold.ttf");
    font-weight: bold;
}
 @font-face {
    font-family: "DejaVuMono";
    src: url("styles/DejaVuSansMono.ttf");
}
Cedric Simon
  • 4,571
  • 4
  • 40
  • 52
19

nowadays,2017-12-17. I don't find any description about Font-property-order‘s necessity in spec. And I test in chrome always works whatever the order is.

@font-face {
  font-family: 'Font Awesome 5 Free';
  font-weight: 900;
  src: url('#{$fa-font-path}/fa-solid-900.eot');
  src: url('#{$fa-font-path}/fa-solid-900.eot?#iefix') format('embedded-opentype'),
  url('#{$fa-font-path}/fa-solid-900.woff2') format('woff2'),
  url('#{$fa-font-path}/fa-solid-900.woff') format('woff'),
  url('#{$fa-font-path}/fa-solid-900.ttf') format('truetype'),
  url('#{$fa-font-path}/fa-solid-900.svg#fontawesome') format('svg');
}

@font-face {
  font-family: 'Font Awesome 5 Free';
  font-weight: 400;
  src: url('#{$fa-font-path}/fa-regular-400.eot');
  src: url('#{$fa-font-path}/fa-regular-400.eot?#iefix') format('embedded-opentype'),
  url('#{$fa-font-path}/fa-regular-400.woff2') format('woff2'),
  url('#{$fa-font-path}/fa-regular-400.woff') format('woff'),
  url('#{$fa-font-path}/fa-regular-400.ttf') format('truetype'),
  url('#{$fa-font-path}/fa-regular-400.svg#fontawesome') format('svg');
}
xlaoyu.Lee
  • 333
  • 2
  • 9
15

If you are using Google fonts I would suggest the following.

If you want the fonts to run from your localhost or server you need to download the files.

Instead of downloading the ttf packages in the download links, use the live link they provide, for example:

http://fonts.googleapis.com/css?family=Source+Sans+Pro:300,400,600,300italic,400italic,600italic

Paste the URL in your browser and you should get a font-face declaration similar to the first answer.

Open the URLs provided, download and rename the files.

Stick the updated font-face declarations with relative paths to the woff files in your CSS, and you are done.

Peter Mortensen
  • 30,738
  • 21
  • 105
  • 131
Dieter Gribnitz
  • 5,062
  • 2
  • 41
  • 38
6
/*
# +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
# dejavu sans
# +++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
*/
/*default version*/
@font-face {
    font-family: 'DejaVu Sans';
    src: url('dejavu/DejaVuSans.ttf'); /* IE9 Compat Modes */
    src: 
        local('DejaVu Sans'),
        local('DejaVu-Sans'), /* Duplicated name with hyphen */
        url('dejavu/DejaVuSans.ttf') 
        format('truetype');
}
/*bold version*/
@font-face {
    font-family: 'DejaVu Sans';
    src: url('dejavu/DejaVuSans-Bold.ttf'); 
    src: 
        local('DejaVu Sans'),
        local('DejaVu-Sans'),
        url('dejavu/DejaVuSans-Bold.ttf') 
        format('truetype');
    font-weight: bold;
}
/*italic version*/
@font-face {
    font-family: 'DejaVu Sans';
    src: url('dejavu/DejaVuSans-Oblique.ttf'); 
    src: 
        local('DejaVu Sans'),
        local('DejaVu-Sans'),
        url('dejavu/DejaVuSans-Oblique.ttf') 
        format('truetype');
    font-style: italic;
}
/*bold italic version*/
@font-face {
    font-family: 'DejaVu Sans';
    src: url('dejavu/DejaVuSans-BoldOblique.ttf'); 
    src: 
        local('DejaVu Sans'),
        local('DejaVu-Sans'),
        url('dejavu/DejaVuSans-BoldOblique.ttf') 
        format('truetype');
    font-weight: bold;
    font-style: italic;
}
Jerry T
  • 1,541
  • 1
  • 19
  • 17
4

I added a custom font like this to my styles.less

@font-face {
    font-family: EuclidSquare;
    src: url('/fonts/EuclidSquare-LightItalic.woff2') format('woff2'),
        url('/fonts/EuclidSquare-LightItalic.woff') format('woff'),
        url('/fonts/EuclidSquare-LightItalic.otf') format('opentype');
    font-weight: 300;
    font-style: italic, oblique;
}
@font-face {
    font-family: EuclidSquare;
    src: url('/fonts/EuclidSquare-Light.woff2') format('woff2'),
        url('/fonts/EuclidSquare-Light.woff') format('woff'),
        url('/fonts/EuclidSquare-Light.otf') format('opentype');
    font-weight: 300;
}
@font-face {
    font-family: EuclidSquare;
    src: url('/fonts/EuclidSquare-RegularItalic.woff2') format('woff2'),
        url('/fonts/EuclidSquare-RegularItalic.woff') format('woff'),
        url('/fonts/EuclidSquare-RegularItalic.otf') format('opentype');
    font-style: italic, oblique;
}
@font-face {
    font-family: EuclidSquare;
    src: url('/fonts/EuclidSquare-Regular.woff2') format('woff2'),
        url('/fonts/EuclidSquare-Regular.woff') format('woff'),
        url('/fonts/EuclidSquare-Regular.otf') format('opentype');
}
@font-face {
    font-family: EuclidSquare;
    src: url('/fonts/EuclidSquare-MediumItalic.woff2') format('woff2'),
        url('/fonts/EuclidSquare-MediumItalic.woff') format('woff'),
        url('/fonts/EuclidSquare-MediumItalic.otf') format('opentype');
    font-weight: 500;
    font-style: italic, oblique;
}
@font-face {
    font-family: EuclidSquare;
    src: url('/fonts/EuclidSquare-Medium.woff2') format('woff2'),
        url('/fonts/EuclidSquare-Medium.woff') format('woff'),
        url('/fonts/EuclidSquare-Medium.otf') format('opentype');
    font-weight: 500;
}
@font-face {
    font-family: EuclidSquare;
    src: url('/fonts/EuclidSquare-SemiboldItalic.woff2') format('woff2'),
        url('/fonts/EuclidSquare-SemiboldItalic.woff') format('woff'),
        url('/fonts/EuclidSquare-SemiboldItalic.otf') format('opentype');
    font-weight: 600;
    font-style: italic, oblique;
}
@font-face {
    font-family: EuclidSquare;
    src: url('/fonts/EuclidSquare-Semibold.woff2') format('woff2'),
        url('/fonts/EuclidSquare-Semibold.woff') format('woff'),
        url('/fonts/EuclidSquare-Semibold.otf') format('opentype');
    font-weight: 600;
}
@font-face {
    font-family: EuclidSquare;
    src: url('/fonts/EuclidSquare-BoldItalic.woff2') format('woff2'),
        url('/fonts/EuclidSquare-BoldItalic.woff') format('woff'),
        url('/fonts/EuclidSquare-BoldItalic.otf') format('opentype');
    font-weight: bold;
    font-style: italic, oblique;
}
@font-face {
    font-family: EuclidSquare;
    src: url('/fonts/EuclidSquare-Bold.woff2') format('woff2'),
        url('/fonts/EuclidSquare-Bold.woff') format('woff'),
        url('/fonts/EuclidSquare-Bold.otf') format('opentype');
    font-weight: bold;
}

body {
    font-family: EuclidSquare, Lato, sans-serif;
}
Abdul Malik
  • 541
  • 4
  • 16
0

For Create React App see my other SO answer here

  1. If you choose to link the css file directly to your public/index.html:
@font-face {
  font-family: "FontName"; <---
  font-style: normal; <---
  font-weight: normal;
  src: url("path-to-assets/fonts/FontName.ttf") format("truetype");
}
@font-face {
  font-family: "FontName"; <---
  font-style: italic; <---
  font-weight: normal;
  src: url("path-to-assets/fonts/FontName-Italic.ttf") format("truetype");
}
  1. If you choose to link the css file via Js for bundling:
@font-face {
  font-family: "FontName"; <---
  font-style: normal; <---
  font-weight: normal; /* normal | 300 | 400 | 600 | bold | etc */
  src: url("path-to-assets/fonts/FontName.ttf") format("truetype");
}
@font-face {
  font-family: "FontNameItalic"; <---
  font-style: normal; <----
  font-weight: normal; /* normal | 300 | 400 | 600 | bold | etc */
  src: url("path-to-assets/fonts/FontName-Italic.ttf") format("truetype");
}
piouson
  • 3,328
  • 3
  • 29
  • 29
0

If you are using a Google Font, I suggest using @import url("@import url('https://fonts.googleapis.com/css2?family=Saira+Condensed:wght@900&display=swap');") and specifying font-family: 'Saira Condensed', sans-serif; as the CSS Rule.

Tux
  • 51
  • 1
  • 2