如何在Python中检测边缘和裁剪图像

时间:2017-06-06 06:53:06

标签: python opencv image-processing pillow canny-operator

我是Python的图像处理新手,我正在尝试解决一个常见问题。我的图像上有一个人的签名。我想找到边缘并裁剪它以适合图像中的签名。

输入图像

enter image description here

预期产出

enter image description here

我尝试了Canny Edge Detection并使用PIL,CV2使用现有解决方案(文章和答案)列表裁剪图像,但似乎都没有。我正在寻找一个有效的解决方案。

我尝试了一些解决方案:

  1. https://www.quora.com/How-can-I-detect-an-object-from-static-image-and-crop-it-from-the-image-using-openCV

  2. Crop Image from all sides after edge detection

  3. How to crop biggest rectangle out of an image

  4. 还有更多......虽然看起来非常简单但没有工作。我使用任何现有的解决方案都遇到了错误或预期的输出。

1 个答案:

答案 0 :(得分:21)

您需要的是阈值处理。在OpenCV中,您可以使用cv2.threshold()完成此操作。

我开了一枪。我的方法如下:

  1. 转换为灰度
  2. 将图像限制为仅获取签名而不是其他任何内容
  3. 查找在阈值图像中显示的像素的位置
  4. 以原始灰度
  5. 在该区域周围裁剪
  6. 从裁剪中创建一个新的阈值图像,不严格显示
  7. 这是我的尝试,我认为它运作得很好。

    import cv2
    import numpy as np
    
    # load image
    img = cv2.imread('image.jpg') 
    rsz_img = cv2.resize(img, None, fx=0.25, fy=0.25) # resize since image is huge
    gray = cv2.cvtColor(rsz_img, cv2.COLOR_BGR2GRAY) # convert to grayscale
    
    # threshold to get just the signature
    retval, thresh_gray = cv2.threshold(gray, thresh=100, maxval=255, type=cv2.THRESH_BINARY)
    
    # find where the signature is and make a cropped region
    points = np.argwhere(thresh_gray==0) # find where the black pixels are
    points = np.fliplr(points) # store them in x,y coordinates instead of row,col indices
    x, y, w, h = cv2.boundingRect(points) # create a rectangle around those points
    x, y, w, h = x-10, y-10, w+20, h+20 # make the box a little bigger
    crop = gray[y:y+h, x:x+w] # create a cropped region of the gray image
    
    # get the thresholded crop
    retval, thresh_crop = cv2.threshold(crop, thresh=200, maxval=255, type=cv2.THRESH_BINARY)
    
    # display
    cv2.imshow("Cropped and thresholded image", thresh_crop) 
    cv2.waitKey(0)
    

    结果如下:Cropped signature with thresholding