Skip to content
Torna al blog
Tutorial

Immagine compressa più grande? Le 3 cause reali

Il compressore non è rotto: il canvas ricodifica in RGBA a 32 bit e ingrandisce i file. Su 83 PNG reali, tutti e 83 sono cresciuti. Comprimi gratis online.

14 min di lettura

Immagine compressa più grande? Le 3 cause reali

Il tuo compressore quasi certamente funziona. Quando la compressione delle immagini non funziona, cioè quando il file torna della stessa dimensione o visibilmente più grande di quello che hai caricato, la causa è quasi sempre una di tre, e nessuna delle tre è uno strumento rotto.

La prima e più comune: qualsiasi strumento che comprime attraverso l’elemento canvas del browser scarta il color type del tuo PNG e ricodifica ogni pixel come RGBA a 32 bit. Abbiamo passato tutte le 83 card PNG Open Graph di questo sito attraverso canvas.toBlob('image/png') in Chrome 151.0.0.0. Tutte e 83 sono tornate più grandi. La crescita mediana è stata +76.6%, la più piccola +35.6%, la più grande +237.2%.

La seconda causa: il tuo JPEG è già compresso. Passalo per cinque round a qualità 0.8 e la dimensione del file smette di muoversi dopo la seconda passata, mentre ogni passata continua a degradare l’immagine.

La terza: il tuo PNG è già stato quantizzato. Non è rimasta nessuna ridondanza di colore che una seconda passata possa rimuovere.

Nessuna di queste si risolve trascinando più in basso il cursore della qualità. La soluzione è un formato diverso o un encoder diverso. Quegli stessi 83 PNG convertiti in WebP a qualità 0.8 sono diventati tutti più piccoli, mediana −94.2%.

Come sono stati prodotti questi numeri. Chrome 151.0.0.0 pilotato da Playwright, macOS 26.5.2, Node v25.8.2, upng-js 2.1.0, ImageMagick. Il set da 83 file è ogni PNG nella directory public/og di questo sito, non un suo campione. Altri quattro file controllati a 1200×630 e 800×600 coprono separatamente i casi foto, grafica, palette e JPEG.

1. La compressione delle immagini non funziona: triage in trenta secondi

Trova la tua riga, poi leggi la sezione che indica.

Cosa hai caricatoCosa hai ottenutoCausa alla radiceLeggi
PNG di uno screenshot o di una graficaPiù grande dell’originaleil canvas l’ha ricodificato in RGBA a 32 bitSezione 2
Foto JPEGPiù grande dell’originaleÈ stata salvata come PNGSezione 2
Foto JPEGQuasi nessun cambiamentoHa già raggiunto il suo plateau di dimensioneSezione 3
PNG già passato per un compressoreNessun cambiamento, o leggermente più grandeNon è rimasto margineSezione 4
Qualsiasi cosaPiù piccolo, ma sfocato o con i colori sbagliatiPerdita di generazione, o profilo ICC rimossoSezioni 3 e 6

Le righe non si escludono a vicenda. Una foto JPEG buttata dentro un esportatore PNG basato su canvas colpisce le prime due insieme, ed è così che un file da 47,828 byte diventa un file da 809,415 byte.

Se vuoi saltare la diagnosi e ottenere semplicemente un file più piccolo, il nostro compressore immagini usa un encoder PNG con quantizzazione invece di un round-trip su canvas, e scarta il proprio output ogni volta che il risultato non è più piccolo di quello che hai caricato.

2. Causa uno: il canvas del browser scrive sempre RGBA a 32 bit

Cosa fa davvero canvas.toBlob() al tuo PNG

In un round-trip su canvas non c’è nessuna fase di compressione. C’è una decodifica e una ricodifica, e tutto ciò che non è un valore di pixel si perde nel mezzo.

Disegna un’immagine su un canvas e il browser la decodifica in un buffer RGBA piatto: quattro byte per pixel, senza palette, senza trucchi sulla profondità di bit e senza metadati. HTMLCanvasElement.toBlob() codifica poi quel buffer da zero. La specifica PNG definisce sei color type, e un encoder PNG è libero di scegliere il più economico che rappresenti l’immagine. L’encoder canvas di Chrome non sceglie. Emette sempre il color type 6.

