python查找模糊图片_如何从python中的模糊图像中找到变形矩形的准确角位置?

I am looking for a procedure to detect the corners of an distorted rectangle accurately with OpenCV in Python.

I've tried the solution of different suggestions by googling, but through a sinusoidal superposition of a straight line (see the thresholded image) I probably can't detect the corners. I tried findContours and HoughLines so far without good results.

Unfortunately I don't understand the C-Code from Xu Bin in how to find blur corner position with opencv?

This is my initial image:

After resizing and thresholding I apply canny edge detection to get following image:

contours, hierarchy = cv2.findContours(g_mask, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)

box = cv2.minAreaRect(contour)

box = cv2.cv.BoxPoints(box) if imutils.is_cv2() else cv2.boxPoints(box)

box = np.array(box, dtype="float")

box = perspective.order_points(box)

I only get the following result with some extra drawing:

I thought line fitting would be a good way to solve the problem, but unfortunately I couldn't get HoughLines working and after looking in OpenCV Python - How to implement RANSAC to detect straight lines? RANSAC seems also difficult to apply for my problem.

Any help is highly appreciated.

解决方案

To detect corners, you can use cv2.goodFeaturesToTrack(). The function takes four parameters

corners = cv2.goodFeaturesToTrack(image, maxCorners, qualityLevel, minDistance)

image - Input 8-bit or floating-point 32-bit grayscale single-channel image

maxCorners - Maximum number of corners to return

qualityLevel - Minimum accepted quality level of corners between 0-1. All corners below quality level are rejected

minDistance - Minimum possible Euclidean distance between corners

Now that we know how to find corners, we have to find the rotated rectangle and apply the function. Here's an approach:

We first enlarge the image, convert to grayscale, apply a bilateral filter, then Otsu's threshold to get a binary image

Next we find the distorted rectangle by finding contours with cv2.findContours() then obtain the rotated bounding box highlighted in green. We draw this bounding box onto a mask

Now that we have the mask, we simply use cv2.goodFeaturesToTrack() to find the corners on the mask

Here's the result on the original input image and the (x, y) coordinates for each corner

Corner points

(377.0, 375.0)

(81.0, 344.0)

(400.0, 158.0)

(104.0, 127.0)

Code

import cv2

import numpy as np

import imutils

# Resize image, blur, and Otsu's threshold

image = cv2.imread('1.png')

resize = imutils.resize(image, width=500)

mask = np.zeros(resize.shape, dtype=np.uint8)

gray = cv2.cvtColor(resize, cv2.COLOR_BGR2GRAY)

blur = cv2.bilateralFilter(gray,9,75,75)

thresh = cv2.threshold(blur, 0, 255, cv2.THRESH_BINARY + cv2.THRESH_OTSU)[1]

# Find distorted rectangle contour and draw onto a mask

cnts = cv2.findContours(thresh, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)

cnts = cnts[0] if len(cnts) == 2 else cnts[1]

rect = cv2.minAreaRect(cnts[0])

box = cv2.boxPoints(rect)

box = np.int0(box)

cv2.drawContours(resize,[box],0,(36,255,12),2)

cv2.fillPoly(mask, [box], (255,255,255))

# Find corners on the mask

mask = cv2.cvtColor(mask, cv2.COLOR_BGR2GRAY)

corners = cv2.goodFeaturesToTrack(mask, maxCorners=4, qualityLevel=0.5, minDistance=150)

for corner in corners:

x,y = corner.ravel()

cv2.circle(resize,(x,y),8,(155,20,255),-1)

print("({}, {})".format(x,y))

cv2.imshow('resize', resize)

cv2.imshow('thresh', thresh)

cv2.imshow('mask', mask)

cv2.waitKey()

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值