È possibile unire in qualche modo immagini PNG a un'immagine animata APNG utilizzando nodejs?Unisci immagini PNG a un'immagine animata APNG
ho trovato libreria PHP solo: link
È possibile unire in qualche modo immagini PNG a un'immagine animata APNG utilizzando nodejs?Unisci immagini PNG a un'immagine animata APNG
ho trovato libreria PHP solo: link
io non sono sicuro di nodejs, ma si potrebbe provare APNG-canvas. APNG utilizza HTML5 (-webkit-canvas), JavaScript (jQuery).
"APNG-canvas è una libreria per la visualizzazione di file PNG animati nei browser con supporto canvas (Google Chrome, Internet Explorer 9, Apple Safari)."
Lavoro demo è qui.
Questa libreria non supporta la creazione di file APNG. – 1j01
Currently, no, non sembra. Wikipedia lists the available software, e come puoi vedere non c'è supporto per ImageMagick che ha un wrapper Node. Tuttavia, potresti scoprire che puoi scaricare lo command line tool apngasm e utilizzarlo come shell, se trovi che vale la pena che ci siano i wrapper della riga di comando del nodo per collegarlo a un'applicazione esistente usando child_process
(http://nodejs.org/api/child_process.html).
Non esiste una libreria per questo, ma è abbastanza semplice da implementare. Algoritmo per la fusione di più file PNG in un'unica APNG è descritto in Wikipedia:
- adottare tutti pezzi del primo file PNG come base dell'edificio.
- Inserire un blocco di controllo animazione (acTL) dopo il frammento di intestazione dell'immagine (IHDR).
- Se il primo PNG deve far parte dell'animazione, inserire un blocco di controllo del frame (fcTL) prima del blocco dei dati di immagine (IDAT).
- Per ciascuno dei fotogrammi rimanenti, aggiungere un blocco di controllo del frame (fcTL) e un blocco di dati del frame (fdAT). Quindi aggiungere il pezzo finale dell'immagine (IEND). Il contenuto per i blocchi di dati del frame (fdAT) viene ricavato dai blocchi di dati di immagine (IDAT) delle rispettive immagini di origine.
Ecco un esempio di implementazione:
const fs = require('fs')
const crc32 = require('crc').crc32
function findChunk(buffer, type) {
let offset = 8
while (offset < buffer.length) {
let chunkLength = buffer.readUInt32BE(offset)
let chunkType = buffer.slice(offset + 4, offset + 8).toString('ascii')
if (chunkType === type) {
return buffer.slice(offset, offset + chunkLength + 12)
}
offset += 4 + 4 + chunkLength + 4
}
throw new Error(`Chunk "${type}" not found`)
}
const images = process.argv.slice(2).map(path => fs.readFileSync(path))
const actl = Buffer.alloc(20)
actl.writeUInt32BE(8, 0) // length of chunk
actl.write('acTL', 4) // type of chunk
actl.writeUInt32BE(images.length, 8) // number of frames
actl.writeUInt32BE(0, 12) // number of times to loop (0 - infinite)
actl.writeUInt32BE(crc32(actl.slice(4, 16)), 16) // crc
const frames = images.map((data, idx) => {
const ihdr = findChunk(data, 'IHDR')
const fctl = Buffer.alloc(38)
fctl.writeUInt32BE(26, 0) // length of chunk
fctl.write('fcTL', 4) // type of chunk
fctl.writeUInt32BE(idx ? idx * 2 - 1 : 0, 8) // sequence number
fctl.writeUInt32BE(ihdr.readUInt32BE(8), 12) // width
fctl.writeUInt32BE(ihdr.readUInt32BE(12), 16) // height
fctl.writeUInt32BE(0, 20) // x offset
fctl.writeUInt32BE(0, 24) // y offset
fctl.writeUInt16BE(1, 28) // frame delay - fraction numerator
fctl.writeUInt16BE(1, 30) // frame delay - fraction denominator
fctl.writeUInt8(0, 32) // dispose mode
fctl.writeUInt8(0, 33) // blend mode
fctl.writeUInt32BE(crc32(fctl.slice(4, 34)), 34) // crc
const idat = findChunk(data, 'IDAT')
// All IDAT chunks except first one are converted to fdAT chunks
let fdat;
if (idx === 0) {
fdat = idat
} else {
const length = idat.length + 4
fdat = Buffer.alloc(length)
fdat.writeUInt32BE(length - 12, 0) // length of chunk
fdat.write('fdAT', 4) // type of chunk
fdat.writeUInt32BE(idx * 2, 8) // sequence number
idat.copy(fdat, 12, 8) // image data
fdat.writeUInt32BE(crc32(4, length - 4), length - 4) // crc
}
return Buffer.concat([ fctl, fdat ])
})
const signature = Buffer.from('\211PNG\r\n\032\n', 'ascii')
const ihdr = findChunk(images[0], 'IHDR')
const iend = Buffer.from('0000000049454e44ae426082', 'hex')
const output = Buffer.concat([ signature, ihdr, actl, ...frames, iend ])
fs.writeFileSync('output.png', output)
UPNG.js in grado di analizzare e costruire i file APNG - https://github.com/photopea/UPNG.js
Dal readme -
UPNG. js supporta APNG e l'interfaccia si aspetta "frame".
UPNG.encode (IMG, w, h, cnum, [dels])
imgs: array of frames. A frame is an ArrayBuffer containing the pixel data (RGBA, 8 bits per channel) w, h : width and height of the image cnum: number of colors in the result; 0: all colors (lossless PNG) dels: array of delays for each frame (only when 2 or more frames) returns an ArrayBuffer with binary data of a PNG file
UPNG.js può fare una minimizzazione lossy di file PNG, simili a TinyPNG e altri strumenti. Esegue la quantizzazione del colore usando l'algoritmo k-means .
La compressione loss è consentita dall'ultimo parametro cnum. Impostalo su zero per una compressione senza perdita di dati oppure scrivi il numero di colori consentiti nell'immagine. Valori più piccoli producono file più piccoli.Oppure usa 0 per senza perdita/256 per perdita.
penso che troverete quello che vi serve su Wikipedia sotto la sezione Application Support: http://en.wikipedia.org/wiki/APNG#Application_support –