Color type in ingressoCosa restituisce canvas.toBlob('image/png')
RGB (color type 2)RGBA (color type 6)
Palette (color type 3)RGBA (color type 6)
JPEG (non ha un color type PNG)RGBA (color type 6)

Puoi leggerlo direttamente dai byte. Il byte 25 di un file PNG è la profondità di bit e il byte 26 è il color type, entrambi dentro il chunk IHDR:

xxd -s 24 -l 2 -p suspect.png
# 0806  ->  profondità di bit 8, color type 6 (RGBA)

Tutti e tre i tipi di input qui sopra hanno prodotto depth=8 type=6. Un’immagine con palette a 64 colori memorizza un byte per pixel più una piccola tabella; dopo il round-trip ne memorizza quattro per pixel e la tabella non c’è più. Deflate ne recupera una parte, ma non tutta.

Riproducilo nel tuo browser con questo snippet da console, che sceglie un file, gli fa fare il round-trip e stampa entrambe le dimensioni più il color type:

const input = document.createElement('input');
input.type = 'file';
input.accept = 'image/png,image/jpeg';
input.onchange = async () => {
  const file = input.files[0];
  const bitmap = await createImageBitmap(file);
  const canvas = document.createElement('canvas');
  canvas.width = bitmap.width;
  canvas.height = bitmap.height;
  canvas.getContext('2d').drawImage(bitmap, 0, 0);
  const blob = await new Promise((r) => canvas.toBlob(r, 'image/png'));
  const head = new Uint8Array(await blob.slice(0, 26).arrayBuffer());
  console.log(file.name, file.size, '->', blob.size);
  console.log('bit depth', head[24], 'color type', head[25]);
};
input.click();

L’argomento di qualità passato a toBlob viene ignorato per image/png. PNG è lossless, quindi non c’è niente che un numero di qualità possa barattare, e un cursore che sembra controllare la compressione PNG in uno strumento basato su canvas non controlla niente.

83 file misurati: ogni immagine compressa è tornata più grande dell’originale

Il run completo, senza selezioni di comodo:

MisuraValore
File testati83 (ogni PNG in public/og, sia con color type RGB sia con palette)
File cresciuti83 / 83 (100%)
Aumento minimo+35.6%
Aumento mediano+76.6%
Aumento massimo+237.2%

Un file singolo, così ne vedi la forma: aes-decrypt.png è passato da 505,516 B a 898,014 B, un aumento del +77.6%. Lo stesso file codificato in WebP a qualità 0.8 pesa 27,188 B, −94.6%.

Il confine del campione conta. Questi 83 file sono card Open Graph: 1200×630, sfondi piatti, testo grande, una manciata di colori del brand. Sono esattamente il tipo di grafica che un buon encoder PNG gestisce bene, ed è proprio per questo che un round-trip su canvas li danneggia così tanto. È un risultato forte per i PNG di tipo grafico; non è un’affermazione sul fatto che ogni PNG al mondo cresca dopo un round-trip su canvas. Un PNG fotografico già memorizzato in RGBA completo ha molto meno da perdere.

Il risultato stabilisce però questo: se la tua immagine compressa è più grande dell’originale e lo strumento gira in una scheda del browser, il primo posto dove guardare è l’encoder, non le tue impostazioni.

Perché un JPEG salvato come PNG cresce di 16.9×

Questa è la riga più estrema del set di dati. Quattro file controllati, tutti e quattro passati per lo stesso percorso canvas:

FileCaratteristicaOriginalecanvas PNGVariazioneJPEG q92JPEG q80WebP q80
og-a.pngGrafica, 2,351 colori, RGB306,302607,481+98.3%56,45937,69513,852
quantized.pngPalette a 64 colori59,843184,856+208.9%78,38844,44216,046
photo.pngFoto, 479,373 colori498,639867,763+74.0%77,32145,05024,068
photo.jpgJPEG q8247,828809,415+1,592% (16.9×)58,762 (+22.9%)47,15223,862

Quell’ultima riga sono 47,828 byte in ingresso e 809,415 byte in uscita.

