How to Use AVIF and WebP in Picture Elements

Modern web designers optimize website performance by serving lightweight, next-generation image formats like AVIF and WebP using the HTML5 <picture> element. This guide explains how to structure the <picture> tag to prioritize AVIF for the highest compression efficiency, fall back to WebP for broader compatibility, and include standard formats like JPEG or PNG for legacy browsers, all while maintaining responsiveness across varying screen sizes and resolutions.

The Role of the <picture> Tag

The HTML <picture> element acts as a wrapper that contains one or more <source> tags followed by a single standard <img> tag. Browsers read <source> elements from top to bottom and select the first format they support. Because AVIF provides superior compression to WebP, designers place AVIF sources first, followed by WebP sources, and finally a standard image format in the fallback <img> element.

Basic Format Switching

To alternate between formats based on browser support, use the type attribute on each <source> element. The browser checks its capability against the MIME type specified:

<picture>
  <!-- Browser checks for AVIF support first -->
  <source srcset="hero.avif" type="image/avif">
  
  <!-- Browser checks for WebP if AVIF is unsupported -->
  <source srcset="hero.webp" type="image/webp">
  
  <!-- Default fallback for older browsers -->
  <img src="hero.jpg" alt="A descriptive alt text" width="800" height="600" loading="lazy">
</picture>

Combining Format Negotiation with Responsive Widths

Modern responsive design requires serving not only the right format, but also the correct image dimensions based on device viewport size. This is achieved by combining the type, srcset, and sizes attributes.

<picture>
  <!-- AVIF sources for various screen widths -->
  <source 
    type="image/avif"
    srcset="hero-400.avif 400w, hero-800.avif 800w, hero-1200.avif 1200w"
    sizes="(max-width: 600px) 100vw, (max-width: 1200px) 50vw, 1200px">

  <!-- WebP sources for various screen widths -->
  <source 
    type="image/webp"
    srcset="hero-400.webp 400w, hero-800.webp 800w, hero-1200.webp 1200w"
    sizes="(max-width: 600px) 100vw, (max-width: 1200px) 50vw, 1200px">

  <!-- Fallback image with matching responsive sizes -->
  <img 
    src="hero-800.jpg" 
    srcset="hero-400.jpg 400w, hero-800.jpg 800w, hero-1200.jpg 1200w"
    sizes="(max-width: 600px) 100vw, (max-width: 1200px) 50vw, 1200px"
    alt="A descriptive alt text"
    width="1200" 
    height="800"
    loading="lazy">
</picture>

Implementation Rules