UNPKG

@sinedied/mini-scraper

Version:

Artwork scraper for handheld emulators.

67 lines (66 loc) 2.96 kB
import { mkdir } from 'node:fs/promises'; import path from 'node:path'; import { Jimp } from 'jimp'; import { decode, encode } from 'fast-png'; import createDebug from 'debug'; const debug = createDebug('image'); export async function loadImage(url) { url = encodeURI(url); try { return await Jimp.read(url); } catch (error_) { const error = error_; if (error.message?.includes('unrecognised content at end of stream')) { debug(`Failed to load image from "${url}", trying to fix incorrect PNG...`); const response = await fetch(url); const buffer = await response.arrayBuffer(); const png = decode(buffer); const fixedPng = encode(png); return Jimp.read(Buffer.from(fixedPng)); } throw error; } } export async function resizeImageTo(url, destination, size) { try { const width = size?.width ?? 300; const height = size?.height; const image = await loadImage(url); const isLargerThanTaller = !height || image.bitmap.width >= image.bitmap.height; const imgWidth = isLargerThanTaller ? width : undefined; const imgHeight = isLargerThanTaller ? undefined : height; await mkdir(path.dirname(destination), { recursive: true }); await image.resize({ w: imgWidth, h: imgHeight }).write(destination); } catch (error) { console.error(`Failed to download art from "${url}": ${error.message}`); } } export async function composeImageTo(url1, url2, destination, size) { try { const width = size?.width ?? 300; const margin = Math.round((width * 5) / 100); const height = size?.height ?? width; await mkdir(path.dirname(destination), { recursive: true }); const image1 = url1 ? await loadImage(url1) : undefined; const image2 = url2 ? await loadImage(url2) : undefined; const image = new Jimp({ width, height, color: 0x00_00_00_00 }); if (image2) { const img2Width = image2.bitmap.width >= image2.bitmap.height ? width - margin : undefined; const img2Height = image2.bitmap.width < image2.bitmap.height ? height - margin : undefined; image2.resize({ w: img2Width, h: img2Height }); image.composite(image2, 0, (height - image2.bitmap.height) / 2 - margin); } if (image1) { const img1Width = image1.bitmap.width >= image1.bitmap.height ? width / 2 - margin : undefined; const img1Height = image1.bitmap.width < image1.bitmap.height ? height / 2 - margin : undefined; image1.resize({ w: img1Width, h: img1Height }); image.composite(image1, width - image1.bitmap.width, height - image1.bitmap.height); } await image.write(destination); } catch (error) { console.error(`Failed to download art from "${url1}" or "${url2}": ${error.message}`); } }