Il meccanismo spiega un’intera famiglia di segnalazioni del tipo “la compressione l’ha fatto diventare più grande”. JPEG è un codec lossy nel dominio delle frequenze: trasforma blocchi 8×8 in coefficienti DCT, li quantizza in modo aggressivo e memorizza i sopravvissuti. PNG è un codec lossless nel dominio spaziale: predice ogni pixel dai suoi vicini e comprime i residui con deflate. Decodifica un JPEG e ottieni pixel che portano con sé ogni artefatto introdotto dal quantizzatore: ringing vicino ai bordi, blocchettatura nelle sfumature morbide, rumore sottile dove l’originale non ne aveva.

Salva quei pixel come PNG e stai chiedendo a un codec lossless di memorizzare gli artefatti alla perfezione. E lui obbedisce. Proprio il rumore che JPEG ha creato per rendere piccolo il file è ora la cosa che rende grande il PNG, perché il rumore è esattamente ciò che un encoder lossless predittivo non riesce a comprimere.

Ovunque un’impostazione predefinita “salva come PNG” si trovi davanti a una foto, sta succedendo questo: strumenti per screenshot, export dai tool di design, client di chat, alcuni widget di upload.

Gli stessi pixel, 3.46× di distanza, entrambi lossless

L’encoder canvas è misurabilmente debole. Prendi il buffer di pixel di og-a.png e codificalo in due modi, entrambi completamente lossless:

EncoderOutputColor type
Chrome canvas toBlob('image/png')607,481 BRGBA (upsample forzato)
upng-js encode(..., cnum=0)175,491 BRGB (color type originale mantenuto)

3.46×, per pixel identici. Abbiamo verificato la proprietà lossless invece di darla per scontata: decodificando l’output di upng-js a cnum=0 si ottiene un buffer identico byte per byte al buffer RGBA di partenza. Per quel 3.46× non è stato barattato niente.

Questo spiega perché due compressori online, entrambi gratuiti, entrambi con la stessa promessa, danno risultati che non sono neanche lontanamente paragonabili. “Comprimere nel browser” descrive due implementazioni completamente diverse. Una passa i pixel a canvas.toBlob e spedisce quello che torna indietro. L’altra si porta dietro un vero encoder PNG e controlla il color type. Stesso input, stesso browser, 3.46× di distanza.

3. Causa due: al tuo JPEG non è rimasto niente da dare

Cinque round di ricompressione, e la dimensione smette di muoversi

Prendi photo.jpg, che era già stato salvato a qualità 82, e ricomprimilo a qualità 0.8 cinque volte di fila, ogni generazione che alimenta la successiva:

GenerazioneBytevs. precedente
0 (originale, q82)47,828
147,152−1.4%
247,164+0.0%
347,156−0.0%
447,1560.0%
547,1560.0%

La prima passata ti fa guadagnare l’1.4%. Dalla generazione 2 in poi la dimensione del file resta bloccata in una fascia di ±12 byte, e le generazioni 4 e 5 hanno esattamente la stessa dimensione della generazione 3.

Ecco che aspetto ha la “compressione che non funziona” quando l’input è un JPEG. Lo strumento ha girato. L’encoder ha girato. Semplicemente non era rimasto niente da rimuovere, perché le tabelle di quantizzazione a qualità 80 azzeravano già all’incirca i coefficienti che la qualità 82 aveva tenuto. Una volta che un coefficiente è sparito, non lo puoi rimuovere una seconda volta.

Puoi vederlo succedere in locale:

cp photo.jpg gen0.jpg
for i in 1 2 3 4 5; do
  magick "gen$((i-1)).jpg" -quality 80 "gen$i.jpg"
done
stat -f%z gen0.jpg gen1.jpg gen2.jpg gen3.jpg gen4.jpg gen5.jpg

Su Linux usa invece stat -c%s. Il conteggio esatto dei byte dipende dall’encoder a cui è linkata la tua build di ImageMagick, quindi non aspettarti che la tabella qui sopra si riproduca cifra per cifra. Conta la forma: un calo significativo, poi una linea piatta.

Alzare il numero della qualità non è comprimere

Guarda di nuovo la riga photo.jpg nella sezione 2. Ricomprimere quell’originale di qualità 82 a qualità 92 ha prodotto 58,762 byte: +22.9%.

Sorprende chi dà per scontato che il parametro di qualità sia una manopola che va da “piccolo” a “grande”, da impostare dove si vuole. Non è un obiettivo di qualità assoluto. Seleziona una tabella di quantizzazione, e far ripassare un’immagine decodificata attraverso una tabella più fine di quella che l’ha prodotta memorizza gli artefatti esistenti con più precisione, aggiungendoci sopra un nuovo giro di perdita. File più grande e immagine peggiore, tutto insieme.

