mirror of
https://github.com/lovell/sharp.git
synced 2026-02-05 06:06:18 +01:00
Compare commits
28 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
eefaa99872 | ||
|
|
dbce6fab79 | ||
|
|
af0fcb37c2 | ||
|
|
c6f54e59da | ||
|
|
846563e45f | ||
|
|
9c217ab580 | ||
|
|
e7381e522e | ||
|
|
4340d60ccf | ||
|
|
7f64d464de | ||
|
|
67e927bdb6 | ||
|
|
9c7713ed54 | ||
|
|
8be6da1def | ||
|
|
95635683ac | ||
|
|
44a0ee3fd3 | ||
|
|
ccd51c8cbf | ||
|
|
bb7469b2d1 | ||
|
|
a2cac61209 | ||
|
|
5c19f6dd9b | ||
|
|
3d01775972 | ||
|
|
87562a5111 | ||
|
|
2829e17743 | ||
|
|
ffefbd2ecc | ||
|
|
bc8f983329 | ||
|
|
440936a699 | ||
|
|
0bc79cdb95 | ||
|
|
9a66e25f53 | ||
|
|
8370935ccf | ||
|
|
f908987f35 |
@@ -1,4 +1,6 @@
|
|||||||
## removeAlpha
|
## removeAlpha
|
||||||
|
> removeAlpha() ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Remove alpha channel, if any. This is a no-op if the image does not have an alpha channel.
|
Remove alpha channel, if any. This is a no-op if the image does not have an alpha channel.
|
||||||
|
|
||||||
See also [flatten](/api-operation#flatten).
|
See also [flatten](/api-operation#flatten).
|
||||||
@@ -15,6 +17,8 @@ sharp('rgba.png')
|
|||||||
|
|
||||||
|
|
||||||
## ensureAlpha
|
## ensureAlpha
|
||||||
|
> ensureAlpha([alpha]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Ensure the output image has an alpha transparency channel.
|
Ensure the output image has an alpha transparency channel.
|
||||||
If missing, the added alpha channel will have the specified
|
If missing, the added alpha channel will have the specified
|
||||||
transparency level, defaulting to fully-opaque (1).
|
transparency level, defaulting to fully-opaque (1).
|
||||||
@@ -48,6 +52,8 @@ const rgba = await sharp(rgb)
|
|||||||
|
|
||||||
|
|
||||||
## extractChannel
|
## extractChannel
|
||||||
|
> extractChannel(channel) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Extract a single channel from a multi-channel image.
|
Extract a single channel from a multi-channel image.
|
||||||
|
|
||||||
|
|
||||||
@@ -78,6 +84,8 @@ const [red1, red2, ...] = await sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## joinChannel
|
## joinChannel
|
||||||
|
> joinChannel(images, options) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Join one or more channels to the image.
|
Join one or more channels to the image.
|
||||||
The meaning of the added channels depends on the output colourspace, set with `toColourspace()`.
|
The meaning of the added channels depends on the output colourspace, set with `toColourspace()`.
|
||||||
By default the output image will be web-friendly sRGB, with additional channels interpreted as alpha channels.
|
By default the output image will be web-friendly sRGB, with additional channels interpreted as alpha channels.
|
||||||
@@ -102,6 +110,8 @@ For raw pixel input, the `options` object should contain a `raw` attribute, whic
|
|||||||
|
|
||||||
|
|
||||||
## bandbool
|
## bandbool
|
||||||
|
> bandbool(boolOp) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Perform a bitwise boolean operation on all input image channels (bands) to produce a single channel output image.
|
Perform a bitwise boolean operation on all input image channels (bands) to produce a single channel output image.
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -1,4 +1,6 @@
|
|||||||
## tint
|
## tint
|
||||||
|
> tint(rgb) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Tint the image using the provided chroma while preserving the image luminance.
|
Tint the image using the provided chroma while preserving the image luminance.
|
||||||
An alpha channel may be present and will be unchanged by the operation.
|
An alpha channel may be present and will be unchanged by the operation.
|
||||||
|
|
||||||
@@ -21,6 +23,8 @@ const output = await sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## greyscale
|
## greyscale
|
||||||
|
> greyscale([greyscale]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Convert to 8-bit greyscale; 256 shades of grey.
|
Convert to 8-bit greyscale; 256 shades of grey.
|
||||||
This is a linear operation. If the input image is in a non-linear colour space such as sRGB, use `gamma()` with `greyscale()` for the best results.
|
This is a linear operation. If the input image is in a non-linear colour space such as sRGB, use `gamma()` with `greyscale()` for the best results.
|
||||||
By default the output image will be web-friendly sRGB and contain three (identical) color channels.
|
By default the output image will be web-friendly sRGB and contain three (identical) color channels.
|
||||||
@@ -41,6 +45,8 @@ const output = await sharp(input).greyscale().toBuffer();
|
|||||||
|
|
||||||
|
|
||||||
## grayscale
|
## grayscale
|
||||||
|
> grayscale([grayscale]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Alternative spelling of `greyscale`.
|
Alternative spelling of `greyscale`.
|
||||||
|
|
||||||
|
|
||||||
@@ -52,6 +58,8 @@ Alternative spelling of `greyscale`.
|
|||||||
|
|
||||||
|
|
||||||
## pipelineColourspace
|
## pipelineColourspace
|
||||||
|
> pipelineColourspace([colourspace]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Set the pipeline colourspace.
|
Set the pipeline colourspace.
|
||||||
|
|
||||||
The input image will be converted to the provided colourspace at the start of the pipeline.
|
The input image will be converted to the provided colourspace at the start of the pipeline.
|
||||||
@@ -82,6 +90,8 @@ await sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## pipelineColorspace
|
## pipelineColorspace
|
||||||
|
> pipelineColorspace([colorspace]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Alternative spelling of `pipelineColourspace`.
|
Alternative spelling of `pipelineColourspace`.
|
||||||
|
|
||||||
|
|
||||||
@@ -97,6 +107,8 @@ Alternative spelling of `pipelineColourspace`.
|
|||||||
|
|
||||||
|
|
||||||
## toColourspace
|
## toColourspace
|
||||||
|
> toColourspace([colourspace]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Set the output colourspace.
|
Set the output colourspace.
|
||||||
By default output image will be web-friendly sRGB, with additional channels interpreted as alpha channels.
|
By default output image will be web-friendly sRGB, with additional channels interpreted as alpha channels.
|
||||||
|
|
||||||
@@ -120,6 +132,8 @@ await sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## toColorspace
|
## toColorspace
|
||||||
|
> toColorspace([colorspace]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Alternative spelling of `toColourspace`.
|
Alternative spelling of `toColourspace`.
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@@ -1,4 +1,6 @@
|
|||||||
## composite
|
## composite
|
||||||
|
> composite(images) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Composite image(s) over the processed (resized, extracted etc.) image.
|
Composite image(s) over the processed (resized, extracted etc.) image.
|
||||||
|
|
||||||
The images to composite must be the same size or smaller than the processed image.
|
The images to composite must be the same size or smaller than the processed image.
|
||||||
|
|||||||
@@ -1,9 +1,13 @@
|
|||||||
## Sharp
|
## Sharp
|
||||||
|
> Sharp
|
||||||
|
|
||||||
|
|
||||||
**Emits**: <code>Sharp#event:info</code>, <code>Sharp#event:warning</code>
|
**Emits**: <code>Sharp#event:info</code>, <code>Sharp#event:warning</code>
|
||||||
<a name="new_Sharp_new"></a>
|
<a name="new_Sharp_new"></a>
|
||||||
|
|
||||||
### new
|
### new
|
||||||
|
> new Sharp([input], [options])
|
||||||
|
|
||||||
Constructor factory to create an instance of `sharp`, to which further methods are chained.
|
Constructor factory to create an instance of `sharp`, to which further methods are chained.
|
||||||
|
|
||||||
JPEG, PNG, WebP, GIF, AVIF or TIFF format image data can be streamed out from this object.
|
JPEG, PNG, WebP, GIF, AVIF or TIFF format image data can be streamed out from this object.
|
||||||
@@ -159,6 +163,8 @@ await sharp({
|
|||||||
|
|
||||||
|
|
||||||
## clone
|
## clone
|
||||||
|
> clone() ⇒ [<code>Sharp</code>](#Sharp)
|
||||||
|
|
||||||
Take a "snapshot" of the Sharp instance, returning a new instance.
|
Take a "snapshot" of the Sharp instance, returning a new instance.
|
||||||
Cloned instances inherit the input of their parent instance.
|
Cloned instances inherit the input of their parent instance.
|
||||||
This allows multiple output Streams and therefore multiple processing pipelines to share a single input Stream.
|
This allows multiple output Streams and therefore multiple processing pipelines to share a single input Stream.
|
||||||
|
|||||||
@@ -1,4 +1,6 @@
|
|||||||
## metadata
|
## metadata
|
||||||
|
> metadata([callback]) ⇒ <code>Promise.<Object></code> \| <code>Sharp</code>
|
||||||
|
|
||||||
Fast access to (uncached) image metadata without decoding any compressed pixel data.
|
Fast access to (uncached) image metadata without decoding any compressed pixel data.
|
||||||
|
|
||||||
This is read from the header of the input image.
|
This is read from the header of the input image.
|
||||||
@@ -22,6 +24,7 @@ A `Promise` is returned when `callback` is not provided.
|
|||||||
- `isProgressive`: Boolean indicating whether the image is interlaced using a progressive scan
|
- `isProgressive`: Boolean indicating whether the image is interlaced using a progressive scan
|
||||||
- `pages`: Number of pages/frames contained within the image, with support for TIFF, HEIF, PDF, animated GIF and animated WebP
|
- `pages`: Number of pages/frames contained within the image, with support for TIFF, HEIF, PDF, animated GIF and animated WebP
|
||||||
- `pageHeight`: Number of pixels high each page in a multi-page image will be.
|
- `pageHeight`: Number of pixels high each page in a multi-page image will be.
|
||||||
|
- `paletteBitDepth`: Bit depth of palette-based image (GIF, PNG).
|
||||||
- `loop`: Number of times to loop an animated image, zero refers to a continuous loop.
|
- `loop`: Number of times to loop an animated image, zero refers to a continuous loop.
|
||||||
- `delay`: Delay in ms between each page in an animated image, provided as an array of integers.
|
- `delay`: Delay in ms between each page in an animated image, provided as an array of integers.
|
||||||
- `pagePrimary`: Number of the primary page in a HEIF image
|
- `pagePrimary`: Number of the primary page in a HEIF image
|
||||||
@@ -80,6 +83,8 @@ function getNormalSize({ width, height, orientation }) {
|
|||||||
|
|
||||||
|
|
||||||
## stats
|
## stats
|
||||||
|
> stats([callback]) ⇒ <code>Promise.<Object></code>
|
||||||
|
|
||||||
Access to pixel-derived image statistics for every channel in the image.
|
Access to pixel-derived image statistics for every channel in the image.
|
||||||
A `Promise` is returned when `callback` is not provided.
|
A `Promise` is returned when `callback` is not provided.
|
||||||
|
|
||||||
|
|||||||
@@ -1,4 +1,6 @@
|
|||||||
## rotate
|
## rotate
|
||||||
|
> rotate([angle], [options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Rotate the output image by either an explicit angle
|
Rotate the output image by either an explicit angle
|
||||||
or auto-orient based on the EXIF `Orientation` tag.
|
or auto-orient based on the EXIF `Orientation` tag.
|
||||||
|
|
||||||
@@ -11,7 +13,7 @@ the background colour can be provided with the `background` option.
|
|||||||
If no angle is provided, it is determined from the EXIF data.
|
If no angle is provided, it is determined from the EXIF data.
|
||||||
Mirroring is supported and may infer the use of a flip operation.
|
Mirroring is supported and may infer the use of a flip operation.
|
||||||
|
|
||||||
The use of `rotate` implies the removal of the EXIF `Orientation` tag, if any.
|
The use of `rotate` without an angle will remove the EXIF `Orientation` tag, if any.
|
||||||
|
|
||||||
Only one rotation can occur per pipeline.
|
Only one rotation can occur per pipeline.
|
||||||
Previous calls to `rotate` in the same pipeline will be ignored.
|
Previous calls to `rotate` in the same pipeline will be ignored.
|
||||||
@@ -57,11 +59,11 @@ const resizeThenRotate = await sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## flip
|
## flip
|
||||||
|
> flip([flip]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Mirror the image vertically (up-down) about the x-axis.
|
Mirror the image vertically (up-down) about the x-axis.
|
||||||
This always occurs before rotation, if any.
|
This always occurs before rotation, if any.
|
||||||
|
|
||||||
The use of `flip` implies the removal of the EXIF `Orientation` tag, if any.
|
|
||||||
|
|
||||||
This operation does not work correctly with multi-page images.
|
This operation does not work correctly with multi-page images.
|
||||||
|
|
||||||
|
|
||||||
@@ -77,11 +79,11 @@ const output = await sharp(input).flip().toBuffer();
|
|||||||
|
|
||||||
|
|
||||||
## flop
|
## flop
|
||||||
|
> flop([flop]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Mirror the image horizontally (left-right) about the y-axis.
|
Mirror the image horizontally (left-right) about the y-axis.
|
||||||
This always occurs before rotation, if any.
|
This always occurs before rotation, if any.
|
||||||
|
|
||||||
The use of `flop` implies the removal of the EXIF `Orientation` tag, if any.
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
| Param | Type | Default |
|
| Param | Type | Default |
|
||||||
@@ -95,6 +97,8 @@ const output = await sharp(input).flop().toBuffer();
|
|||||||
|
|
||||||
|
|
||||||
## affine
|
## affine
|
||||||
|
> affine(matrix, [options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Perform an affine transform on an image. This operation will always occur after resizing, extraction and rotation, if any.
|
Perform an affine transform on an image. This operation will always occur after resizing, extraction and rotation, if any.
|
||||||
|
|
||||||
You must provide an array of length 4 or a 2x2 affine transformation matrix.
|
You must provide an array of length 4 or a 2x2 affine transformation matrix.
|
||||||
@@ -146,6 +150,8 @@ inputStream
|
|||||||
|
|
||||||
|
|
||||||
## sharpen
|
## sharpen
|
||||||
|
> sharpen([options], [flat], [jagged]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Sharpen the image.
|
Sharpen the image.
|
||||||
|
|
||||||
When used without parameters, performs a fast, mild sharpen of the output image.
|
When used without parameters, performs a fast, mild sharpen of the output image.
|
||||||
@@ -197,6 +203,8 @@ const data = await sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## median
|
## median
|
||||||
|
> median([size]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Apply median filter.
|
Apply median filter.
|
||||||
When used without parameters the default window is 3x3.
|
When used without parameters the default window is 3x3.
|
||||||
|
|
||||||
@@ -221,6 +229,8 @@ const output = await sharp(input).median(5).toBuffer();
|
|||||||
|
|
||||||
|
|
||||||
## blur
|
## blur
|
||||||
|
> blur([sigma]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Blur the image.
|
Blur the image.
|
||||||
|
|
||||||
When used without parameters, performs a fast 3x3 box blur (equivalent to a box linear filter).
|
When used without parameters, performs a fast 3x3 box blur (equivalent to a box linear filter).
|
||||||
@@ -252,6 +262,8 @@ const gaussianBlurred = await sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## flatten
|
## flatten
|
||||||
|
> flatten([options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Merge alpha transparency channel, if any, with a background, then remove the alpha channel.
|
Merge alpha transparency channel, if any, with a background, then remove the alpha channel.
|
||||||
|
|
||||||
See also [removeAlpha](/api-channel#removealpha).
|
See also [removeAlpha](/api-channel#removealpha).
|
||||||
@@ -272,6 +284,8 @@ await sharp(rgbaInput)
|
|||||||
|
|
||||||
|
|
||||||
## unflatten
|
## unflatten
|
||||||
|
> unflatten()
|
||||||
|
|
||||||
Ensure the image has an alpha channel
|
Ensure the image has an alpha channel
|
||||||
with all white pixel values made fully transparent.
|
with all white pixel values made fully transparent.
|
||||||
|
|
||||||
@@ -297,6 +311,8 @@ await sharp(rgbInput)
|
|||||||
|
|
||||||
|
|
||||||
## gamma
|
## gamma
|
||||||
|
> gamma([gamma], [gammaOut]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Apply a gamma correction by reducing the encoding (darken) pre-resize at a factor of `1/gamma`
|
Apply a gamma correction by reducing the encoding (darken) pre-resize at a factor of `1/gamma`
|
||||||
then increasing the encoding (brighten) post-resize at a factor of `gamma`.
|
then increasing the encoding (brighten) post-resize at a factor of `gamma`.
|
||||||
This can improve the perceived brightness of a resized image in non-linear colour spaces.
|
This can improve the perceived brightness of a resized image in non-linear colour spaces.
|
||||||
@@ -319,6 +335,8 @@ Supply a second argument to use a different output gamma value, otherwise the fi
|
|||||||
|
|
||||||
|
|
||||||
## negate
|
## negate
|
||||||
|
> negate([options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Produce the "negative" of the image.
|
Produce the "negative" of the image.
|
||||||
|
|
||||||
|
|
||||||
@@ -343,6 +361,8 @@ const output = await sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## normalise
|
## normalise
|
||||||
|
> normalise([options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Enhance output image contrast by stretching its luminance to cover a full dynamic range.
|
Enhance output image contrast by stretching its luminance to cover a full dynamic range.
|
||||||
|
|
||||||
Uses a histogram-based approach, taking a default range of 1% to 99% to reduce sensitivity to noise at the extremes.
|
Uses a histogram-based approach, taking a default range of 1% to 99% to reduce sensitivity to noise at the extremes.
|
||||||
@@ -373,6 +393,8 @@ const output = await sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## normalize
|
## normalize
|
||||||
|
> normalize([options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Alternative spelling of normalise.
|
Alternative spelling of normalise.
|
||||||
|
|
||||||
|
|
||||||
@@ -392,6 +414,8 @@ const output = await sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## clahe
|
## clahe
|
||||||
|
> clahe(options) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Perform contrast limiting adaptive histogram equalization
|
Perform contrast limiting adaptive histogram equalization
|
||||||
[CLAHE](https://en.wikipedia.org/wiki/Adaptive_histogram_equalization#Contrast_Limited_AHE).
|
[CLAHE](https://en.wikipedia.org/wiki/Adaptive_histogram_equalization#Contrast_Limited_AHE).
|
||||||
|
|
||||||
@@ -423,6 +447,8 @@ const output = await sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## convolve
|
## convolve
|
||||||
|
> convolve(kernel) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Convolve the image with the specified kernel.
|
Convolve the image with the specified kernel.
|
||||||
|
|
||||||
|
|
||||||
@@ -457,6 +483,8 @@ sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## threshold
|
## threshold
|
||||||
|
> threshold([threshold], [options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Any pixel value greater than or equal to the threshold value will be set to 255, otherwise it will be set to 0.
|
Any pixel value greater than or equal to the threshold value will be set to 255, otherwise it will be set to 0.
|
||||||
|
|
||||||
|
|
||||||
@@ -475,6 +503,8 @@ Any pixel value greater than or equal to the threshold value will be set to 255,
|
|||||||
|
|
||||||
|
|
||||||
## boolean
|
## boolean
|
||||||
|
> boolean(operand, operator, [options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Perform a bitwise boolean operation with operand image.
|
Perform a bitwise boolean operation with operand image.
|
||||||
|
|
||||||
This operation creates an output image where each pixel is the result of
|
This operation creates an output image where each pixel is the result of
|
||||||
@@ -499,6 +529,8 @@ the selected bitwise boolean `operation` between the corresponding pixels of the
|
|||||||
|
|
||||||
|
|
||||||
## linear
|
## linear
|
||||||
|
> linear([a], [b]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Apply the linear formula `a` * input + `b` to the image to adjust image levels.
|
Apply the linear formula `a` * input + `b` to the image to adjust image levels.
|
||||||
|
|
||||||
When a single number is provided, it will be used for all image channels.
|
When a single number is provided, it will be used for all image channels.
|
||||||
@@ -533,6 +565,8 @@ await sharp(rgbInput)
|
|||||||
|
|
||||||
|
|
||||||
## recomb
|
## recomb
|
||||||
|
> recomb(inputMatrix) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Recombine the image with the specified matrix.
|
Recombine the image with the specified matrix.
|
||||||
|
|
||||||
|
|
||||||
@@ -563,6 +597,8 @@ sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## modulate
|
## modulate
|
||||||
|
> modulate([options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Transforms the image using brightness, saturation, hue rotation, and lightness.
|
Transforms the image using brightness, saturation, hue rotation, and lightness.
|
||||||
Brightness and lightness both operate on luminance, with the difference being that
|
Brightness and lightness both operate on luminance, with the difference being that
|
||||||
brightness is multiplicative whereas lightness is additive.
|
brightness is multiplicative whereas lightness is additive.
|
||||||
|
|||||||
@@ -1,4 +1,6 @@
|
|||||||
## toFile
|
## toFile
|
||||||
|
> toFile(fileOut, [callback]) ⇒ <code>Promise.<Object></code>
|
||||||
|
|
||||||
Write output image data to a file.
|
Write output image data to a file.
|
||||||
|
|
||||||
If an explicit output format is not selected, it will be inferred from the extension,
|
If an explicit output format is not selected, it will be inferred from the extension,
|
||||||
@@ -39,6 +41,8 @@ sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## toBuffer
|
## toBuffer
|
||||||
|
> toBuffer([options], [callback]) ⇒ <code>Promise.<Buffer></code>
|
||||||
|
|
||||||
Write output to a Buffer.
|
Write output to a Buffer.
|
||||||
JPEG, PNG, WebP, AVIF, TIFF, GIF and raw pixel data output are supported.
|
JPEG, PNG, WebP, AVIF, TIFF, GIF and raw pixel data output are supported.
|
||||||
|
|
||||||
@@ -108,9 +112,11 @@ await sharp(pixelArray, { raw: { width, height, channels } })
|
|||||||
|
|
||||||
|
|
||||||
## withMetadata
|
## withMetadata
|
||||||
|
> withMetadata([options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Include all metadata (EXIF, XMP, IPTC) from the input image in the output image.
|
Include all metadata (EXIF, XMP, IPTC) from the input image in the output image.
|
||||||
This will also convert to and add a web-friendly sRGB ICC profile unless a custom
|
This will also convert to and add a web-friendly sRGB ICC profile if appropriate,
|
||||||
output profile is provided.
|
unless a custom output profile is provided.
|
||||||
|
|
||||||
The default behaviour, when `withMetadata` is not used, is to convert to the device-independent
|
The default behaviour, when `withMetadata` is not used, is to convert to the device-independent
|
||||||
sRGB colour space and strip all metadata, including the removal of any ICC profile.
|
sRGB colour space and strip all metadata, including the removal of any ICC profile.
|
||||||
@@ -167,6 +173,8 @@ const data = await sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## toFormat
|
## toFormat
|
||||||
|
> toFormat(format, options) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Force output to a given format.
|
Force output to a given format.
|
||||||
|
|
||||||
|
|
||||||
@@ -190,6 +198,8 @@ const data = await sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## jpeg
|
## jpeg
|
||||||
|
> jpeg([options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Use these JPEG options for output image.
|
Use these JPEG options for output image.
|
||||||
|
|
||||||
|
|
||||||
@@ -235,6 +245,8 @@ const data = await sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## png
|
## png
|
||||||
|
> png([options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Use these PNG options for output image.
|
Use these PNG options for output image.
|
||||||
|
|
||||||
By default, PNG output is full colour at 8 or 16 bits per pixel.
|
By default, PNG output is full colour at 8 or 16 bits per pixel.
|
||||||
@@ -278,6 +290,8 @@ const data = await sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## webp
|
## webp
|
||||||
|
> webp([options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Use these WebP options for output image.
|
Use these WebP options for output image.
|
||||||
|
|
||||||
|
|
||||||
@@ -319,6 +333,8 @@ const outputWebp = await sharp(inputWebp, { animated: true })
|
|||||||
|
|
||||||
|
|
||||||
## gif
|
## gif
|
||||||
|
> gif([options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Use these GIF options for the output image.
|
Use these GIF options for the output image.
|
||||||
|
|
||||||
The first entry in the palette is reserved for transparency.
|
The first entry in the palette is reserved for transparency.
|
||||||
@@ -378,6 +394,8 @@ await sharp('in.gif', { animated: true })
|
|||||||
|
|
||||||
|
|
||||||
## jp2
|
## jp2
|
||||||
|
> jp2([options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Use these JP2 options for output image.
|
Use these JP2 options for output image.
|
||||||
|
|
||||||
Requires libvips compiled with support for OpenJPEG.
|
Requires libvips compiled with support for OpenJPEG.
|
||||||
@@ -420,6 +438,8 @@ const data = await sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## tiff
|
## tiff
|
||||||
|
> tiff([options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Use these TIFF options for output image.
|
Use these TIFF options for output image.
|
||||||
|
|
||||||
The `density` can be set in pixels/inch via [withMetadata](#withmetadata)
|
The `density` can be set in pixels/inch via [withMetadata](#withmetadata)
|
||||||
@@ -461,6 +481,8 @@ sharp('input.svg')
|
|||||||
|
|
||||||
|
|
||||||
## avif
|
## avif
|
||||||
|
> avif([options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Use these AVIF options for output image.
|
Use these AVIF options for output image.
|
||||||
|
|
||||||
Whilst it is possible to create AVIF images smaller than 16x16 pixels,
|
Whilst it is possible to create AVIF images smaller than 16x16 pixels,
|
||||||
@@ -498,6 +520,8 @@ const data = await sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## heif
|
## heif
|
||||||
|
> heif([options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Use these HEIF options for output image.
|
Use these HEIF options for output image.
|
||||||
|
|
||||||
Support for patent-encumbered HEIC images using `hevc` compression requires the use of a
|
Support for patent-encumbered HEIC images using `hevc` compression requires the use of a
|
||||||
@@ -528,6 +552,8 @@ const data = await sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## jxl
|
## jxl
|
||||||
|
> jxl([options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Use these JPEG-XL (JXL) options for output image.
|
Use these JPEG-XL (JXL) options for output image.
|
||||||
|
|
||||||
This feature is experimental, please do not use in production systems.
|
This feature is experimental, please do not use in production systems.
|
||||||
@@ -557,6 +583,8 @@ Image metadata (EXIF, XMP) is unsupported.
|
|||||||
|
|
||||||
|
|
||||||
## raw
|
## raw
|
||||||
|
> raw([options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Force output to be raw, uncompressed pixel data.
|
Force output to be raw, uncompressed pixel data.
|
||||||
Pixel ordering is left-to-right, top-to-bottom, without padding.
|
Pixel ordering is left-to-right, top-to-bottom, without padding.
|
||||||
Channel ordering will be RGB or RGBA for non-greyscale colourspaces.
|
Channel ordering will be RGB or RGBA for non-greyscale colourspaces.
|
||||||
@@ -592,6 +620,8 @@ const data = await sharp('input.png')
|
|||||||
|
|
||||||
|
|
||||||
## tile
|
## tile
|
||||||
|
> tile([options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Use tile-based deep zoom (image pyramid) output.
|
Use tile-based deep zoom (image pyramid) output.
|
||||||
|
|
||||||
Set the format and options for tile images via the `toFormat`, `jpeg`, `png` or `webp` functions.
|
Set the format and options for tile images via the `toFormat`, `jpeg`, `png` or `webp` functions.
|
||||||
@@ -653,6 +683,8 @@ readableStream
|
|||||||
|
|
||||||
|
|
||||||
## timeout
|
## timeout
|
||||||
|
> timeout(options) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Set a timeout for processing, in seconds.
|
Set a timeout for processing, in seconds.
|
||||||
Use a value of zero to continue processing indefinitely, the default behaviour.
|
Use a value of zero to continue processing indefinitely, the default behaviour.
|
||||||
|
|
||||||
|
|||||||
@@ -1,4 +1,6 @@
|
|||||||
## resize
|
## resize
|
||||||
|
> resize([width], [height], [options]) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Resize image to `width`, `height` or `width x height`.
|
Resize image to `width`, `height` or `width x height`.
|
||||||
|
|
||||||
When both a `width` and `height` are provided, the possible methods by which the image should **fit** these are:
|
When both a `width` and `height` are provided, the possible methods by which the image should **fit** these are:
|
||||||
@@ -10,7 +12,7 @@ When both a `width` and `height` are provided, the possible methods by which the
|
|||||||
|
|
||||||
Some of these values are based on the [object-fit](https://developer.mozilla.org/en-US/docs/Web/CSS/object-fit) CSS property.
|
Some of these values are based on the [object-fit](https://developer.mozilla.org/en-US/docs/Web/CSS/object-fit) CSS property.
|
||||||
|
|
||||||
<img alt="Examples of various values for the fit property when resizing" width="100%" style="aspect-ratio: 998/243" src="https://cdn.jsdelivr.net/gh/lovell/sharp@main/docs/image/api-resize-fit.png">
|
<img alt="Examples of various values for the fit property when resizing" width="100%" style="aspect-ratio: 998/243" src="https://cdn.jsdelivr.net/gh/lovell/sharp@main/docs/image/api-resize-fit.svg">
|
||||||
|
|
||||||
When using a **fit** of `cover` or `contain`, the default **position** is `centre`. Other options are:
|
When using a **fit** of `cover` or `contain`, the default **position** is `centre`. Other options are:
|
||||||
- `sharp.position`: `top`, `right top`, `right`, `right bottom`, `bottom`, `left bottom`, `left`, `left top`.
|
- `sharp.position`: `top`, `right top`, `right`, `right bottom`, `bottom`, `left bottom`, `left`, `left top`.
|
||||||
@@ -146,6 +148,8 @@ const scaleByHalf = await sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## extend
|
## extend
|
||||||
|
> extend(extend) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Extend / pad / extrude one or more edges of the image with either
|
Extend / pad / extrude one or more edges of the image with either
|
||||||
the provided background colour or pixels derived from the image.
|
the provided background colour or pixels derived from the image.
|
||||||
This operation will always occur after resizing and extraction, if any.
|
This operation will always occur after resizing and extraction, if any.
|
||||||
@@ -204,6 +208,8 @@ sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## extract
|
## extract
|
||||||
|
> extract(options) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Extract/crop a region of the image.
|
Extract/crop a region of the image.
|
||||||
|
|
||||||
- Use `extract` before `resize` for pre-resize extraction.
|
- Use `extract` before `resize` for pre-resize extraction.
|
||||||
@@ -245,6 +251,8 @@ sharp(input)
|
|||||||
|
|
||||||
|
|
||||||
## trim
|
## trim
|
||||||
|
> trim(trim) ⇒ <code>Sharp</code>
|
||||||
|
|
||||||
Trim pixels from all edges that contain values similar to the given background colour, which defaults to that of the top-left pixel.
|
Trim pixels from all edges that contain values similar to the given background colour, which defaults to that of the top-left pixel.
|
||||||
|
|
||||||
Images with an alpha channel will use the combined bounding box of alpha and non-alpha channels.
|
Images with an alpha channel will use the combined bounding box of alpha and non-alpha channels.
|
||||||
|
|||||||
@@ -1,4 +1,6 @@
|
|||||||
## versions
|
## versions
|
||||||
|
> versions
|
||||||
|
|
||||||
An Object containing the version numbers of sharp, libvips and its dependencies.
|
An Object containing the version numbers of sharp, libvips and its dependencies.
|
||||||
|
|
||||||
|
|
||||||
@@ -9,6 +11,8 @@ console.log(sharp.versions);
|
|||||||
|
|
||||||
|
|
||||||
## interpolators
|
## interpolators
|
||||||
|
> interpolators : <code>enum</code>
|
||||||
|
|
||||||
An Object containing the available interpolators and their proper values
|
An Object containing the available interpolators and their proper values
|
||||||
|
|
||||||
|
|
||||||
@@ -27,6 +31,8 @@ An Object containing the available interpolators and their proper values
|
|||||||
|
|
||||||
|
|
||||||
## format
|
## format
|
||||||
|
> format ⇒ <code>Object</code>
|
||||||
|
|
||||||
An Object containing nested boolean values representing the available input and output formats/methods.
|
An Object containing nested boolean values representing the available input and output formats/methods.
|
||||||
|
|
||||||
|
|
||||||
@@ -37,6 +43,8 @@ console.log(sharp.format);
|
|||||||
|
|
||||||
|
|
||||||
## vendor
|
## vendor
|
||||||
|
> vendor
|
||||||
|
|
||||||
An Object containing the platform and architecture
|
An Object containing the platform and architecture
|
||||||
of the current and installed vendored binaries.
|
of the current and installed vendored binaries.
|
||||||
|
|
||||||
@@ -48,6 +56,8 @@ console.log(sharp.vendor);
|
|||||||
|
|
||||||
|
|
||||||
## queue
|
## queue
|
||||||
|
> queue
|
||||||
|
|
||||||
An EventEmitter that emits a `change` event when a task is either:
|
An EventEmitter that emits a `change` event when a task is either:
|
||||||
- queued, waiting for _libuv_ to provide a worker thread
|
- queued, waiting for _libuv_ to provide a worker thread
|
||||||
- complete
|
- complete
|
||||||
@@ -62,6 +72,8 @@ sharp.queue.on('change', function(queueLength) {
|
|||||||
|
|
||||||
|
|
||||||
## cache
|
## cache
|
||||||
|
> cache([options]) ⇒ <code>Object</code>
|
||||||
|
|
||||||
Gets or, when options are provided, sets the limits of _libvips'_ operation cache.
|
Gets or, when options are provided, sets the limits of _libvips'_ operation cache.
|
||||||
Existing entries in the cache will be trimmed after any change in limits.
|
Existing entries in the cache will be trimmed after any change in limits.
|
||||||
This method always returns cache statistics,
|
This method always returns cache statistics,
|
||||||
@@ -89,6 +101,8 @@ sharp.cache(false);
|
|||||||
|
|
||||||
|
|
||||||
## concurrency
|
## concurrency
|
||||||
|
> concurrency([concurrency]) ⇒ <code>number</code>
|
||||||
|
|
||||||
Gets or, when a concurrency is provided, sets
|
Gets or, when a concurrency is provided, sets
|
||||||
the maximum number of threads _libvips_ should use to process _each image_.
|
the maximum number of threads _libvips_ should use to process _each image_.
|
||||||
These are from a thread pool managed by glib,
|
These are from a thread pool managed by glib,
|
||||||
@@ -132,6 +146,8 @@ sharp.concurrency(0); // 4
|
|||||||
|
|
||||||
|
|
||||||
## counters
|
## counters
|
||||||
|
> counters() ⇒ <code>Object</code>
|
||||||
|
|
||||||
Provides access to internal task counters.
|
Provides access to internal task counters.
|
||||||
- queue is the number of tasks this module has queued waiting for _libuv_ to provide a worker thread from its pool.
|
- queue is the number of tasks this module has queued waiting for _libuv_ to provide a worker thread from its pool.
|
||||||
- process is the number of resize tasks currently being processed.
|
- process is the number of resize tasks currently being processed.
|
||||||
@@ -144,6 +160,8 @@ const counters = sharp.counters(); // { queue: 2, process: 4 }
|
|||||||
|
|
||||||
|
|
||||||
## simd
|
## simd
|
||||||
|
> simd([simd]) ⇒ <code>boolean</code>
|
||||||
|
|
||||||
Get and set use of SIMD vector unit instructions.
|
Get and set use of SIMD vector unit instructions.
|
||||||
Requires libvips to have been compiled with liborc support.
|
Requires libvips to have been compiled with liborc support.
|
||||||
|
|
||||||
@@ -169,6 +187,8 @@ const simd = sharp.simd(false);
|
|||||||
|
|
||||||
|
|
||||||
## block
|
## block
|
||||||
|
> block(options)
|
||||||
|
|
||||||
Block libvips operations at runtime.
|
Block libvips operations at runtime.
|
||||||
|
|
||||||
This is in addition to the `VIPS_BLOCK_UNTRUSTED` environment variable,
|
This is in addition to the `VIPS_BLOCK_UNTRUSTED` environment variable,
|
||||||
@@ -191,6 +211,8 @@ sharp.block({
|
|||||||
|
|
||||||
|
|
||||||
## unblock
|
## unblock
|
||||||
|
> unblock(options)
|
||||||
|
|
||||||
Unblock libvips operations at runtime.
|
Unblock libvips operations at runtime.
|
||||||
|
|
||||||
This is useful for defining a list of allowed operations.
|
This is useful for defining a list of allowed operations.
|
||||||
|
|||||||
@@ -29,7 +29,7 @@ const jsdoc2md = require('jsdoc-to-markdown');
|
|||||||
});
|
});
|
||||||
|
|
||||||
const cleanMarkdown = markdown
|
const cleanMarkdown = markdown
|
||||||
.replace(/(## [A-Za-z0-9]+)[^\n]*/g, '$1') // simplify headings to match those of documentationjs, ensures existing URLs work
|
.replace(/(## )([A-Za-z0-9]+)([^\n]*)/g, '$1$2\n> $2$3\n') // simplify headings to match those of documentationjs, ensures existing URLs work
|
||||||
.replace(/<a name="[A-Za-z0-9+]+"><\/a>/g, '') // remove anchors, let docute add these (at markdown to HTML render time)
|
.replace(/<a name="[A-Za-z0-9+]+"><\/a>/g, '') // remove anchors, let docute add these (at markdown to HTML render time)
|
||||||
.replace(/\*\*Kind\*\*: global[^\n]+/g, '') // remove all "global" Kind labels (requires JSDoc refactoring)
|
.replace(/\*\*Kind\*\*: global[^\n]+/g, '') // remove all "global" Kind labels (requires JSDoc refactoring)
|
||||||
.trim();
|
.trim();
|
||||||
|
|||||||
@@ -2,7 +2,46 @@
|
|||||||
|
|
||||||
## v0.32 - *flow*
|
## v0.32 - *flow*
|
||||||
|
|
||||||
Requires libvips v8.14.3
|
Requires libvips v8.14.5
|
||||||
|
|
||||||
|
### v0.32.6 - 18th September 2023
|
||||||
|
|
||||||
|
* Upgrade to libvips v8.14.5 for upstream bug fixes.
|
||||||
|
|
||||||
|
* Ensure composite tile images are fully decoded (regression in 0.32.0).
|
||||||
|
[#3767](https://github.com/lovell/sharp/issues/3767)
|
||||||
|
|
||||||
|
* Ensure `withMetadata` can add ICC profiles to RGB16 output.
|
||||||
|
[#3773](https://github.com/lovell/sharp/issues/3773)
|
||||||
|
|
||||||
|
* Ensure `withMetadata` does not reduce 16-bit images to 8-bit (regression in 0.32.5).
|
||||||
|
[#3773](https://github.com/lovell/sharp/issues/3773)
|
||||||
|
|
||||||
|
* TypeScript: Add definitions for block and unblock.
|
||||||
|
[#3799](https://github.com/lovell/sharp/pull/3799)
|
||||||
|
[@ldrick](https://github.com/ldrick)
|
||||||
|
|
||||||
|
### v0.32.5 - 15th August 2023
|
||||||
|
|
||||||
|
* Upgrade to libvips v8.14.4 for upstream bug fixes.
|
||||||
|
|
||||||
|
* TypeScript: Add missing `WebpPresetEnum` to definitions.
|
||||||
|
[#3748](https://github.com/lovell/sharp/pull/3748)
|
||||||
|
[@pilotso11](https://github.com/pilotso11)
|
||||||
|
|
||||||
|
* Ensure compilation using musl v1.2.4.
|
||||||
|
[#3755](https://github.com/lovell/sharp/pull/3755)
|
||||||
|
[@kleisauke](https://github.com/kleisauke)
|
||||||
|
|
||||||
|
* Ensure resize with a `fit` of `inside` respects 90/270 degree rotation.
|
||||||
|
[#3756](https://github.com/lovell/sharp/issues/3756)
|
||||||
|
|
||||||
|
* TypeScript: Ensure `minSize` property of `WebpOptions` is boolean.
|
||||||
|
[#3758](https://github.com/lovell/sharp/pull/3758)
|
||||||
|
[@sho-xizz](https://github.com/sho-xizz)
|
||||||
|
|
||||||
|
* Ensure `withMetadata` adds default sRGB profile.
|
||||||
|
[#3761](https://github.com/lovell/sharp/issues/3761)
|
||||||
|
|
||||||
### v0.32.4 - 21st July 2023
|
### v0.32.4 - 21st July 2023
|
||||||
|
|
||||||
|
|||||||
Binary file not shown.
|
Before Width: | Height: | Size: 16 KiB |
61
docs/image/api-resize-fit.svg
Normal file
61
docs/image/api-resize-fit.svg
Normal file
@@ -0,0 +1,61 @@
|
|||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="998" height="243" viewBox="0 0 998 243">
|
||||||
|
<defs>
|
||||||
|
<g id="placeholder">
|
||||||
|
<rect width="180" height="128" fill="#64bed8"/>
|
||||||
|
<circle cx="61.1" cy="36.8" r="19.3" fill="#ffefa9"/>
|
||||||
|
<circle cx="61.1" cy="36.8" r="18.1" fill="#fdda42"/>
|
||||||
|
<path d="m67.2 34.7 15.2 46L90 57.9l30.4 38 7.8-15.2 7.5 15.4H44z" fill="#6a696f"/>
|
||||||
|
<path d="m82.4 80.7-15.2-46-.3 69h22.9z" fill="#474749"/>
|
||||||
|
<path d="m90.1 58 12.2 15 18.2 23-13.9.1z" fill="#474749"/>
|
||||||
|
<path d="M135.8 96H131l-2.8-15.3z" fill="#474749"/>
|
||||||
|
<path d="M35.2 96h107.1c0 1.7-1.4 3.2-3.2 3.2H38.4a3.2 3.2 0 0 1-3.2-3.2z" fill="#b9c861"/>
|
||||||
|
<path d="m67.2 34.7-.1 31-6.2-3-5.3 2.7z" fill="#fff"/>
|
||||||
|
<path d="m67.2 34.7 7.6 23-7.7 8z" fill="#b3b1b4"/>
|
||||||
|
<rect width="30.8" height="7.7" x="71.1" y="27.2" rx="2.8" ry="4.1" fill="#fff"/>
|
||||||
|
<rect width="30.8" height="7.7" x="82.2" y="34.8" rx="2.8" ry="4.1" fill="#fff"/>
|
||||||
|
<rect width="30.8" height="7.7" x="36.2" y="19.6" rx="2.8" ry="4.1" fill="#fff"/>
|
||||||
|
<path d="m89.6 72.8-7.2 7.9L90 57.9l10 23z" fill="#fff"/>
|
||||||
|
<path d="m90.1 58 10 23 2.2-8z" fill="#b3b1b4"/>
|
||||||
|
<path d="M131.2 85.2 137 68l9 17.2-8 6z" fill="#8da128"/>
|
||||||
|
<rect width="109.4" height="6.8" x="33.9" y="99.1" rx="13.2" ry="11.4" fill="#22b0d6"/>
|
||||||
|
<path d="m137 68-5.8 17.2 6.8 6.1.3-13.7z" fill="#727d2e"/>
|
||||||
|
<rect width="83.3" height="6.8" x="50.8" y="103.6" rx="10" ry="11.4" fill="#22b0d6"/>
|
||||||
|
<rect width=".7" height="18.4" x="138" y="77.6" fill="#585657"/>
|
||||||
|
<rect width=".5" height="5.2" x="2" y="-161.3" fill="#585657" transform="rotate(120)"/>
|
||||||
|
<rect width=".5" height="5.3" x="5.5" y="-163.3" fill="#585657" transform="rotate(120)"/>
|
||||||
|
<rect width=".5" height="4.8" x="-142.4" y="77.7" fill="#585657" transform="rotate(240)"/>
|
||||||
|
<rect width=".5" height="5.1" x="-146" y="75.6" fill="#585657" transform="rotate(240)"/>
|
||||||
|
</g>
|
||||||
|
<pattern id="img" height="100%" width="100%" viewBox="0 0 180 128">
|
||||||
|
<use xlink:href="#placeholder"/>
|
||||||
|
</pattern>
|
||||||
|
<pattern id="img-fill" width="100%" height="100%" viewBox="0 0 180 128" preserveAspectRatio="none">
|
||||||
|
<use xlink:href="#placeholder"/>
|
||||||
|
</pattern>
|
||||||
|
</defs>
|
||||||
|
<rect x="0" y="0" width="998" height="243" fill="#ddd"/>
|
||||||
|
<g id="cover">
|
||||||
|
<rect x="22" y="28" width="180" height="132" fill="url(#img)"/>
|
||||||
|
<rect x="48" y="30" width="128" height="128" fill="none" stroke="#000" stroke-width="4"/>
|
||||||
|
<text x="112" y="85%" dominant-baseline="middle" text-anchor="middle" font-family="sans" font-size="32" font-weight="bold">cover</text>
|
||||||
|
</g>
|
||||||
|
<g id="contain">
|
||||||
|
<rect x="240" y="30" width="128" height="128" fill="url(#img)" stroke="#000" stroke-width="4"/>
|
||||||
|
<text x="304" y="85%" dominant-baseline="middle" text-anchor="middle" font-family="sans" font-size="32" font-weight="bold" fill="#555">contain</text>
|
||||||
|
</g>
|
||||||
|
<g id="fill">
|
||||||
|
<rect x="432" y="30" width="128" height="128" fill="url(#img-fill)" stroke="#000" stroke-width="4"/>
|
||||||
|
<text x="496" y="85%" dominant-baseline="middle" text-anchor="middle" font-family="sans" font-size="32" font-weight="bold">fill</text>
|
||||||
|
</g>
|
||||||
|
<g id="inside">
|
||||||
|
<rect x="624" y="48" width="128" height="92" fill="url(#img)" stroke="#000" stroke-width="4"/>
|
||||||
|
<rect x="624" y="30" width="128" height="128" fill="none" stroke="#000" stroke-width="4" stroke-dasharray="12 4" stroke-dashoffset="6"/>
|
||||||
|
<text x="688" y="85%" dominant-baseline="middle" text-anchor="middle" font-family="sans" font-size="32" font-weight="bold" fill="#555">inside</text>
|
||||||
|
</g>
|
||||||
|
<g id="outside">
|
||||||
|
<rect x="792" y="30" width="176" height="128" fill="url(#img)" stroke="#000" stroke-width="4"/>
|
||||||
|
<rect x="816" y="30" width="128" height="128" fill="none" stroke="#000" stroke-width="4" stroke-dasharray="12 4" stroke-dashoffset="-2"/>
|
||||||
|
<text x="880" y="85%" dominant-baseline="middle" text-anchor="middle" font-family="sans" font-size="32" font-weight="bold">outside</text>
|
||||||
|
</g>
|
||||||
|
</svg>
|
||||||
|
After Width: | Height: | Size: 4.0 KiB |
File diff suppressed because one or more lines are too long
@@ -40,7 +40,7 @@ for (const match of matches) {
|
|||||||
].forEach((section) => {
|
].forEach((section) => {
|
||||||
const contents = fs.readFileSync(path.join(__dirname, '..', `api-${section}.md`), 'utf8');
|
const contents = fs.readFileSync(path.join(__dirname, '..', `api-${section}.md`), 'utf8');
|
||||||
const matches = contents.matchAll(
|
const matches = contents.matchAll(
|
||||||
/## (?<title>[A-Za-z]+)\n(?<firstparagraph>.+?)\n\n.+?(?<parameters>\| Param .+?\n\n)?\*\*Example/gs
|
/## (?<title>[A-Za-z]+)\n[^\n]+\n(?<firstparagraph>.+?)\n\n.+?(?<parameters>\| Param .+?\n\n)?\*\*Example/gs
|
||||||
);
|
);
|
||||||
for (const match of matches) {
|
for (const match of matches) {
|
||||||
const { title, firstparagraph, parameters } = match.groups;
|
const { title, firstparagraph, parameters } = match.groups;
|
||||||
|
|||||||
59
lib/index.d.ts
vendored
59
lib/index.d.ts
vendored
@@ -139,6 +139,52 @@ declare namespace sharp {
|
|||||||
*/
|
*/
|
||||||
function simd(enable?: boolean): boolean;
|
function simd(enable?: boolean): boolean;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Block libvips operations at runtime.
|
||||||
|
*
|
||||||
|
* This is in addition to the `VIPS_BLOCK_UNTRUSTED` environment variable,
|
||||||
|
* which when set will block all "untrusted" operations.
|
||||||
|
*
|
||||||
|
* @since 0.32.4
|
||||||
|
*
|
||||||
|
* @example <caption>Block all TIFF input.</caption>
|
||||||
|
* sharp.block({
|
||||||
|
* operation: ['VipsForeignLoadTiff']
|
||||||
|
* });
|
||||||
|
*
|
||||||
|
* @param {Object} options
|
||||||
|
* @param {Array<string>} options.operation - List of libvips low-level operation names to block.
|
||||||
|
*/
|
||||||
|
function block(options: { operation: string[] }): void;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Unblock libvips operations at runtime.
|
||||||
|
*
|
||||||
|
* This is useful for defining a list of allowed operations.
|
||||||
|
*
|
||||||
|
* @since 0.32.4
|
||||||
|
*
|
||||||
|
* @example <caption>Block all input except WebP from the filesystem.</caption>
|
||||||
|
* sharp.block({
|
||||||
|
* operation: ['VipsForeignLoad']
|
||||||
|
* });
|
||||||
|
* sharp.unblock({
|
||||||
|
* operation: ['VipsForeignLoadWebpFile']
|
||||||
|
* });
|
||||||
|
*
|
||||||
|
* @example <caption>Block all input except JPEG and PNG from a Buffer or Stream.</caption>
|
||||||
|
* sharp.block({
|
||||||
|
* operation: ['VipsForeignLoad']
|
||||||
|
* });
|
||||||
|
* sharp.unblock({
|
||||||
|
* operation: ['VipsForeignLoadJpegBuffer', 'VipsForeignLoadPngBuffer']
|
||||||
|
* });
|
||||||
|
*
|
||||||
|
* @param {Object} options
|
||||||
|
* @param {Array<string>} options.operation - List of libvips low-level operation names to unblock.
|
||||||
|
*/
|
||||||
|
function unblock(options: { operation: string[] }): void;
|
||||||
|
|
||||||
//#endregion
|
//#endregion
|
||||||
|
|
||||||
const gravity: GravityEnum;
|
const gravity: GravityEnum;
|
||||||
@@ -1124,9 +1170,11 @@ declare namespace sharp {
|
|||||||
/** Level of CPU effort to reduce file size, integer 0-6 (optional, default 4) */
|
/** Level of CPU effort to reduce file size, integer 0-6 (optional, default 4) */
|
||||||
effort?: number | undefined;
|
effort?: number | undefined;
|
||||||
/** Prevent use of animation key frames to minimise file size (slow) (optional, default false) */
|
/** Prevent use of animation key frames to minimise file size (slow) (optional, default false) */
|
||||||
minSize?: number;
|
minSize?: boolean;
|
||||||
/** Allow mixture of lossy and lossless animation frames (slow) (optional, default false) */
|
/** Allow mixture of lossy and lossless animation frames (slow) (optional, default false) */
|
||||||
mixed?: boolean;
|
mixed?: boolean;
|
||||||
|
/** Preset options: one of default, photo, picture, drawing, icon, text (optional, default 'default') */
|
||||||
|
preset?: keyof PresetEnum | undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
interface AvifOptions extends OutputOptions {
|
interface AvifOptions extends OutputOptions {
|
||||||
@@ -1476,6 +1524,15 @@ declare namespace sharp {
|
|||||||
lanczos3: 'lanczos3';
|
lanczos3: 'lanczos3';
|
||||||
}
|
}
|
||||||
|
|
||||||
|
interface PresetEnum {
|
||||||
|
default: 'default';
|
||||||
|
picture: 'picture';
|
||||||
|
photo: 'photo';
|
||||||
|
drawing: 'drawing';
|
||||||
|
icon: 'icon';
|
||||||
|
text: 'text';
|
||||||
|
}
|
||||||
|
|
||||||
interface BoolEnum {
|
interface BoolEnum {
|
||||||
and: 'and';
|
and: 'and';
|
||||||
or: 'or';
|
or: 'or';
|
||||||
|
|||||||
@@ -432,6 +432,7 @@ function _isStreamInput () {
|
|||||||
* - `isProgressive`: Boolean indicating whether the image is interlaced using a progressive scan
|
* - `isProgressive`: Boolean indicating whether the image is interlaced using a progressive scan
|
||||||
* - `pages`: Number of pages/frames contained within the image, with support for TIFF, HEIF, PDF, animated GIF and animated WebP
|
* - `pages`: Number of pages/frames contained within the image, with support for TIFF, HEIF, PDF, animated GIF and animated WebP
|
||||||
* - `pageHeight`: Number of pixels high each page in a multi-page image will be.
|
* - `pageHeight`: Number of pixels high each page in a multi-page image will be.
|
||||||
|
* - `paletteBitDepth`: Bit depth of palette-based image (GIF, PNG).
|
||||||
* - `loop`: Number of times to loop an animated image, zero refers to a continuous loop.
|
* - `loop`: Number of times to loop an animated image, zero refers to a continuous loop.
|
||||||
* - `delay`: Delay in ms between each page in an animated image, provided as an array of integers.
|
* - `delay`: Delay in ms between each page in an animated image, provided as an array of integers.
|
||||||
* - `pagePrimary`: Number of the primary page in a HEIF image
|
* - `pagePrimary`: Number of the primary page in a HEIF image
|
||||||
|
|||||||
@@ -19,7 +19,7 @@ const is = require('./is');
|
|||||||
* If no angle is provided, it is determined from the EXIF data.
|
* If no angle is provided, it is determined from the EXIF data.
|
||||||
* Mirroring is supported and may infer the use of a flip operation.
|
* Mirroring is supported and may infer the use of a flip operation.
|
||||||
*
|
*
|
||||||
* The use of `rotate` implies the removal of the EXIF `Orientation` tag, if any.
|
* The use of `rotate` without an angle will remove the EXIF `Orientation` tag, if any.
|
||||||
*
|
*
|
||||||
* Only one rotation can occur per pipeline.
|
* Only one rotation can occur per pipeline.
|
||||||
* Previous calls to `rotate` in the same pipeline will be ignored.
|
* Previous calls to `rotate` in the same pipeline will be ignored.
|
||||||
@@ -83,8 +83,6 @@ function rotate (angle, options) {
|
|||||||
* Mirror the image vertically (up-down) about the x-axis.
|
* Mirror the image vertically (up-down) about the x-axis.
|
||||||
* This always occurs before rotation, if any.
|
* This always occurs before rotation, if any.
|
||||||
*
|
*
|
||||||
* The use of `flip` implies the removal of the EXIF `Orientation` tag, if any.
|
|
||||||
*
|
|
||||||
* This operation does not work correctly with multi-page images.
|
* This operation does not work correctly with multi-page images.
|
||||||
*
|
*
|
||||||
* @example
|
* @example
|
||||||
@@ -102,8 +100,6 @@ function flip (flip) {
|
|||||||
* Mirror the image horizontally (left-right) about the y-axis.
|
* Mirror the image horizontally (left-right) about the y-axis.
|
||||||
* This always occurs before rotation, if any.
|
* This always occurs before rotation, if any.
|
||||||
*
|
*
|
||||||
* The use of `flop` implies the removal of the EXIF `Orientation` tag, if any.
|
|
||||||
*
|
|
||||||
* @example
|
* @example
|
||||||
* const output = await sharp(input).flop().toBuffer();
|
* const output = await sharp(input).flop().toBuffer();
|
||||||
*
|
*
|
||||||
|
|||||||
@@ -162,8 +162,8 @@ function toBuffer (options, callback) {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Include all metadata (EXIF, XMP, IPTC) from the input image in the output image.
|
* Include all metadata (EXIF, XMP, IPTC) from the input image in the output image.
|
||||||
* This will also convert to and add a web-friendly sRGB ICC profile unless a custom
|
* This will also convert to and add a web-friendly sRGB ICC profile if appropriate,
|
||||||
* output profile is provided.
|
* unless a custom output profile is provided.
|
||||||
*
|
*
|
||||||
* The default behaviour, when `withMetadata` is not used, is to convert to the device-independent
|
* The default behaviour, when `withMetadata` is not used, is to convert to the device-independent
|
||||||
* sRGB colour space and strip all metadata, including the removal of any ICC profile.
|
* sRGB colour space and strip all metadata, including the removal of any ICC profile.
|
||||||
@@ -1046,6 +1046,7 @@ function jxl (options) {
|
|||||||
*
|
*
|
||||||
* @param {Object} [options] - output options
|
* @param {Object} [options] - output options
|
||||||
* @param {string} [options.depth='uchar'] - bit depth, one of: char, uchar (default), short, ushort, int, uint, float, complex, double, dpcomplex
|
* @param {string} [options.depth='uchar'] - bit depth, one of: char, uchar (default), short, ushort, int, uint, float, complex, double, dpcomplex
|
||||||
|
* @returns {Sharp}
|
||||||
* @throws {Error} Invalid options
|
* @throws {Error} Invalid options
|
||||||
*/
|
*/
|
||||||
function raw (options) {
|
function raw (options) {
|
||||||
|
|||||||
@@ -126,7 +126,7 @@ function isResizeExpected (options) {
|
|||||||
*
|
*
|
||||||
* Some of these values are based on the [object-fit](https://developer.mozilla.org/en-US/docs/Web/CSS/object-fit) CSS property.
|
* Some of these values are based on the [object-fit](https://developer.mozilla.org/en-US/docs/Web/CSS/object-fit) CSS property.
|
||||||
*
|
*
|
||||||
* <img alt="Examples of various values for the fit property when resizing" width="100%" style="aspect-ratio: 998/243" src="https://cdn.jsdelivr.net/gh/lovell/sharp@main/docs/image/api-resize-fit.png">
|
* <img alt="Examples of various values for the fit property when resizing" width="100%" style="aspect-ratio: 998/243" src="https://cdn.jsdelivr.net/gh/lovell/sharp@main/docs/image/api-resize-fit.svg">
|
||||||
*
|
*
|
||||||
* When using a **fit** of `cover` or `contain`, the default **position** is `centre`. Other options are:
|
* When using a **fit** of `cover` or `contain`, the default **position** is `centre`. Other options are:
|
||||||
* - `sharp.position`: `top`, `right top`, `right`, `right bottom`, `bottom`, `left bottom`, `left`, `left top`.
|
* - `sharp.position`: `top`, `right top`, `right`, `right bottom`, `bottom`, `left bottom`, `left`, `left top`.
|
||||||
|
|||||||
30
package.json
30
package.json
@@ -1,7 +1,7 @@
|
|||||||
{
|
{
|
||||||
"name": "sharp",
|
"name": "sharp",
|
||||||
"description": "High performance Node.js image processing, the fastest module to resize JPEG, PNG, WebP, GIF, AVIF and TIFF images",
|
"description": "High performance Node.js image processing, the fastest module to resize JPEG, PNG, WebP, GIF, AVIF and TIFF images",
|
||||||
"version": "0.32.4",
|
"version": "0.32.6",
|
||||||
"author": "Lovell Fuller <npm@lovell.info>",
|
"author": "Lovell Fuller <npm@lovell.info>",
|
||||||
"homepage": "https://github.com/lovell/sharp",
|
"homepage": "https://github.com/lovell/sharp",
|
||||||
"contributors": [
|
"contributors": [
|
||||||
@@ -153,25 +153,25 @@
|
|||||||
"mocha": "^10.2.0",
|
"mocha": "^10.2.0",
|
||||||
"mock-fs": "^5.2.0",
|
"mock-fs": "^5.2.0",
|
||||||
"nyc": "^15.1.0",
|
"nyc": "^15.1.0",
|
||||||
"prebuild": "lovell/prebuild#add-nodejs-20-drop-nodejs-10-and-12",
|
"prebuild": "^12.0.0",
|
||||||
"semistandard": "^16.0.1",
|
"semistandard": "^16.0.1",
|
||||||
"tsd": "^0.28.1"
|
"tsd": "^0.29.0"
|
||||||
},
|
},
|
||||||
"license": "Apache-2.0",
|
"license": "Apache-2.0",
|
||||||
"config": {
|
"config": {
|
||||||
"libvips": "8.14.3",
|
"libvips": "8.14.5",
|
||||||
"integrity": {
|
"integrity": {
|
||||||
"darwin-arm64v8": "sha512-zeb7jQ/5ARZfBH9Uy5wlpN05bFpiIN0qN3gIIpfJhpN0rhGDnjJZQgK0W+pOmG1YiLL42BMCS0SHldb0xE33rA==",
|
"darwin-arm64v8": "sha512-1QZzICfCJd4wAO0P6qmYI5e5VFMt9iCE4QgefI8VMMbdSzjIXA9L/ARN6pkMQPZ3h20Y9RtJ2W1skgCsvCIccw==",
|
||||||
"darwin-x64": "sha512-C3N6smxdfprfz58cjojv0aekYXDl6+f9SwpGpxPG5RrZnrDMn5NOXtUQOEQ8PZ3Hd9VzfkJTnW/s36EvcMPfYg==",
|
"darwin-x64": "sha512-sMIKMYXsdU9FlIfztj6Kt/SfHlhlDpP0Ups7ftVFqwjaszmYmpI9y/d/q3mLb4jrzuSiSUEislSWCwBnW7MPTw==",
|
||||||
"linux-arm64v8": "sha512-hT6B+OswqVQH10Fggq3jpOdn+GhxNx+5bk+EMr3lY3RZy72PZ+n4ZHJDfYSxAymdiz5rCdzGxsRLMb9GgD4OSw==",
|
"linux-arm64v8": "sha512-CD8owELzkDumaom+O3jJ8fKamILAQdj+//KK/VNcHK3sngUcFpdjx36C8okwbux9sml/T7GTB/gzpvReDrAejQ==",
|
||||||
"linux-armv6": "sha512-cW9giVrBssHXFt07l+PgqGu7P7XRDv7oW8jC6iXGBcjG75N7rXz2CK0DyPclfnyoWH4IQ78dh5SkQWmb6X4tig==",
|
"linux-armv6": "sha512-wk6IPHatDFVWKJy7lI1TJezHGHPQut1wF2bwx256KlZwXUQU3fcVcMpV1zxXjgLFewHq2+uhyMkoSGBPahWzlA==",
|
||||||
"linux-armv7": "sha512-hgqFt3UkZHK6D91JtYrYmT1niznh+N93Zxj2EWXgTLAdcS1D3QqaDPEg2EhInHbXqYvfOuQYAAXPxt7zVtKqcw==",
|
"linux-armv7": "sha512-HEZC9KYtkmBK5rUR2MqBhrVarnQVZ/TwLUeLkKq0XuoM2pc/eXI6N0Fh5NGEFwdXI2XE8g1ySf+OYS6DDi+xCQ==",
|
||||||
"linux-x64": "sha512-FKbMBbCcFcSugRtuiTsA6Cov+M2WQ8nzvmmJ5xYYpRg/rsrWvObFT+6x/YBpblur9uXGjGIehjXVZtB3VXc+pg==",
|
"linux-x64": "sha512-SlFWrITSW5XVUkaFPQOySAaSGXnhkGJCj8X2wGYYta9hk5piZldQyMp4zwy0z6UeRu1qKTKtZvmq28W3Gnh9xA==",
|
||||||
"linuxmusl-arm64v8": "sha512-RTf6mrFyLGWnyt0DH4nHeXv5oSZMSJWxTdTt4cjvJsgp2Husz3mNJLQJGeehCuqPCYj/liJ9NIczw8u71eHFng==",
|
"linuxmusl-arm64v8": "sha512-ga9iX7WUva3sG/VsKkOD318InLlCfPIztvzCZKZ2/+izQXRbQi8VoXWMHgEN4KHACv45FTl7mJ/8CRqUzhS8wQ==",
|
||||||
"linuxmusl-x64": "sha512-y/8UOkHzKhi/5UM1/ONyPvpuhO11nPQmuJWfzqUKj8kSKnDasmxv3FN46yI0XY3xA2oFC8lQNFBnLudQsi3Nvw==",
|
"linuxmusl-x64": "sha512-yeaHnpfee1hrZLok2l4eFceHzlfq8gN3QOu0R4Mh8iMK5O5vAUu97bdtxeZZeJJvHw8tfh2/msGi0qysxKN8bw==",
|
||||||
"win32-arm64v8": "sha512-D3PiVL981S7V0bSUwW3OqDS48H9QRw2vqQhYIY3JcIEssOnjWxmJGaz0Y9Zb8TYF5DHnnD6g5kEhob5Y2PIVEw==",
|
"win32-arm64v8": "sha512-kR91hy9w1+GEXK56hLh51+hBCBo7T+ijM4Slkmvb/2PsYZySq5H7s61n99iDYl6kTJP2y9sW5Xcvm3uuXDaDgg==",
|
||||||
"win32-ia32": "sha512-FuLIaSIYJGJAcxyKkG/3/uuTzputekKSCcRCpRHkQS9J8IwM+yHzQeJ5W2PyAvNdeGIEwlYq3wnCNcXe1UGXWA==",
|
"win32-ia32": "sha512-HrnofEbzHNpHJ0vVnjsTj5yfgVdcqdWshXuwFO2zc8xlEjA83BvXZ0lVj9MxPxkxJ2ta+/UlLr+CFzc5bOceMw==",
|
||||||
"win32-x64": "sha512-VQg4aBqpEfybgV8bjnrjfvnosxQDII/23mouFUfKHCsH5kvvHV5tTuPsxm6qbl+SCVploDK/zK1qpjop8YEvtg=="
|
"win32-x64": "sha512-BwKckinJZ0Fu/EcunqiLPwOLEBWp4xf8GV7nvmVuKKz5f6B+GxoA2k9aa2wueqv4r4RJVgV/aWXZWFKOIjre/Q=="
|
||||||
},
|
},
|
||||||
"runtime": "napi",
|
"runtime": "napi",
|
||||||
"target": 7
|
"target": 7
|
||||||
|
|||||||
@@ -964,12 +964,7 @@ namespace sharp {
|
|||||||
}
|
}
|
||||||
|
|
||||||
std::pair<double, double> ResolveShrink(int width, int height, int targetWidth, int targetHeight,
|
std::pair<double, double> ResolveShrink(int width, int height, int targetWidth, int targetHeight,
|
||||||
Canvas canvas, bool swap, bool withoutEnlargement, bool withoutReduction) {
|
Canvas canvas, bool withoutEnlargement, bool withoutReduction) {
|
||||||
if (swap && canvas != Canvas::IGNORE_ASPECT) {
|
|
||||||
// Swap input width and height when requested.
|
|
||||||
std::swap(width, height);
|
|
||||||
}
|
|
||||||
|
|
||||||
double hshrink = 1.0;
|
double hshrink = 1.0;
|
||||||
double vshrink = 1.0;
|
double vshrink = 1.0;
|
||||||
|
|
||||||
|
|||||||
11
src/common.h
11
src/common.h
@@ -15,8 +15,8 @@
|
|||||||
|
|
||||||
#if (VIPS_MAJOR_VERSION < 8) || \
|
#if (VIPS_MAJOR_VERSION < 8) || \
|
||||||
(VIPS_MAJOR_VERSION == 8 && VIPS_MINOR_VERSION < 14) || \
|
(VIPS_MAJOR_VERSION == 8 && VIPS_MINOR_VERSION < 14) || \
|
||||||
(VIPS_MAJOR_VERSION == 8 && VIPS_MINOR_VERSION == 14 && VIPS_MICRO_VERSION < 3)
|
(VIPS_MAJOR_VERSION == 8 && VIPS_MINOR_VERSION == 14 && VIPS_MICRO_VERSION < 5)
|
||||||
#error "libvips version 8.14.3+ is required - please see https://sharp.pixelplumbing.com/install"
|
#error "libvips version 8.14.5+ is required - please see https://sharp.pixelplumbing.com/install"
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#if ((!defined(__clang__)) && defined(__GNUC__) && (__GNUC__ < 4 || (__GNUC__ == 4 && __GNUC_MINOR__ < 6)))
|
#if ((!defined(__clang__)) && defined(__GNUC__) && (__GNUC__ < 4 || (__GNUC__ == 4 && __GNUC_MINOR__ < 6)))
|
||||||
@@ -362,13 +362,10 @@ namespace sharp {
|
|||||||
VImage EnsureAlpha(VImage image, double const value);
|
VImage EnsureAlpha(VImage image, double const value);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
Calculate the shrink factor, taking into account auto-rotate, the canvas
|
Calculate the horizontal and vertical shrink factors, taking the canvas mode into account.
|
||||||
mode, and so on. The hshrink/vshrink are the amount to shrink the input
|
|
||||||
image axes by in order for the output axes (ie. after rotation) to match
|
|
||||||
the required thumbnail width/height and canvas mode.
|
|
||||||
*/
|
*/
|
||||||
std::pair<double, double> ResolveShrink(int width, int height, int targetWidth, int targetHeight,
|
std::pair<double, double> ResolveShrink(int width, int height, int targetWidth, int targetHeight,
|
||||||
Canvas canvas, bool swap, bool withoutEnlargement, bool withoutReduction);
|
Canvas canvas, bool withoutEnlargement, bool withoutReduction);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
Ensure decoding remains sequential.
|
Ensure decoding remains sequential.
|
||||||
|
|||||||
@@ -20,18 +20,15 @@
|
|||||||
#include "operations.h"
|
#include "operations.h"
|
||||||
#include "pipeline.h"
|
#include "pipeline.h"
|
||||||
|
|
||||||
#if defined(WIN32)
|
#ifdef _WIN32
|
||||||
#define STAT64_STRUCT __stat64
|
#define STAT64_STRUCT __stat64
|
||||||
#define STAT64_FUNCTION _stat64
|
#define STAT64_FUNCTION _stat64
|
||||||
#elif defined(__APPLE__)
|
#elif defined(_LARGEFILE64_SOURCE)
|
||||||
#define STAT64_STRUCT stat
|
|
||||||
#define STAT64_FUNCTION stat
|
|
||||||
#elif defined(__FreeBSD__) || defined(__OpenBSD__) || defined(__NetBSD__) || defined(__DragonFly__)
|
|
||||||
#define STAT64_STRUCT stat
|
|
||||||
#define STAT64_FUNCTION stat
|
|
||||||
#else
|
|
||||||
#define STAT64_STRUCT stat64
|
#define STAT64_STRUCT stat64
|
||||||
#define STAT64_FUNCTION stat64
|
#define STAT64_FUNCTION stat64
|
||||||
|
#else
|
||||||
|
#define STAT64_STRUCT stat
|
||||||
|
#define STAT64_FUNCTION stat
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
class PipelineWorker : public Napi::AsyncWorker {
|
class PipelineWorker : public Napi::AsyncWorker {
|
||||||
@@ -160,15 +157,18 @@ class PipelineWorker : public Napi::AsyncWorker {
|
|||||||
int targetResizeWidth = baton->width;
|
int targetResizeWidth = baton->width;
|
||||||
int targetResizeHeight = baton->height;
|
int targetResizeHeight = baton->height;
|
||||||
|
|
||||||
// Swap input output width and height when rotating by 90 or 270 degrees
|
// When auto-rotating by 90 or 270 degrees, swap the target width and
|
||||||
bool swap = !baton->rotateBeforePreExtract &&
|
// height to ensure the behavior aligns with how it would have been if
|
||||||
(rotation == VIPS_ANGLE_D90 || rotation == VIPS_ANGLE_D270 ||
|
// the rotation had taken place *before* resizing.
|
||||||
autoRotation == VIPS_ANGLE_D90 || autoRotation == VIPS_ANGLE_D270);
|
if (!baton->rotateBeforePreExtract &&
|
||||||
|
(autoRotation == VIPS_ANGLE_D90 || autoRotation == VIPS_ANGLE_D270)) {
|
||||||
|
std::swap(targetResizeWidth, targetResizeHeight);
|
||||||
|
}
|
||||||
|
|
||||||
// Shrink to pageHeight, so we work for multi-page images
|
// Shrink to pageHeight, so we work for multi-page images
|
||||||
std::tie(hshrink, vshrink) = sharp::ResolveShrink(
|
std::tie(hshrink, vshrink) = sharp::ResolveShrink(
|
||||||
inputWidth, pageHeight, targetResizeWidth, targetResizeHeight,
|
inputWidth, pageHeight, targetResizeWidth, targetResizeHeight,
|
||||||
baton->canvas, swap, baton->withoutEnlargement, baton->withoutReduction);
|
baton->canvas, baton->withoutEnlargement, baton->withoutReduction);
|
||||||
|
|
||||||
// The jpeg preload shrink.
|
// The jpeg preload shrink.
|
||||||
int jpegShrinkOnLoad = 1;
|
int jpegShrinkOnLoad = 1;
|
||||||
@@ -302,7 +302,7 @@ class PipelineWorker : public Napi::AsyncWorker {
|
|||||||
// Shrink to pageHeight, so we work for multi-page images
|
// Shrink to pageHeight, so we work for multi-page images
|
||||||
std::tie(hshrink, vshrink) = sharp::ResolveShrink(
|
std::tie(hshrink, vshrink) = sharp::ResolveShrink(
|
||||||
inputWidth, pageHeight, targetResizeWidth, targetResizeHeight,
|
inputWidth, pageHeight, targetResizeWidth, targetResizeHeight,
|
||||||
baton->canvas, swap, baton->withoutEnlargement, baton->withoutReduction);
|
baton->canvas, baton->withoutEnlargement, baton->withoutReduction);
|
||||||
|
|
||||||
int targetHeight = static_cast<int>(std::rint(static_cast<double>(pageHeight) / vshrink));
|
int targetHeight = static_cast<int>(std::rint(static_cast<double>(pageHeight) / vshrink));
|
||||||
int targetPageHeight = targetHeight;
|
int targetPageHeight = targetHeight;
|
||||||
@@ -326,7 +326,7 @@ class PipelineWorker : public Napi::AsyncWorker {
|
|||||||
try {
|
try {
|
||||||
image = image.icc_transform(processingProfile, VImage::option()
|
image = image.icc_transform(processingProfile, VImage::option()
|
||||||
->set("embedded", TRUE)
|
->set("embedded", TRUE)
|
||||||
->set("depth", image.interpretation() == VIPS_INTERPRETATION_RGB16 ? 16 : 8)
|
->set("depth", sharp::Is16Bit(image.interpretation()) ? 16 : 8)
|
||||||
->set("intent", VIPS_INTENT_PERCEPTUAL));
|
->set("intent", VIPS_INTENT_PERCEPTUAL));
|
||||||
} catch(...) {
|
} catch(...) {
|
||||||
sharp::VipsWarningCallback(nullptr, G_LOG_LEVEL_WARNING, "Invalid embedded profile", nullptr);
|
sharp::VipsWarningCallback(nullptr, G_LOG_LEVEL_WARNING, "Invalid embedded profile", nullptr);
|
||||||
@@ -653,7 +653,7 @@ class PipelineWorker : public Napi::AsyncWorker {
|
|||||||
if (across != 0 || down != 0) {
|
if (across != 0 || down != 0) {
|
||||||
int left;
|
int left;
|
||||||
int top;
|
int top;
|
||||||
compositeImage = compositeImage.replicate(across, down);
|
compositeImage = sharp::StaySequential(compositeImage, access).replicate(across, down);
|
||||||
if (composite->hasOffset) {
|
if (composite->hasOffset) {
|
||||||
std::tie(left, top) = sharp::CalculateCrop(
|
std::tie(left, top) = sharp::CalculateCrop(
|
||||||
compositeImage.width(), compositeImage.height(), image.width(), image.height(),
|
compositeImage.width(), compositeImage.height(), image.width(), image.height(),
|
||||||
@@ -763,6 +763,7 @@ class PipelineWorker : public Napi::AsyncWorker {
|
|||||||
if (baton->withMetadata && sharp::HasProfile(image) && baton->withMetadataIcc.empty()) {
|
if (baton->withMetadata && sharp::HasProfile(image) && baton->withMetadataIcc.empty()) {
|
||||||
image = image.icc_transform("srgb", VImage::option()
|
image = image.icc_transform("srgb", VImage::option()
|
||||||
->set("embedded", TRUE)
|
->set("embedded", TRUE)
|
||||||
|
->set("depth", sharp::Is16Bit(image.interpretation()) ? 16 : 8)
|
||||||
->set("intent", VIPS_INTENT_PERCEPTUAL));
|
->set("intent", VIPS_INTENT_PERCEPTUAL));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -788,12 +789,13 @@ class PipelineWorker : public Napi::AsyncWorker {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Apply output ICC profile
|
// Apply output ICC profile
|
||||||
if (!baton->withMetadataIcc.empty()) {
|
if (baton->withMetadata) {
|
||||||
image = image.icc_transform(
|
image = image.icc_transform(
|
||||||
const_cast<char*>(baton->withMetadataIcc.data()),
|
baton->withMetadataIcc.empty() ? "srgb" : const_cast<char*>(baton->withMetadataIcc.data()),
|
||||||
VImage::option()
|
VImage::option()
|
||||||
->set("input_profile", processingProfile)
|
->set("input_profile", processingProfile)
|
||||||
->set("embedded", TRUE)
|
->set("embedded", TRUE)
|
||||||
|
->set("depth", sharp::Is16Bit(image.interpretation()) ? 16 : 8)
|
||||||
->set("intent", VIPS_INTENT_PERCEPTUAL));
|
->set("intent", VIPS_INTENT_PERCEPTUAL));
|
||||||
}
|
}
|
||||||
// Override EXIF Orientation tag
|
// Override EXIF Orientation tag
|
||||||
|
|||||||
@@ -5,7 +5,7 @@ ARG BRANCH=main
|
|||||||
RUN apt-get -y update && apt-get install -y build-essential curl git
|
RUN apt-get -y update && apt-get install -y build-essential curl git
|
||||||
|
|
||||||
# Install latest Node.js LTS
|
# Install latest Node.js LTS
|
||||||
RUN curl -fsSL https://deb.nodesource.com/setup_16.x | bash -
|
RUN curl -fsSL https://deb.nodesource.com/setup_18.x | bash -
|
||||||
RUN apt-get install -y nodejs
|
RUN apt-get install -y nodejs
|
||||||
|
|
||||||
# Install benchmark dependencies
|
# Install benchmark dependencies
|
||||||
@@ -23,4 +23,9 @@ RUN cat /etc/os-release | grep VERSION=
|
|||||||
RUN node -v
|
RUN node -v
|
||||||
|
|
||||||
WORKDIR /tmp/sharp/test/bench
|
WORKDIR /tmp/sharp/test/bench
|
||||||
|
|
||||||
|
# Workaround for: https://github.com/emscripten-core/emscripten/pull/16917
|
||||||
|
# This could be removed once Squoosh is an optional dependency.
|
||||||
|
ENV NODE_OPTIONS="--no-experimental-fetch"
|
||||||
|
|
||||||
CMD [ "node", "perf" ]
|
CMD [ "node", "perf" ]
|
||||||
|
|||||||
@@ -9,15 +9,15 @@
|
|||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@squoosh/cli": "0.7.3",
|
"@squoosh/cli": "0.7.3",
|
||||||
"@squoosh/lib": "0.4.0",
|
"@squoosh/lib": "0.5.3",
|
||||||
"async": "3.2.4",
|
"async": "3.2.4",
|
||||||
"benchmark": "2.1.4",
|
"benchmark": "2.1.4",
|
||||||
"gm": "1.25.0",
|
"gm": "1.25.0",
|
||||||
"imagemagick": "0.1.3",
|
"imagemagick": "0.1.3",
|
||||||
"jimp": "0.22.7"
|
"jimp": "0.22.10"
|
||||||
},
|
},
|
||||||
"optionalDependencies": {
|
"optionalDependencies": {
|
||||||
"@tensorflow/tfjs-node": "4.2.0",
|
"@tensorflow/tfjs-node": "4.9.0",
|
||||||
"mapnik": "4.5.9"
|
"mapnik": "4.5.9"
|
||||||
},
|
},
|
||||||
"license": "Apache-2.0",
|
"license": "Apache-2.0",
|
||||||
|
|||||||
@@ -109,7 +109,7 @@ async.series({
|
|||||||
jpegSuite.add('squoosh-lib-buffer-buffer', {
|
jpegSuite.add('squoosh-lib-buffer-buffer', {
|
||||||
defer: true,
|
defer: true,
|
||||||
fn: function (deferred) {
|
fn: function (deferred) {
|
||||||
const pool = new squoosh.ImagePool();
|
const pool = new squoosh.ImagePool(os.cpus().length);
|
||||||
const image = pool.ingestImage(inputJpgBuffer);
|
const image = pool.ingestImage(inputJpgBuffer);
|
||||||
image.decoded
|
image.decoded
|
||||||
.then(function () {
|
.then(function () {
|
||||||
@@ -652,7 +652,7 @@ async.series({
|
|||||||
throw err;
|
throw err;
|
||||||
} else {
|
} else {
|
||||||
image
|
image
|
||||||
.resize(width, heightPng)
|
.resize(width, heightPng, jimp.RESIZE_BICUBIC)
|
||||||
.deflateLevel(6)
|
.deflateLevel(6)
|
||||||
.filterType(0)
|
.filterType(0)
|
||||||
.getBuffer(jimp.MIME_PNG, function (err) {
|
.getBuffer(jimp.MIME_PNG, function (err) {
|
||||||
@@ -673,7 +673,7 @@ async.series({
|
|||||||
throw err;
|
throw err;
|
||||||
} else {
|
} else {
|
||||||
image
|
image
|
||||||
.resize(width, heightPng)
|
.resize(width, heightPng, jimp.RESIZE_BICUBIC)
|
||||||
.deflateLevel(6)
|
.deflateLevel(6)
|
||||||
.filterType(0)
|
.filterType(0)
|
||||||
.write(outputPng, function (err) {
|
.write(outputPng, function (err) {
|
||||||
@@ -707,7 +707,7 @@ async.series({
|
|||||||
pngSuite.add('squoosh-lib-buffer-buffer', {
|
pngSuite.add('squoosh-lib-buffer-buffer', {
|
||||||
defer: true,
|
defer: true,
|
||||||
fn: function (deferred) {
|
fn: function (deferred) {
|
||||||
const pool = new squoosh.ImagePool();
|
const pool = new squoosh.ImagePool(os.cpus().length);
|
||||||
const image = pool.ingestImage(inputPngBuffer);
|
const image = pool.ingestImage(inputPngBuffer);
|
||||||
image.decoded
|
image.decoded
|
||||||
.then(function () {
|
.then(function () {
|
||||||
|
|||||||
@@ -524,7 +524,7 @@ sharp('input.tiff').jxl({ lossless: true }).toFile('out.jxl');
|
|||||||
sharp('input.tiff').jxl({ effort: 7 }).toFile('out.jxl');
|
sharp('input.tiff').jxl({ effort: 7 }).toFile('out.jxl');
|
||||||
|
|
||||||
// Support `minSize` and `mixed` webp options
|
// Support `minSize` and `mixed` webp options
|
||||||
sharp('input.tiff').webp({ minSize: 1000, mixed: true }).toFile('out.gif');
|
sharp('input.tiff').webp({ minSize: true, mixed: true }).toFile('out.gif');
|
||||||
|
|
||||||
// 'failOn' input param
|
// 'failOn' input param
|
||||||
sharp('input.tiff', { failOn: 'none' });
|
sharp('input.tiff', { failOn: 'none' });
|
||||||
@@ -651,3 +651,13 @@ sharp(input).composite([
|
|||||||
unlimited: true,
|
unlimited: true,
|
||||||
}
|
}
|
||||||
]);
|
]);
|
||||||
|
|
||||||
|
// Support for webp preset in types
|
||||||
|
// https://github.com/lovell/sharp/issues/3747
|
||||||
|
sharp('input.tiff').webp({ preset: 'photo' }).toFile('out.webp');
|
||||||
|
sharp('input.tiff').webp({ preset: 'picture' }).toFile('out.webp');
|
||||||
|
sharp('input.tiff').webp({ preset: 'icon' }).toFile('out.webp');
|
||||||
|
sharp('input.tiff').webp({ preset: 'drawing' }).toFile('out.webp');
|
||||||
|
sharp('input.tiff').webp({ preset: 'text' }).toFile('out.webp');
|
||||||
|
sharp('input.tiff').webp({ preset: 'default' }).toFile('out.webp');
|
||||||
|
|
||||||
|
|||||||
@@ -472,4 +472,28 @@ describe('composite', () => {
|
|||||||
assert.strictEqual(b, 19);
|
assert.strictEqual(b, 19);
|
||||||
assert.strictEqual(a, 128);
|
assert.strictEqual(a, 128);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('Ensure tiled overlay is fully decoded', async () => {
|
||||||
|
const tile = await sharp({
|
||||||
|
create: {
|
||||||
|
width: 8, height: 513, channels: 3, background: 'red'
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.png({ compressionLevel: 0 })
|
||||||
|
.toBuffer();
|
||||||
|
|
||||||
|
const { info } = await sharp({
|
||||||
|
create: {
|
||||||
|
width: 8, height: 514, channels: 3, background: 'green'
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.composite([{
|
||||||
|
input: tile,
|
||||||
|
tile: true
|
||||||
|
}])
|
||||||
|
.toBuffer({ resolveWithObject: true });
|
||||||
|
|
||||||
|
assert.strictEqual(info.width, 8);
|
||||||
|
assert.strictEqual(info.height, 514);
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -781,6 +781,55 @@ describe('Image metadata', function () {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('withMetadata adds default sRGB profile', async () => {
|
||||||
|
const data = await sharp(fixtures.inputJpg)
|
||||||
|
.resize(32, 24)
|
||||||
|
.withMetadata()
|
||||||
|
.toBuffer();
|
||||||
|
|
||||||
|
const metadata = await sharp(data).metadata();
|
||||||
|
const { colorSpace, deviceClass, intent } = icc.parse(metadata.icc);
|
||||||
|
assert.strictEqual(colorSpace, 'RGB');
|
||||||
|
assert.strictEqual(deviceClass, 'Monitor');
|
||||||
|
assert.strictEqual(intent, 'Perceptual');
|
||||||
|
});
|
||||||
|
|
||||||
|
it('withMetadata adds default sRGB profile to RGB16', async () => {
|
||||||
|
const data = await sharp({
|
||||||
|
create: {
|
||||||
|
width: 8, height: 8, channels: 4, background: 'orange'
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.toColorspace('rgb16')
|
||||||
|
.png()
|
||||||
|
.withMetadata()
|
||||||
|
.toBuffer();
|
||||||
|
|
||||||
|
const metadata = await sharp(data).metadata();
|
||||||
|
assert.strictEqual(metadata.depth, 'ushort');
|
||||||
|
|
||||||
|
const { description } = icc.parse(metadata.icc);
|
||||||
|
assert.strictEqual(description, 'sRGB');
|
||||||
|
});
|
||||||
|
|
||||||
|
it('withMetadata adds P3 profile to 16-bit PNG', async () => {
|
||||||
|
const data = await sharp({
|
||||||
|
create: {
|
||||||
|
width: 8, height: 8, channels: 4, background: 'orange'
|
||||||
|
}
|
||||||
|
})
|
||||||
|
.toColorspace('rgb16')
|
||||||
|
.png()
|
||||||
|
.withMetadata({ icc: 'p3' })
|
||||||
|
.toBuffer();
|
||||||
|
|
||||||
|
const metadata = await sharp(data).metadata();
|
||||||
|
assert.strictEqual(metadata.depth, 'ushort');
|
||||||
|
|
||||||
|
const { description } = icc.parse(metadata.icc);
|
||||||
|
assert.strictEqual(description, 'sP3C');
|
||||||
|
});
|
||||||
|
|
||||||
it('File input with corrupt header fails gracefully', function (done) {
|
it('File input with corrupt header fails gracefully', function (done) {
|
||||||
sharp(fixtures.inputJpgWithCorruptHeader)
|
sharp(fixtures.inputJpgWithCorruptHeader)
|
||||||
.metadata(function (err) {
|
.metadata(function (err) {
|
||||||
|
|||||||
@@ -192,6 +192,23 @@ describe('Rotation', function () {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('Auto-rotate by 270 degrees, rectangular output ignoring aspect ratio', function (done) {
|
||||||
|
sharp(fixtures.inputJpgWithLandscapeExif8)
|
||||||
|
.resize(320, 240, { fit: sharp.fit.fill })
|
||||||
|
.rotate()
|
||||||
|
.toBuffer(function (err, data, info) {
|
||||||
|
if (err) throw err;
|
||||||
|
assert.strictEqual(320, info.width);
|
||||||
|
assert.strictEqual(240, info.height);
|
||||||
|
sharp(data).metadata(function (err, metadata) {
|
||||||
|
if (err) throw err;
|
||||||
|
assert.strictEqual(320, metadata.width);
|
||||||
|
assert.strictEqual(240, metadata.height);
|
||||||
|
done();
|
||||||
|
});
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
it('Rotate by 30 degrees, rectangular output ignoring aspect ratio', function (done) {
|
it('Rotate by 30 degrees, rectangular output ignoring aspect ratio', function (done) {
|
||||||
sharp(fixtures.inputJpg)
|
sharp(fixtures.inputJpg)
|
||||||
.resize(320, 240, { fit: sharp.fit.fill })
|
.resize(320, 240, { fit: sharp.fit.fill })
|
||||||
@@ -489,4 +506,28 @@ describe('Rotation', function () {
|
|||||||
.timeout({ seconds: 5 })
|
.timeout({ seconds: 5 })
|
||||||
.toBuffer()
|
.toBuffer()
|
||||||
);
|
);
|
||||||
|
|
||||||
|
it('Rotate 90 then resize with inside fit', async () => {
|
||||||
|
const data = await sharp({ create: { width: 16, height: 8, channels: 3, background: 'red' } })
|
||||||
|
.rotate(90)
|
||||||
|
.resize({ width: 6, fit: 'inside' })
|
||||||
|
.png({ compressionLevel: 0 })
|
||||||
|
.toBuffer();
|
||||||
|
|
||||||
|
const { width, height } = await sharp(data).metadata();
|
||||||
|
assert.strictEqual(width, 6);
|
||||||
|
assert.strictEqual(height, 12);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('Resize with inside fit then rotate 90', async () => {
|
||||||
|
const data = await sharp({ create: { width: 16, height: 8, channels: 3, background: 'red' } })
|
||||||
|
.resize({ width: 6, fit: 'inside' })
|
||||||
|
.rotate(90)
|
||||||
|
.png({ compressionLevel: 0 })
|
||||||
|
.toBuffer();
|
||||||
|
|
||||||
|
const { width, height } = await sharp(data).metadata();
|
||||||
|
assert.strictEqual(width, 3);
|
||||||
|
assert.strictEqual(height, 6);
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
Reference in New Issue
Block a user