基于Java BufferedImage实现识别图片中的黑色矩形
前言:在项目中需要实现将图片中的黑色矩形替换为其他图形,其中的难点在于图片中存在其他黑点或者黑色小方块。
实现思路:
二值化,将纯黑的区域保留下来,其他区域编程白色。
去噪:去除噪点
转为矩阵,将黑色像素点的位置的值设为1,其他位置的值设为0
求极大全为1的子矩阵,使用悬吊法求极大全为1的子矩阵
二值化代码:
public static void binaryImage(String filePath,double threshold){
try {
BufferedImage image = ImageIO.read(new File(filePath));
int minX = 0;//图片起始点X
int minY = 0;//图片起始点Y
int width = image.getWidth();//图片的宽度
m = width;
int height = image.getHeight();//图片的高度
n = height;
//将黑色区域化为1,其他为0
for (int i = minX; i < width; i++) {
for (int j = minY; j < height; j++) {
Object data = image.getRaster().getDataElements(i, j, null);//获取该点像素,并以object类型表示
int red = image.getColorModel().getRed(data);
int blue = image.getColorModel().getBlue(data);
int green = image.getColorModel().getGreen(data);
if(red==0&&green==0&&blue==0){
a[i+1 ][j+1 ] = 1;
}
}
}
}catch (IOException e) {
e.printStackTrace();
}
}
去噪:
public static void removeNoise(int whiteThreshold,int blackThreshold){
int i,j,nValue,nCount,m,n;
int nWidth=Calculate.maxn;
int nHeight=Calculate.maxn;
//对图像上下边缘去噪
for(i=0;i
a[i][0]=0;
a[i][nHeight-1]=0;
}
//对图像上下边缘去噪
for( i=0;i
a[0][i]=0;
a[0][nWidth-1]=0;
}
//根据周围点的颜色去噪
//遍历所有的点 //j是y, i是x
for(i=1;i
for( j=1;j
nValue=a[i][j];
if(nValue==1&&whiteThreshold!=0){//如果一点是黑点
nCount=0;
//遍历他周围的八个点,如果他
for(m=j-1;m<=j+1;m++){
for(n=i-1;n<=i+1;n++){
if(a[n][m]==0){//周围白点的个数
nCount++;
}
}
}
if(nCount>=whiteThreshold){//周围白点的个数大于阈值则变为白色
a[i][j]=0;
}
}else{//如果一个点是白色的点,周围的点是黑色
nCount=0;
for(m=j-1;m<=j+1;m++){
for(n=i-1;n<=i+1;n++){
if(a[n][m]==1){
<