Image saved in JavaFX as jpg is pink toned

Image saved in JavaFX as jpg is pink toned.




I want to save an Image from my ImageView to files with different resolutions. Doing it as .png results as expected. As for .jpg - I get all files pink toned.




  
  Where is the trick? Here is the code:

Object[] imagesFromFotoListView = ta.myFotoListView.getItems().toArray();
new File(localDir).mkdirs();
for (int i = 0; i < imagesFromFotoListView.length; i++) {
    new File(localDir + "/" + i).mkdirs(); 
    final ImageView iv = new ImageView((Image) imagesFromFotoListView[i]);
    ImageIO.write(SwingFXUtils.fromFXImage(iv.snapshot(null, null), null), "jpg", new File(localModelFotoDir + "/" + i + "/large.jpg")); // JPG THAT FAILS PINK.
    BufferedImage bi = SwingFXUtils.fromFXImage(iv.snapshot(null, null), null);
    int resolution[] = new int[]{500, 250, 75};
    for (int j = 0; j < resolution.length; j++) {
        BufferedImage resizedBImage;
        if (bi.getWidth() == bi.getHeight()) {
            resizedBImage = resizeBufferedImage(bi, Scalr.Method.ULTRA_QUALITY, Scalr.Mode.AUTOMATIC, resolution[j], resolution[j]);
        } else if (bi.getWidth() > bi.getHeight()) {
            resizedBImage = resizeBufferedImage(bi, Scalr.Method.ULTRA_QUALITY, Scalr.Mode.AUTOMATIC, resolution[j], (int) ((double) resolution[j] * bi.getHeight() / bi.getWidth()));
        } else {
            resizedBImage = resizeBufferedImage(bi, Scalr.Method.ULTRA_QUALITY, Scalr.Mode.AUTOMATIC, (int) ((double) resolution[j] * bi.getWidth() / bi.getHeight()), resolution[j]);
        }
        Image resizedI = (Image) SwingFXUtils.toFXImage(resizedBImage, null);
        ImageIO.write(SwingFXUtils.fromFXImage((Image) SwingFXUtils.toFXImage(resizedBImage, null), null), "png", new File(localModelFotoDir + "/" + i + "/" + resolution[j] + ".png")); // PNG THAT GOES WELL
    }
}


Solution


I found a solution on Oracle forums. As widely discussed, the problem is in alpha-channel that needs to be excluded from the source image, targeted for .jpg save. I also rearranged my code to make it shorter. The workaround is:

// Get buffered image:
BufferedImage image = SwingFXUtils.fromFXImage(myJavaFXImage, null); 

// Remove alpha-channel from buffered image:
BufferedImage imageRGB = new BufferedImage(
    image.getWidth(), 
    image.getHeight(), 
    BufferedImage.OPAQUE); 

Graphics2D graphics = imageRGB.createGraphics();

graphics.drawImage(image, 0, 0, null);

ImageIO.write(imageRGB, "jpg", new File("/mydir/foto.jpg"));

graphics.dispose();

Fixed in Java 8: https://bugs.openjdk.java.net/browse/JDK-8114609



image,save,png,javafx,jpeg

No comments

Powered by Blogger.