Add support for input array to join or animate #1580

This commit is contained in:
Lovell Fuller
2025-02-07 13:53:27 +00:00
parent 67ff930535
commit 5ab9168813
12 changed files with 377 additions and 20 deletions

View File

@@ -14,9 +14,13 @@ const sharp = require('./sharp');
*/
const align = {
left: 'low',
top: 'low',
low: 'low',
center: 'centre',
centre: 'centre',
right: 'high'
right: 'high',
bottom: 'high',
high: 'high'
};
/**
@@ -72,6 +76,18 @@ function _createInputDescriptor (input, inputOptions, containerOptions) {
} else if (!is.defined(input) && !is.defined(inputOptions) && is.object(containerOptions) && containerOptions.allowStream) {
// Stream without options
inputDescriptor.buffer = [];
} else if (Array.isArray(input)) {
if (input.length > 1) {
// Join images together
if (!this.options.joining) {
this.options.joining = true;
this.options.join = input.map(i => this._createInputDescriptor(i));
} else {
throw new Error('Recursive join is unsupported');
}
} else {
throw new Error('Expected at least two images to join');
}
} else {
throw new Error(`Unsupported input '${input}' of type ${typeof input}${
is.defined(inputOptions) ? ` when also providing options of type ${typeof inputOptions}` : ''
@@ -369,6 +385,57 @@ function _createInputDescriptor (input, inputOptions, containerOptions) {
throw new Error('Expected a valid string to create an image with text.');
}
}
// Join images together
if (is.defined(inputOptions.join)) {
if (is.defined(this.options.join)) {
if (is.defined(inputOptions.join.animated)) {
if (is.bool(inputOptions.join.animated)) {
inputDescriptor.joinAnimated = inputOptions.join.animated;
} else {
throw is.invalidParameterError('join.animated', 'boolean', inputOptions.join.animated);
}
}
if (is.defined(inputOptions.join.across)) {
if (is.integer(inputOptions.join.across) && is.inRange(inputOptions.join.across, 1, 1000000)) {
inputDescriptor.joinAcross = inputOptions.join.across;
} else {
throw is.invalidParameterError('join.across', 'integer between 1 and 100000', inputOptions.join.across);
}
}
if (is.defined(inputOptions.join.shim)) {
if (is.integer(inputOptions.join.shim) && is.inRange(inputOptions.join.shim, 0, 1000000)) {
inputDescriptor.joinShim = inputOptions.join.shim;
} else {
throw is.invalidParameterError('join.shim', 'integer between 0 and 100000', inputOptions.join.shim);
}
}
if (is.defined(inputOptions.join.background)) {
const background = color(inputOptions.join.background);
inputDescriptor.joinBackground = [
background.red(),
background.green(),
background.blue(),
Math.round(background.alpha() * 255)
];
}
if (is.defined(inputOptions.join.halign)) {
if (is.string(inputOptions.join.halign) && is.string(this.constructor.align[inputOptions.join.halign])) {
inputDescriptor.joinHalign = this.constructor.align[inputOptions.join.halign];
} else {
throw is.invalidParameterError('join.halign', 'valid alignment', inputOptions.join.halign);
}
}
if (is.defined(inputOptions.join.valign)) {
if (is.string(inputOptions.join.valign) && is.string(this.constructor.align[inputOptions.join.valign])) {
inputDescriptor.joinValign = this.constructor.align[inputOptions.join.valign];
} else {
throw is.invalidParameterError('join.valign', 'valid alignment', inputOptions.join.valign);
}
}
} else {
throw new Error('Expected input to be an array of images to join');
}
}
} else if (is.defined(inputOptions)) {
throw new Error('Invalid input options ' + inputOptions);
}