Merge pull request #1151 from ergunsh/improve-encode-types

Improve `encode` API and its types
This commit is contained in:
Surma
2021-09-17 13:50:29 +01:00
committed by GitHub

View File

@@ -26,6 +26,20 @@ type PreprocessOptions = {
quant?: QuantOptions; quant?: QuantOptions;
rotate?: RotateOptions; rotate?: RotateOptions;
}; };
type EncodeResult = {
optionsUsed: object;
binary: Uint8Array;
extension: string;
size: number;
};
type EncoderOptions = {
mozjpeg?: Partial<MozJPEGEncodeOptions>;
webp?: Partial<WebPEncodeOptions>;
avif?: Partial<AvifEncodeOptions>;
jxl?: Partial<JxlEncodeOptions>;
wp2?: Partial<WP2EncodeOptions>;
oxipng?: Partial<OxiPngEncodeOptions>;
};
async function decodeFile({ async function decodeFile({
file, file,
@@ -83,7 +97,7 @@ async function encodeImage({
encConfig: any; encConfig: any;
optimizerButteraugliTarget: number; optimizerButteraugliTarget: number;
maxOptimizerRounds: number; maxOptimizerRounds: number;
}) { }): Promise<EncodeResult> {
let binary: Uint8Array; let binary: Uint8Array;
let optionsUsed = encConfig; let optionsUsed = encConfig;
const encoder = await encoders[encName].enc(); const encoder = await encoders[encName].enc();
@@ -172,7 +186,7 @@ class Image {
public file: ArrayBuffer | ArrayLike<number>; public file: ArrayBuffer | ArrayLike<number>;
public workerPool: WorkerPool<JobMessage, any>; public workerPool: WorkerPool<JobMessage, any>;
public decoded: Promise<{ bitmap: ImageData }>; public decoded: Promise<{ bitmap: ImageData }>;
public encodedWith: { [key: string]: any }; public encodedWith: { [key in EncoderKey]?: EncodeResult };
constructor( constructor(
workerPool: WorkerPool<JobMessage, any>, workerPool: WorkerPool<JobMessage, any>,
@@ -213,22 +227,16 @@ class Image {
/** /**
* Define one or several encoders to use on the image. * Define one or several encoders to use on the image.
* @param {object} encodeOptions - An object with encoders to use, and their settings. * @param {object} encodeOptions - An object with encoders to use, and their settings.
* @returns {Promise<void>} - A promise that resolves when the image has been encoded with all the specified encoders. * @returns {Promise<{ [key in keyof T]: EncodeResult }>} - A promise that resolves when the image has been encoded with all the specified encoders.
*/ */
async encode( async encode<T extends EncoderOptions>(
encodeOptions: { encodeOptions: {
optimizerButteraugliTarget?: number; optimizerButteraugliTarget?: number;
maxOptimizerRounds?: number; maxOptimizerRounds?: number;
} & { } & T,
mozjpeg?: Partial<MozJPEGEncodeOptions>; ): Promise<{ [key in keyof T]: EncodeResult }> {
webp?: Partial<WebPEncodeOptions>;
avif?: Partial<AvifEncodeOptions>;
jxl?: Partial<JxlEncodeOptions>;
wp2?: Partial<WP2EncodeOptions>;
oxipng?: Partial<OxiPngEncodeOptions>;
} = {},
): Promise<void> {
const { bitmap } = await this.decoded; const { bitmap } = await this.decoded;
const setEncodedWithPromises = [];
for (const [name, options] of Object.entries(encodeOptions)) { for (const [name, options] of Object.entries(encodeOptions)) {
if (!Object.keys(encoders).includes(name)) { if (!Object.keys(encoders).includes(name)) {
continue; continue;
@@ -239,18 +247,26 @@ class Image {
typeof options === 'string' typeof options === 'string'
? options ? options
: Object.assign({}, encRef.defaultEncoderOptions, options); : Object.assign({}, encRef.defaultEncoderOptions, options);
this.encodedWith[encName] = this.workerPool.dispatchJob({ setEncodedWithPromises.push(
operation: 'encode', this.workerPool
bitmap, .dispatchJob({
encName, operation: 'encode',
encConfig, bitmap,
optimizerButteraugliTarget: Number( encName,
encodeOptions.optimizerButteraugliTarget ?? 1.4, encConfig,
), optimizerButteraugliTarget: Number(
maxOptimizerRounds: Number(encodeOptions.maxOptimizerRounds ?? 6), encodeOptions.optimizerButteraugliTarget ?? 1.4,
}); ),
maxOptimizerRounds: Number(encodeOptions.maxOptimizerRounds ?? 6),
})
.then((encodeResult) => {
this.encodedWith[encName] = encodeResult;
}),
);
} }
await Promise.all(Object.values(this.encodedWith));
await Promise.all(setEncodedWithPromises);
return this.encodedWith as { [key in keyof T]: EncodeResult };
} }
} }