Kolay, yüksek DPI resimler

Boris Smus
Boris Smus

Yüksek piksel yoğunluğuna sahip ekranlar hızla normal hale geliyor. İçerik üreticilerin bu gerçeğe uyum sağlaması gerekiyor. Bu, çoklu dolgular, JavaScript, CSS hack'leri ve henüz tam olarak uygulanmayan tarayıcı özellikleri olmadan web'de yüksek kaliteli resimlerin nasıl sunulacağıyla ilgili kısa bir kılavuzdur. Kısaca ifade etmek gerekirse, iş akışınızda çok büyük değişiklikler yapmanıza gerek kalmaz.

Bugün birçok duyarlı resim teklifi var ve bunların çoğu web geliştiricisi için önemli değişiklikler içeriyor. Standard-track srcset <img> özelliğinin uygulanması, özellikle srcset öğesinin ek görüntü alanına dayalı seçiminin karmaşıklığı nedeniyle zordur:

banner-HD.jpeg 2x, banner-phone.jpeg 100w, banner-phone-HD.jpeg 100w 2x

image-set CSS özelliği hangi resmin yükleneceğine karar vermek için yalnızca devicePixelRatio değerini kullansa da geliştiricileri her resim için ekstra işaretleme yazmaya zorlar.

<picture> öğesi gibi diğer teklifler daha da ayrıntılıdır. Dahası, bunlar standart izleme değildir; bu nedenle, her yerde kullanılabilirlikleri srcset özelliğinden daha da uzaktır. JavaScript ve sunucu tarafı çözümleri diğer alternatiflerdir, ancak bu yaklaşımların diğer makalelerde ele alındığı gibi kendi dezavantajları vardır.

Bu makalede, web'de yaygın olarak bulunan resimlerin çeşitli kullanımları ele alınıp yüksek piksel yoğunluğuna sahip ekranlarda ve sıradan ekranlarda çalışan basit çözümler önerilecektir. Bu tartışmada, window.devicePixelRatio değerini 1'den büyük bildiren tüm cihazlar yüksek DPI olarak kabul edilebilir. Çünkü bu durum, CSS piksellerinin cihaz pikselleriyle aynı olmadığı ve resimlerin ölçeklendirildiği anlamına gelir.

Yeniliklerin özetini aşağıda bulabilirsiniz.

  • Mümkünse kafes görüntüler yerine CSS/SVG kullanın.
  • Varsayılan olarak yüksek yoğunluklu ekranlar için optimize edilmiş resimleri kullanın.
  • Basit çizimler ve piksel sanatı (ör. logolar) için PNG kullanın.
  • Çeşitli renklerdeki resimler (ör. fotoğraflar) için sıkıştırılmış JPEG'ler kullanın.
  • Tüm resim öğelerinde her zaman uygunsuz boyutları ayarlayın (CSS veya HTML kullanarak).

Basit çizimler ve piksel sanatı

CSS özellikleri veya SVG kullanılarak küçük resimler çoğu zaman önlenebilir. Örneğin, border-radius CSS özelliği yaygın olarak desteklendiğinden yuvarlatılmış köşeler için resimler kullanmanıza gerek yoktur. Benzer şekilde, özel yazı tipleri yaygın olarak desteklendiğinden, "görselleştirilmiş" metin kullanılması tavsiye edilmez.

Ancak logolar gibi bazı durumlarda, öne çıkarmak için tek yol resim olabilir. Örneğin, bu Chrome logosunun doğal boyutu 256x256'dır. Retina ekranda, özellikle net olarak oluşturulmuş metinle karşılaştırıldığında ise köşegen ve eğriler olan çizginin kenarlığını ortaya çıkardığını görebilirsiniz. Bu durum, özellikle de net bir şekilde oluşturulmuş metinle karşılaştırıldığında

Chrome 1x
1x

Doğal boyutlar: 256x256px, öğe boyutu: 31 kB, biçim: PNG

İkna oldun mu? Güzel. Şimdi yüksek yoğunluklu bir resim kullanalım. Logonuzu JPEG olarak depolayarak yerden tasarruf etmek cazip gelse de, logoları ve diğer grafikleri kayıplı bir biçimde kaydetmekte hatalar ortaya çıktığı için bu iyi bir fikir olmayabilir. Burada, çok yüksek bir sıkıştırma kullanarak sorunu abarttım ancak gradyanlardaki şerit oluşumuna, beyaz arka planlarda beneklere ve dağınık çizgilere dikkat edin:

Chrome 2x
2x Jpeg

Doğal boyutlar: 512x512px, öğe boyutu: 13 kB, biçim: JPEG

