Image optimization

pluginImage() resizes and converts images, generating image variants and srcset so the browser can choose according to display width. Change the photo added in Image bundling to use optimization.

Table of Contents

Add the image plugin

vite.config.ts
import { defineConfig, pluginSsg, pluginImage } from "minista"

export default defineConfig({
  plugins: [pluginSsg(), pluginImage()],
})

Add pluginImage() alongside pluginSsg(), which is required for static HTML output. Keep using your existing plugins. The examples below show the minimal setup needed for each page.

Use Image

Pass the source image path to Image. Here, use a 1200×800-pixel photo and convert it to WebP.

src/pages/index.tsx
import { Image } from "minista/assets"

export default function Page() {
  return (
    <>
      <h1>My Site</h1>
      <Image
        src="/src/assets/photo.jpg"
        alt="View of the creative studio"
        format="webp"
        breakpoints={[400, 800, 1200]}
      />
    </>
  )
}

src is a path relative to the project root. Attributes such as width, height, and srcset are generated automatically, allowing the browser to choose a suitable image.

Check optimized image output

Project structure
src/
├── assets/
│   └── photo.jpg
└── pages/
    └── index.tsx
Example build output
dist/
├── index.html
└── assets/
    ├── photo-400x267-[hash].webp
    ├── photo-800x533-[hash].webp
    └── photo-1200x800-[hash].webp

Image output locations and hashes follow Vite's naming settings. Generated sizes depend on the source image, display size, and specified aspect ratio. Candidates larger than the source image are not simply generated by upscaling it.

Image size and aspect ratio

Use layout="fixed" for images with a fixed display width. For example, generate standard and high-resolution versions of a 200-pixel-wide thumbnail.

<Image
  src="/src/assets/photo.jpg"
  alt="Creative studio"
  layout="fixed"
  width={200}
  resolutions={[1, 2]}
  aspect="1:1"
  fit="cover"
/>

Set the ratio with aspect, fitting behavior with fit, and crop alignment with position. Put shared settings in pluginImage({ optimize: { ... } }) and override them with individual props.

Use Picture

Use Picture to output WebP along with the original format.

import { Picture } from "minista/assets"

<Picture
  src="/src/assets/photo.jpg"
  alt="View of the creative studio"
  formats={["webp", "inherit"]}
  loading="lazy"
/>

A picture containing source and img is generated. Use artDirectives to switch source images according to viewport width.

<Picture
  src="/src/assets/photo.jpg"
  alt="View of the creative studio"
  formats={["webp", "inherit"]}
  artDirectives={[
    { media: "(max-width: 640px)", src: "/src/assets/photo-mobile.jpg" },
  ]}
/>

Also prepare photo-mobile.jpg for this example. Load the main image visible on the initial screen immediately and use loading="lazy" for offscreen images.

Remote images

src also accepts HTTPS image URLs. Images are downloaded and optimized during development and builds, so the published site does not fetch images from the source URL.

By default, an image at the same URL is not fetched again until the cache is deleted. For images updated without changing their URL, set an expiration time in milliseconds.

pluginImage({ remoteCache: { maxAge: 60 * 60 * 1000 } })

Output images do not retain metadata such as EXIF, XMP, or IPTC, or ICC profiles. Orientation correction based on EXIF Orientation is applied.

See pluginImage for all settings and component props.

Next, SVG optimization embeds SVG in HTML.