Vì sao web font ảnh hưởng trực tiếp đến SEO và trải nghiệm
- Tốc độ: Web font lớn hoặc tải chậm sẽ làm tăng FCP/LCP, ảnh hưởng thứ hạng tìm kiếm.
- Trải nghiệm: FOUT/FOIT gây nhấp nháy chữ hoặc chữ “mất tích”, làm tăng CLS.
- Khả năng đọc: Bộ chữ không tối ưu tiếng Việt (dấu, ký tự ₫) làm giảm UX và tỷ lệ chuyển đổi.
Kết luận nhanh: dùng WOFF2, bật font-display: swap, chia nhỏ theo unicode-range, preload hợp lý, và subsetting dành riêng cho tiếng Việt.
Định dạng và chiến lược phân phối
- Ưu tiên WOFF2; chỉ thêm WOFF nếu thật sự cần tương thích cũ.
- Tránh TTF/OTF/EOT trên production.
- Tự host web font để chủ động cache, domain, và chính sách quyền riêng tư; hoặc dùng CDN uy tín, preconnect đúng đích.
- HTTP/2/3 giúp nhiều request nhỏ trở nên hiệu quả; vẫn nên giảm số file bằng variable font hoặc gộp subset thông minh.
Subset tiếng Việt: những gì cần có
Tiếng Việt cần nhiều ký tự có dấu và một số ký tự tổ hợp. Tối thiểu nên bao gồm:
- Phạm vi Unicode thường dùng: U+0102-0103 (Ăă), U+0110-0111 (Đđ), U+0128-0129 (Ĩĩ), U+0168-0169 (Ũũ), U+01A0-01A1 (Ơơ), U+01AF-01B0 (Ưư).
- Dấu thanh và dấu phụ: U+0300-0301, U+0303-0304, U+0308-0309, U+0323, U+0329.
- Khối chữ Việt có dấu đầy đủ: U+1EA0-1EF9.
- Ký hiệu tiền tệ: U+20AB (₫).
Mẹo: tách unicode-range theo ngôn ngữ (latin, latin-ext, vietnamese) để trình duyệt chỉ tải phần cần thiết.
Cấu hình @font-face chuẩn production
- file format: chỉ WOFF2 + fallback WOFF khi cần.
- font-display: swap để tránh FOIT, giảm CLS.
- unicode-range: chia nhỏ theo ngôn ngữ để giảm tải.
- Preload file thực sự dùng ở viewport đầu.
- Cache dài hạn (immutable, 1 năm) với versioning trong tên file.
Ví dụ gọn nhẹ:
/* Sans chính cho nội dung */
@font-face {
font-family: "Open Sans";
src: url("/fonts/open-sans-vn.woff2") format("woff2");
font-weight: 400 700;
font-style: normal;
font-display: swap;
unicode-range: U+0102-0103, U+0110-0111, U+0128-0129, U+0168-0169,
U+01A0-01A1, U+01AF-01B0, U+0300-0301, U+0303-0304,
U+0308-0309, U+0323, U+0329, U+1EA0-1EF9, U+20AB;
}
@font-face {
font-family: "Open Sans";
src: url("/fonts/open-sans-latin.woff2") format("woff2");
font-weight: 400 700;
font-style: normal;
font-display: swap;
unicode-range: U+0000-00FF, U+0131, U+0152-0153;
}
Preload hợp lý:
<link rel="preload" href="/fonts/open-sans-vn.woff2" as="font" type="font/woff2" crossorigin>
Lưu ý:
- Chỉ preload font xuất hiện ở Above The Fold (tiêu đề, menu, hero).
- Dùng crossorigin khi font nằm trên domain khác hoặc có CORS.
Chọn font phù hợp cho tiếng Việt
- Roboto, Open Sans: Trung tính, dễ đọc, hỗ trợ Việt tốt; hợp UI, nội dung dài.
- Oswald, Anton: Tiêu đề mạnh mẽ, đậm tính thương hiệu; dùng hạn chế cho heading.
- PT Serif: Nội dung dài theo kiểu editorial, blog/chuyên sâu; cần kiểm tra hinting trên màn hình thấp DPI.
- Advent Pro: Phong cách hiện đại, dùng cho accent/heading; test độ đọc ở kích thước nhỏ.
Gợi ý kết hợp:
- Heading: Oswald/Aton/Advent Pro
- Body: Roboto/Open Sans/PT Serif
- Accent number/price: Roboto Mono (hoặc stack monospace) nếu cần căn cột số.
Fallback stack chống “chớp chữ”
Thiết lập fallback gần giống metric để giảm layout shift:
:root {
--font-body: "Open Sans", system-ui, -apple-system, "Segoe UI",
Roboto, Helvetica, Arial, "Apple Color Emoji",
"Segoe UI Emoji", "Segoe UI Symbol", sans-serif;
}
body { font-family: var(--font-body); }
Mẹo:
- Chọn fallback có chiều rộng ký tự gần font chính để hạn chế CLS.
- Kiểm tra dấu tiếng Việt hiển thị đúng ở fallback.
Variable font: ít file, nhiều trọng lượng
Ưu điểm:
- Một file bao phủ nhiều weight/width/italic → giảm số request.
- Mượt khi dùng clamp() + font-variation-settings.
Nhược điểm:
- Kích thước file có thể lớn hơn 1–1.5× so với từng file woff2 đơn lẻ nếu dùng ít weight.
- Cần subsetting unicode để tối ưu thực tế.
Ví dụ:
@font-face {
font-family: "Roboto VF";
src: url("/fonts/roboto-vf-vn.woff2") format("woff2-variations");
font-weight: 300 700;
font-stretch: 100%;
font-style: normal;
font-display: swap;
unicode-range: U+1EA0-1EF9, U+0102-0103, U+0110-0111, U+20AB, U+0300-0301, U+0309, U+0323, U+0329;
}
Tạo subset font cho tiếng Việt
Công cụ đề xuất:
- fonttools (pyftsubset)
- glyphhanger
- subfont
Ví dụ với fonttools:
pyftsubset OpenSans[wght].ttf
--output-file=OpenSans-vn.woff2
--flavor=woff2
--unicodes="U+0102-0103,U+0110-0111,U+0128-0129,U+0168-0169,U+01A0-01A1,U+01AF-01B0,U+0300-0301,U+0303,U+0309,U+0323,U+0329,U+1EA0-1EF9,U+20AB"
--layout-features='*'
--no-hinting
Mẹo:
- Nếu size vẫn lớn, cân nhắc chỉ giữ weight thật sự dùng (400, 600, 700).
- Đừng bỏ các dấu tổ hợp cần thiết (U+0300…); dễ khiến chữ sai dấu.
Tối ưu tải và cache
- Cache-Control: max-age=31536000, immutable; đổi tên file khi cập nhật (hash).
- Preconnect khi dùng CDN font:
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
- Tránh chặn render: đặt CSS quan trọng inline nhỏ gọn, chỉ preload font cần thiết.
- Dùng Priority Hints nếu phù hợp:
<link rel="preload" href="/fonts/open-sans-vn.woff2" as="font" fetchpriority="high" type="font/woff2" crossorigin>
Kiểm thử và giám sát
- Lighthouse/Pagespeed: theo dõi LCP, CLS, Font Display.
- Chrome DevTools Coverage: xem byte font không dùng.
- WebPageTest: so sánh với/tắt web font, đo FCP/LCP.
- RUM (Real User Monitoring): đo tỉ lệ FOUT/FOIT và CLS thực tế.
Checklist triển khai nhanh
- [ ] Dùng WOFF2 (cộng WOFF nếu cần).
- [ ] Subset tiếng Việt bằng unicode-range; kiểm tra đủ ký tự.
- [ ] font-display: swap.
- [ ] Preload đúng font xuất hiện trên Above The Fold.
- [ ] Fallback stack gần metric font chính.
- [ ] Cache 1 năm + versioning filename.
- [ ] Test Lighthouse, Coverage, WebPageTest.
- [ ] Theo dõi CLS, LCP sau phát hành.
Câu hỏi thường gặp
- Có nên dùng Google Fonts hay tự host? Tự host kiểm soát tốt cache, quyền riêng tư; Google Fonts có hạ tầng CDN mạnh. Hãy đo đạc A/B trên dự án của bạn.
- Vì sao đã swap vẫn bị “nhảy chữ”? Fallback và web font khác metric; cân chỉnh line-height/letter-spacing và chọn fallback tương thích hơn.
- Variable font có đáng không? Có, nếu dùng nhiều weight/italic. Nếu chỉ 1–2 weight, cân nhắc woff2 rời để nhỏ hơn.
- Có cần italic riêng? Nếu nội dung dùng italic, hãy cung cấp trục italic hoặc file italic để tránh giả lập nghiêng xấu.
Kết luận: Muốn SEO và Core Web Vitals tốt trên thị trường Việt Nam, hãy coi web font là một phần của hiệu năng. Subset tiếng Việt đúng, phân phối WOFF2 thông minh, và kiểm thử liên tục sẽ mang lại tốc độ và trải nghiệm vượt trội.