Nispeten küçük resimler için yapılacak şey 2x PNG kullanmaktır. 1x ve 2x PNG arasındaki boyut farkının genellikle oldukça yüksek (bu örnekte 52 kB) olduğunu unutmayın. Ancak, logo söz konusu olduğunda bu, web sitenizin yüzüdür ve ziyaretçilerinizin göreceği ilk şeydir. Boyut karşılığında kaliteye çok fazla değinerek bu aynı zamanda ziyaretçilerinizin göreceği son şeydir!

Aşağıda, 2x ekranlar için doğal boyutlarının yarısına kadar küçültülmüş olarak tüm ihtişamıyla Chrome logosu bulunmaktadır:

Chrome 2x
PNG 2x

Doğal boyutlar: 512x512px, öğe boyutu: 83 kB, biçim: PNG

Yukarıdakinin oluşturulması için işaretleme şu şekildedir:

<img src="chrome2x.png" style="width: 256px; height: 256px;"/>

Resmin genişliği ve yüksekliği belirtilmiş olmalıdır. Resmin doğal boyutu 512 piksel olduğu için bu gereklidir. Oluşturma motoru, öğenin boyutunu iyi bir şekilde kavradığı ve bunu hesaplamak için çok fazla çaba gerektirmemesi nedeniyle performans için de iyidir.

İşe yarayabilecek olası bir optimizasyon, 24 bit PNG'yi paletli 8 bite indirmektir. Bu yöntem, Chrome logosu dahil olmak üzere az sayıda renkli resimlerde kullanılabilir. Bu optimizasyonu yapmak için http://pngquant.org/ gibi bir araç kullanabilirsiniz. Burada biraz şerit oluşumu görebilirsiniz, ancak bu dosya yalnızca 13 kB boyutundadır. Bu da orijinal 512x512 PNG dosyasıyla karşılaştırıldığında 6 kat daha büyük bir boyut tasarrufu anlamına gelir.

Chrome 2x 8bit
PNG 2x 8 bit

Doğal boyutlar: 512x512px, öğe boyutu: 13 kB, biçim: PNG, 8-bit palette

Çeşitli renklerde resimler

Birkaç farklı duyarlı resim tekniğini inceleyen bir HTML5Rocks makalesi yazdım ve 1x ve 2x JPEG sıkıştırması ve elde edilen boyutlar ile görsel kalitenin karşılaştırılması konusunda bazı araştırmalar yaptım. Yukarıdaki makalede yer alan bloklardan birini aşağıda görebilirsiniz:

Döşe.

Resimleri, sıkıştırma düzeylerine (JPEG kalitesiyle gösterilir), boyutlarına (bayt cinsinden) ve kendi karşılaştırmalı görsel doğruluklarına (sayılara göre sıralanmış şekilde) ilişkin görüşlerimle etiketledim. Buradaki ilginç nokta, yüksek düzeyde sıkıştırılmış 2x resmin (3 olarak etiketlenmiştir) daha küçük boyutlu olması ve sıkıştırılmamış 1x resimden (4 etiketli) daha iyi görünmesidir. Başka bir deyişle, 4. ve 3. resimler arasında, her bir boyutu ikiye katlayarak ve sıkıştırmayı önemli ölçüde artırarak resim kalitesini 2 kB küçültmeyi başardık.

Sıkıştırma, boyutlar ve görsel kalite

Sıkıştırma düzeyi, resim boyutları, görsel kalite ve resim boyutu arasındaki dengeleri daha iyi anlamak istedim. Yukarıdaki çalışmaya dayanarak şu hipotezi kullanarak bir çalışma yaptım:

Hipotez

Yeterli sıkıştırma yapılırsa 2x boyutundaki bir resim, başka bir (düşük) sıkıştırmada 1x boyutlu aynı resme eşdeğer görünür. Ancak, bu durumda, yüksek sıklıkta sıkıştırılmış 2x resmin boyutu, 1x resimden daha küçük olur.

İşleme

  • 2x resmi verildiğinde 1x olanı oluşturun.
  • Her iki resmi çeşitli düzeylerde sıkıştırın.
  • Her iki resim grubunu yan yana gösteren bir test sayfası oluşturun.
  • İki kümede resimlerin eşdeğer olduğu yeri bulun.
  • Eşdeğer resim boyutlarına ve sıkıştırma düzeylerine dikkat edin.
  • Bu özelliği hem 1x hem 2x ekranda deneyin.

