为简化起见,我有一组用相机拍摄的照片。摄像机在丙烯酸球罩后面,并且该球罩上有划痕。图片中的划痕非常明显。
使用opencv,我试图检测并清除这些划痕。
我的第一种方法是将图片的子集相乘以创建遮罩,而不是应用修复遮罩。我在正确的轨道上吗?在乘以图像之前,我可以对图像进行处理吗?

image - 检测(并去除)一组照片中的划痕-LMLPHP
image - 检测(并去除)一组照片中的划痕-LMLPHP
image - 检测(并去除)一组照片中的划痕-LMLPHP
image - 检测(并去除)一组照片中的划痕-LMLPHP

编辑:
这是突出显示划痕image - 检测(并去除)一组照片中的划痕-LMLPHP的图像

最佳答案

经过几次测试,我提出了一种可靠的方法来消除一组图像上的重复刮痕和灰尘。首先,我拍摄了10到15张图片的子集,将其打开,然后应用sobel derivatives提取轮廓。

        private Image<Gray, byte> GetImageContours(String strImage)
        {
            Image<Gray, Byte> img = new Image<Gray, byte>(strImage);
            Image<Gray, float> gradx = img.Sobel(1, 0, 5);
            Image<Gray, Byte> gradxconv = gradx.ConvertScale<Byte>(1, 0);
            Image<Gray, float> grady = img.Sobel(0, 1, 5);
            Image<Gray, Byte> gradyconv = grady.ConvertScale<Byte>(1, 0);
            Image<Gray, Byte> imgContours = gradxconv.AddWeighted(gradyconv, 0.5, 0.5, 0);

            img.Dispose();
            gradx.Dispose();
            grady.Dispose();
            gradxconv.Dispose();
            gradyconv.Dispose();

            return imgContours;
        }

然后,我将图像转换回16位深度,然后将它们全部相乘。这应该只给我一张划痕的图像。
要创建划痕的遮罩,我会腐 eclipse 该图像一次,然后将其放大10倍。在那之后,我通过运行阈值为40的TresholdBinary将其转换为黑白。

最后一步是对所有带有防刮蒙版的图像使用Inpaint功能。
            Image<Gray, float> _img1 = img1.Convert<Gray, float>();
            Image<Gray, float> _img2 = img2.Convert<Gray, float>();
            Image<Gray, float> _img3 = img3.Convert<Gray, float>();
            Image<Gray, float> _img4 = img4.Convert<Gray, float>();
            Image<Gray, float> _img5 = img5.Convert<Gray, float>();
            Image<Gray, float> _img6 = img6.Convert<Gray, float>();
            Image<Gray, float> _img7 = img7.Convert<Gray, float>();
            Image<Gray, float> _img8 = img8.Convert<Gray, float>();
            Image<Gray, float> _img9 = img9.Convert<Gray, float>();
            Image<Gray, float> _img10 = img10.Convert<Gray, float>();
            Image<Gray, float> _img11 = img11.Convert<Gray, float>();
            Image<Gray, float> _img12 = img12.Convert<Gray, float>();
            Image<Gray, float> imgMask = _img1.Mul(_img2).Mul(_img3).Mul(_img4).Mul(_img5).Mul(_img6).Mul(_img7).Mul(_img8).Mul(_img9).Mul(_img10).Mul(_img11).Mul(_img12).Erode(1);
            Image<Gray, Byte> imgMask2 = imgMask.Convert<Gray, Byte>();
            Image<Gray, Byte> imgMask3 = imgMask2.Dilate(10).ThresholdBinary(new Gray(40), new Gray(255));

            //img is one of the original images to remove scratches on
            ImageViewer viewer3 = new ImageViewer(img.InPaint(imgMask3, 3), "image3");
            viewer3.Show();

以下是每个步骤拍摄的示例图像:

原始图像
image - 检测(并去除)一组照片中的划痕-LMLPHP

该图像的轮廓
image - 检测(并去除)一组照片中的划痕-LMLPHP

所有轮廓相乘
image - 检测(并去除)一组照片中的划痕-LMLPHP

面具腐 eclipse 并膨胀
image - 检测(并去除)一组照片中的划痕-LMLPHP

最终结果
image - 检测(并去除)一组照片中的划痕-LMLPHP

关于image - 检测(并去除)一组照片中的划痕,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/33418641/

10-08 20:38