Python/OpenCV - Detect lines in a tennis court usi

2020-06-23 06:09发布

问题:

I'm trying to detect lines in a tennis court using openCV and hough transform. I would like to find horizontal and vertical lines in order to find intersection and finally detect the corner of the tennis court.

Here the original image.

But i have some problems.

1)I tried to use HoughLineP . Here the code :

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

edges = cv2.Canny(gray,100,200,apertureSize = 3)
lines = cv2.HoughLinesP(edges, 1, np.pi/2, 6, None, 50, 10);
for line in lines[0]:
    pt1 = (line[0],line[1])
    pt2 = (line[2],line[3])
    cv2.line(img, pt1, pt2, (0,0,255), 2)
cv2.imshow('dst',img)

return res

Here the result : Result of houghLineP

2)I tried to use HoughLines Here the code

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

edges = cv2.Canny(gray,100,200,apertureSize = 3)


#Lignes
lines = cv2.HoughLines(edges,1,np.pi/70,110)
for rho,theta in lines[0]:
    if (np.pi/70 <= theta <= np.pi/7) or (2.056 < theta < 4.970) or (1.570 <= theta <= 1.600): #(2,6 <=theta <= 26) or (theta >118 and theta <= 285)

        a = np.cos(theta)
        b = np.sin(theta)
        x0 = a*rho
        y0 = b*rho
        x1 = int(x0 + 1000*(-b))
        y1 = int(y0 + 1000*(a))

        x2 = int(x0 - 1000*(-b))
        y2 = int(y0 - 1000*(a))

        cv2.line(res,(x1,y1),(x2,y2),(0,0,255),1)

Here the result : Result of houghLine

In the first case, i have only little lines, and i thought about prolong them but i didn't find...I tried using fitLine but it only works with find contours (findContours method is awful in this picture)

In the second case, it works well but i have lots of lines, almost the same and on the bottom right, i don't have any intersection in order to detect the corner...

Maybe i'm on the wrong way...

Do you have some ideas or something that could be works ? At the end, i would like only interest points concerning only the tennis court.

ps : I did a method which calculate the intersection between the horizontal lines and the vertical lines.

Many thanks,

回答1:

Looks line the HougLines output contains the lines you want. You only need to filter out the outliers.

For this, you could use a model of your tennis field. What you know about it is that you have :

  • The outer limits of the field, represented by a big rectangle
  • The two corridors, represented by two lines that cut the rectangle on the sides
  • The service squares, represented again each by two lines, one parallel to the service line and one parallel to the sides

You could try for instance to take profit from the model you have to filter out the outliers. Some approaches, like RANSAC, are made for this. The basic idea is to take random points, compute the model and check within the data if that fits. After some iterations, the best fit is most probably the model you look for. This is a quite known approach (first published by Fischler in 1986) so you can find lots of documentation on it. Let's take a simple example algorithm that could work for you (probably with adaptations):

  1. Take 4 random points within the lines intersections. Compute the perspective projection P that maps those points to a top view of the field. You can use OpenCV's getPerspectiveTransform for this. You now have your model of the field, in the top view.

  2. Since you have a model of the field (based on the rules of tennis), you are able to say where the other intersections of lines (service lines with corridor lines, service squares ..) should be on the top view. If you apply the inverse of the perspective transform P^{-1} for these points, you have them in the image space.

  3. Check for consensus : look for closest intersections of lines in the image space to the ones of your model. Here you should have a metric : number of intersections of lines at a distance less than x pixels, or SSD. You will use this metric to rate different models.

  4. Rate your model : if the metric that you defined is less than the best previously found, this is now your current best model

  5. Iterate. The number of iterations that you do directly relates to the probability of selecting a good model in the end. Look in seminal work of Fischler and Bolls for ow to set the number of iterations.

Here it is, in the end of the iterations you will have found the model that best fits your data, ie inliers that describe a tennis field and outliers that don't. Note that this method is robust to a large number of outliers (more than 50 percent), but the chance of having a good result is only statistical (you can set the expected quality of your result by tuning the number of iterations, though).

Hope this helps,

Ben