Convert / resize / transcode / down-sample photos & videos to be web-friendly
This is one of the core modules of thumbsup.github.io.
npm install thumbsup-downsize --save
This module requires the following binaries available in the system path:
- GraphicsMagick for processing images
- FFMpeg for processing videos
- Gifsicle for processing animated GIFs
const downsize = require('thumbsup-downsize')
const options = { height: 100, width: 100 }
downsize.image('source.tiff', 'thumb.jpg', options, (err) => {
console.log(err || 'Thumbnail created successfully')
})
.image(source, target, options, callback)
Processes the image in source
and creates a new image in target
.
The image is appropriately converted if needed based on the target
file extension.
You can specify the following options:
// proportionally resize the photo to a maximum height
opts = { height: 300 }
// proportionally resize the photo to a maximum width
opts = { width: 300 }
// resize and crop the photo to exactly height x width
// the image will not be distorted
opts = { height: 100, width: 100 }
// quality between 0 and 100
opts = { quality: 80 }
You can overlay a transparent watermark over the final image:
opts = {
watermark: {
file: 'path/watermark.png', // transparent PNG
position: 'NorthEast' // position of the watermark
}
}
The possible values for position
are:
Repeat
to repeat the watermark across the whole imageCenter
to position the watermark in the middleNorthWest
,North
,NorthEast
,West
,East
,SouthWest
,South
,SouthEast
to position the watermark along the edge
Note: watermarks are not compatible with cropped images.
The watermark
option will simply be ignored if both width and height are specified.
You can specify extra arguments that will be passed to GraphicsMagick. This only works with output arguments.
opts = {
args: [
'-unsharp 2 0.5 0.7 0',
'-modulate 120'
]
}
By default, only the first frame of an animated GIF is exported. You can keep the entire animation by specifying:
opts = { animated: true }
This offloads the processing of the image to Gifsicle. Note that:
- The destination file extension must be
.gif
- The only other supported parameters are
width
andheight
(e.g. no watermarks) - Cropping (specifying both width and height) is not supported and will throw an error
The flag is simply ignored if the source file is not a GIF.
.still(source, target, options, callback)
Extract a single frame from the video in source
, and writes the image to target
.
This method supports all the same options as .image()
.
.video(source, target, options, callback)
Transcodes the video in source
to a web-friendly format and lower bitrate, and writes it in target
.
Currently doesn't support any options, simply pass an empty hash ({}
).
The .video()
call returns an EventEmitter
to follow the progress of the conversion, since it can take a long time.
const emitter = downsize.video(/* ... */)
emitter.on('progress', percent => console.log(`${percent}%`))
Image/video resizing is hard to unit test. Instead, this repo contains an integration test suite made of many different resized files, covering different file formats and edge cases.
When submitting a change, make sure you run the build locally.
npm test
If you don't have all dependencies installed, you can also run the tests in Docker.
docker build -t downsize-test .
docker run downsize-test