Vesture

Inputs

ImageCropper

A draggable, resizable crop rectangle over a source image, with an imperative ref handle that exports the crop at the image's native resolution — not its on-screen display size.

ImageCropper

Preview

Drag the handles, then crop.

Usage

tsx
import { useRef } from "react";
import { ImageCropper, Button } from "@vesture/react";
import type { ImageCropperHandle } from "@vesture/react";

function Example() {
  const cropperRef = useRef<ImageCropperHandle>(null);
  return (
    <>
      <ImageCropper ref={cropperRef} src="/photo.jpg" aspectRatio={1} />
      <Button
        onClick={() => {
          const dataUrl = cropperRef.current?.getCroppedImage();
          if (dataUrl) uploadAvatar(dataUrl);
        }}
      >
        Crop & save
      </Button>
    </>
  );
}

Behavior

  • Drag the rectangle to move it, or its corner/edge handles to resize — both are clamped to the source image's bounds and to minCropSize. Setting aspectRatio locks resizing to that ratio (only corner handles render in that mode).
  • This is a controlled primitive, not a full crop-and-confirm widget: getCroppedImage() (via ref) reads the crop rectangle, draws the corresponding region onto an offscreen canvas at naturalWidth/naturalHeight resolution, and returns a PNG data URL. It also calls onCropComplete with the same result.
  • showConfirmButton is a cheap opt-in convenience that renders a built-in "Crop" button wired to the same ref method, for when you don't need custom button placement.

Props

ImageCropper

PropTypeDefaultDescription
srcstringRequired. Image URL or data URL to crop.
aspectRationumberLocks the crop rectangle's ratio, e.g. 1 for square, 16 / 9. Freeform when omitted.
onCropComplete(dataUrl: string) => voidFires only when the crop is explicitly committed via the ref or the built-in confirm button — never continuously while dragging.
minCropSizenumber20Floor on the crop rectangle's width/height, in displayed CSS pixels.
showConfirmButtonbooleanfalseRenders a built-in "Crop" button wired to getCroppedImage().
altstring""Alt text for the underlying image element.

ImageCropperHandle (ref)

PropTypeDefaultDescription
getCroppedImage()() => stringReturns the current crop as a native-resolution PNG data URL, and fires onCropComplete with the same value.