Uwaga! Trwają prace nad nową wersją serwisu. Mogą występować przejściowe problemy z jego funkcjonowaniem. Przepraszam za niedogodności!

⛔ Masz dość walki z kodem i samym sobą? 🔄 Czas na RESET! ✅ Dołącz do bezpłatnego wyzwania!

Jak dołączyć własne fonty – @font-face i font-family w CSS

Zapisuj "font family" w plikach projektu!

Na początku nauki HTML-a i CSS-a korzystamy z fontów dostępnych w naszym systemie. Wkrótce jednak nabieramy ochoty na czcionki bardziej finezyjne niż zwykły Arial czy Times New Roman zapisany w font-family. Dzięki temu artykułowi dowiesz się, jak zadbać o to, by font w naszym projekcie wyświetlał się na każdym urządzeniu w ten sam sposób.

Chcesz być (lepszym) programistą i lepiej zarabiać? Umów się na rozmowę - powiem Ci jak to zrobić!

Spis treści

 Skąd pochodzą fonty w projekcie czyli font family w CSS

Nie przedłużając, mamy co najmniej trzy sposoby „dodania” fontów do projektu:

  1. Trzymanie się fontów bezpiecznych, czyli takich, które jako domyślne znajdują się na większości urządzeń użytkowników. Do takich fontów należą m.in. Times New Roman, Tahoma czy Impact.
  2. Ładowanie fontów z zewnętrznego serwisu – np. Google Fonts – za pomocą znacznika <link>.
  3. Zamieszczenie plików z pobranym fontem w katalogu projektu – tym zajmiemy się w artykule, ponieważ opcja ta pozwala nam uniezależnić się od ładowania zasobów z zewnątrz.

Uwaga! Jeśli jesteś na etapie nauki HTML i CSS to na pewno zainteresuje Cię temat: menu wielopoziomowe i rozwijane w HTML i CSS. Otwórz stronę w nowej zakładce i wróć do niej po przeczytaniu obecnego artykułu.

 Przygotuj pliki z różnymi krojami fontu

Bez względu na to, skąd pobierasz fonty, zawsze sprawdź licencję, zwłaszcza jeśli tworzysz projekt komercyjny. Być może font trzeba będzie kupić.

Na potrzeby artykułu skorzystajmy z bezpłatnych fontów Google Fonts. Po upewnieniu się, że polskie znaki są obsługiwane, pobrałam kilka krojów fontu Overpass: thin, medium i bold oraz italic dla wszystkich trzech opcji.

Pliki pobierają się w formacie ZIP, dlatego trzeba je rozpakować i zapisać w katalogu naszego projektu, np. w podkatalogu fonts/Overpass. Overpass jest fontem zmiennym (ang. variable font), lecz ponieważ nie wszystkie aplikacje takie fonty wspierają, skorzystamy z opcji statycznej.

Całość kodu znajdziesz na repozytorium na GitHubie, a rozwiązanie na żywo podejrzysz dzięki GitHub Pages.

 Fonty webowe – zadbaj o wsparcie dla przeglądarek

Jeżeli pobrany font masz tylko w jednym formacie – font Overpass z Google Fonts ma tylko format .ttf – warto zadbać o parę innych formatów ze względu na wsparcie przeglądarek. Do wygenerowania innych formatów użyjemy narzędzia online transfonter.org (jest też jeszcze np. Font Squirrel). Nowe pliki zapiszemy w tym samym podkatalogu, co resztę. U mnie to fonts/Overpass.

Struktura plików po małych porządkach prezentuje się u mnie w ten sposób:

struktura plików z otwartym katalogiem fontu Overpass

 @font-face – zdefiniuj, z jakich fontów korzystasz

W pliku CSS za pomocą reguły @font-face wskazujemy font i kroje, z których chcemy korzystać przy stylowaniu.

Uwaga: w tym miejscu osoby początkujące często tworzą nieoptymalne reguły. Sprawdź poniżej – jak sądzisz, co będzie lepsze?

