Frage

I am attempting to read a jpg with ImageIO and then write it as a PNG after resizing the image.

Here is my code:

BufferedImage img = ImageIO.read(new FileInputStream("/u/my.jpg"));
    BufferedImage out = new BufferedImage(img.getWidth(), img.getHeight(), BufferedImage.TYPE_INT_ARGB);
    Graphics2D g = out.createGraphics();
    g.drawImage(img, 0, 0, img.getWidth()/2, img.getHeight()/2, null);
    g.dispose();
    ImageIO.write(out, "png", new FileOutputStream("/u/my2.png"));

The problem I have is that this results in a PNG-8881 (Binary/Bitmask Alpha Layer). I want to end up with a PNG-8888 with 8 bits for alpha instead of 1 bit for alpha.

Here is Image Magick identify output:

Image: /u/my2.png
Format: PNG (Portable Network Graphics)
Class: DirectClass
Geometry: 2848x4288+0+0
Units: Undefined
Type: TrueColorAlpha
Endianess: Undefined
Colorspace: sRGB
Depth: 8-bit
Channel depth:
  red: 8-bit
  green: 8-bit
  blue: 8-bit
  alpha: 1-bit
Channel statistics:
  Red:
    min: 0 (0)
    max: 252 (0.988235)
    mean: 42.2154 (0.165551)
    standard deviation: 84.6142 (0.33182)
    kurtosis: 1.41395
    skewness: 1.77533
  Green:
    min: 0 (0)
    max: 252 (0.988235)
    mean: 45.1979 (0.177247)
    standard deviation: 86.0758 (0.337552)
    kurtosis: 0.935575
    skewness: 1.62013
  Blue:
    min: 0 (0)
    max: 255 (1)
    mean: 46.4455 (0.182139)
    standard deviation: 87.2088 (0.341995)
    kurtosis: 0.742603
    skewness: 1.56331
  Alpha:
    min: 0 (0)
    max: 255 (1)
    mean: 63.75 (0.25)
    standard deviation: 110.418 (0.433013)
    kurtosis: -0.666667
    skewness: -1.1547
Image statistics:
  Overall:
    min: 0 (0)
    max: 255 (1)
    mean: 81.2772 (0.318734)
    standard deviation: 92.6906 (0.363492)
    kurtosis: 0.642375
    skewness: 1.36843
Alpha: none   #00000000
Rendering intent: Perceptual
Gamma: 0.454545
Chromaticity:
  red primary: (0.64,0.33)
  green primary: (0.3,0.6)
  blue primary: (0.15,0.06)
  white point: (0.3127,0.329)
Background color: white
Border color: srgba(223,223,223,1)
Matte color: grey74
Transparent color: none
Interlace: None
Intensity: Undefined
Compose: Over
Page geometry: 2848x4288+0+0
Dispose: Undefined
Iterations: 0
Compression: Zip
Orientation: Undefined
Properties:
  date:create: 2014-01-06T12:15:38-06:00
  date:modify: 2014-01-06T12:15:38-06:00
  png:IHDR.bit-depth-orig: 8
  png:IHDR.bit_depth: 8
  png:IHDR.color-type-orig: 6
  png:IHDR.color_type: 6 (RGBA)
  png:IHDR.interlace_method: 0 (Not interlaced)
  png:IHDR.width,height: 2848, 4288
  png:sRGB: intent=0 (Perceptual Intent)
  signature: f1cd61ef11890cb9981e30787ee13f9a27e0836b4b634fa7b9daf2f6bb14de66
Artifacts:
  filename: /u/my2.png
  verbose: true
Tainted: False
Filesize: 3.321MB
Number pixels: 12.21M
Pixels per second: 55.51MB
User time: 0.210u
Elapsed time: 0:01.219
Version: ImageMagick 6.8.6-6 2013-10-12 Q16 http://www.imagemagick.org

I need the PNG to be a 32-Bit PNG file with Full 8 bit alpha. How do I go about doing this?

Thank You.

Okay, so after reading one of the comments from @haraldK.

Updated Code:

