I have the following class with a nested async function, however, somehow the line
await Jimp.loadFont(font)
doesn't block the loop from executing, instead the following source code gives the output
2
3
index 0 start
index 0 about to loadFont xxxxxx
index 0 start
index 0 about to loadFont xxxxx
/* crash due to this unintended async behavior */
I want it to wait until Jimp has loaded the font, i.e. the ideal output is
2
3
index 0 start
index 0 about to loadFont xxxxxx
index 0 loadFont start
index 0 loadFont end
index 0 loadFont end
index 1 start
index 1 about to loadFont xxxxxx
index 1 loadFont start
index 1 loadFont end
index 1 loadFont end
index 2 start
index 2 about to loadFont xxxxxx
index 2 loadFont start
index 2 loadFont end
index 2 loadFont end
/* repeat for 1 more time as inputGif.frames.length = 2 */
Here is the source
export class GifWriter {
async writeTextOnGif(options: GifWriterOptions) {
let src = this.getSrc(options.src);
let dest = options.dest;
var frames: GifFrame[] = [];
await GifUtil.read(src).then(async inputGif => {
console.log(inputGif.frames.length);
console.log(options.text_options.length);
inputGif.frames.forEach(async frame => {
var jimpCopied = GifUtil.copyAsJimp(Jimp, frame);
for (var index = 0; index < options.text_options.length; index++) {
console.log(`index ${index} start`);
let text = options.text_options[index].text;
let font = this.getFont(options.text_options[index].font_path, options.text_options[index].font_color, options.text_options[index].font_size);
let alignmentX = this.getAlignmentX(options.text_options[index].alignmentX);
let alignmentY = this.getAlignmentY(options.text_options[index].alignmentY);
let positionX = options.text_options[index].positionX;
let positionY = options.text_options[index].positionY;
// print(font, x axis offset, y axis offset, text options, maxWidth, maxHeight)
let [offsetX, offsetY, maxWidth, maxHeight] = this.getPosition(jimpCopied, positionX, positionY);
console.log(`index ${index} about to loadFont ${font}`);
await Jimp.loadFont(font).then(font => {
console.log(`index ${index} loadFont start`);
jimpCopied.print(font, offsetX, offsetY, {
text: text,
alignmentX: alignmentX,
alignmentY: alignmentY
},
maxWidth,
maxHeight);
console.log(`index ${index} end`);
});
console.log(`index ${index} end`);
}
console.log(`create GifFrame`);
const GifCopied = new GifFrame(jimpCopied.bitmap,{
disposalMethod: frame.disposalMethod,
delayCentisecs: frame.delayCentisecs,
});
GifUtil.quantizeSorokin(GifCopied, 256);
frames.push(GifCopied);
});
});
// write to the destination file.
GifUtil.write(dest, frames);
}
My guess is inputGif.frames.forEach(async frame => { is making the execution for each frame async? But if I remove the async keyword then I can't use await with Jimp.loadFont, could someone give an advice on how can I achieve the intended output?