Tiefenblick

Die Geburt von WebP: Wie VP8 zum Bildformat wurde

koboshiCo-founder
·18 min Lesezeit
Die Geburt von WebP: Wie VP8 zum Bildformat wurde
Zusammenfassung

WebP ist ein RIFF-basierter Behälter, der VP8-Videoframes für Standbilder kapselt. Google stellte es 2010 mit dem kühnen Anspruch vor, 25-34 % kleinere Dateien als JPEG und PNG zu erzeugen. Hier ist die vollständige technische Geschichte – von der Dateisignatur bis zur Lücke in der realen Einführung.

Öffne eine WebP-Datei in einem Hex-Editor. Die ersten zwölf Bytes:

52 49 46 46 ?? ?? ?? ?? 57 45 42 50

Das ist der RIFF/WAVE-Behälter-Header. 52 49 46 46 buchstabiert "RIFF" in ASCII. Die nächsten vier Bytes sind die Dateigröße in Little-Endian uint32. 57 45 42 50 buchstabiert "WEBP". Eine WebP-Datei ist kein roher Bitstrom. Es ist ein Behälter, genau wie WAV-Audio oder AVI-Video, aufgebaut nach derselben RIFF-Spezifikation, die Microsoft 1991 einführte. Innerhalb dieses Behälters sitzt ein VP8-Videoframe, umgewidmet für ein Standbild. Diese Designentscheidung – einen Videocodec für Fotos zu verwenden – ist das wichtigste Detail, um WebP zu verstehen.

Google stellte WebP am 30. September 2010 vor. Die Verkaufsargumente waren simpel: dieselbe Bildqualität wie JPEG, aber 25-34 % kleinere Dateien. Für PNG war die Behauptung noch kühner – 26 % kleinere Dateien bei verlustfreien Bildern. In einem Web, in dem Bilddaten etwa die Hälfte aller übertragenen Daten ausmachen, hätten diese Zahlen eigentlich für eine Masseneinführung reichen müssen. Taten sie nicht.

Die Übernahme, die WebP schuf

WebP kam nicht aus einem Bildlabor. Es kam aus einem Videocodec.

Im Februar 2010 übernahm Google On2 Technologies für etwa 124 Millionen Dollar. On2 war ein Unternehmen für Videokompression mit langer Historie – ihre Codecs trieben Flash-Video, Skype-Videotelefonie und AOL-Streaming an. Ihr Flaggschiff war VP8, ein Videocodec, der entwickelt wurde, um mit H.264 zu konkurrieren, ohne Patentgebühren zu erheben.

Google veröffentlichte VP8 im Mai 2010 als Open Source unter dem Namen WebM, kombiniert mit dem Vorbis-Audio-Codec und dem Matroska-Behälter. Das Ziel war klar: einen patentfreien Videostack aufbauen, um dem H.264-Lizenzpool von MPEG-LA zu trotzen, der begann, Gebühren für Web-Video-Streaming zu verlangen.

Aber Google hatte einen zweiten Anwendungsfall im Kopf. Die Intra-Frame-Kompression von VP8 – die Kompression eines einzelnen Videoframes ohne Bezug auf andere Frames – war im Grunde ein Standbild-Codec. Dieselben Prädiktionsmodi, Transformationscodierung und Entropiecodierung, die VP8 für Video effizient machten, funktionierten auch für Fotografien. Google extrahierte den Intra-Frame-Modus, kapselte ihn in einen RIFF-Behälter und nannte es WebP.

Der Name war eine Marketingentscheidung. "Web", weil es für das Web entwickelt wurde. "P", weil Bildformate auf P enden – JPEG, PNG, BMP, TIFF. Das Ergebnis war ein Format, das technisch gesehen ein Videoframe war, der vorgab, ein Foto zu sein.

Warum überhaupt ein neues Format entwickeln?

2010 war JPEG achtzehn Jahre alt und PNG vierzehn. Beide waren fest etabliert. Warum also die Mühe?

Die Einschränkungen von JPEG waren real und bekannt:

  • Keine Transparenz. Ein JPEG-Pixel ist entweder vollständig deckend, oder man braucht eine separate Maske.
  • Keine Animation. Animated JPEG existiert nicht als Standard.
  • Nur verlustbehaftet. Die Basisspezifikation von JPEG hat keinen verlustfreien Modus. (JPEG-LS und JPEG 2000 existieren, aber keines ist webkompatibel.)
  • 8-bit Farbtiefe pro Kanal. Kein Wide-Gamut- oder HDR-Support in der Basisspezifikation.
  • Blocking-Artefakte bei niedriger Qualität. Das 8 x 8 DCT-Raster ist bei Qualitätseinstellungen unter 75 sichtbar.

