V 80. letech minulého století vyvinula společnost Microsoft řešení pro agnostické vykreslování bitmapových obrázků na zařízení: Formát souborů BMP.¹ Ti, kdo dříve používali program Microsoft Paint, si mohli vychutnat gigantickou velikost souboru vytvořeného z jednoduchých tahů a barevných výplní.
Myšlenka formátu souborů BMP spočívá v tom, že každému pixelu je přiřazena hodnota barvy. Pokud tedy mám bitmapu o rozměrech 480×360, která podporuje 16 milionů barev (24 bitů), bitmapa by nakonec měla velikost někde na sever od 4 MB.
To samozřejmě není ideální, pokud chceme vykreslit více kvalitních obrázků. Proto je třeba si položit otázku. „Existuje způsob, jak optimalizovat bitmapovou reprezentaci tak, aby bylo možné stále zachovat vizuální integritu obrázku, ale s menší spotřebou prostředků?“
Odpověď zní ano. Ukazuje se, že uživatele většinou zajímají spíše obrázky jako vizuální pomůcky než důkladnost. Předpokládejme například, že dostanu obrázek mostu Golden Gate, jak je uvedeno níže:
Ačkoli vím, že skutečný most při osobním pohledu obsahuje mnohem více detailů, to, co vidím zde, je pro jeho účely dostatečné. Takže většina lidí je vlastně ochotna vyměnit vizuální integritu za rychlost, pokud je kompromis přijatelný. Pokud je například zhoršení subjektivní vizuální kvality 1 %, ale uživatel si užije 90% úsporu místa, je to většinou vítaný kompromis.
Jedním z klíčových hledisek při kompresi bitmap je tedy optimalizace pro vizuální nerozlišitelnost. To znamená odstranění určitých prvků obrazu, u kterých pouhé oko není schopno identifikovat rozdíl. Tomu se říká ztrátová komprese, která představuje většinu typů komprese, s nimiž se setkáváme při streamování videa na internetu. Takto fungují kodeky H.264, HEVC, HEIF a JPEG.
Jiné typy obrázků, například PNG, jsou komprimovány bezeztrátově. Jde o to, že se zachovává plná vizuální integrita původního obrázku, ale spotřebuje se méně bajtů na reprezentaci téhož. Přesto existují další formáty souborů, například WebP, které podporují jak ztrátovou, tak bezeztrátovou kompresi. Proč chceme komprimovat bezeztrátově? Jak je uvedeno výše, vychází to z toho, čeho chceme pro obrázek dosáhnout. Například ikony v aplikacích jsou obvykle ve formátu PNG (a v poslední době i ve vektorové grafice).
Bezztrátová komprese obrázků spočívá ve větší velikosti souboru na rozdíl od ztrátové komprese. Důvodem je především to, že v prvním případě existuje méně možností komprese než ve druhém. Pro účely tohoto blogu budeme hovořit o ztrátové kompresi.
Obecné kroky při kompresi JPEG se dodnes provádějí při kompresi videa. V průběhu let se algoritmus zdokonalil, ale obecné koncepty zůstávají stejné.
KROK 1. Převod barevného prostoru
Převod obrazu začíná převodem surového formátu RGB na jeho hodnoty Chroma (r a b) a Luminance (Y). Jde o to, že naše oči jsou citlivější na změny světelnosti než na barvy. Proto jsme vlastně schopni snížit rozsah barev v obrázku, aniž by to znatelně ovlivnilo vizuální kvalitu obrázku. To se provádí pomocí podvzorkování chromatičnosti, jak je vysvětleno níže.
KROK 2. Podvzorkování chromatičnosti
Mnozí hráči si možná vzpomenou, že podvzorkování patří mezi možné knoflíky, které mohou nastavit pro optimalizaci herního zážitku. Hlavní myšlenkou je, že čím více podvzorkování člověk provede, tím rychlejší je herní výkon. Je to proto, že hra potřebuje k vykreslení menší rozsah barev.
Podvzorkování barev se značí J:a:b, přičemž J je počet pixelů pro podvzorkování, a představuje pixely horní řady a b pixely dolní řady.
V případě 4:4:4 to znamená, že v pixelech 4×2 musí mít první řádek (a) 4 barvy a stejně tak druhý řádek. V případě 4:2:2 to znamená, že ve 4×2 pixelech musí mít první řádek dvě barvy a stejně tak i druhý řádek. V případě 4:2:0 to znamená, že ve 4×2 pixelech by měl být první řádek reprezentován dvěma barvami a druhý řádek kopíruje to, co je na prvním řádku.
Jak vidíte. pomocí podvzorkování barev je možné snížit rozsah barev až o 75 %.
KROK 3. Diskrétní kosinová transformace
Komprese JPEG se provádí rozřezáním původního obrazu na kousky 8×8 pixelů. V tomto kroku přiřadíme koeficienty pro kousek 8×8 na základě níže uvedených signálů.