OpenCV: calculating distance from contour points to an pygame object fails

Viewed 772

I am receiving real-time contours of moving objects with the help of a camera and OpenCV. It runs in a pygame window:

           # Find contours on thresholded image
           nada, contours, nada = cv2.findContours(frame5.copy(), cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)

When i loop through all these contour points, i can visualize them by drawing small white circles for each contour point like this:

           for i in contours:
              for j in range(len(i)):
                 coordinates = i[j][0]
                 pygame.draw.circle(screen, WHITE, coordinates, 1, 0)

enter image description here

The small white circles are the contour points. Their coordinates are visualized correctly (i have checked manually).

The big green circle has a fixed position at (960, 540).

Now I want to find the closest white contour point to the big green circle and display it as a big blue circle.

For this i am calculating each contour points' distance to the green circle and the one with the smallest distance is displayed as a big blue circle. However, as you can see in the picture the blue circle is far away from the green circle.

What am i doing wrong? The distance function is working, i have tested it manually by calculating only 1 points' distance to the green circle.

Here is the relevant code snippet:

     ...

     while True:

        ...

        screen.fill(BLACK)

        # Find contours on thresholded image
        nada, contours, nada = cv2.findContours(frame5.copy(), cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)

        if len(contours) != 0:
            distanceList = []

            for i in contours:
                for j in range(len(i)):
                    coordinates = i[j][0]

                    # rigidbody.x and .y represents green circle's coordinates
                    distanceList.append(math.sqrt((rigidbody.x - coordinates[0]) ** 2 + (rigidbody.y - coordinates[1]) ** 2))
                    minDistance = distanceList[0]

                    # Find smallest distance of all contour points
                    if distanceList[j] < minDistance:
                        minCoordinates = coordinates

            for i in contours:
                for j in range(len(i)):
                    coordinates = i[j][0]
                    pygame.draw.circle(screen, WHITE, coordinates, 1, 0) # Render white contour points
                    pygame.draw.circle(screen, BLUE, minCoordinates, 50, 0)  # Render closest contour point to game object

EDIT

I realized that the minimizer for distance is not minimizing:

                # Find smallest distance of all contour points
                if distanceList[j] < minDistance:
                    print(frame)
                    print(distanceList[j])
                    minCoordinates = coordinates

So for frame number 106 the values are increasing and decreasing. But it should only decrease.

Frame: 106
Distance:365.6364314452268

Frame: 106
Distance: 357.816992329878

Frame: 106
Distance: 359.133679846377
1 Answers

You do not have to keep track of all distances to find the min distance, you can do so with only the current/last distance.

Initialize minDistance with float('inf') outside the loops.

Then use this condition:

if distanceList[-1] < minDistance:
   minDistance = distanceList[-1]
   minCoordinates = coordinates
Related