分類: 網頁開發

CSS 網頁字型 @font-face 使用教學與範例

這裡介紹 CSS 的 @font-face 使用方式與範例,讓網頁設計者可以在網頁的字型使用上更有彈性。

@font-face 這個 CSS 的 at-rule 可以讓網頁設計者可以使用網路上的字型檔來顯示網頁中的文字,甚至還可以讓設計者使用自己所提供的字型檔,讓網頁的設計更具有彈性,在選擇字型時就可以不需要考慮一般的電腦是否有安裝,凡是放在網路上的任何字型檔都可以使用。而 @font-face 除了在 CSS 的頂層設定上使用之外,在任何 CSS 條件群組(conditional-group)at-rule 中也可以使用。


@font-face 的基本使用方式如下:
@font-face {
  font-family: Gentium;
  src: url(http://example.com/fonts/Gentium.woff);
}

p { font-family: Gentium, serif; }

這裡我們指定了 Gentium 這個字型的字型檔案網址為 http://example.com/fonts/Gentium.woff,並設定讓所有網頁中的 <p> 都使用 Gentium 來顯示,而如果碰到不支援 @font-face 的瀏覽器,則會使用第二順位的 serif 這個一般的字型來顯示。

這是另外一個範例:

@font-face {
  font-family: MyHelvetica;
  src: local("Helvetica Neue Bold"),
    local("HelveticaNeue-Bold"),
    url(MgOpenModernaBold.ttf);
  font-weight: bold;
}

這裡定義一個名稱為 MyHelvetica 的粗體字,而可使用的字型位置依序為使用者電腦中的 Helvetica Neue BoldHelveticaNeue-Bold 兩個字型名稱,如果使用者電腦中找不到這些字型,則從網頁上下載 MgOpenModernaBold.ttf 這個字型檔。

以下是 @font-face 中各種屬性的詳細介紹。

Descriptors

以下是在 @font-face 這個 at-rule 中可以使用的 descriptor 標籤,其中 font-familysrc 這兩個是必要的 descriptor,其餘的則是選擇性的。

font-family

指定字型名稱,這個名稱會把原本在字型檔中的名稱覆蓋掉,在 CSS 中指定字型時都會以這個名稱為準,這樣的方式可以讓設計者自行定義名稱的命名方式,而不會受到原本字型名稱的干擾。

src

src 可用來指定字型檔案的位置,設計者可以一次指定多個字型檔案位置,依照優先順序並以逗點分隔的方式一一指定,當瀏覽器需要載入字型檔的時候,就會依序從這裡所指定的位置嘗試進行載入,如果碰到不支援或無法連接的位置,就會自動跳過並嘗試下一個,直到取得正確的字型檔為止。這裡可以使用的指定方式有兩種,一個是使用 url() 指定字型檔案的 URL 網址,另一種則是使用 local() 配合字型名稱來指定使用者電腦中所安裝的字型。

在指定字型的 URL 網址的規則跟一般 CSS 設定 URL 的慣例相同,可以使用相對位置或絕對位置,如果使用相對位置的話,則其位置的參考點會是包含這個 @font-face 的 CSS 設定檔所在的目錄。

src: url(fonts/simple.woff);   /* 相對於 CSS 設定檔的位置 */
src: url(/fonts/simple.woff);  /* 絕對位置 */

由於 SVG 格式的檔案可以包含多個字型,如果是使用 SVG 格式的字型檔,則在 URL 中就必須要指定出要使用 SVG 檔案中的哪一個字型,例如:

src: url(fonts.svg#simple);    /* 使用 SVG 檔案中 id 為 'simple' 的字型 */

在一個 @font-face 中使用類似 SVG 這樣可以包含多個字型的檔案時,一次只能使用其中一個字型,而要判斷使用者所指定的字型是哪一個,則是依據字型檔案中的 fragment identifier 來判斷,如果某些字型檔案沒有 fragment identifier,則可以使用字型的順序來指定,例如 font-collection#1 就是指 font-collection 中第一個字型,以此類推。如果設計者沒有指定要使用的字型,則預設會直接使用檔案中的第一個字型。

在使用 URL 網址指定字型檔時,除了必要的 url() 之外,還可以再加上一個選擇性的 format() 來告訴瀏覽器這個字型檔案的格式為何,如果瀏覽器發現它不支援該字型格式,就可以直接跳過這個字型,省去下載字型檔案的時間,如果沒有指定 format() 的話,瀏覽器就只能將字型下載之後才能進行判斷是否要使用該字型檔案。

/* 如果 WOFF 格式不支援,則改用 OpenType 格式 */
@font-face {
  font-family: bodytext;
  src: url(ideal-sans-serif.woff) format("woff"),
       url(basic-sans-serif.ttf) format("opentype");
}

下表是各種字型格式與 format() 指定方式的對應。

字型格式 附檔名 format() 指定方式
WOFF(Web Open Font Format) .woff "woff"
TrueType .ttf "truetype"
OpenType .ttf 或 .otf "opentype"
Embedded OpenType .eot "embedded-opentype"
SVG Font .svg 或 .svgz "svg"

由於一些歷史發展上的因素,TrueType 與 OpenType 兩種字型格式有重疊的部分,"truetype""opentype" 這兩個格式在實務上應該被視為同一種字型,也就是說指定為 "opentype" 的字型檔,並不一定會包含 Postscript CFF 或 OpenType 相關的資訊。

設計者也可以讓瀏覽器先嘗試從使用者的電腦中載入字型,如果使用者電腦中沒有安裝該字型,再從網路上下載,像這樣的狀況就可以使用 local() 配合使用者電腦中的字型名稱來指定要使用的字型,例如:

/* Gentium 字型 */
@font-face {
  font-family: MyGentium;
  src: local(Gentium),    /* 指定使用者電腦中的 Gentium 字型 */
       url(Gentium.woff); /* 如果使用者電腦中找不到,則從網路下載 */
}

local() 中指定字型名稱時,也可以將字型的名稱使用引號包起來,如果沒有使用引號的話,字型的名稱就會被自動轉換為以單一空白字元連接的字串。

對於 OpenType 與 TrueType 的字型而言,local() 中的名稱會用來比對 Postscript 名稱或是字形的完整名稱,至於會使用哪一種則會因為不同的平台或字型而有不同,所以設計者如果要讓自己的網頁字型在各種平台都可以顯示,最好將兩種名稱都指定上去:

/* Gentium 字型 */
@font-face {
  font-family: MyGentium;
  src: local(Gentium Bold),    /* 字型的完整名稱 */
       local(Gentium-Bold),    /* Postscript 名稱 */
       url(GentiumBold.woff);  /* 從網路下載 */
}

這是使用使用者電腦的字型與網路上 SVG 字型檔的例子:

@font-face {
  font-family: Headline;
  src: local(Futura-Medium),
       url(fonts.svg#MyGeometricModern) format("svg");
}

如果要使用多個字型位置,要把所有的位置寫在一個 src 屬性中,不可以分成多個,否則後來的 src 會將前面的設定覆蓋掉:

@font-face {
  font-family: MainText;
  src: url(gentium.eot);                     /* 適用於舊的瀏覽器 */
  src: local("Gentium"), url(gentium.woff);  /* 覆蓋掉上面的 src 設定 */
}

這裡的 gentium.eot 這個字型設定會被覆蓋掉,等於沒有這行設定。

font-style

指定字型的 style 設定值。可用的選項有 normalitalicoblique,預設為 normal

font-weight

指定字型的 weight 值。可用的選項有 normalbold100200300400500600700800900,預設為 normal

font-stretch

指定字型的 stretch 設定值。可用的選項有 normalultra-condensedextra-condensedcondensedsemi-condensedsemi-expandedexpandedextra-expandedultra-expanded,預設為 normal

font-stylefont-weightfont-stretch 這三個屬性是用來定義該 @font-face 的字型特性,讓瀏覽器在解析 CSS 樣式的字型時,可以透過這些資訊比對特定的字型,讓瀏覽器可以選擇只下載那些真正有在網頁上被使用的字型檔。而在這些 descriptors 中可以使用的選項裡面,除了一些相對性的選項無法使用之外(如 bolderlighter),其餘的都跟一般 CSS 字型屬性所使用的選項相同。

unicode-range

指定 @font-face 所定義的字型中,所涵蓋的萬國碼(unicode)範圍,這個資訊可提供給瀏覽器作為參考,來決定是否要下載該字型檔。

萬國碼的範圍表示方式是以 U+u+ 開頭,而範圍的指定則可使用下面三種方式:

單一 codepoint(U+416
使用 1 至 6 位數的十六進位數字,指定一個 Unicode 的 codepoint。
範圍區間(U+400-4ff
使用連字線(-)與兩個 Unicode 的 codepoints 來指定一段範圍區間。
萬用字元(U+4??
使用萬用字元(?)指定 codepoint 範圍。這裡的 ? 代表任何一個十六進位的數字。

設計者可以使用逗點分隔的方式,結合多個範圍表示方式,例如:

@font-face {
  font-family: BBCBengali;
  src: url(fonts/BBCBengali.woff) format("woff");
  unicode-range: U+00-FF, U+980-9FF;
}

設計者可以利用多個 @font-face 與不同的萬國碼範圍,將一個字型區分為常用的區段與不常用的區段,讓瀏覽器只需要下載該網頁上需要的部份,這樣的作法可以節省一部分的網路傳輸量。例如:

/* 備用字型 - 大小:4.5MB */
@font-face {
  font-family: DroidSans;
  src: url(DroidSansFallback.woff);
  /* 沒有指定萬國碼區間,預設涵蓋所有的範圍 */
}

/* 日文 - 大小: 1.2MB */
@font-face {
  font-family: DroidSans;
  src: url(DroidSansJapanese.woff);
  unicode-range: U+3000-9FFF, U+ff??;
}

/* 英文字型與一些符號等 - 大小: 190KB */
@font-face {
  font-family: DroidSans;
  src: url(DroidSans.woff);
  unicode-range: U+000-5FF, U+1e00-1fff, U+2000-2300;
}

而其使用方式跟一般的 @font-face 一樣:

body { font-family: DroidSans; }

使用這樣的分開的字型檔時,如果碰到只含有一般英文字的網頁:

<p>This is that</p>

瀏覽器就只需要下載英文字型的部份(DroidSans.woff)。

接著我們來看這個含有特殊符號(⇨)的例子:

<p>This &#x21e8; that<p>

首先瀏覽器會檢查英文字型的萬國碼範圍,因為 U+2000-2300 這個範圍有包含 U+21E8 這個 code point,所以瀏覽器會先下載這個英文字型,但是這個英文字型中實際上並沒有對應這個符號的 glyph,所以瀏覽器接著就檢查日文字型的萬國碼範圍(U+3000-9FFFU+ff??),而這兩個範圍都沒有包含 U+21E8 這個 code point,所以瀏覽器就會直接跳過這個日文字型,不會進行下載的動作。最後因為備用字型沒有指定萬國碼的範圍,預設會包含所有的 code points,所以瀏覽器就會下載 DroidSansFallback.woff 這個字型檔來顯示這個特殊符號。

將不同字型檔與萬國碼範圍的 @font-face 指定成同一個 font-family 的方式,除了可以減低網路的覆載之外,還有另外一個用處,就是建立一個複合式的字型:

@font-face {
  font-family: JapaneseWithGentium;
  src: local(MSMincho);
  /* 沒有指定萬國碼區間,預設涵蓋所有的範圍 */
}

@font-face {
  font-family: JapaneseWithGentium;
  src: url(http://www.example.com/fonts/Gentium.woff);
  unicode-range: U+0-2FF;
}

這樣在使用 JapaneseWithGentium 這個字型時,只要碰到拉丁字母(U+0-2FF)就會自動使用 Gentium.woff 這個字型檔。

font-variant

這個部份跟字型檔案的選擇無關,指示指定字型預設的 variant 設定值而已。

參考資料:W3C

G. T. Wang

個人使用 Linux 經驗長達十餘年,樂於分享各種自由軟體技術與實作文章。

Share
Published by
G. T. Wang
標籤: CSS字型

Recent Posts

光陽 KYMCO GP 125 機車接電發動、更換電瓶記錄

本篇記錄我的光陽 KYMCO ...

2 年 ago

[開箱] YubiKey 5C NFC 實體金鑰

本篇是 YubiKey 5C ...

3 年 ago

[DIY] 自製竹火把

本篇記錄我拿竹子加上過期的苦茶...

3 年 ago