Skip to content

Arc Distortion

TIP

See Arc Distortion at ImageMagick distortions guide for examples.

Explanation

Arc distortion curves image into arc or even into full circle.

By default, it will curve the given image into a perfectly circular arc over the angle given, and without other arguments it will try to preserve the scaling of both the horizontal center-line of the image, and the image's aspect ratio, as much as possible.

To do this it takes up to four arguments:

  1. arc angle
  2. rotation angle
  3. outer radius
  4. inner radius

However only the arc angle is required, the other arguments are optional, and can be added as needed, in the sequence given.

Adding the second argument rotation angle allows you to rotate the output image around the circle.

When no specific radius argument has been set, the Arc distortion method takes great pains to try to ensure the original images scale is preserved as much as possible. To do this the horizontal center line of the image is set to the 'ideal radius' for the width and the given arc angle of the source image.

This means that if you arc the image over a larger arc angle, the radius of the center-line used will also shrink by the same factor. As such the radius of the center-line will be smaller and tighter.

If you set large angle over which to arc the image, the bottom edge will hit the center of the distortion, and beyond, which results in the lower part of the source image disappearing into oblivion.

The third argument outer radius will override the 'ideal' center line radius that is calculated, so that the top of the image will become a circle of the radius given. Actual output image will be 2px larger that outer radius x 2 to allow anti-aliasing.

The image still remains the same aspect ratio, just scaled so as to fit the circle of the radius requested. Remember the radius can be floating point, but the center of an arc will always be aligned to a pixel 'corner', so the resulting image will still be an even number of pixels wide.

If you provide the fourth inner radius argument, you can get complete control of the width of the ring, or its 'radial height'.

This will distort the radial scaling of the image, and effectively separates the radial scaling from the 'arc width' or angle of the resulting image. In other words the original image aspect ratio will no longer be preserved.

You can even force it to completely fill the inside of the circle, wrapping the bottom edge of the input image at the center, or 'pole' of the distortion.

Usage example

ts
const arcAngle = 360;
const rotationAngle = 0;
const outerRadius = 100;
const innerRadius = 0;

const result = await distort(image, "Arc", [
  arcAngle,
  rotationAngle,
  outerRadius,
  innerRadius,
]);

Note about viewport

Arc distortion forces generation of best-fit viewport for resulting image regardless of viewport option. But you can override it by providing custom output viewport:

ts
const result = await distort(image, "Arc", [90], {
  viewport: { x1: -10, y1: -10, x2: 10, y2: 10 },
});

Also, arc center will be located at (0, 0), according to generated best fit virtual viewport. Corresponding result image point can be then found like so:

ts
const { image } = await distort(sourceImage, "Arc", args);
const viewport = image.getViewport();
const arcCenterX = -viewport.x1;
const arcCenterY = -viewport.y1;

TIP

See Arc Center Point Placement at ImageMagick Arc distortion details

Arc into Full Circle Rings

Longer images will 'Arc' distort a lot better over very large angles. For example you can wrap long images (like text messages) into rings.

If you want to distort image into full circle, VirtualPixelMethod.HORIZONTAL_TILE virtual pixel method is recommended to use in order to hide small gap between edges:

ts
import { distort, VirtualPixelMethod } from "@alxcube/lens";

// ...

const result = await distort(image, "Arc", [360], {
  virtualPixelMethod: VirtualPixelMethod.HORIZONTAL_TILE,
});