Image Kit
1.4.1
2026-10-03
- Fixed: in
vite devthe plugin could regenerate images in an endless loop. A hot update rangenerate()for any image file that changed, including the filesgenerate()itself wrote tooutput, and withincremental: falseevery run rewrote them, which started the next run — hundreds of runs a second. A hot update now runs only for an image insideinputand never for one insideoutput, and runs no longer overlap: changes that arrive during a run collapse into one follow-up run. See Vite Plugin. - Fixed: an
outputfolder insideinputis skipped wheninputis scanned, instead of being fed back in as source images. - Fixed: the dev server no longer reloads the page for every generated file; the placeholders manifest watches only the folders listed in
placeholders.dirs. - Fixed: a huge SVG (for example 30000×30000) made
?placeholderfail with sharp's pixel limit. The size is now read from the file's ownwidth/height/viewBox, and the color is computed from a small render. - Fixed: a corrupt SVG failed the whole build on
?placeholder. It now warns and returns the declared size (or an empty object); a corrupt raster image still fails. - Changed:
?blurhashand?thumbhashon an SVG print a warning that a vector has only a color and point to?placeholder, instead of silently returning an empty string.
1.4.0
2026-10-01
- Placeholders for whole folders.
npx vue-image-kit placeholders --dir public/imagescomputes every image of a folder, recursively, and adds it to the manifest under the URL it is served at, so an image whosesrcis built at runtime (:src="category.image") gets its placeholder too.--dir src/img=/assets/imgmaps a folder that is served from another URL, and--urladds a single remote or CDN image without--remote. See Folders and URLs. - The Vite plugin builds the same manifest by itself. With
vueImageKit({ generate: false, placeholders: { dirs: [...] } })it is the virtual modulevirtual:vue-image-kit/placeholders, rebuilt when a file in those folders changes and cached between builds. See Placeholders manifest from folders. - The Nuxt module registers it all.
vueImageKit: { placeholders: { dirs: [...] } }adds the Vite plugin and gives the manifest to every<VImage>— no command to run and no entry invite.plugins. The old string form, a path to a manifest file, still works, andmanifestmerges such a file in. See Module options. - New Vite imports that compute only a placeholder and write no files.
import placeholder from './photo.jpg?placeholder'returns{ blurhash, placeholderColor, width, height }— the props of<VImage>itself, so<VImage v-bind="placeholder" />is enough.?placeholder=thumbhashreturns a ThumbHash instead of a BlurHash,?placeholder=coloronly the dominant color and the size, and the new?blurhashimport returns just the BlurHash string, like?thumbhash. They also work throughimport.meta.glob(..., { query: '?placeholder' }). - New
generate: falseoption of the Vite plugin. The plugin then no longer processes the wholeinputfolder on start and on hot updates; it only answers?vik,?placeholder,?blurhash,?thumbhashand the virtual manifest.inputdoesn't have to exist. See Placeholders only, no resizing. - The hashes can be tuned:
--components 4x3(BlurHash components),--sample 100(the size the image is downscaled to before hashing) and--color dominant|averageon the command, andtuning: { components, sample, color }in the config file, the Vite plugin and the Nuxt module. The cache is dropped when the tuning changes. See Tuning the hashes. - The Vite plugin caches placeholders in the same file the
placeholderscommand uses, so a repeated build only reads the images that changed. v-lazy-imganduseBackgroundImage()read the placeholders manifest. With noplaceholderof their own they show the decoded blur and the dominant color of the entry for theirsrcwhile the image loads, and theplaceholderscommand fills the manifest for their static usages. See v-lazy-img and useBackgroundImage().?thumbhashand?blurhashnow compute their values the same way as theplaceholderscommand — BlurHash over a white background, ThumbHash fitted into 100×100 — so the same image gets the same hash from either.