NOTE: Since you linked a tutorial for OpenCV 2.4.x, I initially assumed you also wrote your code with OpenCV 2.4.11. As it turns out, you're actually using OpenCV 3.x. Keep in mind that there are subtle changes in the API between 2.x and 3.x.
You call HoughLinesP
incorrectly.
According to the documentation, the signature of the Python function is:
cv2.HoughLinesP(image, rho, theta, threshold[, lines[, minLineLength[, maxLineGap]]]) → lines
If we label the parameters in your call, we get the following:
lines = cv2.HoughLinesP(cannied, rho=1, theta=np.pi / 180
, threshold=80, lines=30, minLineLength=10)
However, the C++ code correctly ported to Python would be
lines = cv2.HoughLinesP(cannied, rho=1, theta=np.pi / 180
, threshold=80, minLineLength=30, maxLineGap=10)

Similar situation with Canny
cv2.Canny(image, threshold1, threshold2[, edges[, apertureSize[, L2gradient]]]) → edges
Again, let's label the parameters:
cannied = cv2.Canny(img, threshold1=50, threshold2=200, edges=3)
But it should be:
cannied = cv2.Canny(img, threshold1=50, threshold2=200, apertureSize=3)
However this makes no difference in the output, since the default value for apertureSize is 3.
Finally, as we identified with Vasanth and namatoj, there is a difference in the format of the output generated by cv2.HoughLinesP
:
- In 2.4 it looks like
[[[x1, y1, x2, y2], [...], ..., [...]]]
- In 3.x it looks like
[[[x1, y1, x2, y2]], [[...]], ..., [[...]]]
I added a short get_lines
function to transform the lines into consistent layout ([[x1, y1, x2, y2], [...], ..., [...]]
) in both versions.
Full script that works in both OpenCV versions:
import cv2
import numpy as np
def get_lines(lines_in):
if cv2.__version__ < '3.0':
return lines_in[0]
return [l[0] for l in lines]
img = cv2.imread('building.jpg')
img_gray = gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
cannied = cv2.Canny(img_gray, threshold1=50, threshold2=200, apertureSize=3)
lines = cv2.HoughLinesP(cannied, rho=1, theta=np.pi / 180, threshold=80, minLineLength=30, maxLineGap=10)
for line in get_lines(lines):
leftx, boty, rightx, topy = line
cv2.line(img, (leftx, boty), (rightx,topy), (255, 255, 0), 2)
cv2.imwrite('lines.png',img)
cv2.imwrite('canniedHouse.png',cannied)
cv2.waitKey(0)
cv2.destroyAllWindows()