my input :
my code :
# import the necessary packages
import numpy as np
import argparse
import imutils
import cv2
print("Your OpenCV version: {}".format(cv2.__version__))
print("Are you using OpenCV 2.X? {}".format(imutils.is_cv2()))
print("Are you using OpenCV 3.X? {}".format(imutils.is_cv3()))
print("Are you using OpenCV 4.X? {}".format(imutils.is_cv4()))
# load the image
image_orig = cv2.imread('box1.jpg')
height_orig, width_orig = image_orig.shape[:2]
# cv2.imshow('image_orig' , image_orig)
# cv2.waitKey(0)
cv2.imwrite('image_orig.png', image_orig)
# copy of original image
image_to_process = image_orig.copy()
image_gray = cv2.cvtColor(image_to_process, cv2.COLOR_BGR2GRAY)
image_gray = cv2.GaussianBlur(image_gray, (5, 5), 0)
# cv2.imshow('image_gray' , image_gray)
# cv2.waitKey(0)
cv2.imwrite('image_gray.png', image_gray)
# perform edge detection, then perform a dilation + erosion to close gaps in between object edges
image_edged = cv2.Canny(image_gray, 50, 100)
image_edged = cv2.dilate(image_edged, None, iterations=1)
image_edged = cv2.erode(image_edged, None, iterations=1)
# cv2.imshow('image_edged' , image_edged)
# cv2.waitKey(0)
cv2.imwrite('image_edged.png', image_edged)
# find contours in the edge map
cnts = cv2.findContours(image_edged, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_NONE)
cnts = cnts[1] if imutils.is_cv2() else cnts[0] #### #### using CV4
print(len(cnts))
# loop over the contours individually
# prints contours in red color thickness = 1
image_contours = image_to_process.copy()
for c in cnts:
cv2.drawContours(image_contours, c , -1 ,(0,0,255),1)
cv2.imshow('1', image_contours)
cv2.waitKey(0)
# prints contours in red color thickness = 10
image_contours = image_to_process.copy()
for c in cnts:
cv2.drawContours(image_contours, c , -1 ,(0,0,255),10)
cv2.imshow('10', image_contours)
cv2.waitKey(0)
# prints contours in red color thickness = cv2.FILLED
image_contours = image_to_process.copy()
for c in cnts:
cv2.drawContours(image_contours, c , -1 ,(0,0,255), cv2.FILLED)
cv2.imshow('filled', image_contours)
cv2.waitKey(0)
# prints contours in red color thickness = cv2.FILLED
image_contours = image_to_process.copy()
for c in cnts:
cv2.drawContours(image_contours, [c] , -1 ,(0,0,255), cv2.FILLED)
cv2.imshow('filled_[]', image_contours)
cv2.waitKey(0)
output:
Any particular reason:
cv2.drawContours(image_contours, [c] , -1 ,(0,0,255), cv2.FILLED)
works while
cv2.drawContours(image_contours, c , -1 ,(0,0,255), cv2.FILLED)
doesn't , and why
cv2.drawContours(image_contours, c , -1 ,(0,0,255), 10)
do work ?
Which one is the right way to code it ? Am I missing anything ?
cv.drawContours()
always expects a list of contours.
cv.findContours()
always returns a list of contours.
They mirror each other.
There is no findContour
and no drawContour
.
Always pass a list of contours, even if it's a list of one contour.
If you pass it just a contour, which is an array of points, it'll interpret that as a list of contours (of course), where each contour is a list of one point. So it'll draw the individual points of your single contour.
Try giving it a simplified contour, so that the points of it aren't so densely spaced. Or give it a decimated contour, something like contour[::10]
. You'll see that it draws those points.
im = cv.imread("19nHf6z3.jpg")
gray = cv.cvtColor(im, cv.COLOR_BGR2GRAY)
(_, binarized) = cv.threshold(gray, 0, 255, cv.THRESH_BINARY_INV | cv.THRESH_OTSU)
(contours, _) = cv.findContours(binarized, cv.RETR_EXTERNAL, cv.CHAIN_APPROX_NONE)
canvas = (im >> 1) # the original but dimmed
for contour in contours:
contour_decimated = contour[::10]
cv.drawContours(canvas, contour_decimated, -1, color=(0, 0, 255), thickness=5)
# expecting a list, it'll intepret each point as a contour
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With