homeaboutvideotry it nowpricingdocs
Docs

Getting Started

Image transforms

Every transform below goes in the transform query parameter. Chain them with ; and they run in order, for example smartCrop:400x400;radius:max;format:auto. Up to 20 transforms can be chained. Overlay and text layers draw a logo, a watermark or a caption on top.

A transform that is not written correctly, or that would make the image too large, is answered with a 400 and a JSON body whose message says what is wrong. Numbers past a transform's range are clamped to it. Sources larger than about 67 megapixels cannot be transformed. GIF, SVG and other files that are not JPEG, PNG, WebP, BMP or TIFF are served unchanged.

Resize

The resize transform allows you to alter the size of any image. This allows you to reduce the amount of data a user will need to download by serving images of the exact size you need.

The full format of resize is shown below - we will go over each part in more detail afterwards.

1
?transform=resize:200x100~position:top~fit:contain~background:blue

Width and Height

Specify the dimensions of the image. If you only specify one of the dimensions we will maintain the aspect ratio.

demo+boat?transform=resize:50x100
resize:50x100
demo+boat?transform=resize:200x100
resize:200x100
1
2
3
4
5
6
7
8
?transform=resize:100x100


// If you only want to specify a single dimension
// then use an _ as a placeholder

?transform=resize:_x100
?transform=resize:100x_
demo+boat?transform=resize:_x100
resize:_x100
demo+boat?transform=resize:50x_
resize:50x_

Fit

When changing the size of an image there are many strategies that can be used to"fit" the image into the space. The strategy can be given using the

fit
option.

Possible fit options are:

  • contain - without cropping any of the image, ensure it fits within the given dimensions using "letterboxing" where necessary.
  • cover - ensure the image covers both provided dimensions without stretching.
  • fill - stretch the image to the specified dimensions
  • inside - without stretching, resize the image to be as large as possible whilst fitting within the dimensions
  • outside - maintaining aspect ratio, resize the image to be as small as possible while still being greater or equal to the specified dimensions.
demo+boat?transform=resize:200x75~fit:contain~background:hex(ff9999)
resize:200x75~fit:contain
demo+boat?transform=resize:200x75~fit:cover~background:hex(ff9999)
resize:200x75~fit:cover
demo+boat?transform=resize:200x75~fit:fill~background:hex(ff9999)
resize:200x75~fit:fill
demo+boat?transform=resize:200x75~fit:inside~background:hex(ff9999)
resize:200x75~fit:inside
demo+boat?transform=resize:200x75~fit:outside~background:hex(ff9999)
resize:200x75~fit:outside
1
?transform=resize:200x100~fit:contain

Position

Move where the image is in the canvas. Possible values include:

Only the "contain" fit option will allow images to be produced with a visible background. For other fit types, position will do nothing.
  • center (default)
  • top
  • right
  • bottom
  • left
demo+boat?transform=resize:150x150~fit:contain~position:center~background:hex(ff9999)
resize:150x150~fit:contain~position:center
demo+boat?transform=resize:150x150~fit:contain~position:top~background:hex(ff9999)
resize:150x150~fit:contain~position:top
demo+boat?transform=resize:150x150~fit:contain~position:bottom~background:hex(ff9999)
resize:150x150~fit:contain~position:bottom
demo+boat?transform=resize:200x100~fit:contain~position:right~background:hex(ff9999)
resize:200x100~fit:contain~position:right
demo+boat?transform=resize:200x100~fit:contain~position:left~background:hex(ff9999)
resize:200x100~fit:contain~position:left
1
?transform=resize:200x100~position:top

Background

When resizing an image you may get into a scenario where there is blank space on some sides of the new image. By default this blank space will be transparent (for JPEG files it will be white). You can customize this with the background option:

For more information about the format of a color, see the key concepts section
If you are performing many transforms which make use of a background color, you can use the
background
transform to remove duplication.
1
?transform=resize:200x100~background:hex(ff0000)

Focus point

With the default cover fit, part of the image is cut off. Give a focus point to choose what stays in view: ~focus:X,Y in pixels or percent of the original image. The crop is centred on the point as far as the image edges allow.

