从文件中检测空像素
Detect Empty Pixel From File
要查看完整的项目,请在此处查看回购协议。随意克隆和 运行。注意测试图像
https://github.com/AshGale/Image2RGBA
当在 GIMP 中读取部分显示为空(散列)的 PNG 时,读入程序的值为 [0,0,0,255](红色、绿色、蓝色、Alpha)。我希望空位具有 Alpha 0,因此完全为空 [0,0,0,0]。但是值为 [0,0,0,255] 也是全黑。
问题,如果像素完全为空,即在 gimp 中散列,我如何检查 java。
然后我如何将其写入带有 bufferedImage 的图像文件。
如图所示,对于空的图像,alpha值是否应该为0?请建议读取文件或文件格式的方法。
//代码摘录完整代码见Git
...
for (int i = 0; i < imageHeight; i++) {
for (int j = 0; j < imageWidth; j++) {
individualPixel = new Color(buffImage.getRGB(j, i));
//TODO find a way to detect a empty pixel an keep perfect black
if(individualPixel.getRed() == 0
&& individualPixel.getGreen() == 0
&& individualPixel.getBlue() ==0
) {
//set pixel at location to empty
buffRed.setRGB(j, i, getIntFromColor(0, 0, 0, 0));
buffGreen.setRGB(j, i, getIntFromColor(0, 0, 0, 0));
buffBlue.setRGB(j, i, getIntFromColor(0, 0, 0, 0));
}else {
// RED
tempPixel = new Color(individualPixel.getRed(), 0, 0, individualPixel.getAlpha());
buffRed.setRGB(j, i, getIntFromColor(tempPixel.getRed(), 0, 0, tempPixel.getAlpha()));
// GREEN
// BLUE
}
...
ImageIO.write(buffRed, "png", redImg);
这是工作示例,您也可以在我的 github 问题中查看完整内容。
感谢 Thomas 拒绝使用 getAlphaRaster()
// get RGB from image
BufferedImage buffImage = new BufferedImage(image.getWidth(), image.getHeight(), BufferedImage.TYPE_INT_ARGB);
try {
buffImage = ImageIO.read(imageFile);
} catch (IOException e) {
}
int imageHeight = buffImage.getHeight();
int imageWidth = buffImage.getWidth();
Color individualPixel = null;
Color tempPixel = null;
BufferedImage buffRed = new BufferedImage(imageWidth, imageHeight, BufferedImage.TYPE_INT_ARGB);
BufferedImage buffGreen = new BufferedImage(imageWidth, imageHeight, BufferedImage.TYPE_INT_ARGB);
BufferedImage buffBlue = new BufferedImage(imageWidth, imageHeight, BufferedImage.TYPE_INT_ARGB);
WritableRaster imageRaster = buffImage.getAlphaRaster();
int[] pixel = new int[4];
int alpha = 0;
for (int i = 0; i < imageHeight; i++) {
for (int j = 0; j < imageWidth; j++) {
individualPixel = new Color(buffImage.getRGB(j, i));
imageRaster.getPixel(j, i, pixel);
alpha = pixel[0];//return 0 for empty
//if(individualPixel.getAlpha() <255 || alpha >0)
System.out.println(j + "," + i + " : " + individualPixel.getAlpha()+ "-"+alpha+ " =>" +
pixel[0] + " " + pixel[1] + " " + pixel[2] + " " + pixel[3]);
//TODO find a way to detect a empty pixel an keep perfect black
if(individualPixel.getRed() == 0
&& individualPixel.getGreen() == 0
&& individualPixel.getBlue() ==0
& alpha == 0) {
//set pixel at location to empty
buffRed.setRGB(j, i, getIntFromColor(0, 0, 0, 0));
buffGreen.setRGB(j, i, getIntFromColor(0, 0, 0, 0));
buffBlue.setRGB(j, i, getIntFromColor(0, 0, 0, 0));
}else {
// RED
tempPixel = new Color(individualPixel.getRed(), 0, 0, individualPixel.getAlpha());
buffRed.setRGB(j, i, getIntFromColor(tempPixel.getRed(), 0, 0, tempPixel.getAlpha()));
// GREEN
tempPixel = new Color(0, individualPixel.getGreen(), 0, individualPixel.getAlpha());
buffGreen.setRGB(j, i, getIntFromColor(0, tempPixel.getGreen(), 0, tempPixel.getAlpha()));
// BLUE
tempPixel = new Color(0, 0, individualPixel.getBlue(), individualPixel.getAlpha());
buffBlue.setRGB(j, i, getIntFromColor(0, 0, tempPixel.getBlue(), tempPixel.getAlpha()));
}
}
System.out.println("");
}
// Save Images to path of selected file
try {
ImageIO.write(buffRed, "png", redImg);
ImageIO.write(buffGreen, "png", greenImg);
ImageIO.write(buffBlue, "png", blueImg);
} catch (IOException e) {
JOptionPane.showMessageDialog(null, "Failed to create RGB files");
e.printStackTrace();
}
我相信您的原始代码中的问题就是这一行:
individualPixel = new Color(buffImage.getRGB(j, i));
此 Color
构造函数有效地丢弃了 alpha 分量。 JavaDoc 说(强调我的):
Creates an opaque sRGB color with the specified combined RGB value [...] Alpha is defaulted to 255.
应该是:
individualPixel = new Color(buffImage.getRGB(j, i), true); // hasAlpha = true
这个构造函数 JavaDoc 说:
Creates an sRGB color with the specified combined RGBA value [...] If the hasalpha
argument is false
, alpha is defaulted to 255.
您真的不必使用 alpha 栅格(并非所有 BufferedImage
都有)来实现这一点,避免它既简单又兼容。
最后,完全透明像素的 R、G 和 B 值并不重要。所以测试它是否全黑可能是一个过于严格的检查(尽管它似乎对你的输入图像工作正常)。
PS:我认为更精确的术语是 "transparent",而不是 "empty"。
要查看完整的项目,请在此处查看回购协议。随意克隆和 运行。注意测试图像 https://github.com/AshGale/Image2RGBA
当在 GIMP 中读取部分显示为空(散列)的 PNG 时,读入程序的值为 [0,0,0,255](红色、绿色、蓝色、Alpha)。我希望空位具有 Alpha 0,因此完全为空 [0,0,0,0]。但是值为 [0,0,0,255] 也是全黑。
问题,如果像素完全为空,即在 gimp 中散列,我如何检查 java。
然后我如何将其写入带有 bufferedImage 的图像文件。
如图所示,对于空的图像,alpha值是否应该为0?请建议读取文件或文件格式的方法。
//代码摘录完整代码见Git
...
for (int i = 0; i < imageHeight; i++) {
for (int j = 0; j < imageWidth; j++) {
individualPixel = new Color(buffImage.getRGB(j, i));
//TODO find a way to detect a empty pixel an keep perfect black
if(individualPixel.getRed() == 0
&& individualPixel.getGreen() == 0
&& individualPixel.getBlue() ==0
) {
//set pixel at location to empty
buffRed.setRGB(j, i, getIntFromColor(0, 0, 0, 0));
buffGreen.setRGB(j, i, getIntFromColor(0, 0, 0, 0));
buffBlue.setRGB(j, i, getIntFromColor(0, 0, 0, 0));
}else {
// RED
tempPixel = new Color(individualPixel.getRed(), 0, 0, individualPixel.getAlpha());
buffRed.setRGB(j, i, getIntFromColor(tempPixel.getRed(), 0, 0, tempPixel.getAlpha()));
// GREEN
// BLUE
}
...
ImageIO.write(buffRed, "png", redImg);
这是工作示例,您也可以在我的 github 问题中查看完整内容。 感谢 Thomas 拒绝使用 getAlphaRaster()
// get RGB from image
BufferedImage buffImage = new BufferedImage(image.getWidth(), image.getHeight(), BufferedImage.TYPE_INT_ARGB);
try {
buffImage = ImageIO.read(imageFile);
} catch (IOException e) {
}
int imageHeight = buffImage.getHeight();
int imageWidth = buffImage.getWidth();
Color individualPixel = null;
Color tempPixel = null;
BufferedImage buffRed = new BufferedImage(imageWidth, imageHeight, BufferedImage.TYPE_INT_ARGB);
BufferedImage buffGreen = new BufferedImage(imageWidth, imageHeight, BufferedImage.TYPE_INT_ARGB);
BufferedImage buffBlue = new BufferedImage(imageWidth, imageHeight, BufferedImage.TYPE_INT_ARGB);
WritableRaster imageRaster = buffImage.getAlphaRaster();
int[] pixel = new int[4];
int alpha = 0;
for (int i = 0; i < imageHeight; i++) {
for (int j = 0; j < imageWidth; j++) {
individualPixel = new Color(buffImage.getRGB(j, i));
imageRaster.getPixel(j, i, pixel);
alpha = pixel[0];//return 0 for empty
//if(individualPixel.getAlpha() <255 || alpha >0)
System.out.println(j + "," + i + " : " + individualPixel.getAlpha()+ "-"+alpha+ " =>" +
pixel[0] + " " + pixel[1] + " " + pixel[2] + " " + pixel[3]);
//TODO find a way to detect a empty pixel an keep perfect black
if(individualPixel.getRed() == 0
&& individualPixel.getGreen() == 0
&& individualPixel.getBlue() ==0
& alpha == 0) {
//set pixel at location to empty
buffRed.setRGB(j, i, getIntFromColor(0, 0, 0, 0));
buffGreen.setRGB(j, i, getIntFromColor(0, 0, 0, 0));
buffBlue.setRGB(j, i, getIntFromColor(0, 0, 0, 0));
}else {
// RED
tempPixel = new Color(individualPixel.getRed(), 0, 0, individualPixel.getAlpha());
buffRed.setRGB(j, i, getIntFromColor(tempPixel.getRed(), 0, 0, tempPixel.getAlpha()));
// GREEN
tempPixel = new Color(0, individualPixel.getGreen(), 0, individualPixel.getAlpha());
buffGreen.setRGB(j, i, getIntFromColor(0, tempPixel.getGreen(), 0, tempPixel.getAlpha()));
// BLUE
tempPixel = new Color(0, 0, individualPixel.getBlue(), individualPixel.getAlpha());
buffBlue.setRGB(j, i, getIntFromColor(0, 0, tempPixel.getBlue(), tempPixel.getAlpha()));
}
}
System.out.println("");
}
// Save Images to path of selected file
try {
ImageIO.write(buffRed, "png", redImg);
ImageIO.write(buffGreen, "png", greenImg);
ImageIO.write(buffBlue, "png", blueImg);
} catch (IOException e) {
JOptionPane.showMessageDialog(null, "Failed to create RGB files");
e.printStackTrace();
}
我相信您的原始代码中的问题就是这一行:
individualPixel = new Color(buffImage.getRGB(j, i));
此 Color
构造函数有效地丢弃了 alpha 分量。 JavaDoc 说(强调我的):
Creates an opaque sRGB color with the specified combined RGB value [...] Alpha is defaulted to 255.
应该是:
individualPixel = new Color(buffImage.getRGB(j, i), true); // hasAlpha = true
这个构造函数 JavaDoc 说:
Creates an sRGB color with the specified combined RGBA value [...] If the
hasalpha
argument isfalse
, alpha is defaulted to 255.
您真的不必使用 alpha 栅格(并非所有 BufferedImage
都有)来实现这一点,避免它既简单又兼容。
最后,完全透明像素的 R、G 和 B 值并不重要。所以测试它是否全黑可能是一个过于严格的检查(尽管它似乎对你的输入图像工作正常)。
PS:我认为更精确的术语是 "transparent",而不是 "empty"。