Skip to content

shadcn.io is an independent project built on shadcn/ui

Components

Free

Pixel Image for Vue

An image that arrives as a grid of pieces, each fading in on its own beat, grey first and then in colour. For Vue with Ark UI, in CSS keyframes.

UI library: Ark UI

An image arrives as a grid of pieces, each fading in on its own beat, grey at first and then in colour.

Use it once on a page, where the picture itself is the moment: a hero shot, a portfolio piece, a cover. A gallery of them is a distraction, and a photo that only needs to load is an img. In Vue, the motion is CSS keyframes that start once the image has loaded, and with reduced motion the picture shows at once, in colour.

Preview width

Installation

Sign in to get your install command
Free with an account. It carries your token, so the CLI installs everything in one go.
Use email insteadNo credit card

Anatomy

Pixel Image anatomy: root, piece, replay
PixelImage
โ”œโ”€โ”€ pieces (one img per grid cell, hidden from assistive tech)
โ””โ”€โ”€ Replay (a Button, with showReplayButton)

Usage

<script setup lang="ts">
import { PixelImage } from "@/components/ui/pixel-image";
</script>
<template>
  <PixelImage
    alt="Mountain peaks above a sea of clouds"
    grid="6x4"
    showReplayButton
    src="/peaks.jpg"
  />
</template>

Accessibility

The picture is one image to assistive tech (role="img", named by alt); the pieces are copies of it and stay hidden. With reduced motion there is no reveal: the picture shows at once, in colour, and the Replay button is gone since there's nothing to replay. The reveal waits for the image to load, so a slow connection doesn't play it to an empty frame.

Demos

Grids

grid names five splits, columns by rows: 6x4 (the default), 8x8, 8x3, 4x6 and 3x8. More pieces read as a finer mosaic, three columns as tall strips, three rows as bands. Each one here has its own Replay button.

Preview width

Colour

With grayscaleAnimation off, the pieces arrive in colour and the only motion is the fade. Use it when the grey step would fight the picture, such as one that's already muted, or a brand image that must stay in its colours.

Preview width

Custom Grid

customGrid takes any columns and rows from 1 to 16 each way, here 16 by 9 to match a wide frame. The timing props slow it into a longer reveal: each piece fades in 500 ms (pixelFadeInDuration), the starts spread over 2.4 s (maxAnimationDelay), and the colour arrives at 2.6 s (colorRevealDelay).

Preview width

FAQ

How many pieces should Pixel Image use?

The default 6x4 suits most pictures. 8x8 makes a finer mosaic, and 3x8 or 8x3 make strips or bands. customGrid takes any size up to 16 by 16. Each piece is a copy of the image, so the browser loads it once, but hundreds of pieces cost more to draw than a few dozen.

How do I make the Pixel Image reveal faster or slower?

pixelFadeInDuration sets how long each piece fades (1000 ms by default), maxAnimationDelay how far apart the first and last pieces start (1200 ms), and colorRevealDelay when the colour arrives (1300 ms). The Custom Grid demo slows all three.

Can I skip the black and white step?

Yes: set grayscaleAnimation to false and the pieces arrive in full colour, as in the Colour demo. The fade and the scattered order stay the same.

How do people replay the Pixel Image animation in Vue?

Set showReplayButton and a Replay Button sits in the top-end corner; pressing it plays the reveal again from nothing. It hides under reduced motion, where there is no reveal to replay.

When does the Pixel Image reveal start?

When the image has loaded, so a slow connection doesn't play the reveal over an empty frame. An image the browser already has starts at once. The order of the pieces is fixed by their place in the grid, so the server and the browser draw the same thing.

How do I size Pixel Image?

It's square and up to 24rem wide by default (aspect-square w-full max-w-96). Pass className to change it, such as aspect-video max-w-xl for a wide frame, and the image covers whatever shape you give it.

How do I install Pixel Image in Vue?

Run the command in the Installation section on this page. It adds PixelImage and the Button it uses for Replay, and its keyframes to your stylesheet. The command uses the shadcn-vue CLI.

API Reference

PixelImage

<div> data-slot="pixel-image"

PropType
altstring

What the picture shows, for assistive tech. The pieces themselves are hidden from it.

srcstring

The image's URL.

colorRevealDelay?number

The delay before the pieces turn from grey to colour, in milliseconds.

Default
1300
customGrid?object

Any grid from 1 ร— 1 to 16 ร— 16; it replaces grid when it's valid.

Type
{ cols: number; rows: number }
grayscaleAnimation?boolean

Whether the pieces arrive grey and turn to colour once assembled.

Default
true
grid?PixelImageGrid

The grid the picture splits into, columns ร— rows.

Default
"6x4"
maxAnimationDelay?number

The spread of the pieces' start times, in milliseconds: the last piece starts this long after the first.

Default
1200
pixelFadeInDuration?number

How long each piece takes to fade in, in milliseconds.

Default
1000
showReplayButton?boolean

Whether a Replay button sits in the top-end corner. It's hidden under reduced motion, where the picture shows at once.

Default
false
class?string

Merged with the part's classes.

AttributeType
data-run?string

Mirrors run.

CSS variableType
--pixel-image-clipstring
--pixel-image-color-delaystring

When the colour arrives (colorRevealDelay).

--pixel-image-durationstring

How long each piece fades in (pixelFadeInDuration).