1
?transform=resize:200x200~focus:80pc,30pc
demo+boat?transform=resize:200x200
resize:200x200
demo+boat?transform=resize:200x200~focus:0pc,50pc
resize:200x200~focus:0pc,50pc
demo+boat?transform=resize:200x200~focus:100pc,50pc
resize:200x200~focus:100pc,50pc

Never upscale

Add ~upscale:false and a small original is never made bigger than it is, which is what you want for responsive images. When the fit would have scaled it up, the box shrinks by the same amount instead, so cover still crops to the box's shape and contain still pads in proportion. With one side free, the image keeps its own size.

1
?transform=resize:1600x_~upscale:false

Limits and errors

Width and height are capped at 4000px. A resize that is not written correctly is answered with a 400 and a JSON body whose message says what is wrong:

resize:300The size must be WIDTHxHEIGHT, with _ for a free side.
resize:_x_At least one of width and height is needed.
resize:-10x10, resize:1.5x10Sizes must be positive whole numbers.
resize:10x10~fitEvery option needs a value.
resize:10x10~color:redUnknown option.
resize:_x100~fit:insideInside and outside need both sides.
resize:10x10~fit:contain~focus:1,1Focus only works with fit cover.
resize:10x10~upscale:noUpscale is true or false.
For older URLs, an unknown fit falls back to cover, an unknown position to center and an invalid background colour is ignored, as they always have been.

Resize Aspect Ratio

The resizeAR transform is very similar to the resize transform with the only exception being instead of setting the width and height you set the desired aspect ratio.

All of the options that can be supplied to the resize transforms can be given to the resizeAR transform. For details of the options, please refer to the resize transform documentation.

1
?transform=resizeAR:16x9
demo+boat
Original
demo+boat?transform=resizeAR:16x9
resizeAR:16x9
demo+boat?transform=resizeAR:2x3
resizeAR:2x3
demo+boat?transform=resizeAR:2x1~background:green~fit:contain
resizeAR:2x1~background:green~fit:contain

Crop

Extract a section of the image, specifying the width and height of the area to extract.

If the given width or height is larger than the image, it is reduced to fit. Sizes can be pixels or a percentage of the image, like crop:50pcx50pc.

In addition to specifying the size of the crop area, you can also specify its placement. The placement can be given in px or percent (pc) and defines where the center of the crop area is. The crop area will always be within the original image meaning if the placement is outside of the bounds it may be adjusted.

Instead of a placement you can anchor the crop to an edge or corner with ~position:, using the same positions as resize.

Crop
1
?transform=crop:50x50
Crop anchored to the top right
1
?transform=crop:200x100~position:top-right
Crop with placement (100px left and 50% down)
1
?transform=crop:50x50@100,50pc
demo+boat
Original
demo+boat?transform=crop:100x100
crop:100x100
demo+boat?transform=crop:100x300@100pc,0pc
crop:100x300@100pc,0pc
demo+boat?transform=crop:1000x100@5000,65pc
crop:1000x100@5000,65pc Here the crop placement is clamped to within the image as it is set to 5000px

Smart Crop

Crop to the most interesting part of the image at the width and height you give. The image is scaled to cover the size, like resize with fit cover, and the crop is moved to where there is the most detail, colour and skin tone instead of the centre.

If the size is larger than the image it is scaled down, keeping its shape, so the image is never enlarged.

It looks at edges, colour and skin tones on a small copy of the image, so it is fast and always gives the same result. An image with no stand-out area is cropped from the centre.

Crop
1
?transform=smartCrop:50x50
demo+boat
Original
demo+boat?transform=smartCrop:100x100
smartCrop:100x100

Rotate

Rotate the image clockwise by any number of degrees. Negative angles turn it anticlockwise. Multiples of 90 are exact; other angles make the image larger to fit the corners.

type: number

1
?transform=rotate:20
demo+boat
Original
demo+boat?transform=rotate:180
rotate = 180
demo+boat?transform=rotate:30
rotate = 30
demo+boat?transform=rotate:-30
rotate = -30

Background

When rotating, unless using angles of 90, 180, or 270 the produced image will have a visible background. By default this blank space is transparent (white for JPEG and BMP, which cannot be transparent). The colour of the background can be customised.