Pisanie pełnej nazwy fontu i kroju (np. Overpass Regular Italic, Overpass Bold) przy każdym stylowanym elemencie:

h1 {
  font-family: 'Overpass Bold';
}

h2 {
  font-family: 'Overpass Regular Italic';
}

Pisanie tylko nazwy rodziny (Overpass) i regulowanie reszty przez właściwości font-weight i font-style:

h1 {
  font-family: 'Overpass';
  font-weight: bold;
}

h2 {
  font-family: 'Overpass';
  font-weight: normal;
  font-style: italic;
}

Ponieważ pierwsza opcja jest krótsza, może wydawać się lepsza, lecz widać tutaj co najmniej dwa niebezpieczeństwa:

  1. Jeśli coś zawiedzie i nasze pliki z fontem się nie załadują, przeglądarka użytkownika zapewni jakiś font systemowy. Niestety bold czy kursywa zostaną utracone, bo nie określiliśmy tego w stylach.
  2. Jeśli postanowimy zmienić font, będziemy musieli zmienić też wszystkie nazwy krojów w wielu miejscach. Jest to dokuczliwe tym bardziej, że nazwy krojów również mogą nam się zmienić, np. tu wykorzystujemy Overpass Bold, ale po zmianie może chcielibyśmy korzystać z Open Sans SemiBold.

Wracając do reguły @font-face, dla każdego kroju określamy:

  • rodzinę fontu (font-family),
  • dostępne dla przeglądarki formaty (src) wraz ze ścieżkami do plików, w których są przechowywane (url),
  • grubość (font-weight),
  • styl (font-style).

Ustaliliśmy wyżej, że pierwszy zapis (pełna nazwa fontu i kroju) jest nieoptymalny, dlatego nie chcesz takiej reguły:

