Yerel Yazı Tipi Erişimi API'sinin, kullanıcının yerel olarak yüklenen yazı tiplerine erişmenize ve bunlarla ilgili ayrıntılı bilgiler edinmenize nasıl olanak tanıdığını öğrenin
Web'de kullanıma uygun yazı tipleri
Web geliştirme konusunda uzun süredir çalışıyorsanız web'de kullanılabilen yazı tipleri olarak bilinenleri hatırlayabilirsiniz.
Bu yazı tiplerinin, en çok kullanılan işletim sistemlerinin (Windows, macOS, en yaygın Linux dağıtımları, Android ve iOS) neredeyse tüm sürümlerinde kullanılabildiği bilinmektedir. 2000'lerin başlarında Microsoft, Web için TrueType temel yazı tipleri adlı bir girişime öncülük etti. Bu girişim, bu yazı tiplerini belirten bir web sitesini her ziyaret ettiğinizde sayfaları site tasarımcısının amaçladığı şekilde göreceğiniz hedefiyle bu yazı tiplerini ücretsiz olarak indirmenizi sağlıyordu. Evet, Comic Sans MS yazı tipiyle ayarlanmış siteler de bu kapsamdadır. Klasik bir web'de kullanıma uygun yazı tipi grubu (sans-serif
yazı tipinin nihai yedeğiyle birlikte) aşağıdaki gibi görünebilir:
body {
font-family: Helvetica, Arial, sans-serif;
}
Web yazı tipleri
Web'de kullanılabilen yazı tiplerinin gerçekten önemli olduğu günler çoktan geride kaldı. Günümüzde, bazılarında çeşitli açığa çıkarılan eksenlerin değerlerini değiştirerek daha da ince ayar yapabileceğimiz web yazı tipleri var. Hatta bunların bazıları değişken yazı tipleridir. CSS'nin başında, indirilecek yazı tipi dosyalarını belirten bir @font-face
bloğu tanımlayarak web yazı tiplerini kullanabilirsiniz:
@font-face {
font-family: 'FlamboyantSansSerif';
src: url('flamboyant.woff2');
}
Ardından, normalde olduğu gibi font-family
değerini belirterek özel web yazı tipini kullanabilirsiniz:
body {
font-family: 'FlamboyantSansSerif';
}
Parmak izi vektörü olarak yerel yazı tipleri
Çoğu web yazı tipi web'den gelir. Ancak @font-face
beyanında yer alan src
özelliği, url()
işlevinin yanı sıra local()
işlevini de kabul eder. Bu sayede özel yazı tipleri yerel olarak yüklenebilir. Kullanıcının işletim sisteminde FlamboyantSansSerif yüklüyse indirilmek yerine yerel kopya kullanılır:
@font-face {
font-family: 'FlamboyantSansSerif';
src: local('FlamboyantSansSerif'), url('flamboyant.woff2');
}
Bu yaklaşım, bant genişliğinden tasarruf etmenizi sağlayacak iyi bir yedek mekanizma sağlar. İnternette maalesef her şey yolunda gitmez. local()
işlevinin sorunu, tarayıcı parmak izi için kötüye kullanılabilmesidir. Kullanıcının yüklediği yazı tiplerinin listesi oldukça tanımlayıcı olabilir. Birçok şirketin, çalışanlarının dizüstü bilgisayarlarına yüklenen kendi kurumsal yazı tipleri vardır. Örneğin, Google'ın Google Sans adlı bir kurumsal yazı tipi vardır.
Saldırganlar, Google Sans gibi çok sayıda bilinen kurumsal yazı tipinin varlığını test ederek kullanıcının hangi şirkette çalıştığını belirlemeye çalışabilir. Saldırgan, bu yazı tiplerinde ayarlanmış metni bir kanvasta oluşturmaya ve glifleri ölçmeye çalışır. Glifler, kurumsal yazı tipinin bilinen şekliyle eşleşirse saldırgan isabet elde eder. Simgeler eşleşmiyorsa saldırgan, kurumsal yazı tipi yüklenmediği için varsayılan bir değişim yazı tipinin kullanıldığını bilir. Bu ve diğer tarayıcı parmak izi saldırılarıyla ilgili tüm ayrıntılar için Laperdix ve arkadaşları tarafından yazılan araştırma makalesini okuyun.
Şirket yazı tipleri dışında, yüklü yazı tiplerinin listesi bile kimliği tanımlayabilir. Bu saldırı vektörüyle ilgili durum o kadar kötüye gitti ki kısa süre önce WebKit ekibi "kullanıcı tarafından yerel olarak yüklenen yazı tiplerini değil, yalnızca web yazı tiplerini ve işletim sistemiyle birlikte gelen yazı tiplerini [kullanılabilir yazı tipleri listesine] dahil etmeye karar verdi. (Ve şimdi buradayım, yerel yazı tiplerine erişim vermeyle ilgili bir makaleyle.)
Yerel Yazı Tipi Erişimi API'si
Bu makalenin başlangıcı sizi olumsuz bir ruh haline sokmuş olabilir. Gerçekten güzel şeylere sahip olamaz mıyız? Endişelenmeyin. Bunu yapabileceğimizi düşünüyoruz ve her şeyin umutsuz olmadığını umuyoruz. Ancak önce aklınızdan geçen bir soruyu yanıtlayayım.
Web yazı tipleri varken neden Yerel Yazı Tipi Erişimi API'sine ihtiyacımız var?
Profesyonel kalitede tasarım ve grafik araçlarını web'de sunmak geçmişte zordu. Tasarımcıların yerel olarak yüklediği profesyonelce oluşturulmuş ve ipucu verilmiş yazı tiplerinin tamamına erişip bunları kullanamama sorunuyla karşılaşıyorduk. Web yazı tipleri bazı yayınlama kullanım alanlarını destekler ancak rasterleştiriciler tarafından glif ana hatlarını oluşturmak için kullanılan vektör glif şekillerine ve yazı tipi tablolarına programatik erişim sağlamaz. Benzer şekilde, bir web yazı tipinin ikili verilerine erişmek de mümkün değildir.
- Tasarım araçlarının kendi OpenType düzeni uygulamalarını gerçekleştirmesi ve tasarım araçlarının, karakter şekillerinde vektör filtreleri veya dönüştürme işlemleri gibi işlemler için daha düşük seviyelerde bağlantı kurmasına izin vermesi için yazı tipi baytlarına erişmesi gerekir.
- Geliştiricilerin, web'e taşıdıkları uygulamaları için eski yazı tipi grupları olabilir. Bu grupları kullanmak için genellikle yazı tipi verilerine doğrudan erişim gerekir. Web yazı tipleri bu erişimi sağlamaz.
- Bazı yazı tipleri web üzerinden yayınlanmak için lisanslı olmayabilir. Örneğin, Linotype'in bazı yazı tipleri için yalnızca masaüstü kullanımını kapsayan bir lisansı vardır.
Yerel Yazı Tipi Erişimi API'si, bu zorlukların üstesinden gelmek için geliştirilmiştir. İki bölümden oluşur:
- Kullanıcıların mevcut sistem yazı tiplerinin tamamına erişim izni vermesine olanak tanıyan bir yazı tipi numaralandırma API'si.
- Her bir listeleme sonucunda, yazı tipi verilerinin tamamını içeren düşük düzey (bayt odaklı) SFNT kapsayıcı erişimi isteğinde bulunma olanağı.
Tarayıcı desteği
Yerel Yazı Tipi Erişimi API'sini kullanma
Özellik algılama
Yerel Yazı Tipi Erişimi API'sinin desteklenip desteklenmediğini kontrol etmek için:
if ('queryLocalFonts' in window) {
// The Local Font Access API is supported
}
Yerel yazı tiplerini numaralandırma
Yerel olarak yüklenen yazı tiplerinin listesini almak için window.queryLocalFonts()
işlevini çağırmanız gerekir. İlk kez bu işlem, kullanıcının onaylayabileceği veya reddedebileceği bir izin istemi tetikler. Kullanıcı, yerel yazı tiplerinin sorgulanması için izin verirse tarayıcı, döngü oluşturabileceğiniz yazı tipi verilerini içeren bir dizi döndürür. Her yazı tipi, family
(ör. "Comic Sans MS"
), fullName
(ör. "Comic Sans MS"
), postscriptName
(ör. "ComicSansMS"
) ve style
(ör. "Regular"
) özelliklerine sahip bir FontData
nesnesi olarak temsil edilir.
// Query for all available fonts and log metadata.
try {
const availableFonts = await window.queryLocalFonts();
for (const fontData of availableFonts) {
console.log(fontData.postscriptName);
console.log(fontData.fullName);
console.log(fontData.family);
console.log(fontData.style);
}
} catch (err) {
console.error(err.name, err.message);
}
Yalnızca yazı tiplerinin bir alt kümesiyle ilgileniyorsanız postscriptNames
parametresi ekleyerek bunları PostScript adlarına göre de filtreleyebilirsiniz.
const availableFonts = await window.queryLocalFonts({
postscriptNames: ['Verdana', 'Verdana-Bold', 'Verdana-Italic'],
});
SFNT verilerine erişme
FontData
nesnesinin blob()
yöntemi aracılığıyla tam SFNT erişimi sağlanabilir. SFNT, PostScript, TrueType, OpenType, Web Open Font Format (WOFF) yazı tipleri gibi diğer yazı tiplerini içerebilen bir yazı tipi dosya biçimidir.
try {
const availableFonts = await window.queryLocalFonts({
postscriptNames: ['ComicSansMS'],
});
for (const fontData of availableFonts) {
// `blob()` returns a Blob containing valid and complete
// SFNT-wrapped font data.
const sfnt = await fontData.blob();
// Slice out only the bytes we need: the first 4 bytes are the SFNT
// version info.
// Spec: https://docs.microsoft.com/en-us/typography/opentype/spec/otff#organization-of-an-opentype-font
const sfntVersion = await sfnt.slice(0, 4).text();
let outlineFormat = 'UNKNOWN';
switch (sfntVersion) {
case '\x00\x01\x00\x00':
case 'true':
case 'typ1':
outlineFormat = 'truetype';
break;
case 'OTTO':
outlineFormat = 'cff';
break;
}
console.log('Outline format:', outlineFormat);
}
} catch (err) {
console.error(err.name, err.message);
}
Demo
Yerel Yazı Tipi Erişimi API'sini aşağıdaki demo'da görebilirsiniz. Kaynak koda da göz atmayı unutmayın. Demoda, yerel yazı tipi seçiciyi uygulayan <font-select>
adlı özel bir öğe gösterilmektedir.
Gizlilik ile ilgili dikkat edilmesi gereken noktalar
"local-fonts"
izni, yüksek oranda parmak izi alınabilen bir yüzey sağlıyor. Ancak tarayıcıların istedikleri her şeyi iade etme hakkı vardır. Örneğin, anonimliğe odaklanan tarayıcılar yalnızca tarayıcıya yerleştirilmiş bir dizi varsayılan yazı tipi sunmayı tercih edebilir. Benzer şekilde, tarayıcıların tablo verilerini tam olarak diskte göründüğü şekilde sağlaması gerekmez.
Yerel Yazı Tipi Erişimi API'si mümkün olduğunda yalnızca belirtilen kullanım alanlarını etkinleştirmek için gereken bilgileri göstermek üzere tasarlanmıştır. Sistem API'leri, yüklü yazı tiplerinin listesini rastgele veya sıralı olarak değil, yazı tipi yükleme sırasına göre oluşturabilir. Bu tür bir sistem API'si tarafından verilen yüklü yazı tiplerinin tam listesini döndürmek, parmak izi oluşturmak için kullanılabilecek ek verileri açığa çıkarabilir ve etkinleştirmek istediğimiz kullanım alanlarına bu sıralamanın korunması yardımcı olmaz. Sonuç olarak bu API, döndürülen verilerin döndürülmeden önce sıralanması gerektiğini belirtir.
Güvenlik ve izinler
Chrome ekibi, yerel yazı tipi erişim API'sini tasarlarken ve uygularken kullanıcı kontrolü, şeffaflık ve ergonomi gibi Güçlü Web Platformu Özelliklerine Erişimi Kontrol Etme başlıklı makalede belirtilen temel ilkeleri temel almıştır.
Kullanıcı denetimi
Kullanıcının yazı tiplerine erişim tamamen kullanıcının kontrolündedir ve izin kayıt defterinde listelenen "local-fonts"
izni verilmediği sürece erişim izni verilmez.
Şeffaflık
Bir siteye kullanıcının yerel yazı tiplerine erişim izni verilip verilmediği site bilgileri sayfasında gösterilir.
İzin kalıcılığı
"local-fonts"
izni, sayfa yeniden yüklemeleri arasında devam eder. Site bilgileri sayfası üzerinden iptal edilebilir.
Geri bildirim
Chrome ekibi, Yerel Yazı Tipi Erişimi API'si ile ilgili deneyimlerinizi öğrenmek istiyor.
API tasarımı hakkında bilgi verin
API ile ilgili olarak beklediğiniz gibi çalışmayan bir şey var mı? Yoksa fikrinizi uygulamak için ihtiyaç duyduğunuz yöntemler veya özellikler eksik mi? Güvenlik modeliyle ilgili sorunuz veya yorumunuz mu var? İlgili GitHub deposunda spesifikasyon sorunu oluşturun veya mevcut bir soruna düşüncelerinizi ekleyin.
Uygulamayla ilgili sorunları bildirme
Chrome'un uygulamasında bir hata mı buldunuz? Yoksa uygulama, spesifikasyondan farklı mı?
new.crbug.com adresinden hata kaydı oluşturun. Mümkün olduğunca fazla ayrıntı ekleyin, hatayı yeniden oluşturmayla ilgili basit talimatlar verin ve Bileşenler kutusuna Blink>Storage>FontAccess
yazın.
Glitch, hızlı ve kolay yeniden oluşturma işlemlerini paylaşmak için idealdir.
API'yi destekleme
Yerel Yazı Tipi Erişimi API'yi kullanmayı planlıyor musunuz? Herkese açık desteğiniz, Chrome ekibinin özelliklere öncelik vermesine yardımcı olur ve diğer tarayıcı tedarikçi firmalarına bu özellikleri desteklemenin ne kadar önemli olduğunu gösterir.
#LocalFontAccess
hashtag'ini kullanarak @ChromiumDev hesabına tweet gönderin ve bu özelliği nerede ve nasıl kullandığınızı bize bildirin.
Faydalı bağlantılar
- Açıklayıcı
- Özellik taslağı
- Yazı tipi numaralandırması için Chromium hatası
- Yazı tipi tablosuna erişim için Chromium hatası
- ChromeStatus girişi
- GitHub deposu
- TAG incelemesi
- Mozilla'nın standartlar konusundaki konumu
Teşekkür ederiz
Yerel Yazı Tipi Erişimi API spesifikasyonu, Emil A. Eklund, Alex Russell, Joshua Bell ve Olivier Yiptong. Bu makale, Joe Medley, Dominik Röttsches ve Olivier Yiptong tarafından incelenmiştir. Unsplash'tan Brett Jordan tarafından oluşturulan hero resim.