I am working on some images to extract the two curves and find their intersection points. The images vary widely in their appearance as you can see in the attached images.
As for now, doing a sobel and then applying canny edge filter pops them out but not quite sure how to fit curves to them and find the two intersection points (which they will have for sure)
import cv2
import numpy as np
img = cv2.imread('image6.jpg')
grad_x = cv2.Sobel(img, cv2.CV_64F, 1, 0, 3)
grad_y = cv2.Sobel(img, cv2.CV_64F, 0, 1, 3)
grad = np.sqrt(grad_x**2 + grad_y**2)
grad_norm = (grad * 255 / grad.max()).astype(np.uint8)
grad_norm = cv2.blur(grad_norm,(3,3))
cv2.imshow('Blur', grad_norm)
cv2.waitKey(0)
# Canny Edge Detection
edges = cv2.Canny(image=grad_norm, threshold1=100, threshold2=200) # Canny Edge Detection
# Display Canny Edge Detection Image
cv2.imshow('Canny Edge Detection', edges)
cv2.waitKey(0)
The red points shown above are the ones that I am looking to get to at
Any suggestions?
thanks and Happy New Year to all
Then you can fit an ellipse as done in this answer.
you can divide the set of points into two halves (above the longest axis, under the longest axis), then you fit each of the two sets into a parabola, the algebraic solution of the two equations will be the intersection points.
here is an example with one of your images using basic thresholding and cropping, and ellipse fitting, the challenge in your case lies in better filtering noise to keep only the ellipse/curves.
#!/usr/bin/python3
import os
import numpy as np
import cv2
from skimage.measure import EllipseModel
from matplotlib.patches import Ellipse
import matplotlib.pyplot as plt
im_id = 1
im_path = f"eliipse_fitting/{im_id}.jpg"
original = cv2.imread(im_path, cv2.IMREAD_GRAYSCALE)
img = original.copy()
width, height = img.shape
## Cropping to remove large objects
img = img[width//3:2*width//3, height//3: 2*height//3]
## Thresholding
th = 50
img[img>=th] = 255
img[img<th] = 0
## TODO: Add Noise Filtering, and Large Objects Removal
nonzero_indices = np.transpose(np.nonzero(img))
points = [(index[1], index[0]) for index in nonzero_indices]
a_points = np.array(points)
x = a_points[:, 0]
y = a_points[:, 1]
ell = EllipseModel()
ell.estimate(a_points)
xc, yc, a, b, theta = ell.params
print("center = ", (xc, yc))
print("angle of rotation = ", theta)
print("axes = ", (a,b))
fig = plt.figure()
ax = fig.add_subplot(1, 1, 1)
plt.imshow(original, cmap='gray')
x0 = xc+height//3
y0 = yc+width//3
plt.scatter(x0, y0, color='green', s=10)
ell_patch = Ellipse((x0, y0), 2*a, 2*b, theta*180/np.pi, edgecolor='green', facecolor='none')
ax.add_patch(ell_patch)
plt.show()