@font-face {
  font-family: 'Overpass Thin';
  src:
    url(./fonts/overpass/Overpass-Thin.ttf) format('truetype'),
    url(./fonts/overpass/Overpass-Thin.eot),
    url(./fonts/overpass/Overpass-Thin.eot?#iefix)
      format('embedded-opentype'),
    url(./fonts/overpass/Overpass-Thin.woff2) format('woff2'),
    url(./fonts/overpass/Overpass-Thin.woff) format('woff');
}

Za to chcesz taką:

@font-face {
  font-family: 'Overpass';
  src:
    url(./fonts/overpass/Overpass-Thin.ttf) format('truetype'),
    url(./fonts/overpass/Overpass-Thin.eot),
    url(./fonts/overpass/Overpass-Thin.eot?#iefix)
      format('embedded-opentype'),
    url(./fonts/overpass/Overpass-Thin.woff2) format('woff2'),
    url(./fonts/overpass/Overpass-Thin.woff) format('woff');
  font-style: normal;
  font-weight: 100;
}

Jak widzisz, grubość i styl fontu deklarujemy w osobnych właściwościach. Dzięki temu przeglądarka odwoła się do odpowiedniego kroju bez potrzeby używania przy stylowaniu pełnej nazwy, np. Overpass Thin.

Reguły @font-face dla pozostałych krojów fontu tworzymy analogicznie:

/* Font style: normal */
@font-face {
  font-family: 'Overpass';
  src:
    url(./fonts/overpass/Overpass-Thin.ttf) format('truetype'),
    url(./fonts/overpass/Overpass-Thin.eot),
    url(./fonts/overpass/Overpass-Thin.eot?#iefix)
      format('embedded-opentype'),
    url(./fonts/overpass/Overpass-Thin.woff2) format('woff2'),
    url(./fonts/overpass/Overpass-Thin.woff) format('woff');
  font-style: normal;
  font-weight: 100;
}
@font-face {
  font-family: 'Overpass';
  src:
    url(./fonts/overpass/Overpass-Medium.ttf) format('truetype'),
    url(./fonts/overpass/Overpass-Medium.eot),
    url(./fonts/overpass/Overpass-Medium.eot?#iefix)
      format('embedded-opentype'),
    url(./fonts/overpass/Overpass-Medium.woff2) format('woff2'),
    url(./fonts/overpass/Overpass-Medium.woff) format('woff');
  font-style: normal;
  font-weight: 500;
}
@font-face {
  font-family: 'Overpass';
  src: 
    url(./fonts/overpass/Overpass-Bold.ttf) format('truetype'),
    url(./fonts/overpass/Overpass-Bold.eot),
    url(./fonts/overpass/Overpass-Bold.eot?#iefix)
      format('embedded-opentype'),
    url(./fonts/overpass/Overpass-Bold.woff2) format('woff2'),
    url(./fonts/overpass/Overpass-Bold.woff) format('woff');
  font-style: normal;
  font-weight: 700;
}

/* Font style: italic */
@font-face {
  font-family: 'Overpass';
  src:
    url(./fonts/overpass/Overpass-ThinItalic.ttf) format('truetype'),
    url(./fonts/overpass/Overpass-ThinItalic.eot),
    url(./fonts/overpass/Overpass-ThinItalic.eot?#iefix)
      format('embedded-opentype'),
    url(./fonts/overpass/Overpass-ThinItalic.woff2) format('woff2'),
    url(./fonts/overpass/Overpass-ThinItalic.woff) format('woff');
  font-style: italic;
  font-weight: 100;
}
@font-face {
  font-family: 'Overpass';
  src:
    url(./fonts/overpass/Overpass-MediumItalic.ttf) format('truetype'),
    url(./fonts/overpass/Overpass-MediumItalic.eot),
    url(./fonts/overpass/Overpass-MediumItalic.eot?#iefix)
      format('embedded-opentype'),
    url(./fonts/overpass/Overpass-MediumItalic.woff2) format('woff2'),
    url(./fonts/overpass/Overpass-MediumItalic.woff) format('woff');
  font-style: italic;
  font-weight: 500;
}
@font-face {
  font-family: 'Overpass';
  src:
    url(./fonts/overpass/Overpass-BoldItalic.ttf) format('truetype'),
    url(./fonts/overpass/Overpass-BoldItalic.eot),
    url(./fonts/overpass/Overpass-BoldItalic.eot?#iefix)
      format('embedded-opentype'),
    url(./fonts/overpass/Overpass-BoldItalic.woff2) format('woff2'),
    url(./fonts/overpass/Overpass-BoldItalic.woff) format('woff');
  font-style: italic;
  font-weight: 700;
}

 Użyj fontu do stylowania w CSS czyli font-family w akcji

Teraz nasz font jest gotowy do użycia. Wystarczy ostylować elementy HTML w pliku CSS tak, jak to zwykle robimy. Jeżeli chcesz przetestować stworzone przez nas rozwiązanie, możesz przekopiować poniższy kod HTML:

<h1>Font Overpass</h1>
<h2>Normal</h2>
<ul class="normal">
    <li class="normal--thin">Overpass Thin</li>
    <li class="normal--regular">Overpass Regular</li>
    <li class="normal--bold">Overpass Bold</li>
</ul>
<h2>Italic</h2>
<ul class="italic">
    <li class="italic--thin">Overpass Thin Italic</li>
    <li class="italic--regular">Overpass Regular Italic</li>
    <li class="italic--bold">Overpass Bold Italic</li>
</ul>

Poniżej znajdziesz style z pliku CSS:

h1 {
    font-family: 'Overpass';
    font-weight: bold;
}

h2 {
    font-family: 'Overpass';
    font-weight: normal;
}

ul {
    font-size: 18px;
}

.normal--thin {
    font-family: 'Overpass';
    font-weight: 100;
}
.normal--regular {
    font-family: 'Overpass';
    font-weight: normal;
}
.normal--bold {
    font-family: 'Overpass';
    font-weight: bold;
}

.italic--thin {
    font-family: 'Overpass';
    font-style: italic;
    font-weight: 100;
}
.italic--regular {
    font-family: 'Overpass';
    font-style: italic;
    font-weight: normal;
}
.italic--bold {
    font-family: 'Overpass';
    font-style: italic;
    font-weight: bold;
}

Reguły CSS można oczywiście skrócić, ponieważ wiele linii się powtarza, lecz obecna forma jest najbardziej czytelna w kontekście zrozumienia zagadnienia @font-face.

Uwaga: jeśli chcesz się upewnić, że fonty ładują się z Twoich plików, możesz sprawdzić ich źródło w DevTools w zakładce Elements -> Computed. Źródło local file oznacza, że pliki ładują się z zasobów systemu (czyli np. Twojego komputera, jeśli na nim pracujesz). My chcemy widzieć wartość network resources.

 Wartości liczbowe czy tekstowe dla font-weight

Być może zastanawiasz się, dlaczego w font-weight w regułach @font-face zastosowaliśmy wartości liczbowe (100, 500, 700), a przy stylowaniu raz piszemy 100, innym razem normal i bold.

Moglibyśmy wszędzie wpisywać wartości liczbowe i byłoby to nawet lepsze rozwiązanie, gdybyśmy mieli więcej krojów różnej grubości lub spodziewali się, że kiedyś je dodamy. W tym przykładzie jednak chciałam zwrócić Twoją uwagę na sposób odczytywania wartości bold i normal przez przeglądarkę.

Wartość normal to to samo co 400, natomiast bold to to samo co 700 (nie ma wartości tekstowej dla fontu „cienkiego”). Jakim sposobem więc nasz font Overpass Medium wyświetla się prawidłowo, skoro w regule @font-face we właściwości font-weight wpisaliśmy wartość 500, a przy stylowaniu piszemy font-weight: normal (równie dobrze moglibyśmy to pominąć, bo normal to wartość domyślna)?

Dzieje się tak za sprawą tzw. fallback weights – gdy pożądana wartość nie zostaje odnaleziona, wykorzystywana jest inna najbliższa zgodnie z opisanymi w dokumentacji zasadami.

 Umieść reguły @font-face w osobnym pliku CSS

Im więcej fontów i krojów, tym więcej reguł w pliku CSS, które niepotrzebnie zajmują tam miejsce. Możemy przenieść je do osobnego pliku np. fonts.css. Pamiętajmy tylko, by podłączyć ten plik w HTML-u.

<!DOCTYPE html>
<html lang="pl">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <link rel="stylesheet" href="fonts.css">
    <link rel="stylesheet" href="style.css">
    <title>Jak dołączyć własne fonty do projektu – @font-face w CSS | DevMentor.pl</title>
</head>
<body>
<!-- ... -->
</body>
</html>
Całość kodu znajdziesz na repozytorium na GitHubie, a rozwiązanie na żywo podejrzysz dzięki GitHub Pages.

Teraz już wiesz, jak dołączyć własne fonty do projektu! Nie przejmuj się, jeśli przytłacza Cię np. liczba formatów. Obecnie TTF i WOFF2 w większości przypadków wystarczą. Jeżeli kiedyś będziesz budować rozwiązanie wspierające mało popularne czy stare przeglądarki, Google pomoże Ci znaleźć odpowiednie opcje.

Udostępnij ten artykuł:

Mentoring to efektywna nauka pod okiem doświadczonej osoby, która:

  • przekazuje Ci swoją wiedzę i nadzoruje Twoje postępy w zdobywaniu umiejętności,
  • uczy Cię dobrych praktyk i wyłapuje złe nawyki,
  • wspiera Twój rozwój i zwiększa zaangażowanie w naukę.

Chcesz zostać (lepszym) programistą i lepiej zarabiać? 

🚀 Porozmawiajmy o nauce programowania, poszukiwaniu pracy, o rozwoju kariery lub przyszłości branży IT!

Umów się na ✅ bezpłatną i niezobowiązującą rozmowę ze mną.

Chętnie porozmawiam o Twojej przyszłości i pomogę Ci osiągnąć Twoje cele! 🎯