2013-06-09 15 views
5

Ho notato una significativa perdita di qualità utilizzando ImageIO.write, come posso disabilitare la compressione automatica?Perdita di qualità utilizzando ImageIO.write

val baos: ByteArrayOutputStream = new ByteArrayOutputStream 
val newBi = new BufferedImage(img.getWidth, img.getHeight, BufferedImage.TYPE_INT_RGB) 
val gr = newBi.createGraphics() 
gr.drawImage(img, 0, 0, img.getWidth(), img.getHeight(), Color.WHITE, null) 
ImageIO.write(newBi, "jpeg", baos) 
val b = baos.toByteArray 
baos.close() 

risposta

9

Utilizzare ImageWriter.

ImageWriter writer = ImageIO.getImageWritersByFormatName("jpeg").next(); 
ImageWriteParam param = writer.getDefaultWriteParam(); 
param.setCompressionMode(ImageWriteParam.MODE_EXPLICIT); // Needed see javadoc 
param.setCompressionQuality(1.0F); // Highest quality 
writer.write(image); 

Per immagini non fotografiche utilizzare .png.


Come commentato da @PiotrekDe, quanto segue sembra più logico.

writer.write(null, new IIOImage(image, null, null), param) 
+1

Ho provato questi metodi ma per alcuni motivi l'immagine di output è piena di nero. Sai da dove potrebbe venire? – Roch

+0

Scusa, sapevo di questi metodi (e che il png è lento), ma in generale scelgo png. –

+2

Penso che sia necessario passare 'param' indietro a' writer', come: 'writer.write (null, new IIOImage (image, null, null), param)' –

0

Le immagini jpeg utilizzano la compressione con perdita. Usa png. Anche questo è compresso ma con un algoritmo senza perdita di dati.

1

In Scala, utilizzando https://github.com/sksamuel/scrimage è possibile impostare il livello di compressione JPEG su

val in = // some input stream or byte array 
val out = // some output stream etc 
Image(in).writer(Format.JPEG).withCompression(1.0).write(out) 

È possibile impostare un valore compreso tra 0 e 1,0 per il livello di compressione.

0

JPEG La compressione è in perdita. Ma la compressione PNG è senza perdite. Quindi, suggerisco di scrivere in formato png. Ciò significa che non perderai la qualità anche se comprimi in formato PNG. Linee semplici:

ImageIO.write(newBI,"png",someOutputStream); 

Ma, se lo si desidera in formato jpg con qualità, impostare Qualità su 100%. Il seguente codice può aiutarti.

ImageWriter jpgWriter = ImageIO.getImageWritersByFormatName("jpg").next(); 
    ImageWriteParam jpgWriteParam = jpgWriter.getDefaultWriteParam(); 
    jpgWriteParam.setCompressionMode(ImageWriteParam.MODE_EXPLICIT); 
    jpgWriteParam.setCompressionQuality(1f); 
    jpgWriter.setOutput(someOutputStream); 
    //better to use ImageOutputStream 
    jpgWriter.write(null,new IIOImage(yourImage, null, null), jpgWriteParam); 
Problemi correlati