Hi I'm quite new in OpenCV, I am currently trying to detect horizontal lines in an image using HoughLinesP function in opencv, in order to calculate the ratio between x and y. The line detection result is shown in the second picture.
Thank you in advance!
import cv2
import numpy as np
# read image
img = cv2.imread('testtube.png')
# convert to grayscale
gray = cv2.cvtColor(img,cv2.COLOR_BGR2GRAY)
# apply canny edge detection
edges = cv2.Canny(gray, 90, 100,apertureSize=3)
# get hough lines
result = img.copy()
lines = cv2.HoughLinesP(edges, rho=1,theta=np.pi/2, threshold=30,lines=np.array([]), minLineLength=30,maxLineGap=20)
a,b,c = lines.shape
for i in range(a):
cv2.line(result, (lines[i][0][0], lines[i][0][1]), (lines[i][0][2], lines[i][0][3]), (0, 0, 255), 2, cv2.LINE_AA)
cv2.imshow("edges", edges)
cv2.imshow("result", result)
cv2.waitKey(0)
cv2.destroyAllWindows()
Here is my approach.
1- Check vertically all pixels. Ignore white pixels. Vertically count black pixels(<15), count other non-white pixels. Keep these counts in a variable.
2- Do this for each vertical column which are not white at all. For each columnd counts keep in an array.
3- get the average of all non-black and black pixel counts inside the array. This will statistically give good results.
For the following applied code I get the x and y length as 273.906, 67.3725 respectively. Which are correct results if we check manually.
import cv2
import numpy as np
# Load the image in grayscale
img = cv2.imread('/home/cvlab/Downloads/xy.jpg', cv2.IMREAD_GRAYSCALE)
cv2.namedWindow('Image', cv2.WINDOW_NORMAL)
# Apply median blur
img = cv2.medianBlur(img, 5)
cv2.imshow('Image', img)
# Initialize lists to store counts
cntsUpper = []
cntsLower = []
# Loop through columns
for i in range(img.shape[1]):
cntUpper = 0
cntLower = 0
for j in range(img.shape[0]):
pixel_value = img[j, i]
if 15 < pixel_value < 250:
cntUpper += 1
elif pixel_value < 15:
cntLower += 1
if cntUpper != 0:
cntsUpper.append(cntUpper)
if cntLower != 0:
cntsLower.append(cntLower)
# Calculate the average for lower counts
if cntsLower:
averageLower = sum(cntsLower) / len(cntsLower)
print(f"Average Lower: {averageLower}")
# Calculate the average for upper counts
if cntsUpper:
averageUpper = sum(cntsUpper) / len(cntsUpper)
print(f"Average Upper: {averageUpper}")
cv2.waitKey(0)
cv2.destroyAllWindows()