Die Einschränkungen von PNG waren ebenso real:

  • Kein verlustbehafteter Modus. PNG ist immer verlustfrei. Ein 12-MP-Foto als PNG ist 15-25 MB groß.
  • Große Dateien für Fotografien. Die DEFLATE-Kompression von PNG kann nicht mit DCT-basierter psycho-visueller Verwerfung konkurrieren.
  • Keine Animation in der Basisspezifikation. APNG existiert, brauchte aber Jahre, um Browser-Support zu erhalten.

Google erkannte eine Lücke: ein einziges Format, das verlustbehaftete und verlustfreie Kompression, Transparenz und Animation beherrscht – alles in kleineren Dateien als die etablierten Formate. Das war das Verkaufsargument von WebP.

Wie WebP tatsächlich funktioniert

WebP hat zwei fundamental unterschiedliche interne Formate: verlustbehaftetes WebP (VP8 Intra-Frame) und verlustfreies WebP (ein separater Codec, ebenfalls aus VP8-Forschung abgeleitet).

Verlustbehaftetes WebP: VP8 Intra

Verlustbehaftetes WebP speichert einen VP8-Bitstrom innerhalb eines RIFF-Behälters. Die Encodierungspipeline ist konzeptionell ähnlich wie bei JPEG, aber mit wichtigen Unterschieden:

PhaseJPEGVerlustbehaftetes WebP
Transformation8 x 8 DCT4 x 4 oder 16 x 16 integer DCT-like transform
PrädiktionKeine (nur Intra)4 Intra-Prädiktionsmodi pro 4 x 4 Block
Chroma subsampling4:2:0 default4:2:0 default
EntropiecodierungHuffmanBinary arithmetic coding
Farbtiefe8-bit8-bit

Die intra prediction ist der größte Gewinn. JPEG kodiert jeden 8 x 8 Block unabhängig. WebP prädiziert jeden 4 x 4 Block von seinen bereits kodierten Nachbarn – oben, links oder beides – und kodiert dann nur den Prädiktionsfehler. Für sanfte Gradienten und große flache Bereiche ist der Fehler winzig, und das Kompressionsverhältnis verbessert sich erheblich.

Der arithmetische Kodierer ist außerdem effizienter als die Huffman-Codierung von JPEG – typischerweise 5-10 % zusätzliche Einsparungen bei gleicher Qualität.

Googles eigene Benchmarks von 2010 behaupteten:

MetrikWebP vs JPEG
Durchschnittliche Dateigrößenreduktion25-34 % bei gleichem SSIM
Encodiergeschwindigkeit~8x langsamer als libjpeg
DecodiergeschwindigkeitVergleichbar mit libjpeg

Die Encodiergeschwindigkeit war die versteckte Kostenstelle. Eine WebP-Datei zu erzeugen, erforderte deutlich mehr CPU als JPEG. Für Fotografen, die Hunderte von Bildern exportieren, machte das einen Unterschied.

Verlustfreies WebP

Verlustfreies WebP verwendet einen komplett anderen Codec. Es ist nicht VP8. Es ist ein benutzerdefiniertes Format, das folgendes kombiniert:

  • Prädiktive Codierung: 14 verschiedene räumliche Prädiktionsmodi pro Pixel.
  • Color cache: Eine Hash-Tabelle kürzlich gesehener Farben, um lokale Wiederholungen auszunutzen.
  • LZ77 back-references: Wie PNGs DEFLATE, aber mit 2D-räumlich-bewusstem Matching.
  • Huffman + arithmetic hybrid: Die Entropiecodierung passt sich lokalen Statistiken an.

Google behauptete durchschnittlich 26 % kleinere Dateien als PNG. In der Praxis variieren die Einsparungen stark – einfache Grafiken mit großen flachen Bereichen profitieren kaum, während Fotos mit feiner Textur 30-40 % Reduktion erreichen können.

Extended WebP (VP8X)

