java - 使用 BufferedImage 读取和写入图像

标签 java rgb pixel bufferedimage

示例代码如下。该代码运行完美并准确地创建了图像。但是创建的图像(当读回并获取像素时),像素似乎有 1 或 2 个值。 我正在通过在读入像素时以及将它们保存回文件之前打印像素来进行简单的测试。然后,我在新图像上运行另一个测试器,打印的像素如我所说,关闭了 1 或 2 个值(以像素为单位,例如“24”到“25”)。 但大多数像素都是准确的,只有少数像素不准确。这与图像的写回方式有关吗?

try
{
    //Read in image 
    BufferedImage  imgBuf = ImageIO.read(new File("image.jpg"));

    //take in pixels etc., and simply do nothing with them - testing puposes

    //Write back the image
    BufferedImage bufferedImage = new BufferedImage(imagePixelArray[0].length, imagePixelArray.length, BufferedImage.TYPE_INT_RGB);

    ImageIO.write(bufferedImage, "jpeg", new File("new-image.jpg"));
}
catch(IOException i){};

编辑

下面是如何将像素拆分为数组,然后使用位移位重新分配回数组的代码。再次强调,不要担心程序的逻辑。我需要确保读回新创建的图像时这些像素(表示为红色像素、绿色像素和蓝色像素)相同。下面的代码使用了上面使用 BufferedImage 的代码。我确实使用了 GIF 文件。但我知道有某种方法可以正确编码 JPEG(而不是压缩数据)

    int i=0;
      //Loop through RGBarray[] assigning their respecctive colour components using bit shifting
      //jpegPixels[255][255][3] - the third part of the array is their colour comonents
      //0 - red
      //1 - green
      //2 - blue
      for(int row=0; row<h; row++)
      {
         for(int col=0; col<w; col++)
         {
            jpegPixels[row][col][0] = ((RGBarray[i]>>16)&0xff);
            jpegPixels[row][col][1] = ((RGBarray[i]>>8)&0xff);
            jpegPixels[row][col][2] = (RGBarray[i]&0xff);
            i++;
         }
      }

//3 arrays - redPixels, greenPixels and bluePixels are assigned from jpegPixels[][][]

//loop again returning back the pixel information using bit shifting
for(int row=0; row<reconstructedJPEG.length; row++)
      {
         for(int col=0; col<reconstructedJPEG[0].length; col++)
         {
            int rgb = (redPixels[row][col] & 0xff) << 16 | (greenPixels[row][col] & 0xff) << 8 | (bluePixels[row][col] & 0xff);

            bufferedImage.setRGB(col, row, rgb);
         }
      }

最佳答案

JPG 使用有损压缩,因此这种类型的文件格式的像素永远不会精确。如果您查看已复制多次的 JPG 文件,您会开始看到错误的累积,这些错误通常出现在图像的边界和边缘处。如果您想要完美存储像素,请使用不同的图像文件格式类型,该类型不使用压缩或无损压缩,例如 PNG。


顺便说一句,代码如下:

catch(IOException i){};

永远不应该出现,即使是“只是一个示例代码来说明......”。


编辑
您声明:

No I am not doing any compression to the pixels at all. For testing purposes I am just reading the pixels in, and writing them back out against using BufferedImage. As in, the pixel values itself are being altered slightly by 1 or 2 values. I don't know wyhy. From testing and testing, it now seems to do with writing the values back to file ?

您正在使用 JPG - 因此,无论您是否知道,您都在进行压缩。

再说一遍,您是否尝试过使用 PNG 格式的图像进行实验?


编辑2
您声明:

But that doesn't explain why only some pixels are unchanged, but there odd ones, are being altered.

更改量和可能更改的像素数量将取决于 ImageWriter 使用的压缩级别(质量级别的倒数)。如果您提取出用于 jpg 图像的实际 ImageWriter,则可以设置此值。查看this question例如。

关于java - 使用 BufferedImage 读取和写入图像,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22330675/

相关文章:

检查颜色相似性的算法

c++ - 从 OpenCV 中的 Matrix 访问值

ios - 无论如何要在谷歌地图上计算英里或米到像素以计算缩放级别?

java - 加入超时的多个线程

c++ - 任何人都可以提供有关 rgbx8888 格式的详细解释吗?

java nio SocketChannel.read 不返回 -1 来指示流结束

python - 在 Python 中将 RGB 像素转换为灰度。没有matplot或PIL

jquery - 如何通过 jQuery 获取内联背景图像的像素高度

java - 在 Java 中访问嵌套的私有(private)静态类

java - Groovy Classpath 上的 Jenkins 包?