Lightroom'un karşılaştırma görünümüne benzer bir yan yana resim karşılaştırma uygulaması oluşturdum. Amaç, bir 1x ve 2x resmi yan yana göstermek, ancak aynı zamanda daha fazla ayrıntı elde etmek için resmin herhangi bir bölümünü yakınlaştırabilmenizi de sağlamaktır. Ayrıca JPEG ve WebP biçimleri arasından seçim yapabilir ve dosya boyutu ve resim kalitesi karşılaştırmalarını görmek için sıkıştırma kalitesini değiştirebilirsiniz. Buradaki amaç, birden fazla resmin ayarlarında ince ayar yapmak, hangi sıkıştırma kalitesi, ölçekleme ve biçim ve biçim dengelerinin sizin için uygun olduğunu belirlemek ve bu ayarı tüm resimleriniz için kullanmaktır.

Karşılaştırma ekran görüntüsü

Aracın kendisini kullanabilirsiniz. Yakınlaştırmak için bir alt alan seçerek resmi yakınlaştırabilirsiniz.

Analiz

Resim kalitesinin öznel bir konu olduğunu söyleyebilirim. Ayrıca, belirli kullanım alanınız muhtemelen önceliklerinizin görsel doğruluk ve dosya boyutu spektrumunda nerede olduğunu belirleyecektir. Ayrıca, farklı türdeki resim özellikleri ölçeklendirme ve sıkıştırma kalitesine farklı tepkiler verir. Bu nedenle, herkese uyan tek bir çözüm burada işe yaramayabilir. Aracın amacı, resim kalitesinde sıkıştırma, ölçek ve biçim işlemleri konusunda sezgi oluşturmanıza yardımcı olmaktır.

Resim zumlayıcıyla oynamaya başladıktan sonra, birkaç şey fark ettim. İlk olarak, ayrıntıdaki artış için quality=90 dpr=1x resim yerine quality=30 dpr=2x resmi tercih ediyorum. Bu resimlerin dosya boyutu da birbirine benzer (düzlem örnekte, sıkıştırılmış 2x resim 76 kB, sıkıştırılmamış 1x ise 80 kB'tır).

Yüksek düzeyde sıkıştırılmış (quality<30) ve gradyanlı resimler bu kuralın istisnalarıdır. Bunlar, resim ölçeği ne olursa olsun eşit derecede kötü olan renk şeritlerinden muzdariptir. Araçta bulunan kuş ve araba örnekleri buna örnektir.

WebP resimleri, özellikle düşük sıkıştırma seviyelerinde JPEG'den çok daha temiz görünür. Bu renk şeritlerinin daha az sorun teşkil ettiği görülüyor. Son olarak, WebP resimleri çok daha kompakttır.

Uyarılar ve yüzgeç

Resimlerin yüksek yoğunluklu ekranlarda iyi görünmesini sağlamak, ekranlardaki büyük farklılıklardan kaynaklanan resimle ilgili sorunların yalnızca yarısıdır. Bazı durumlarda, görüntü alanı boyutuna bağlı olarak tamamen farklı resimler sunmak isteyebilirsiniz. Örneğin, Obama'nın vesikalık fotoğrafı telefon boyutundaki bir ekran için uygun, ancak önündeki stand ve arkasındaki bayrak fotoğrafı dizüstü bilgisayar ekranı için uygun olabilir.

Yalnızca yüksek DPI resimlere odaklanmak için bu "sanat yönetimi" konusundan özellikle uzak durdum. Bu sorun bir dizi farklı yaklaşımla çözülebilir: Medya sorguları ve arka plan resimlerinin kullanılması, JavaScript aracılığıyla, image-set gibi bazı yeni özelliklerin kullanılması veya sunucu üzerinde kullanılması. Bu konu, Değişken Piksel Yoğunlukları için Yüksek DPI Görüntüler konusunu ele almaktadır.

Birkaç açık sorunu kapatacağım:

  • Yüksek sıkıştırmanın performans üzerindeki etkileri. Yüksek oranda sıkıştırılmış resimlerin kodunu çözmenin cezaları nelerdir?
  • 1x ekrana 2x resim yüklendiğinde resmi küçültmek zorunda kalmanın performans açısından olumsuz etkileri nelerdir?

Özetlemek gerekirse, kafes resimler kullanmak yerine CSS ve SVG'yi etkinleştirin. Kare resimler kesinlikle gerekliyse sınırlı paleti ve çok sayıda düz renge sahip resimler için PNG kullanın. Çok renkli ve gradyanlı resimler için JPEG kullanın. Bu yaklaşımın en iyi tarafı, işaretlemenin neredeyse hiç değişmemesidir. Web geliştiricisinin yapması gereken tek şey, 2x öğe oluşturmak ve resimlerinizi DOM'de uygun şekilde boyutlandırmaktır.

Daha fazla bilgi edinmek için benzer bir konu hakkındaki Scott Jehl'in makalesini inceleyebilirsiniz. Resimleriniz net görünsün ve hücresel veri kullanımınız düşük olsun!