Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/image/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
java从像素矩阵创建BMP图像并反转_Java_Image_Bmp - Fatal编程技术网

java从像素矩阵创建BMP图像并反转

java从像素矩阵创建BMP图像并反转,java,image,bmp,Java,Image,Bmp,任务是从int RGB矩阵生成BMP文件,然后从BMP图像读取该矩阵 我使用这个类来生成BMP文件,但似乎很难逆转这种从图像中获取rgbValue数组的方法: /** * Class for creating bmp images from the pixel matrix (an int matrix). * @author eafkuor * @link http://forum.codecall.net/topic/62457-creating-a-bmp-image-in-java

任务是从int RGB矩阵生成BMP文件,然后从BMP图像读取该矩阵

我使用这个类来生成BMP文件,但似乎很难逆转这种从图像中获取
rgbValue
数组的方法:

/**
 * Class for creating bmp images from the pixel matrix (an int matrix).
 * @author eafkuor
 * @link http://forum.codecall.net/topic/62457-creating-a-bmp-image-in-java/
 */
import java.io.File;
import java.io.FileOutputStream;

public class BMP {
    private final static int BMP_CODE = 19778;

    byte[] bytes;

    public void saveBMP(String filename, int[][] rgbValues) {
        try {
            FileOutputStream fos = new FileOutputStream(new File(filename));

            bytes = new byte[54 + 3 * rgbValues.length * rgbValues[0].length + getPadding(rgbValues[0].length) * rgbValues.length];

            saveFileHeader();
            saveInfoHeader(rgbValues.length, rgbValues[0].length);
            saveRgbQuad();
            saveBitmapData(rgbValues);

            fos.write(bytes);

            fos.close();

        } catch (Exception ignored) {}

    }

    private void saveFileHeader() {
        byte[] a = intToByteCouple(BMP_CODE);
        bytes[0] = a[1];
        bytes[1] = a[0];

        a = intToFourBytes(bytes.length);
        bytes[5] = a[0];
        bytes[4] = a[1];
        bytes[3] = a[2];
        bytes[2] = a[3];

        //data offset
        bytes[10] = 54;
    }

    private void saveInfoHeader(int height, int width) {
        bytes[14] = 40;

        byte[] a = intToFourBytes(width);
        bytes[22] = a[3];
        bytes[23] = a[2];
        bytes[24] = a[1];
        bytes[25] = a[0];

        a = intToFourBytes(height);
        bytes[18] = a[3];
        bytes[19] = a[2];
        bytes[20] = a[1];
        bytes[21] = a[0];

        bytes[26] = 1;

        bytes[28] = 24;
    }

    private void saveRgbQuad() {

    }

    private void saveBitmapData(int[][] rgbValues) {
        int i;

        for (i = 0; i < rgbValues.length; i++) {
            writeLine(i, rgbValues);
        }

    }

    private void writeLine(int row, int[][] rgbValues) {
        final int offset = 54;
        final int rowLength = rgbValues[row].length;
        final int padding = getPadding(rgbValues[0].length);
        int i;

        for (i = 0; i < rowLength; i++) {
            int rgb = rgbValues[row][i];
            int temp = offset + 3 * (i + rowLength * row) + row * padding;

            bytes[temp] = (byte) (rgb >> 16);
            bytes[temp + 1] = (byte) (rgb >> 8);
            bytes[temp + 2] = (byte) rgb;
        }
        i--;
        int temp = offset + 3 * (i + rowLength * row) + row * padding + 3;

        for (int j = 0; j < padding; j++)
            bytes[temp + j] = 0;

    }

    private byte[] intToByteCouple(int x) {
        byte[] array = new byte[2];

        array[1] = (byte) x;
        array[0] = (byte) (x >> 8);

        return array;
    }

    private byte[] intToFourBytes(int x) {
        byte[] array = new byte[4];

        array[3] = (byte) x;
        array[2] = (byte) (x >> 8);
        array[1] = (byte) (x >> 16);
        array[0] = (byte) (x >> 24);

        return array;
    }