La regola che ne deriva: non ricomprimere mai un JPEG con un’impostazione di qualità superiore a quella con cui è stato salvato. Se non sai qual era, non ricomprimerlo affatto. Torna alla sorgente.

Perdita di generazione: il degrado da ricompressione JPEG che non vedi

La tabella del plateau nasconde una trappola. La dimensione ha smesso di cambiare dopo la generazione 2, ma l’immagine ha continuato a cambiare. Ogni passata decodifica in pixel, ritrasforma e riquantizza. I coefficienti che in una generazione erano sopravvissuti al limite, nella successiva vengono spinti oltre.

Il danno non compare dove lo cerchi. In miniatura, la generazione 5 e la generazione 1 sono indistinguibili. Porta lo zoom al 100% e controlla i punti in cui JPEG cede sempre per primo: bordi netti su sfondi piatti, testo e sfumature morbide, dove la blocchettatura appare come piastrelle 8×8 visibili. In una pipeline di build che ricomprime a ogni deploy, tutto questo si accumula in silenzio per mesi.

Qui abbiamo misurato dimensioni di file, non qualità percettiva, quindi non ti citeremo un valore PSNR o SSIM per le cinque generazioni. Non l’abbiamo misurato. I dati sulle dimensioni bastano da soli: dalla generazione 2 il costo è tutto sul lato qualità e il beneficio è zero.

Gli spostamenti di colore sono un guasto a parte con lo stesso innesco. Il canvas non porta metadati, quindi un round-trip con toBlob butta via il blocco EXIF e con lui il profilo ICC. Un’immagine taggata Display P3 o Adobe RGB entra taggata ed esce senza tag, e i visualizzatori la interpreteranno come sRGB. I valori dei pixel non si sono mossi. Sono cambiate le istruzioni per interpretarli.

4. Causa tre: il PNG non si riduce perché era già stato quantizzato

Se il tuo PNG è già passato una volta per un compressore, la seconda passata non ha niente su cui lavorare. Questa è la riga quantized.png, un file da 59,843 byte già ridotto a una palette di 64 colori, fatto scendere per tre percorsi separati:

PercorsoRisultatovs. originale
Ricodifica lossless (upng cnum=0)61,377+2.6%
Quantizzazione a 256 colori61,366+2.5%
Quantizzazione a 64 colori61,366+2.5%

Ogni percorso è uscito più grande dell’originale. Non di molto, ma più grande, e questo include quantizzare a 64 colori un file che di colori ne aveva già 64.

La compressione PNG funziona rimuovendo ridondanza: colori ripetuti, vicini prevedibili, una palette piccola. Una passata precedente li ha già raccolti tutti. Quel che resta è quasi incomprimibile, e il piccolo aumento è l’overhead dell’encoder stesso: un ordinamento della palette leggermente diverso, scelte di filtro diverse per ogni scanline, un deflate un po’ meno fortunato.

La conseguenza pratica è che “0% risparmiato” su un PNG già ottimizzato è il risultato corretto, non un fallimento. Uno strumento che segnala un piccolo aumento e poi tiene il tuo file originale si sta comportando bene. Uno che ti consegna comunque il file più grande sta sbagliando.

5. La leva vera per il PNG è la quantizzazione, non la ricodifica

Ricodifica lossless, 256 colori e 64 colori a confronto

Tre file, tre strategie, misurati:

FileOriginaleLossless (cnum=0)256 colori64 colori
og-a.png306,302175,491 (−42.7%)110,772 (−63.8%)76,230 (−75.1%)
photo.png498,639587,863 (+17.9%)109,284 (−78.1%)61,397 (−87.7%)
quantized.png59,84361,377 (+2.6%)61,366 (+2.5%)61,366 (+2.5%)

Due cose saltano all’occhio.

La ricodifica lossless è lo strumento più debole a disposizione. Ha guadagnato il 42.7% sulla grafica, ha restituito il 17.9% sulla foto e ha perso il 2.6% sul file già quantizzato. Il contenuto fotografico mette in difficoltà anche un encoder PNG lossless competente, perché non c’è nessuna palette da trovare e i pixel vicini non si predicono bene a vicenda.

