Skip to main content
WireKit
Copy for LLM

Image Gallery

<x-wirekit::image-gallery> lays out user-content images in a responsive grid. Clicking a thumbnail opens an accessible lightbox — a focus-trapped dialog that navigates with the arrow keys, closes on Escape, and returns focus to the thumbnail you opened it from. Each image is a <x-wirekit::image> figure, so alt text, lazy loading, and a CLS-safe ratio box come for free.

Pass an array of images, each with a src and an alt (and an optional caption). A signed, ACL-protected download URL works unchanged.

Usage

Gallery with lightbox

Columns and ratio

Control the responsive grid with columns (forwarded to the grid) and the thumbnail shape with ratio:

Three columns, 4/3 thumbnails

Static grid (no lightbox)

Set :lightbox="false" for a plain responsive grid of figures — no dialog, no JavaScript:

Static grid

Per-Item Overlays

Pass an itemOverlay closure to layer a control over each thumbnail — a badge, a per-image report button, or a required content label (a synthetic-media disclosure, a license marker). The closure receives ($item, $i) and returns the markup; it renders as a sibling of the zoom trigger, not inside it, so the thumbnail still opens the lightbox. The overlay wrapper is pointer-events-none — give any interactive control inside it pointer-events: auto so it stays clickable without triggering the zoom.

Return a view or an HtmlString for HTML (a plain string is escaped):

Per-item overlay badge
New
New

In real code the closure typically returns a partial view so the overlay can carry its own components and logic:

<x-wirekit::image-gallery
    :images="$photos"
    :item-overlay="fn (array $item, int $i) => view('partials.photo-report', ['photo' => $item, 'index' => $i])"
/>

Props

Prop Type Default Description
images array [] List of images — each an array with src, alt, and optional caption. A plain string is treated as a decorative src.
columns string '2 md:3 lg:4' Responsive grid column spec (forwarded to the grid).
gap string 'md' Grid gap token.
ratio string|null '1/1' Thumbnail aspect-ratio (CLS-safe).
fit string 'cover' object-fit for each thumbnail. 'cover' crops to a uniform grid (right for mixed-orientation sets); 'contain' shows each image whole, letterboxed inside its ratio box — use it when a single portrait shot must not be cropped.
lightbox bool true Enable the click-to-zoom lightbox. false renders a static grid.
itemOverlay Closure|null null Per-item overlay render-callback fn($item, $i). Returns markup layered over thumbnail $i as a sibling of the zoom trigger — a badge, a report control, a synthetic-media label. Return a view or HtmlString for HTML. See Per-Item Overlays.
scope string|null null Scoped personalization key.

Accessibility

  • Each thumbnail is a real <button> with an accessible name ("View image 2: …"), so the gallery is fully keyboard-operable.
  • The lightbox is a role="dialog" aria-modal="true" overlay, focus-trapped with the same helper Modal and Drawer use — focus cannot escape to the page behind it, and it returns to the triggering thumbnail on close.
  • Every image carries its alt; decorative images pass alt="".

Keyboard Interaction

Key Action
Enter / Space Open the lightbox on the focused thumbnail
Escape Close the lightbox (focus returns to the thumbnail)
Previous image
Next image
Tab Move between the lightbox controls (focus stays trapped inside)

Was this page helpful?

Voting requires cookies or local storage. What we store