    private int getPadding(int rowLength) {

        int padding = (3 * rowLength) % 4;
        if (padding != 0)
            padding = 4 - padding;


        return padding;
    }
}
/**
*用于从像素矩阵(int矩阵)创建bmp图像的类。
*@author-eafkuor
*@linkhttp://forum.codecall.net/topic/62457-creating-a-bmp-image-in-java/
*/
导入java.io.File;
导入java.io.FileOutputStream;
公共类BMP{
专用最终静态int BMP_代码=19778;
字节[]字节;
public void saveBMP(字符串文件名,int[][]rgbValue){
试一试{
FileOutputStream fos=新的FileOutputStream(新文件(文件名));
字节=新字节[54+3*rgbValues.length*rgbValues[0]。length+getPadding(rgbValues[0]。length)*rgbValues.length];
saveFileHeader();
saveInfoHeader(rgbValue.length,rgbValue[0].length);
saveRgbQuad();
saveBitmapData(rgbValue);
fos.写入(字节);
fos.close();
}捕获(忽略异常){}
}
私有void saveFileHeader(){
字节[]a=IntToByteCourt(BMP_代码);
字节[0]=a[1];
字节[1]=a[0];
a=四字节(字节.长度);
字节[5]=a[0];
字节[4]=a[1];
字节[3]=a[2];
字节[2]=a[3];
//数据偏移量
字节[10]=54;
}
私有void saveInfoHeader(整数高度、整数宽度){
字节[14]=40;
字节[]a=四个字节(宽度);
字节[22]=a[3];
字节[23]=a[2];
字节[24]=a[1];
字节[25]=a[0];
a=四个字节(高度);
字节[18]=a[3];
字节[19]=a[2];
字节[20]=a[1];
字节[21]=a[0];
字节[26]=1;
字节[28]=24;
}
私有void saveRgbQuad(){
}
私有void saveBitmapData(int[][]rgbValue){
int i;
对于(i=0;i>16);
字节[temp+1]=(字节)(rgb>>8);
字节[temp+2]=(字节)rgb;
}
我--;
int temp=偏移量+3*(i+行长*行)+行*填充+3;
对于(int j=0;j>8);
返回数组;
}
专用字节[]intToFourBytes(intx){
字节[]数组=新字节[4];
数组[3]=(字节)x;
数组[2]=(字节)(x>>8);
数组[1]=(字节)(x>>16);
数组[0]=(字节)(x>>24);
返回数组;
}
私有int getPadding(int行长度){
整数填充=(3*行长度)%4;
如果(填充!=0)
填充=4-填充;
返回填充;
}
}

有没有制作这种东西的java库?或者,也许有人可以建议如何反转BMP文件?

在我看来,如果任务很容易实现,并且您可以更好地了解幕后发生的事情,那么使用API是一件懒惰的事情。在您自己至少做过一次之后,您就可以问心无愧地使用API了。最后,您应该使用一个API,因为工作代码可能比您自己的版本更强大、更安全

至少在理论上,反转图像是一件非常简单的事情。该过程包括两个步骤:

  • 将图像的颜色矩阵放入内存
  • 创建一个新图像,以便从内存中的图像中选择从左侧开始的每个像素,仅从右侧开始

  • 举例说明:

    假设我们有一个宽度为4px,高度为4px的图像。 0表示像素为黑色,1表示像素为白色

    实际上,我们有一个4x4二进制矩阵。让我们把它组成如下:

    [1][0]
    [1][0]
    
    要反转它,我们只需将数组复制到一个新的4x4矩阵中,但我们从右侧开始将值复制到新矩阵中:

    [1][0] => [0][1]
    [1][0] => [0][1]
    
    现在我们有了相反的图像:

    [0][1]
    [0][1]
    
    这就是我的想法

    在RGB上下文中,原始图像的矩阵将如下所示:

    [rgb(255, 255, 255)][rgb(0, 0, 0)]
    [rgb(255, 255, 255)][rgb(0, 0, 0)]
    

    现在,了解如何提取每个像素的颜色并将其写入新像素。这是一项简单的任务。

    javax.imageio.imageio应该为您处理。@BarrySW19它不提供BMP处理它应该-在我的系统上“system.out.println(Arrays.toString(imageio.getReaderFormatNames());“prints”[BMP,BMP,jpg,jpg,wbmp,jpeg,png,jpg,png,wbmp,GIF]“我得到”[jpg,BMP,BMP,jpg,jpeg,wbmp,png,jpeg,png,wbmp,GIF,GIF]“对于作者来说。你给出了什么?实现者在com.sun.imageio.plugins.bmp包中,所有标准的Oracle JDK都应该有这个包。我想要懒方法),因为这不是一个主要任务。而且,事实上,一切都不像你描述的那样容易:有一些bmp格式的头文件和一些其他功能应该在文件中实现