La riduzione vera arriva dalla quantizzazione, e il divario non è affatto ravvicinato: 63.8% contro 42.7% sulla stessa grafica a 256 colori, 75.1% a 64. Da riga di comando:

magick logo.png -colors 64 PNG8:logo-64.png
magick logo.png -colors 256 PNG8:logo-256.png

Il prefisso PNG8: forza un PNG con palette. Senza, ImageMagick può ridurre i colori e poi scrivere comunque un file truecolor, il che butta via gran parte del beneficio.

Quando una palette è sicura e quando ottieni banding

La quantizzazione è lossy. Mappa ogni pixel sulla voce più vicina di una palette limitata, quindi la domanda è se il tuo contenuto abbia abbastanza colori distinti perché la cosa si veda.

Sicuro: icone, loghi, screenshot di interfacce, illustrazioni piatte, diagrammi, tutto ciò che ha grandi regioni di colore uniforme e bordi netti. Di solito contengono al massimo qualche centinaio di colori distinti, quindi una palette da 256 voci è quasi gratis e spesso sopravvivono anche a 64.

Rischioso: fotografie, sfumature morbide, ombre sfumate e sovrapposizioni semitrasparenti. Ridurre una sfumatura a 64 gradini produce bande visibili, e il dithering baratta quelle bande con del rumore che poi ti costa indietro una parte della dimensione del file. La trasparenza parziale sopra una sfumatura è il caso più difficile di tutti.

La trasparenza merita un controllo a parte, perché quanta ne sopravvive dipende dall’encoder più che dalla quantizzazione in sé. Il PNG8: di ImageMagick scrive trasparenza binaria, quindi un pixel è o completamente opaco o completamente trasparente, e un bordo morbido con antialiasing torna indietro duro. Un quantizzatore PNG dedicato mantiene il canale alfa completo e con lui il bordo morbido. Se il tuo asset ha un’ombra o bordi sfumati, confronta i due prima di decidere.

Controlla il risultato al 100%, non in miniatura. Il banding è l’unico artefatto che un’anteprima rimpicciolita nasconde in modo affidabile.

6. La soluzione: cambia formato invece di ricomprimere

Una tabella per decidere il formato

ContenutoUsaPerché
FotografieWebP, oppure JPEG per la massima compatibilitàLa codifica lossy in frequenza è ciò che serve alle foto
Screenshot, grafica di interfacciaPNG quantizzato, o WebPColori piatti, bordi netti, palette piccole
Icone e loghiSVG quando hai il vettoriale, altrimenti PNG quantizzatoI vettoriali non hanno problemi di risoluzione
Qualsiasi cosa richieda trasparenzaWebP o PNGEntrambi portano un canale alfa completo
AnimazioneWebPUn formato solo al posto di una GIF
Archiviazione pixel per pixelPNG, losslessL’unico caso in cui il lossless è un requisito

Questa è la versione breve, di proposito. L’efficienza di codifica e il supporto dei browser tra i formati moderni hanno un articolo tutto loro: WebP vs AVIF vs JPEG.

Cosa ha fatto WebP agli stessi 83 file

Il set da 83 file che è cresciuto nel 100% dei casi passando per il PNG da canvas, convertito invece in WebP a qualità 0.8: 83 su 83 sono diventati più piccoli, mediana −94.2%. Il singolo file di prima, aes-decrypt.png, è passato da 505,516 B a 27,188 B, −94.6%.

I file controllati concordano. og-a.png: 306,302 come PNG, 13,852 come WebP q80. photo.png: 498,639 come PNG, 24,068 come WebP q80. photo.jpg: 47,828 come JPEG, 23,862 come WebP q80.

Una precisazione su quest’ultimo confronto. WebP a qualità 0.8 è lossy, quindi non compete con PNG alle stesse condizioni, e ricodificare un JPEG esistente in WebP ti costa comunque una generazione. Il confronto che conta è con quello che stavi per pubblicare, non con un ipotetico originale perfetto.

Quando conviene tenere comunque il PNG