Der VP8X-Chunk erweitert WebP um zusätzliche Funktionen:

  • Alpha channel: 8-bit Alpha, separat encodiert, komprimiert mit dem Entropie-Coder von verlustfreiem WebP.
  • Animation: Mehrere Frames mit Timing-Metadaten, im Grunde ein abgespecktes VP8-Video.
  • EXIF metadata: Kamera- und Geolokalisierungsdaten.
  • XMP metadata: Adobe-artige Verarbeitungsanweisungen.
  • ICC color profile: Wide-Gamut- und HDR-Farbmanagement.

Eine VP8X-Datei beginnt mit einem VP8X-Chunk-Header, gefolgt von Flags, die anzeigen, welche Erweiterungen vorhanden sind.

Das Dateiformat

WebP ist ein RIFF-Behälter. Das Bytelayout zu verstehen ist simpel, wenn man RIFF kennt.

RIFF-Behälter-Struktur

Bytes 0-3:   "RIFF" (0x52 0x49 0x46 0x46)
Bytes 4-7:   Dateigröße - 8 (Little-Endian uint32)
Bytes 8-11:  "WEBP" (0x57 0x45 0x42 0x50)
Bytes 12-15: Chunk FourCC – "VP8 ", "VP8L" oder "VP8X"
Bytes 16-19: Chunk-Größe (Little-Endian uint32)
Bytes 20+:   Chunk-Daten

VP8X Extended Header

Wenn der FourCC bei Bytes 12-15 "VP8X" (0x56 0x50 0x38 0x58) ist:

Bytes 20-23: Chunk-Größe = 10 (Little-Endian uint32)
Bytes 24:    Flags-Byte
             Bit 0: Animation vorhanden
             Bit 1: XMP-Metadaten vorhanden
             Bit 2: EXIF-Metadaten vorhanden
             Bit 3: Alpha channel vorhanden
             Bit 4: ICC-Profil vorhanden
             Bits 5-7: Reserviert
Bytes 25-27: Canvas-Breite - 1 (Little-Endian uint24)
Bytes 28-30: Canvas-Höhe - 1 (Little-Endian uint24)

Die Canvas-Dimensionen werden als Breite - 1 und Höhe - 1 gespeichert, also speichert ein 1200 x 675 Bild 1199 und 674. Die maximale Canvas-Größe beträgt 16.777.215 x 16.777.215 Pixel.

Chunk-Typen

FourCCInhaltKompression
VP8 VP8-Bitstrom (verlustbehaftet)VP8 intra
VP8LVP8L-Bitstrom (verlustfrei)Custom lossless
VP8XErweiterter Header + FlagsKeine
ALPHAlpha-Channel-DatenVerlustfreie WebP-Entropie
ANMFAnimationsframeVP8/VP8L pro Frame
ICCPICC-FarbprofilKeine
EXIFEXIF-MetadatenKeine
XMP XMP-MetadatenKeine

WebP anhand der Dateisignatur erkennen

Vertraue nicht der .webp-Erweiterung. Lies die ersten 16 Bytes und parste den RIFF-Header.

Exaktes Bytelayout einer einfachen verlustbehafteten WebP-Datei:

Bytes 0-3:   "RIFF"
Bytes 4-7:   Dateigröße (Little-Endian uint32)
Bytes 8-11:  "WEBP"
Bytes 12-15: "VP8 " (lossy) oder "VP8L" (lossless) oder "VP8X" (extended)

TypeScript im Browser:

interface WebPInfo {
  valid: boolean
  type: "lossy" | "lossless" | "extended" | "unknown"
  width?: number
  height?: number
  hasAlpha?: boolean
  isAnimated?: boolean
}

