cv2.findContours doesn't find contours - python

i need to find contours of brown regions. but befıre that, i tried to draw all contours. but i can't see any contour on
i tried this:
contours, hierarchy = cv2.findContours(thresh_dummy, cv2.RETR_LIST, cv2.CHAIN_APPROX_SIMPLE)
cv2.drawContours(thresh_dummy, contours, -1, (0, 255, 0), 3)

I think the reason why you are not seeing contours in the output image is because you are drawing contours with (0, 255, 0), which would not be visible on a grayscale image (thresh_dummy happens to be a grayscale image). What you could do is convert thresh_dummy to RGB before drawing the contours or you could just use a random color like (128, 255, 128) which would be visible on the specific example you have.
contours, hierarchy = cv2.findContours(thresh_dummy, cv2.RETR_LIST, cv2.CHAIN_APPROX_SIMPLE)
thresh_color = cv2.cvtColor(thresh_dummy, cv2.COLOR_GRAY2RGB)
cv2.drawContours(thresh_color, contours, -1, (0, 255, 0), 3)
cv2.imwrite("thresh_color.jpg", thresh_color)

Related

Getting more than expected contours in image

I have a image consisting N almost 90 times but I am getting 105 contours using below code:
gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
#cv2.imshow("Image", gray)
#cv2.waitKey(0)
blurred = cv2.GaussianBlur(gray, (5, 5), 0) #blur to reduce noise
#cv2.imshow("Image", blurred)
#cv2.waitKey(0)
# perform edge detection, find contours in the edge map, and sort the
# resulting contours from left-to-right
edged = cv2.Canny(blurred, 30, 150) #30, 150
#cv2.imwrite("test.png", edged)
#cv2.imshow("Image", edged)
#cv2.waitKey(0)
#find contours of characters(objects) in images
cnts = cv2.findContours(edged.copy(), cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
cnts = imutils.grab_contours(cnts)
if cnts:
cnts = sort_contours(cnts, method="left-to-right")[0]
cv2.drawContours(image, cnts, -1, (0, 0, 255), 2)
cv2.imwrite("all_contours.jpg", image)
I have tried different combinations in Canny and findContours function but cant get the contours equal to the number of N in image.
My image:
image with contours:
Looking at the contours image, I cant see where is the problem.
Any help or hint will be appreciated.
P.S : this image is an ideal image for testing. In real scenario, image will be taken from webcam.
Try without Bluring image.
import cv2
image = cv2.imread("n.png")
image = cv2.resize(image, (800, 800))
gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
_, threshold = cv2.threshold(gray, 100, 255, cv2.THRESH_BINARY_INV)
contours, hierarchy = cv2.findContours(threshold, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_NONE)
cv2.putText(image, "contours found in image : " + str(len(contours)), (20, 20), cv2.FONT_HERSHEY_PLAIN, 1, (255, 0, 0),1)
cv2.drawContours(image, contours, -1, (0, 0, 255), -1)
cv2.imshow("contour_image", image)
cv2.waitKey(0)
cv2.destroyAllWindows()

Python find contours and draw contours function error

I am currently working on a project detecting defects on an image.
The contours are not connected...I don't know why they're discrete point
Here is my code:
ret, thresh1 = cv2.threshold(img, 95, 255, cv2.THRESH_BINARY)
cnts= cv2.findContours(thresh1,cv2.RETR_LIST, cv2.CHAIN_APPROX_NONE)[-2]
cv2.drawContours(img, cnts, -1, (255,255,0), 3)
Also the len(cnts) function isn't return the right number of white point...
It is possible that find contours is picking holes as well. Try this one out and see if it fixes your problem.
ret, thresh1 = cv2.threshold(img, 95, 255, cv2.THRESH_BINARY)
cnts= cv2.findContours(thresh1,cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_NONE)[-2]
cv2.drawContours(img, cnts, -1, (255,255,0), 3)

How can I draw two contours on an image given a contour distance of 100 pixels between them using python and opencv

What I have tried is drawing the external contour using the following lines
cnts, hierarchy = cv2.findContours(edged.copy(), cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
cv2.drawContours(orig, cnts, -1, (0, 255, 0), 3) # this draws the external contour
Referring the below
[![enter image description here][1]][1]
How can I arrive at the answer below?
[![enter image description here][2]][2]
I don't know how it is solved in the links but you can use a blank mask on which you can draw your contour and then use cv2.dilate to expand it using a kernel size of the number of pixels you require between them. Once that is done find contours on the mask and draw the second one onto your original image.
import cv2
import numpy as np
img = cv2.imread('contour.jpg')
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
_, thresh = cv2.threshold(gray, 240, 255, cv2.THRESH_BINARY_INV + cv2.THRESH_OTSU)
cnts, hierarchy = cv2.findContours(thresh, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
cv2.drawContours(img, cnts, -1, (0, 255, 0), 3)
mask = np.zeros(img.shape[:2], dtype=np.uint8)
cv2.drawContours(mask, cnts, -1, 255, 1)
kernel = np.ones((100, 100), np.uint8)
mask = cv2.dilate(mask, kernel, iterations = 1)
cnts, hierarchy = cv2.findContours(mask, cv2.RETR_TREE, cv2.CHAIN_APPROX_SIMPLE)
cv2.drawContours(img, cnts, 1, (255, 0, 0), 3)
cv2.imshow("img", img)
cv2.waitKey(0)
cv2.destroyAllWindows()

Segmenting two contours into two different images of same size using openCV-python

I have two contours in the first image. I need to segment out individual contours and make two images out of it like this: image1 and image2. The individual output image has to be of the same dimension as the input image. How can this be achieved using openCV-python ? My code for drawing contours:
image, contours, hier = cv2.findContours(im, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
for c in contours:
rect = cv2.minAreaRect(c)
box = cv2.boxPoints(rect)
# convert all coordinates floating point values to int
box = np.int0(box)
# draw a red 'nghien' rectangle
cv2.drawContours(im, [box], 0, (0, 0, 255))
cv2.drawContours(im, contours, -1, (255, 255, 0), 1)
You are using the cv2.drawContours in wrong way. Passing the -1 as contour index would draw all the contours and not the individual ones. To draw the individual contours you need to pass the corresponding index as:
_, cnt, hierarchy = cv2.findContours(canvas.copy(), cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_NONE)
for i in xrange(len(cnt)):
output_canvas = np.zeros(canvas.shape, dtype=np.uint8)
cv2.drawContours(output_canvas, cnt, i, np.array([255, 255, 255, 255]), -1)
cv2.imwrite("./contour{}.png".format(i), output_canvas)

How to draw contours using opencv in Python?

I have following image preprocessed:
Now I want to use findContours method in order to find cells from image and then use drawContours in order draw contour for every cell from image. I do this but nothing is shown.
contours = cv2.findContours(img, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
cv2.drawContours(img, contours, -1, (0, 255, 0), 3)
I receive the following error.
contours is not a numpy array, neither a scalar
Another answers didn't helped me.
I also use following solution.
contours = cv2.findContours(img, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)[0]
ctr = numpy.array(contours).reshape((-1,1,2)).astype(numpy.int32)
cv2.drawContours(img, ctr, -1, (0, 255, 0), 3)
But this solution didn't draw anything on the given image.
Update, OpenCV 4.0 change the cv2.findContours. So I modify the code example. And a more general way:
cnts, hiers = cv2.findContours(...)[:-2]
cv2.findContours returns a tuple, not just the contours. You can do like this:
## Find contours
if cv2.__version__.startswith("3."):
_, contours, _ = cv2.findContours(bimg.copy(), cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
else:
contours, _ = cv2.findContours(bimg, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
## Draw contours
cv2.drawContours(img, contours, -1, (0, 255, 0), 3)
Related similar questions:
(1) Python Opencv drawContour error
(2) How to use `cv2.findContours` in different OpenCV versions?
The tuple returned by cv2.findContours has the form (im, contours, hierarchy) where im is the image with contours visualized, contours is a tuple of two numpy arrays in the form (x_values, y_values) and heirarchy depends on the retrieval mode. Since you are using CV_RETR_EXTERNAL, heirarchy doesn't have much significance.

Categories