For more information about the format of a color, see the key concepts section
If you are performing many transforms which make use of a background color, you can use the
background
transform to remove duplication.
1
?transform=rotate:20~background:red
demo+boat
Original
demo+boat?transform=rotate:-30~background:blue
rotate = -30 with background=blue

Flip

Flip the image on the X or Y axis, or both.

type: x, y, xy

1
?transform=flip:x
demo+boat
Original
demo+boat?transform=flip:x
flip = x
demo+boat?transform=flip:y
flip = y
demo+boat?transform=flip:xy
flip = xy

Rounded corners and circles

Round the corners by a radius in pixels, or use max to cut a circle (an ellipse on a rectangle). Crop to a square first for a round avatar. Edges are anti-aliased.

The corners are transparent in PNG and WebP. JPEG cannot be transparent, so they are white there unless you set ~background: or a background transform earlier in the chain.

type: number, max

Rounded corners
1
?transform=radius:40
Round avatar
1
?transform=smartCrop:300x300;radius:max;format:png
demo+boat?transform=resize:400x_
Original
demo+boat?transform=resize:400x_;radius:40;format:png
resize:400x_;radius:40
demo+boat?transform=smartCrop:300x300;radius:max;format:png
smartCrop + radius:max
demo+boat?transform=resize:400x_;radius:max~background:hex(f9ca24)
radius:max~background:hex(f9ca24)

Padding

Add space around the image. Give one number for every side, two for vertical and horizontal, or four for top, right, bottom and left (like CSS). The space uses ~background:, then any earlier background transform, then transparent (white for JPEG). Each side is at most 2000px.

type: number, v,h, top,right,bottom,left

1
?transform=pad:20,40~background:white
demo+boat
Original
demo+boat?transform=resize:400x_;pad:30~background:hex(f9ca24)
pad:30~background:hex(f9ca24)
demo+boat?transform=resize:400x_;pad:0,80~background:black
pad:0,80~background:black

Border

Add a solid border of the given width in pixels around the outside of the image. The colour defaults to black.

type: number

min: 0

max: 1000

1
?transform=border:8~color:white
demo+boat
Original
demo+boat?transform=resize:400x_;border:8
resize:400x_;border:8
demo+boat?transform=resize:400x_;border:16~color:hex(ff6bd6)
border:16~color:hex(ff6bd6)

Trim

Cut away a plain border, such as the white space around a product photo or a scan. The border colour is the top-left pixel's unless you give one with ~color:. The number is the tolerance from 0 to 100 (default 10): how different a pixel can be and still count as border.

An image that is one colour all over is left as it is. Trim pairs well with pad, to put back an even margin: trim;pad:24~background:white.

type: number

min: 0

max: 100

1
?transform=trim:10~color:white
demo+boat?transform=resize:300x_;pad:40~background:white
resize:300x_;pad:40~background:white
demo+boat?transform=resize:300x_;pad:40~background:white;trim
…;trim

Device pixel ratio

Serve sharp images on high density screens without changing your sizes: dpr:2 doubles every pixel size in the chain (resize, crop, smartCrop, pad, border and radius). It can go anywhere in the chain and takes 0.1 to 5.

Sizes are still capped after multiplying, so resize stops at 4000px. Percentages are not changed.

type: number

min: 0.1

max: 5

1
?transform=resize:300x_;dpr:2
demo+boat?transform=resize:150x_
resize:150x_
demo+boat?transform=resize:150x_;dpr:2
resize:150x_;dpr:2 (300px wide)

Blur

Apply a Gaussian blur. The amount is the blur radius (sigma) in pixels, from 0 (no blur) to 100. Larger values are treated as 100.

type: number

min: 0

max: 100

1
?transform=blur:10
demo+boat
Original
demo+boat?transform=blur:1
Blur = 1
demo+boat?transform=blur:5
Blur = 5
demo+boat?transform=blur:10
Blur = 10
demo+boat?transform=blur:40
Blur = 40

Sharpen

Sharpen edges, useful after making an image smaller. The amount is from 0 to 10; leave it out for a gentle default of 1.

type: number

min: 0

max: 10

1
?transform=sharpen:2
demo+boat?transform=resize:300x_
Original
demo+boat?transform=resize:300x_;sharpen
sharpen
demo+boat?transform=resize:300x_;sharpen:4
sharpen:4