async function inspectWebP(file: File): Promise<WebPInfo> {
  const buffer = await file.slice(0, 30).arrayBuffer()
  const bytes = new Uint8Array(buffer)

  if (bytes.length < 12) return { valid: false, type: "unknown" }

  const riff = String.fromCharCode(...bytes.slice(0, 4))
  const webp = String.fromCharCode(...bytes.slice(8, 12))
  if (riff !== "RIFF" || webp !== "WEBP") {
    return { valid: false, type: "unknown" }
  }

  const type = String.fromCharCode(...bytes.slice(12, 16))

  if (type === "VP8 ") {
    // Lossy: Breite/Höhe bei Bytes 26-29
    const w = bytes[26] | (bytes[27] << 8)
    const h = bytes[28] | (bytes[29] << 8)
    return { valid: true, type: "lossy", width: w, height: h, hasAlpha: false }
  }

  if (type === "VP8L") {
    // Lossless: Dimensionen in Bits von Bytes 21-24 gepackt
    const bits =
      bytes[21] | (bytes[22] << 8) | (bytes[23] << 16) | (bytes[24] << 24)
    const w = (bits & 0x3fff) + 1
    const h = ((bits >> 14) & 0x3fff) + 1
    const alpha = ((bits >> 28) & 0x01) !== 0
    return {
      valid: true,
      type: "lossless",
      width: w,
      height: h,
      hasAlpha: alpha,
    }
  }

  if (type === "VP8X") {
    const flags = bytes[20]
    const w = (bytes[24] | (bytes[25] << 8) | (bytes[26] << 16)) + 1
    const h = (bytes[27] | (bytes[28] << 8) | (bytes[29] << 16)) + 1
    return {
      valid: true,
      type: "extended",
      width: w,
      height: h,
      hasAlpha: (flags & 0x10) !== 0,
      isAnimated: (flags & 0x02) !== 0,
    }
  }

  return { valid: false, type: "unknown" }
}

Python

import struct
from typing import TypedDict

class WebPInfo(TypedDict):
    valid: bool
    type: str
    width: int | None
    height: int | None
    has_alpha: bool | None
    is_animated: bool | None

def inspect_webp(path: str) -> WebPInfo:
    with open(path, "rb") as f:
        header = f.read(30)

    if len(header) < 12:
        return {"valid": False, "type": "unknown"}

    if header[:4] != b"RIFF" or header[8:12] != b"WEBP":
        return {"valid": False, "type": "unknown"}

    chunk_type = header[12:16]

    if chunk_type == b"VP8 ":
        w, h = struct.unpack("<HH", header[26:30])
        return {"valid": True, "type": "lossy", "width": w, "height": h,
                "has_alpha": False, "is_animated": None}

    if chunk_type == b"VP8L":
        bits = struct.unpack("<I", header[21:25])[0]
        w = (bits & 0x3FFF) + 1
        h = ((bits >> 14) & 0x3FFF) + 1
        alpha = ((bits >> 28) & 0x01) != 0
        return {"valid": True, "type": "lossless", "width": w, "height": h,
                "has_alpha": alpha, "is_animated": None}

    if chunk_type == b"VP8X":
        flags = header[20]
        w = struct.unpack("<I", header[24:27] + b"\x00")[0] + 1
        h = struct.unpack("<I", header[27:30] + b"\x00")[0] + 1
        return {"valid": True, "type": "extended", "width": w, "height": h,
                "has_alpha": bool(flags & 0x10), "is_animated": bool(flags & 0x02)}

    return {"valid": False, "type": "unknown"}

High-Level-Option mit Pillow:

from PIL import Image

with Image.open("image.webp") as img:
    print(img.format)      # WEBP
    print(img.mode)        # RGB oder RGBA
    print(img.size)        # (Breite, Höhe)
    print(img.is_animated) # True, wenn animiert

Oder mit der webp-Bibliothek:

import webp

info = webp.WebPInfo("image.webp")
print(info.width, info.height, info.has_alpha)

Go

package main

import (
	"encoding/binary"
	"fmt"
	"os"
)

type WebPInfo struct {
	Valid       bool
	Type        string
	Width       int
	Height      int
	HasAlpha    bool
	IsAnimated  bool
}

func inspectWebP(path string) (WebPInfo, error) {
	f, err := os.Open(path)
	if err != nil {
		return WebPInfo{}, err
	}
	defer f.Close()

	buf := make([]byte, 30)
	if _, err := f.Read(buf); err != nil {
		return WebPInfo{}, err
	}

	if string(buf[:4]) != "RIFF" || string(buf[8:12]) != "WEBP" {
		return WebPInfo{Valid: false, Type: "unknown"}, nil
	}

	typeStr := string(buf[12:16])
	switch typeStr {
	case "VP8 ":
		w := int(binary.LittleEndian.Uint16(buf[26:28]))
		h := int(binary.LittleEndian.Uint16(buf[28:30]))
		return WebPInfo{Valid: true, Type: "lossy", Width: w, Height: h, HasAlpha: false}, nil
	case "VP8L":
		bits := binary.LittleEndian.Uint32(buf[21:25])
		w := int(bits&0x3FFF) + 1
		h := int((bits>>14)&0x3FFF) + 1
		alpha := ((bits >> 28) & 0x01) != 0
		return WebPInfo{Valid: true, Type: "lossless", Width: w, Height: h, HasAlpha: alpha}, nil
	case "VP8X":
		flags := buf[20]
		w := int(binary.LittleEndian.Uint32(append(buf[24:27], 0))) + 1
		h := int(binary.LittleEndian.Uint32(append(buf[27:30], 0))) + 1
		return WebPInfo{
			Valid: true, Type: "extended", Width: w, Height: h,
			HasAlpha: (flags & 0x10) != 0, IsAnimated: (flags & 0x02) != 0,
		}, nil
	}

	return WebPInfo{Valid: false, Type: "unknown"}, nil
}

