我們經常撰文討論圖片對網站造成的膨脹問題,而Lighthouse等工具也會指出圖片載入作業對使用者體驗造成負面影響的情況,例如增加載入時間,或將頻寬從更重要的資源中移除。解決這個問題的方法之一,就是使用新式壓縮技術來縮減圖片的檔案大小。AVIF 圖片格式是網頁開發人員的新選擇。本篇文章將說明 AVIF 開放原始碼工具的最新更新內容,並介紹 libaom 和 libavif 編碼程式庫,以及如何使用這些程式庫有效地編碼 AVIF 圖片的教學課程。
AVIF 是一種以 AV1 影片編碼器為基礎的圖片格式,由 Alliance for Open Media 制定標準。相較於 JPEG 和 WebP 等其他圖片格式,AVIF 的壓縮效果大幅提升。雖然實際節省的空間取決於內容、編碼設定和品質目標,但我們和其他研究人員發現,相較於 JPEG,使用 WebP 可節省超過 50% 的空間。
此外,AVIF 還新增了編解碼器和容器支援功能,可支援高動態範圍和寬廣色域、膠卷顆粒合成和漸進式解碼等新圖片功能。
新功能
自 Chrome M85 開始支援 AVIF 以來,開放原始碼生態系統中的 AVIF 支援功能已在許多方面有所改善。
Libaom
Libaom 是開放原始碼 AV1 編碼器和解碼器,由開放媒體聯盟 (Alliance for Open Media) 中的公司維護,並用於 Google 和其他會員公司的許多製作服務。在 libaom 2.0.0 版本 (Chrome 新增 AVIF 支援的同時) 和最近的 3.1.0 版本之間,程式碼庫中已加入許多靜態影像編碼最佳化功能。包括:
- 針對多執行緒和平鋪編碼進行最佳化。
- 記憶體用量減少 5 倍。
- 降低 CPU 使用量 6.5 倍,如下圖所示。
這些變更可大幅降低編碼 AVIF 的成本,尤其是網站上載入頻率最高或優先順序最高的圖片。隨著 AV1 的硬體加速編碼功能在伺服器和雲端服務中越來越普及,建立 AVIF 圖片的成本也會持續降低。
Libavif
Libavif 是 AVIF 的參考實作項目,是一種開放原始碼 AVIF 多路器和剖析器,可在 Chrome 中用於解碼 AVIF 圖片。您也可以搭配使用 libaom,從現有的未壓縮圖片建立 AVIF 圖片,或從現有的網路圖片 (JPEG、PNG 等) 進行轉碼。
Libavif 最近新增了對更多編碼器設定的支援,包括與更進階的 libaom 編碼器設定整合。處理管道中的最佳化功能,例如使用 libyuv 和預乘 alpha 支援快速 YUV 轉換至 RGB,可進一步加快解碼程序。最後,libaom 3.1.0 新增的 all-intra 編碼模式支援功能,可提供上述提到的所有 libaom 改善項目。
使用 avifenc 編碼 AVIF 圖片
Squoosh.app 是實驗 AVIF 的快速方法。Squoosh 會執行 WebAssembly 版本的 libavif,並提供許多與指令列工具相同的功能。這麼做可以輕鬆比較 AVIF 與其他舊版和新版格式。另外,Squoosh 也有專為 Node 應用程式設計的CLI 版本。
不過,WebAssembly 尚未能存取所有 CPU 的效能原始碼,因此如果您想以最快速度執行 libavif,建議您使用命令列編碼器 avifenc。
為瞭解如何編碼 AVIF 圖片,我們將使用上述範例中的相同來源圖片,提供教學課程。開始前,請準備好以下項目:
您也需要安裝 zlib、libpng 和 libjpeg 的開發套件。Debian 和 Ubuntu Linux 發行版本的指令如下:
sudo apt-get install zlib1g-dev
sudo apt-get install libpng-dev
sudo apt-get install libjpeg-dev
建構指令列編碼器 avifenc
1. 取得程式碼
檢查 libavif 的發布標記。
git clone -b v0.9.1 https://github.com/AOMediaCodec/libavif.git
2. 將目錄變更為 libavif
cd libavif
您可以透過多種方式設定 avifenc 和 libavif 以進行建構。詳情請參閱 libavif。我們將建構 avifenc,以便以靜態方式連結至 AV1 編碼器和解碼器程式庫 libaom。
3. 取得及建構 libaom
切換至 libavif 外部相依項目目錄。
cd ext
下一個指令會擷取 libaom 原始碼,並以靜態方式建構 libaom。
./aom.cmd
將目錄變更為 libavif。
cd ..
4. 建構指令列編碼工具 avifenc
建議您為 avifenc 建立建構目錄。
mkdir build
切換至建構目錄。
cd build
建立 avifenc 的建構檔案。
cmake -DCMAKE_BUILD_TYPE=Release -DBUILD_SHARED_LIBS=0 -DAVIF_CODEC_AOM=1 -DAVIF_LOCAL_AOM=1 -DAVIF_BUILD_APPS=1 ..
建構 avifenc。
make
您已成功建構 avifenc!
瞭解 avifenc 指令列參數
avifenc 使用以下指令列結構:
./avifenc [options] input.file output.avif
本教學課程中使用的 avifenc 基本參數如下:
avifenc | |
---|---|
--min 0 | 將顏色的最小量化器設為 0 |
--max 63 | 將顏色的最大量化器設為 63 |
--minalpha 0 | 將 alpha 的 min quantizer 設為 0 |
--maxalpha 63 | 將 alpha 的最大量化器設為 63 |
-a end-usage=q | 將速率控制模式設為「Constant Quality (Q)」(固定品質) 模式 |
-a cq-level=Q | 將顏色和 alpha 的量化等級設為 Q |
-a color:cq-level=Q | 將顏色的量化等級設為 Q |
-a alpha:cq-level=Q | 將 alpha 的量化等級設為 Q |
-a tune=ssim | 為 SSIM 調整 (預設為為 PSNR 調整) |
--jobs J | 使用 J 背景工作執行緒 (預設值:1) |
--speed S | 將編碼器速度設為 0 到 10 (最慢到最快,預設值為 6) |
cq-level 選項會設定量化等級 (0 到 63),用於控制顏色或 Alpha 的品質。
使用預設設定建立 AVIF 圖片
執行 avifenc 時,最基本的參數是設定輸入和輸出檔案。
./avifenc happy_dog.jpg happy_dog.avif
建議您使用下列指令列來編碼圖片,例如在量化等級 18 時:
./avifenc --min 0 --max 63 -a end-usage=q -a cq-level=18 -a tune=ssim happy_dog.jpg happy_dog.avif
Avifenc 有許多選項會影響品質和速度。如要查看選項並進一步瞭解相關資訊,請執行 ./avifenc
您現在擁有自己的 AVIF 圖片了!
加快編碼器速度
視電腦的核心數量而定,您可能需要變更 --jobs
參數。這個參數會設定 avifenc 用來建立 AVIF 圖片的執行緒數量。請嘗試在指令列中執行這段指令。
./avifenc --min 0 --max 63 -a end-usage=q -a cq-level=18 -a tune=ssim --jobs 8 happy_dog.jpg happy_dog.avif
這會指示 avifenc 在建立 AVIF 圖片時使用 8 個執行緒,可將 AVIF 編碼速度加快約 5 倍。
對最大內容繪製 (LCP) 的影響
圖片通常是最大內容繪製 (LCP) 指標的常見候選項目。改善 LCP 圖片的載入速度時,常見的最佳化建議之一,就是確保圖片已完成最佳化。縮減資源的傳輸大小,可改善資源載入時間,這是處理圖片 LCP 候選項目時,要著重的四個重要階段之一。
在最佳化圖片時,強烈建議使用圖片 CDN,因為這比在網站建構程序中設定圖片最佳化管道,或手動使用編碼器二進位檔手動最佳化圖片,所需的努力程度低得多。不過,圖片 CDN 的費用可能會讓某些專案無法負擔。如果是這種情況,請在使用 avifenc 編碼器進行最佳化時,考量以下事項:
- 熟悉編碼器提供的選項。您可以嘗試使用 AVIF 的部分可用編碼功能,進一步節省空間,同時保留足夠的圖片品質。
- AVIF 提供有損和無損編碼。視圖片內容而定,某種編碼方式的成效可能會優於其他方式。舉例來說,通常以 JPEG 格式提供的相片,採用有損編碼效果可能會比較好,而如果圖片含有簡單細節或線條圖,通常以 PNG 格式提供,則無損編碼可能會比較好。
- 如果使用支援 imagemin 的社群支援捆綁器,請考慮使用 imagemin-avif 套件,讓捆綁器輸出 AVIF 圖片變化版本。
在 LCP 候選項目為圖片的情況下,您可以嘗試使用 AVIF,藉此改善網站的 LCP 時間。如要進一步瞭解如何最佳化 LCP,請參閱最佳化 LCP 的指南。
結論
使用 libaom、libavif 和其他開放原始碼工具,您就能為網站使用 AVIF 取得最佳圖片品質和效能。這項格式仍屬於新興格式,我們正積極開發最佳化和工具整合功能。如有任何問題、意見或功能要求,請透過 av1-discuss 電子郵件討論群組、AOM GitHub 社群和 AVIF wiki 與我們聯絡。