Grayscale

Remove all colour. greyscale works too.

1
?transform=grayscale
demo+boat
Original
demo+boat?transform=grayscale
grayscale

Saturate

Change the saturation of the image. The amount multiplies it: 0 is greyscale, 1 leaves the image unchanged and 2 doubles it. Values above 10 are treated as 10.

type: number

min: 0

max: 10

1
?transform=saturate:1.5
demo+boat
Original
demo+boat?transform=saturate:0
saturate = 0
demo+boat?transform=saturate:0
saturate = 0.5
demo+boat?transform=saturate:3
saturate = 3

Brightness and contrast

brightness lightens or darkens and contrast increases or reduces the difference between light and dark. Both take -100 to 100, where 0 leaves the image unchanged.

type: number

min: -100

max: 100

1
?transform=brightness:15;contrast:20
demo+boat
Original
demo+boat?transform=brightness:30
brightness:30
demo+boat?transform=brightness:-30
brightness:-30
demo+boat?transform=contrast:40
contrast:40
demo+boat?transform=contrast:-40
contrast:-40

Hue

Rotate every colour round the colour wheel by a number of degrees.

type: number

1
?transform=hue:90
demo+boat
Original
demo+boat?transform=hue:90
hue:90
demo+boat?transform=hue:180
hue:180

Gamma

Adjust the midtones without clipping the highlights or shadows. Above 1 lightens, below 1 darkens.

type: number

min: 0.1

max: 10

1
?transform=gamma:1.5
demo+boat
Original
demo+boat?transform=gamma:1
gamma:1.8
demo+boat?transform=gamma:0
gamma:0.6

Sepia

Give the image a warm, old photograph look. The amount is from 0 to 100 and defaults to 100.

type: number

min: 0

max: 100

1
?transform=sepia
demo+boat
Original
demo+boat?transform=sepia
sepia
demo+boat?transform=sepia:50
sepia:50

Tint

Give the image the hue of a colour while keeping its light and shade. The colour's alpha sets the strength, so tint:hex(ff000080) is a half strength red tint.

For more information about the format of a color, see the key concepts section

type: color

1
?transform=tint:hex(ff0000)
demo+boat
Original
demo+boat?transform=tint:hex(ff0000)
tint = hex(ff0000)
demo+boat?transform=tint:blue
tint = blue
demo+boat?transform=tint:rgb(255,0,255)
tint = rgb(255,0,255)
demo+boat?transform=tint:hex(ff000080)
tint = hex(ff000080), half strength

Opacity

Make the image see-through. The amount is from 0 (invisible) to 100 (unchanged).

JPEG and BMP cannot be transparent, so in those formats the image is faded towards the background colour (white unless you set one).

type: number

min: 0

max: 100

1
?transform=opacity:50;format:png
demo+boat
Original
demo+boat?transform=opacity:50;format:png
opacity:50

Pixelate

Turn the image into square blocks of the given size in pixels, from 1 to 200.

type: number

min: 1

max: 200

1
?transform=pixelate:12
demo+boat
Original
demo+boat?transform=pixelate:8
pixelate:8
demo+boat?transform=pixelate:24
pixelate:24

Invert

Create a negative of the image.

1
?transform=invert
demo+boat
Original
demo+boat?transform=invert
Inverted

Overlay image

Draw another image on top, such as a logo, a badge or a watermark. The overlay is an image file in the same app, given by its id: Fileboy never fetches an image from a URL. Transparent parts of a PNG or WebP overlay let the image show through.

overlay:FILE_ID~width:20pc~position:bottom-right~x:24~y:24~opacity:80

  • width and height: the overlay's size, in pixels or a percentage of the image (20pc is a fifth of its width). Give one and the overlay keeps its shape; give both and it fits inside that box. Leave both out to draw it at its own size.
  • transform:(…): transforms that run on the overlay first, written like any chain: transform:(resize:200x200~fit:cover;radius:max;grayscale). Format, palette, quality, dpr, strip, background and other layers belong in the main chain. Up to 10, and they count towards the limit of 20.