PHP

function inspectWebP(string $path): array {
    $header = file_get_contents($path, false, null, 0, 30);
    if (strlen($header) < 12) {
        return ["valid" => false, "type" => "unknown"];
    }

    if (substr($header, 0, 4) !== "RIFF" || substr($header, 8, 4) !== "WEBP") {
        return ["valid" => false, "type" => "unknown"];
    }

    $type = substr($header, 12, 4);

    if ($type === "VP8 ") {
        $w = unpack("v", substr($header, 26, 2))[1];
        $h = unpack("v", substr($header, 28, 2))[1];
        return ["valid" => true, "type" => "lossy", "width" => $w, "height" => $h, "has_alpha" => false];
    }

    if ($type === "VP8L") {
        $bits = unpack("V", substr($header, 21, 4))[1];
        $w = ($bits & 0x3FFF) + 1;
        $h = (($bits >> 14) & 0x3FFF) + 1;
        $alpha = (($bits >> 28) & 0x01) !== 0;
        return ["valid" => true, "type" => "lossless", "width" => $w, "height" => $h, "has_alpha" => $alpha];
    }

    if ($type === "VP8X") {
        $flags = ord($header[20]);
        $w = unpack("V", substr($header, 24, 3) . "\x00")[1] + 1;
        $h = unpack("V", substr($header, 27, 3) . "\x00")[1] + 1;
        return [
            "valid" => true, "type" => "extended",
            "width" => $w, "height" => $h,
            "has_alpha" => (bool)($flags & 0x10),
            "is_animated" => (bool)($flags & 0x02),
        ];
    }

    return ["valid" => false, "type" => "unknown"];
}

Mit fileinfo:

$finfo = new finfo(FILEINFO_MIME_TYPE);
$mime = $finfo->file('image.webp');
// image/webp

ImageMagick CLI

magick identify -verbose image.webp | grep "Format:"
# Format: WEBP (WebP Image Format)

Vollständige Metadaten-Extraktion:

magick identify -verbose image.webp

Das gibt Breite, Höhe, Farbtiefe, Alpha-Vorhandensein, Kompressionstyp und ICC-Profil-Informationen aus.

Oder einfach:

file image.webp
# image.webp: RIFF (little-endian) data, Web/P image

Die Stärken

WebP ist in bestimmten Dimensionen technisch beeindruckend:

Kleinere Dateien: In Googles Referenzkorpus waren verlustbehaftete WebP-Dateien im Durchschnitt 25-34 % kleiner als JPEG bei gleichem SSIM. Verlustfreie WebP-Dateien waren durchschnittlich 26 % kleiner als PNG. Für High-Traffic-Seiten übersetzen sich diese Einsparungen direkt in Bandbreitenkosten und schnellere Ladezeiten.

Feature-Konsolidierung: Ein Format ersetzt JPEG und PNG für die meisten Anwendungsfälle. Verlustbehafteter Modus für Fotos, verlustfreier Modus für Grafiken, Alpha channel für Transparenz, Animation für kurze Sequenzen. Ein Web-Entwickler muss ein Format statt drei kennen.

Browser-natives Decoding: Chrome, Firefox, Safari und Edge liefern alle hardwarebeschleunigte oder hochoptimierte softwareseitige WebP-Decoder. Die Decodiergeschwindigkeit ist auf dem Desktop vergleichbar mit JPEG und auf Mobilgeräten nur 10-20 % langsamer.

Progressive Decodierung: WebP unterstützt inkrementelle Anzeige, während Daten eintreffen, ähnlich wie der progressive Modus von JPEG. Für langsame Verbindungen erscheint ein erkennbares Bild nach Empfang von ~30 % der Datei.