public static void main(String[] args) throws IOException{

    BufferedImage img = ImageIO.read(new FileInputStream("/u/my.jpg"));
    BufferedImage out = new BufferedImage(img.getWidth()/2, img.getHeight()/2, BufferedImage.TYPE_INT_ARGB);
    Graphics2D g2D = out.createGraphics();
    g2D.drawImage(img, 0, 0, img.getWidth()/2, img.getHeight()/2, null);

    int w = out.getWidth();
    int h = out.getHeight();

    g2D.dispose();

    WritableRaster ras = out.getColorModel().createCompatibleWritableRaster(out.getWidth(), out.getHeight());
    BufferedImage out2 = new BufferedImage(out.getColorModel(), ras, false, null);

    ColorModel model = out.getColorModel();

    for (int i = 0; i < h; i++) {
        for (int j = 0; j < w; j++) {
            int data = out.getRGB(j, i);
            int pixel = model.getRGB(data);

            int a = pixel >> 24 & 0xff;
            int r = pixel >> 16 & 0xff;
            int g = pixel >> 8 & 0xff;
            int b = pixel & 0xff;

            Color color = new Color(r, g, b, a);
            if(i==25 && j==25){
                out2.setRGB(j, i, new Color(111,111,111,126).getRGB());
            }else{
                out2.setRGB(j, i, pixel);
            }

        }
    }

    ImageIO.write(out2, "png", new FileOutputStream("/u/my126.png"));

}

And the new output from running identify on the Image File:

Image: /u/my126.png
Format: PNG (Portable Network Graphics)
Class: DirectClass
Geometry: 1424x2144+0+0
Units: Undefined
Type: TrueColorAlpha
Endianess: Undefined
Colorspace: sRGB
Depth: 8-bit
Channel depth:
  red: 8-bit
  green: 8-bit
  blue: 8-bit
  alpha: 8-bit
Channel statistics:
  Red:
    min: 34 (0.133333)
    max: 252 (0.988235)
    mean: 168.862 (0.662203)
    standard deviation: 85.1618 (0.333968)
    kurtosis: -1.63932
    skewness: -0.419596
  Green:
    min: 42 (0.164706)
    max: 252 (0.988235)
    mean: 180.791 (0.708986)
    standard deviation: 71.5681 (0.280659)
    kurtosis: -1.51545
    skewness: -0.454524
  Blue:
    min: 44 (0.172549)
    max: 255 (1)
    mean: 185.782 (0.728557)
    standard deviation: 67.3447 (0.264097)
    kurtosis: -1.44714
    skewness: -0.500635
  Alpha:
    min: 126 (0.494118)
    max: 255 (1)
    mean: 255 (1)
    standard deviation: 0.0738282 (0.000289522)
    kurtosis: 3.05305e+06
    skewness: 1747.3
Image statistics:
  Overall:
    min: 0 (0)
    max: 255 (1)
    mean: 133.859 (0.524936)
    standard deviation: 65.0189 (0.254976)
    kurtosis: 5.00426
    skewness: -0.456343
Rendering intent: Perceptual
Gamma: 0.454545
Chromaticity:
  red primary: (0.64,0.33)
  green primary: (0.3,0.6)
  blue primary: (0.15,0.06)
  white point: (0.3127,0.329)
Background color: white
Border color: srgba(223,223,223,1)
Matte color: grey74
Transparent color: none
Interlace: None
Intensity: Undefined
Compose: Over
Page geometry: 1424x2144+0+0
Dispose: Undefined
Iterations: 0
Compression: Zip
Orientation: Undefined
Properties:
  date:create: 2014-01-06T17:08:21-06:00
  date:modify: 2014-01-06T17:08:21-06:00
  png:IHDR.bit-depth-orig: 8
  png:IHDR.bit_depth: 8
  png:IHDR.color-type-orig: 6
  png:IHDR.color_type: 6 (RGBA)
  png:IHDR.interlace_method: 0 (Not interlaced)
  png:IHDR.width,height: 1424, 2144
  png:sRGB: intent=0 (Perceptual Intent)
  signature: 8bb6e37dbde980af0296dfacebff27b217360aac8994dfad8e90efeecac3bbf2
Artifacts:
  filename: /u/my126.png
  verbose: true
Tainted: False
Filesize: 3.01MB
Number pixels: 3.053M
Pixels per second: 20.35MB
User time: 0.090u
Elapsed time: 0:01.150
Version: ImageMagick 6.8.6-6 2013-10-12 Q16 http://www.imagemagick.org

Basically this is what happens. When identify reads nothing but 255 for all alpha values - it incorrectly labels the Image File 8881, but if I change one pixel value to have an arbitrary gradient of transparency - identify recognizes the PNG File correctly as 8888.

War es hilfreich?

Lösung

There seems to be some inconsistencies in the identify output. This leads me to believe that identify is wrong (or at least isn't displaying what we would expect), and that the alpha channel in your image is indeed 8 bits (if you look at the "Channel statistics", Alpa max is 255, and 255 must be an 8 bit value).

This also seems consistent with your further debugging. So, conclusion: The image is correctly 32 bits PNG with 8 bit alpha. :-)

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top