字节数组到 8 位真彩色图像
Byte array to an 8 bit truecolor image
我正在尝试从旧 PC 游戏中提取一些精灵。我已经找到精灵并将它们以灰度形式撕成单独的文件。现在我想弄清楚如何给它们上色。可执行文件或其数据文件中似乎没有任何调色板数据 - 加上游戏所需的颜色深度(256 色)让我相信每个字节实际上是一个 8 位真彩色值。
假设我有一个(在本例中缩短的)数组,如下所示:
12 11 12 11
0A 13 12 11
13 12 11 0A
12 11 13 13
一些类似于我用来编写图像的示例代码如下所示:
DataInputStream dis = new DataInputStream(new FileInputStream("GAME.EXE"));
dis.skipBytes(bytesToImage);
BufferedImage bufferedImage = new BufferedImage(columns, rows, BufferedImage.TYPE_BYTE_INDEXED);
for (int i = 0; i < rows; i++) {
for (int j = 0; j < columns; j++) {
byte pixel = dis.readByte();
System.out.print(toHexString(pixel));
//For now, greyscale everything.
int value = pixel << 16 | pixel << 8 | pixel;
bufferedImage.setRGB(j, i, value);
}
System.out.print(System.getProperty("line.separator"));
}
ImageIO.write(bufferedImage, "PNG", new File("test.png"));
我已经弄乱了传递给构造函数的 imageType 和手动传递的 ColorModel,但似乎都没有做任何有用的事情。在像素上执行二进制 AND 和一些位移主要只是将图像设置为深红色。
在这种情况下,我该如何将每个像素设置为正确的真彩色值?
8位真彩色表示第7位到第5位包含红色,第4位到第2位包含绿色,第1位和第0位包含蓝色。 (即。RRRGGGBB
)您需要将这些转移到 24 位真彩色模型中的高位。
对 RGB 颜色使用 24 位颜色模型,例如 TYPE_INT_RGB 或 TYPE_INT_ARGB,并从 8 位值导出 24 位像素值:
int pixel24 =
((pixel & (128+64+32)) << (16+5-5)) |
((pixel & (16+8+4)) << (8+5-2)) |
((pixel & (2+1)) << 6);
换句话说:
int pixel24 =
((pixel & 224) << 16) | ((pixel & 28) << 11) | ((pixel & 3) << 6);
或者
int pixel24 =
((pixel & 0xE0) << 16) | ((pixel & 0x1C) << 11) | ((pixel & 0x03) << 6);
我正在尝试从旧 PC 游戏中提取一些精灵。我已经找到精灵并将它们以灰度形式撕成单独的文件。现在我想弄清楚如何给它们上色。可执行文件或其数据文件中似乎没有任何调色板数据 - 加上游戏所需的颜色深度(256 色)让我相信每个字节实际上是一个 8 位真彩色值。
假设我有一个(在本例中缩短的)数组,如下所示:
12 11 12 11
0A 13 12 11
13 12 11 0A
12 11 13 13
一些类似于我用来编写图像的示例代码如下所示:
DataInputStream dis = new DataInputStream(new FileInputStream("GAME.EXE"));
dis.skipBytes(bytesToImage);
BufferedImage bufferedImage = new BufferedImage(columns, rows, BufferedImage.TYPE_BYTE_INDEXED);
for (int i = 0; i < rows; i++) {
for (int j = 0; j < columns; j++) {
byte pixel = dis.readByte();
System.out.print(toHexString(pixel));
//For now, greyscale everything.
int value = pixel << 16 | pixel << 8 | pixel;
bufferedImage.setRGB(j, i, value);
}
System.out.print(System.getProperty("line.separator"));
}
ImageIO.write(bufferedImage, "PNG", new File("test.png"));
我已经弄乱了传递给构造函数的 imageType 和手动传递的 ColorModel,但似乎都没有做任何有用的事情。在像素上执行二进制 AND 和一些位移主要只是将图像设置为深红色。
在这种情况下,我该如何将每个像素设置为正确的真彩色值?
8位真彩色表示第7位到第5位包含红色,第4位到第2位包含绿色,第1位和第0位包含蓝色。 (即。RRRGGGBB
)您需要将这些转移到 24 位真彩色模型中的高位。
对 RGB 颜色使用 24 位颜色模型,例如 TYPE_INT_RGB 或 TYPE_INT_ARGB,并从 8 位值导出 24 位像素值:
int pixel24 =
((pixel & (128+64+32)) << (16+5-5)) |
((pixel & (16+8+4)) << (8+5-2)) |
((pixel & (2+1)) << 6);
换句话说:
int pixel24 =
((pixel & 224) << 16) | ((pixel & 28) << 11) | ((pixel & 3) << 6);
或者
int pixel24 =
((pixel & 0xE0) << 16) | ((pixel & 0x1C) << 11) | ((pixel & 0x03) << 6);