将字节数组转换为png [英] Converting byte array to png

查看:446
本文介绍了将字节数组转换为png的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我使用以下代码从图像中获取了一个字节数组。

I have a byte array obtained from an image using the following code.

String path = "/home/mypc/Desktop/Steganography/image.png";
File file = new File(path);
BufferedImage bfimage = ImageIO.read(file);

ByteArrayOutputStream baos = new ByteArrayOutputStream();
ImageIO.write(bfimage, "png", baos);
baos.flush();
byte[] img_in_bytes = baos.toByteArray();
baos.close();

然后我使用以下代码将这些字节转换回png图像。

Then I converted these bytes back to png image using the following code.

BufferedImage final_img = ImageIO.read(new ByteArrayInputStream(img_in_bytes));
File output_file = new File("Stegano2.png");
ImageIO.write(final_img, "png", output_file);

如果我只执行这段代码,那就完全没问题了。但是,如果我尝试修改其间的一些字节,请像这样说:

It is perfectly fine if i just execute this piece of code. But if i try to modify some of the bytes in between, say like this :

    Insert_number_to_image(image_in_bytes,  10);

我的方法Inset_number_to_image是这样的:

and my method "Inset_number_to_image" goes like this :

static void Insert_number_to_image(byte[] image, int size){     
    byte[] size_in_byte = new byte[4];
    size_in_byte[0] = (byte)(size >>> 0);
    size_in_byte[1] = (byte)(size >>> 8);
    size_in_byte[2] = (byte)(size >>> 16);
    size_in_byte[3] = (byte)(size >>> 24);

    byte temp;
    int count = 0;

    for(int i=0; i<4; i++)
    {
        for(int j=0; j<8; j++)
        {
            temp = size_in_byte[i];
            temp = (byte)(temp >>> j);
            temp = (byte)(temp & 1);
            if(temp == 1)
            {
                image[count] = (byte)(image[count] | 1);
            }
            else if(temp == 0)
            {
                image[count] = (byte)(image[count] & (byte)(~(1)));
            }
            count++;
        }
    }
}

然后在那之后,当我我使用上面提到的相同代码将修改后的字节数组保存为png图像,我收到此错误:

then after that, when i save the modified byte array as png image using same code mentioned above, i am getting this error :

Exception in thread "main" java.lang.IllegalArgumentException: image == null!
    at javax.imageio.ImageTypeSpecifier.createFromRenderedImage(ImageTypeSpecifier.java:925)
    at javax.imageio.ImageIO.getWriter(ImageIO.java:1591)
    at javax.imageio.ImageIO.write(ImageIO.java:1520)
    at Steganography.main(Steganography.java:211)


推荐答案

您正在使用的是PNG图像的原始字节流。 PNG是压缩格式,其中字节流不反映任何像素值直接甚至更改一个字节可能会不可逆转地损坏文件。

What you're using is the raw bytestream of a PNG image. PNG is a compressed format, where the bytestream doesn't reflect any of the pixel values directly and even changing one byte might irreversibly corrupt the file.

您想要的是将像素数据提取到一个字节数组

What you want instead is to extract the pixel data to a byte array with

byte[] pixels = ((DataBufferByte) img.getRaster().getDataBuffer()).getData();

现在您可以根据需要修改像素值。当您准备将其保存回文件时,将像素阵列放入将像素字节数组转换为BufferedImage 一个 DataBufferByte 对象并将其传递给 WriteableRaster ,然后用它来创建 BufferedImage

Now you can modify the pixel values however you want. When you are ready to save that back to a file, convert the pixel byte array to a BufferedImage by putting your pixel array in a DataBufferByte object and passing that to a WriteableRaster, which you then use to create a BufferedImage.

您的方法适用于原始字节流直接表示像素的格式,例如 BMP 。但是,即使这样,你也必须跳过前几个字节以避免损坏标题。

Your method would work for formats where the raw bytestream does directly represent the pixels, such as in BMP. However, even then you'd have to skip the first few bytes to avoid corrupting the header.

这篇关于将字节数组转换为png的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