Overlays and text both take these options as well:

  • position: the corner, edge or centre the layer is anchored to: center (the default), top, bottom, left, right, top-left, top-right, bottom-left or bottom-right.
  • x and y: move the layer in from that edge, in pixels or a percentage of the image (5pc). From the centre, or along the middle of an edge, they move it right and down. Negative values move it the other way, and anything past the edge is cut off.
  • opacity: 0 to 100 (default 100).
  • rotate: degrees clockwise, applied after the layer is sized.
  • tile:true repeats the layer across the whole image, lined up with where one copy would go, for a watermark pattern. gap is the space between copies, in pixels or a percentage of the image's width. A pattern can have up to 2,500 copies.
Reading the overlay is checked like any read. An id from another app is answered with a 400, the same as one that does not exist. If the overlay file is set to Signed URLs only, the image URL must be signed, even when the image itself is public: the signature covers the whole transform, overlay included. Those responses are never stored by a shared cache. Overlays can be up to 25 MB and are held to the same pixel limits as any image, and a chain can draw up to 5 overlay and text layers.
A logo in the corner
1
?transform=overlay:3f2a9c1e-7b4d-4e8a-9c6f-1d2e3f4a5b6c~width:20pc~position:bottom-right~x:24~y:24~opacity:80
A watermark pattern
1
?transform=overlay:3f2a9c1e-7b4d-4e8a-9c6f-1d2e3f4a5b6c~width:120~opacity:25~rotate:-30~tile:true~gap:60~transform:(grayscale)

Text

Write text on top: a caption, a photo credit or a repeated watermark. The text comes first and is URL-encoded inside the transform, so %20 is a space, %3B a ;, %7E a ~, %25 a % and %0A a new line. In the URL itself that encoding is encoded again (%2520); the SDKs do both for you.

  • font: sans (the default), sans-bold, sans-italic, mono or mono-bold. These are the Go fonts, which cover Latin, Greek and Cyrillic; other scripts and emoji show as boxes.
  • size: pixels (default 32), or a percentage of the image's height (5pc) so it scales with the image.
  • color: default black. background fills a box behind the text, with padding pixels around it. Colours with alpha work for both.
  • wrap: lines wider than this break at spaces, in pixels or a percentage of the image's width. align lines up the lines: left, center or right.
  • Plus position, x, y, opacity, rotate, tile and gap, as for overlays.