Animation: Animated WebP-Dateien sind typischerweise 60-80 % kleiner als animated GIFs bei gleicher Bildqualität, mit vollem 24-bit-Farbraum und 8-bit Alpha pro Frame.

Die Schwächen

WebPs Probleme sind nicht technischer Natur. Sie sind ökologisch.

Encodiergeschwindigkeit: 2010 war die WebP-Encodierung etwa 8-mal langsamer als libjpeg. Die Lücke hat sich verringert – libwebp 2026 ist etwa 2-3-mal langsamer als libjpeg-turbo – aber es zählt immer noch für Batch-Workflows. Ein Fotograf, der 1.000 Bilder exportiert, wartet merklich länger.

Kein 16-bit- oder HDR-Support: WebP ist strikt 8-bit pro Kanal. Für Wide-Gamut-Fotografie, medizinische Bildgebung oder HDR-Inhalte ist WebP unbrauchbar. HEIC, AVIF und JPEG XL unterstützen alle höhere Bittiefen.

Keine verlustfreie JPEG-Rekompression: JPEG XL kann ein bestehendes JPEG verlustfrei rekomprimieren für ~20 % Einsparungen. WebP kann das nicht. Die Konvertierung von JPEG zu WebP erfordert eine vollständige Neuencodierung, die Generation Loss einführt.

Tooling-Lücken: Photoshop unterstützte WebP nicht nativ bis 2022. ImageMagicks WebP-Support erforderte eine libwebp-Plugin-Kompilierung, die viele Distributionen standardmäßig wegließen. Viele Content-Management-Systeme generieren immer noch standardmäßig JPEG/PNG.

Die VP8-Patentwolke: Google veröffentlichte VP8 mit einem Patent-Entschädigungsversprechen, aber die Patentlandschaft des Codecs war nie so sauber wie die von PNG oder JPEG. Einige Organisationen vermieden WebP gezielt, weil sie Googles rechtlichen Schutzschild nicht für gerichtsfest hielten.

Warum das "inferiore" Format gewann

JPEG ist vierunddreißig Jahre alt. Es hat keine Transparenz, keine Animation, keinen verlustfreien Modus und sichtbare Artefakte bei Qualität 75. WebP schlägt es in fast jeder Metrik. Trotzdem gibt der Web Almanac 2025 JPEG mit etwa 46 % aller Web-Bilder gegenüber WebP mit 19 % an.

Der Grund ist nicht technischer Natur. Es sind Netzwerkeffekte und Wechselkosten.

JPEG ist das QWERTY der Bildformate. Jede Kamera speichert standardmäßig JPEG. Jedes Telefon zeigt JPEG nativ an. Jeder Drucker akzeptiert JPEG. Jedes soziale Netzwerk, CMS, CDN und jeder E-Mail-Client verarbeitet JPEG ohne Plugins, Codecs oder Konvertierung. Das Format ist so universell, dass "Bild" und "JPEG" für die meisten Nutzer funktional synonym sind.

WebPs Einführungskurve erzählt die Geschichte:

JahrMeilenstein
2010Google kündigt WebP an (Chrome 8)
2012Chrome 23 fügt lossless- und Alpha-Support hinzu
2013Chrome fügt animated WebP hinzu
2014Android 4.0+ fügt nativen WebP-Support hinzu
2015Facebook konvertiert alle mobilen Fotos zu WebP
2016Safari 14 fügt WebP-Support hinzu
2020Universeller Browser-Support erreicht
2022Photoshop fügt nativen WebP-Export hinzu
2025WebP bei 19 % der Web-Bilder laut Web Almanac

Chrome trieb WebP aggressiv voran, weil Google sowohl den Browser als auch das Format kontrollierte. Facebook adoptierte es, weil es Petabytes an Bandbreite sparte. Aber der Long Tail des Webs – WordPress-Blogs, kleine E-Commerce-Seiten, Enterprise-CMS-Deployments, E-Mail-Newsletter – bewegte sich langsam oder gar nicht.

Der kritische Scheiternspunkt war Apples Ökosystem. iPhones speicherten standardmäßig HEIC, nicht WebP. macOS Preview unterstützte WebP erst ab macOS 11 Big Sur (2020). Das iOS-Share-Sheet bot keinen WebP-Export. Für Fotografen, Designer und Social-Media-Creator, die hauptsächlich auf Apple-Geräten arbeiteten, war WebP unsichtbar.