A volte il lossless è un requisito, non una preferenza. Tieni il PNG per gli asset che rientrano in una pipeline di design e vengono modificati di nuovo, per gli screenshot usati nei test di confronto pixel per pixel, per i ritagli di interfaccia dove un solo colore spostato rompe un diff visivo, e per tutto ciò che verrà composto più avanti, dove gli artefatti di quantizzazione si sommerebbero. In quei casi, usa un vero encoder con quantizzazione se il contenuto lo permette, e accetta la dimensione del file se non lo permette.

Un altro tipo di “più grande” che non c’entra con la compressione

Se incorpori le immagini come data URI, la dimensione nel tuo CSS o HTML non è la dimensione su disco. Base64 codifica ogni 3 byte in 4 caratteri, più il padding, quindi il testo è aritmeticamente +33% più grande dei byte che trasporta, prima di qualsiasi compressione in transito. Un’immagine perfettamente ottimizzata diventa comunque un terzo più grande nel momento in cui la incorpori. Se il compromesso convenga o no lo trattiamo nella guida all’inline con data URI.

7. In pratica: browser, riga di comando, pipeline di build

Nel browser

La distinzione che conta quando scegli uno strumento basato su browser è se il PNG passa per il canvas. Nel nostro compressore immagini non ci passa. L’input PNG viene quantizzato su una palette di colori e riscritto come un vero PNG con il canale alfa intatto, così trasparenza e bordi morbidi sopravvivono; il cursore della qualità corrisponde a una dimensione di palette e non a un argomento di toBlob che il PNG ignorerebbe comunque. Qualità 100 corrisponde a una ricodifica lossless. JPEG e WebP invece passano per il canvas, dove il parametro di qualità è reale e fa quello che ti aspetti.

Un comportamento sembra un bug e non lo è: se il risultato compresso non è più piccolo del file che hai caricato, lo strumento butta via il proprio output e tiene i byte originali. Su un PNG già ottimizzato vedrai “0% risparmiato”. È la sezione 4 che funziona come previsto.

L’elaborazione avviene in locale: il browser non carica niente da nessuna parte.

Da riga di comando

cwebp è incluso in libwebp ed è il modo più veloce per verificare se un cambio di formato risolve il tuo problema:

# WebP lossy, qualità 0-100
cwebp -q 80 photo.png -o photo.webp

# WebP lossless, sforzo di compressione 0-9
cwebp -z 9 logo.png -o logo.webp

ImageMagick 7 copre i casi di conversione e di quantizzazione:

# Da PNG a JPEG con una qualità scelta
magick photo.png -quality 80 photo.jpg

# Quantizza in un PNG con palette a 64 colori
magick logo.png -colors 64 PNG8:logo-64.png

# Rimuovi EXIF e altri metadati
magick photo.jpg -strip photo-clean.jpg

Su macOS, sips è già installato e non richiede dipendenze:

# Converti in JPEG; formatOptions accetta 0-100 oppure low/normal/high/best
sips -s format jpeg -s formatOptions 80 photo.png --out photo.jpg

# Ridimensiona così che il lato più lungo sia 1200 px, proporzioni mantenute
sips -Z 1200 photo.jpg --out photo-1200.jpg

# Rileggi le dimensioni
sips -g pixelWidth -g pixelHeight photo-1200.jpg

Ridimensiona prima di comprimere. Gli encoder lavorano sui pixel, e il pixel più economico è quello che non esiste.

In una pipeline di build

Quando il lavoro diventa automatico invece che manuale, la decisione si sposta su dove avviene il lavoro e su quale libreria lo fa, il che cambia completamente i compromessi: compressione immagini nel browser rispetto a Node.js copre quel confronto. L’unica regola che si porta dietro da questo articolo: comprimi dal file sorgente originale a ogni build, mai dall’output della build precedente. È così che una pipeline scende lungo la curva della perdita di generazione mentre le dimensioni dei file sembrano perfettamente stabili.

8. Cinque convinzioni che le misure non sostengono

“Comprimere due volte rende il file più piccolo.” La generazione 1 ha guadagnato l’1.4%. Le generazioni da 2 a 5 sono rimaste entro ±12 byte mentre l’immagine continuava a degradarsi. La seconda passata è puro costo.

“PNG è lossless, quindi è il formato migliore.” Lossless è una proprietà, non una virtù. La nostra foto di test pesa 498,639 byte come PNG e 24,068 come WebP q80. Conservare una fotografia bit per bit quando verrà guardata solo su uno schermo non serve a niente e costa gran parte del file.