Text can be up to 500 characters and 20 lines. Different text is a different URL, so each version is transformed and cached on its own.
A credit in a box
1
?transform=text:%C2%A9%20Jane%20Doe~size:4pc~color:white~background:hex(00000080)~padding:8~position:bottom-left~x:16~y:16
A repeated watermark
1
?transform=text:DRAFT~font:sans-bold~size:8pc~color:rgba(255,255,255,0.5)~rotate:-30~tile:true~gap:40
demo+boat?transform=resize:300x_;text:%25C2%25A9%2520Fileboy~size:8pc~color:white~background:hex(00000080)~padding:6~position:bottom-left~x:8~y:8
a credit in a box
demo+boat?transform=resize:300x_;text:DRAFT~font:sans-bold~size:10pc~color:rgba(255,255,255,0
a repeated watermark
demo+boat?transform=resize:300x_;text:Fileboy%250Aimage%2520transforms~font:mono~size:9pc~align:center~color:hex(222222)~background:white~padding:6
two lines, centred

Format

Change the file format. auto picks the smallest format the browser says it accepts in its Accept header: AVIF, then WebP, then the original format (BMP and TIFF become PNG). Every current browser sends that header for images, so a plain <img> tag is enough. Each outcome is cached separately and the response sends Vary: Accept, so a CDN in front keeps them apart too.

avif asks for AVIF whatever the browser accepts, except for very large images, which come back as WebP (see below). AVIF is usually the smallest: in our tests, photos came out about 30% smaller than WebP at the same visual quality, and graphics and smooth gradients up to half the size. It keeps transparency exactly. quality means the same in every format, so quality:75 as AVIF looks about as good as quality:75 as WebP.

AVIF is slow to make, so an image over 16 megapixels (4096 × 4096) is sent as WebP instead, for auto and avif alike, and the response's Content-Type says which you got. With lossless in the chain, auto picks WebP over AVIF, because lossless WebP is the smaller. Animated GIF and WebP files cannot be transformed, so they are served as they are, still animated.

If a chain has more than one format transform, the last one wins.

type: auto, avif, webp, jpeg, png, tiff, bmp

1
?transform=format:auto
demo+boat
Original
demo+boat?transform=format:png
Format = PNG
demo+boat?transform=format:jpeg
Format = JPG
demo+boat?transform=format:webp
Format = WEBP
demo+boat?transform=format:avif
Format = AVIF

Image size as JSON

format:json answers with the size of the image instead of the image: the width and height after the other transforms, and the original's size, format and file size. Use it to reserve space for an image before it loads, or to check an upload.

{
  "width": 300,
  "height": 200,
  "original": { "width": 1200, "height": 800, "format": "image/jpeg", "bytes": 254311 }
}
Sizes are as the image is shown, after EXIF orientation. Like any format, the last one in the chain wins.
1
?transform=resize:300x_;format:json

Colour palette

palette answers with the main colours of the image instead of the image: the dominant colour, up to 16 colours with their share of the image, vibrant and muted swatches, and a black or white text colour for each that meets WCAG AA. On its own it describes the original and is answered from the palette stored with the file. After other transforms it describes their result, so crop first to get the colours of part of the image. After an overlay or text it includes what they drew, and needs a signed URL whenever the overlay does.

{
  "dominant": { "hex": "#2f5d8a", "rgb": [47, 93, 138], "share": 0.42, "text": "#ffffff", "contrast": 6.88 },
  "colors": [ ... ],
  "swatches": { "vibrant": { ... }, "darkMuted": { ... }, "lightVibrant": null, ... },
  "transparentShare": 0
}

palette:css answers with CSS custom properties and classes instead. ~colors: sets how many colours are listed (0 to 16, default 6) and ~prefix: names the CSS. See Colour palettes for every field.

Whichever of format and palette comes last decides what the response is. Files that are not JPEG, PNG, WebP, BMP or TIFF are answered with a 422.
1
?transform=palette~colors:4

Lossless

Make WebP or AVIF output lossless: every pixel is kept exactly, at the cost of a bigger file. It suits screenshots, diagrams and logos. PNG, TIFF and BMP are always lossless, and JPEG cannot be, so it only changes WebP and AVIF. Lossless WebP is usually smaller than lossless AVIF, so format:auto picks WebP for a lossless chain.

1
?transform=format:webp;lossless
demo+boat?transform=resize:300x_;format:webp
format:webp
demo+boat?transform=resize:300x_;format:webp;lossless
format:webp;lossless

Quality

Reduce the file size of an image by sacrificing quality. Smaller file sizes will help improve load times on your application especially for slower connections.

You can only have a single quality transform per pipeline. Having multiple will throw an error.

type: integer between 0 and 100

1
?transform=quality:50
demo+boat
Original
demo+boat?transform=format:jpeg;quality:75
quality = 75
demo+boat?transform=format:jpeg;quality:50
quality = 50
demo+boat?transform=format:jpeg;quality:10
quality = 10

Background

The background transform does nothing in and of itself, but rather it affects all other transforms which utilize a background option such as resize or rotate. The background transform will set the default background color for these transforms enabling you to remove possible duplication.

For more information about the format of a color, see the key concepts section
Because the pipeline is processed in order, left to right, the background transform will only affect future transforms.

type: color

min: 0

max: 20

1
?transform=background:hex(ff0000)
demo+boat
Original
demo+boat?transform=background:green;rotate:30
rotate with green background
demo+boat?transform=rotate:30;background:green
rotate:30;background:green; - Because background is used after the rotate, it will not affect it.
demo+boat?transform=background:green;rotate:10;background:red;resize:200x250~fit:contain
background:green;rotate:10; background:red;resize:200x250~fit:contain

Strip metadata

Re-encode the image without changing it, which removes EXIF (including GPS location), ICC profiles and other metadata. Every transform already does this; use strip when you want nothing else changed.

Phone photos are always turned the right way up from their EXIF orientation before any transform runs.
1
?transform=strip
demo+boat?transform=strip
strip
hello@fileboy.io

Fileboy

HomeAboutPricingChangelog
© Copyright 2026, CD2 Solutions Ltd.
Terms and ConditionsPrivacy Policy