Inzwischen kam AVIF 2019 mit besserer Kompression als WebP und lizenzfreier Lizenzierung von der Alliance for Open Media. Chrome, Firefox und Safari liefern alle AVIF. Cloudflare und Cloudinary servieren AVIF automatisch. WebP wurde zu einem Sprungbrett – besser als JPEG, aber bereits von der nächsten Generation überholt.

Wo WebP heute steht

WebP ist kein Fehlschlag. Es ist ein Teilerfolg.

Für Web-Entwickler, die 2026 neue Projekte aufbauen, ist WebP die pragmatische Standardwahl für Bilder, die Transparenz oder Animation benötigen. Es ist kleiner als PNG für verlustfreie Grafiken und kleiner als JPEG für Fotografien. Der Browser-Support ist universell. Das Encode-Tooling ist ausgereift.

Aber WebP hat JPEG nicht abgelöst. Es hat sich eine Nische daneben herausgeschnitten – dieselbe Nische, die PNG bereits innehatte, nur mit kleineren Dateien. Die Vision von "ein Format für alle Bilder" materialisierte sich nicht.

Die praktische Realität für 2026:

AnwendungsfallBestes FormatWarum
Fotografien (Legacy)JPEGUniversell, schnelles Encoding, klein genug
Fotografien (neu)AVIF30 % kleiner als WebP, lizenzfrei
Fotografien (Fallback)WebP25 % kleiner als JPEG, universeller Support
Verlustfreie GrafikenWebP oder PNGWebP ist kleiner; PNG ist der sichere Fallback
TransparenzWebP oder PNGWebP hat kleinere Dateien; PNG ist der sichere Fallback
AnimationWebP oder AVIFBeide schlagen GIF um 60-80 %; AVIF ist neuer
Wide-Gamut / HDRAVIF oder JPEG XL10+ bit depth, ICC/ICC v4-Support
Print-WorkflowsTIFF oder JPEG XLCMYK, 16-bit, verlustfreie JPEG-Rekompression

WebPs wirkliches Erbe ist der Beweis, dass das Web neue Bildformate übernehmen kann, wenn ein großer Browser-Anbieter stark genug drängt. Es ebnete den Weg für AVIF. Es zwang Apple dazu, nicht-JPEG/PNG-Formate nativ zu unterstützen. Es zeigte, dass Transparenz und Animation in einem einzigen Behälter gehören.

Aber es bewies auch, dass technische Überlegenheit nicht ausreicht. Allgegenwart, Trägheit und Ökosystem-Ausrichtung zählen mehr als Kompressionsraten. JPEG wird WebP überleben, nicht weil es besser ist, sondern weil es bereits überall ist.

Das Fazit

WebP wurde aus einem Videocodec entwickelt, um ein Bandbreitenproblem zu lösen. Es hat dieses Problem gelöst – für Google, für Facebook, für jede Seite, die bereit war, ihre Bildpipeline zu konvertieren. Die Kompression ist real, die Features sind nützlich, und der Browser-Support ist vollständig.

Aber das Web wechselt nicht das Format, nur weil ein Whitepaper sagt, das neue sei 25 % kleiner. Es wechselt, wenn das neue Format einfacher zu nutzen ist als das alte, oder wenn das alte so schlecht versagt, dass Migration unvermeidlich ist. JPEG hat nicht schlecht genug versagt. WebP war nicht einfach genug. Und als WebP einfach wurde, war AVIF bereits mit einer größeren Zahl auf dem Datenblatt angekommen.

WebP ist das Betamax der Bildformate – technisch solide, gut unterstützt und letztendlich von etwas überholt, das etwas später mit besserem Marketing und breiterer Unterstützung ankam. Es wird nicht verschwinden. Es wird neben JPEG, PNG, AVIF und was als Nächstes kommt koexistieren, und dieselbe Rolle erfüllen, die PNG heute spielt: der sichere, fähige Fallback, der überall funktioniert.

Wenn du PNG-Dateien hast, die kleinere Dateigrößen für das Web brauchen, konvertiert PNG to WebP sie lokal im Browser – keine Uploads, keine Serververarbeitung. Für JPEGs, die Transparenz oder Animation benötigen, übernimmt JPG to WebP die Konvertierung mit Qualitätskontrolle. Und wenn du den universellen Fallback brauchst, bringen WebP to PNG und WebP to JPG WebP-Dateien zurück in Formate, die in jedem Viewer geöffnet werden.

Mehr Blog-Posts zum Lesen