“Qualità 100 è la scelta sicura.” Ricomprimere un JPEG di qualità 82 a qualità 92 ha prodotto +22.9% e un’immagine peggiore. Sopra l’impostazione di qualità dell’originale, il numero smette di significare “più sicuro” e inizia a significare “più grande”.

“Il file è grande perché la risoluzione è alta.” La risoluzione conta, ma a parità di risoluzione conta di più il formato. og-a.png è 1200×630 in entrambi i casi: 607,481 byte come PNG da canvas, 13,852 byte come WebP q80. Stesso numero di pixel.

“I compressori online sono tutti uguali.” Stessi pixel, stesso browser, entrambi lossless: 607,481 byte dal canvas, 175,491 da upng-js. Una differenza di 3.46× tra due strumenti che si descrivono in modo identico.

9. FAQ

Perché la mia immagine compressa è più grande dell’originale?

Perché lo strumento l’ha ricodificata invece di comprimerla. L’output del canvas del browser è sempre un PNG RGBA a 32 bit, che scarta le palette e memorizza quattro byte per pixel. Nel nostro test su 83 PNG reali, tutti e 83 sono cresciuti, con un aumento mediano del +76.6%. Converti invece in WebP o JPEG.

Perché il mio PNG non diventa più piccolo quando lo comprimo?

PNG è lossless, quindi un cursore della qualità non ha niente da barattare. La riduzione vera arriva tagliando il numero di colori, e se il file era già stato quantizzato non è rimasto niente da tagliare. Il nostro PNG di test a 64 colori è tornato a +2.5% dopo essere stato quantizzato a 64 colori una seconda volta.

Comprimere un JPEG due volte fa perdere qualità?

Sì, e in cambio non ottieni quasi nulla. Cinque round a qualità 0.8: da 47,828 byte a 47,152 alla prima passata, poi bloccato entro 12 byte per le quattro successive. La dimensione ha smesso di muoversi mentre ogni passata continuava a riquantizzare l’immagine. Conserva gli originali.

Meglio PNG o JPEG per ottenere un file più piccolo?

Per le fotografie, JPEG o WebP, senza eccezioni. La nostra foto di test ha misurato 498,639 byte come PNG, 45,050 come JPEG q80 e 24,068 come WebP q80. Riserva il PNG a grafiche piatte, testo nitido e trasparenza, dove è una palette piccola a fare il lavoro di compressione.

Perché la mia immagine è diventata sfocata dopo la compressione?

Due cause diverse. Gli encoder lossy con impostazioni di qualità basse producono blocchettatura visibile intorno a bordi e testo. Le passate ripetute aggiungono perdita di generazione anche quando la dimensione del file smette di cambiare. Se i colori si sono spostati invece di ammorbidirsi, il round-trip su canvas ha buttato via il tuo profilo ICC, dato che il canvas non porta alcun metadato.

Posso comprimere un’immagine senza perdere qualità?

Sì, ma aspettati molto meno. La ricodifica lossless si limita a riscrivere pixel identici in modo più efficiente: da 306,302 a 175,491 byte sulla nostra grafica, verificati identici byte per byte dopo la decodifica. Lo stesso approccio su una foto è andato nella direzione sbagliata, +17.9%. Per risparmi veri senza perdita visibile, usa WebP a qualità 80.

Perché il mio PNG è così grande se è solo uno screenshot?

Gli strumenti di cattura salvano lo schermo come PNG RGBA completo, quattro byte per pixel prima della compressione, e un display Retina raddoppia il numero di pixel in ogni dimensione. Il contenuto piatto risponde bene alla riduzione della palette: la grafica della nostra card Open Graph è calata del 63.8% a 256 colori e del 75.1% a 64.

Ridimensionare riduce la dimensione del file più che comprimere?

Di solito sì, e le due cose si sommano. Dimezzare entrambe le dimensioni rimuove tre quarti dei pixel prima ancora che l’encoder parta, e la dimensione del file segue a grandi linee il numero di pixel. Ridimensiona prima alle dimensioni che mostri davvero, poi comprimi una volta sola. Un file a piena risoluzione uscito dalla fotocamera buttato in uno spazio da miniatura spreca entrambe le passate.

Tag: image-compression png jpeg webp canvas debugging

Articoli correlati

Vedi tutti gli articoli