scalpel@labs: ~/glossary/image-file-format.mdx5 sections

Image File Format

An image file format is how the file is encoded, shown by its extension or its data-URI MIME type: jpg, png, gif, webp, svg or avif. Each suits a job: JPEG for photos, PNG for flat graphics with transparency, SVG for vectors, WebP and AVIF for smaller modern files.

extension: Scalpel Imagesupdated: 2026-08-14read_time: 3 min
less image-file-format.mdx

Why it matters

Filtering by format lets you grab only the SVGs on a page, or every JPEG, in one pass. It also tells you at a glance which images still use older formats that a newer encoding could shrink. A site serving PNGs where WebP would do is wasting bandwidth.

Understanding what each format does also helps you keep the right files. A GIF poster from 2003 is different from a GIF animation from a video gallery. A PNG could be a photograph (which would be smaller as JPEG) or a logo (which would be smaller as SVG). The format hints at the image's purpose.

How it works

The format is determined by the file's header (magic bytes) and its extension. For images in HTML or CSS, you read the extension from the URL. For data URIs, you read the MIME type immediately after data:. Scalpel Images recognises six formats.

JPEG (.jpg, .jpeg) is lossy compression. It throws away information that human eyes don't notice, making photos much smaller. A photograph at 80% quality often looks identical to the original but weighs half as much. The trade-off: you can't get lossless perfection back, and JPEG is bad at graphics with sharp edges (they get blurry).

PNG (.png) is lossless and supports transparency (alpha channel). Every pixel is preserved exactly, so PNG is perfect for logos, icons, and screenshots. It's larger than JPEG for photographs, but smaller than JPEG for flat graphics with few colours. PNG also supports animation (APNG), but it's rarely used.

GIF (.gif) is lossless but limited to 256 colours. It's old and usually smaller than PNG for simple graphics. GIF supports animation (it's the only ancient format that does), so animated GIFs are everywhere. But for modern use, avoid GIF. Use PNG for static graphics and WebP or video for animations.

SVG (.svg) is a vector format: the image is drawn as code (paths, circles, text), not stored as pixels. SVG scales infinitely without quality loss and is tiny for logos and icons. But it doesn't work for photographs or complex artwork. SVGs are text files, so they're also searchable and editable.

WebP (.webp) is modern lossy and lossless compression. It usually beats JPEG and PNG by 25–35 per cent at the same quality. WebP supports transparency and animation too, so it can replace JPEG, PNG and GIF. The catch: older browsers don't support it (anything before 2018 or so), which is why <picture> fallbacks exist.

AVIF (.avif) is even newer compression. It often achieves 20–50 per cent smaller files than WebP. It handles transparency, animation, and high bit-depth beautifully. But support is newer than WebP (roughly 2021 onward for major browsers), so you need a fallback. AVIF also takes much longer to encode, which is why you rarely see it in user uploads.

What does not matter

The MIME type in a data URI doesn't always match the actual format. A string claiming data:image/jpeg;base64,... could be lying. Scalpel Images trusts the data to decode correctly regardless.

Also, file naming convention does not determine the format. A file named photo.png could actually be JPEG data inside a PNG wrapper. The magic bytes at the file's start are the truth; the extension is just a label. But for URLs, the extension is usually reliable, and that's what Scalpel Images reads.

Newer lossy variants like HEIC (Apple's format) or JXQL aren't common on the web yet, so Scalpel Images doesn't list them. But they're coming. The principle stays the same: match the format to the content.

Code example

Here's how to detect an image format from a URL:

function getImageFormat(url) {
  // Extract the path (strip query string and hash)
  const path = url.split('?')[0].split('#')[0];
  
  // Get the extension (last part after the dot)
  const extension = path.split('.').pop().toLowerCase();
  
  // Map to recognised formats
  const formatMap = {
    jpg: 'jpeg',
    jpeg: 'jpeg',
    png: 'png',
    gif: 'gif',
    webp: 'webp',
    svg: 'svg',
    avif: 'avif'
  };
  
  return formatMap[extension] || 'unknown';
}

console.log(getImageFormat('https://example.com/photo.jpg'));
// → "jpeg"

console.log(getImageFormat('data:image/webp;base64,...'));
// → "unknown" (you'd need to parse the MIME type for data URIs)

For data URIs, extract the MIME type:

function getDataUriFormat(dataUrl) {
  // Extract the MIME type between "data:" and ";"
  const mimeMatch = dataUrl.match(/data:([^;,]+)/);
  if (!mimeMatch) return 'unknown';
  
  const mimeType = mimeMatch[1];
  if (mimeType.includes('jpeg')) return 'jpeg';
  if (mimeType.includes('png')) return 'png';
  if (mimeType.includes('gif')) return 'gif';
  if (mimeType.includes('webp')) return 'webp';
  if (mimeType.includes('svg')) return 'svg';
  if (mimeType.includes('avif')) return 'avif';
  
  return 'unknown';
}

console.log(getDataUriFormat('data:image/webp;base64,...'));
// → "webp"

How Scalpel Images shows it

Each image tile carries a format badge (JPEG, PNG, GIF, WebP, SVG or AVIF). The type filter at the top lets you check or uncheck formats to show only the images you want. Filtering by format is the fastest way to find, for example, every SVG on a page to study the logos, or every AVIF to see if the site is using next-gen compression.

Sources