generated from Hazel/python-project
feat: further tests
This commit is contained in:
parent
6101a8d5e4
commit
df4b949dd2
@ -209,40 +209,89 @@ def kernel_detection(blurred, mask, edge_threshold=30, profile_length=21):
|
|||||||
|
|
||||||
kernel = create_gaussian_kernel(sigma)
|
kernel = create_gaussian_kernel(sigma)
|
||||||
|
|
||||||
print(kernel)
|
# print(kernel)
|
||||||
|
|
||||||
return kernel / kernel.sum()
|
return kernel / kernel.sum()
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
def kernel_detection_box(blurred, mask, edge_threshold=30, profile_length=21):
|
||||||
|
def box_function(x, amp, center, width):
|
||||||
|
"""Simple box profile: flat region with sharp transitions."""
|
||||||
|
return amp * ((x >= (center - width / 2)) & (x <= (center + width / 2))).astype(float)
|
||||||
|
|
||||||
|
def fit_box(profile, x_vals):
|
||||||
|
# Initial guess: full amplitude, centered at 0, small width
|
||||||
|
p0 = [1.0, 0.0, 5.0]
|
||||||
|
bounds = ([0, -10, 1], [1.5, 10, len(x_vals)]) # reasonable bounds
|
||||||
|
popt, _ = curve_fit(box_function, x_vals, profile, p0=p0, bounds=bounds)
|
||||||
|
return popt # amp, center, width
|
||||||
|
|
||||||
|
def create_box_kernel(width):
|
||||||
|
"""Generate a normalized 2D box kernel."""
|
||||||
|
ksize = int(round(width))
|
||||||
|
if ksize < 1:
|
||||||
|
ksize = 1
|
||||||
|
if ksize % 2 == 0:
|
||||||
|
ksize += 1 # ensure odd size
|
||||||
|
kernel = np.ones((ksize, ksize), dtype=np.float32)
|
||||||
|
return kernel / kernel.sum()
|
||||||
|
|
||||||
|
|
||||||
|
edges, gradient_mag = color_edge_detection(blurred, threshold=edge_threshold)
|
||||||
|
edges = cv2.bitwise_and(edges, edges, mask=mask)
|
||||||
|
|
||||||
|
y_idxs, x_idxs = np.where(edges > 0)
|
||||||
|
if len(x_idxs) == 0:
|
||||||
|
raise RuntimeError("No edges found.")
|
||||||
|
idx = len(x_idxs) // 2
|
||||||
|
cx, cy = x_idxs[idx], y_idxs[idx]
|
||||||
|
|
||||||
|
gray = cv2.cvtColor(blurred, cv2.COLOR_BGR2GRAY)
|
||||||
|
profile, x_vals = extract_vertical_profile(gray, cx, cy, length=profile_length)
|
||||||
|
popt = fit_box(profile, x_vals)
|
||||||
|
amp, mu, width = popt
|
||||||
|
|
||||||
|
print(f"Estimated box width: {width:.2f} pixels")
|
||||||
|
|
||||||
|
kernel = create_box_kernel(width)
|
||||||
|
return kernel
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
def deconvolution(image_file, edge_threshold=30, profile_length=21):
|
def deconvolution(image_file, edge_threshold=30, profile_length=21):
|
||||||
blurred = cv2.imread(image_file)
|
image = cv2.imread(image_file)
|
||||||
mask = get_mask(image_file)
|
mask = get_mask(image_file)
|
||||||
|
image_rgb = cv2.cvtColor(image, cv2.COLOR_BGR2RGB).astype(np.float32) / 255.0
|
||||||
|
|
||||||
kernel = kernel_detection(blurred, mask, edge_threshold=edge_threshold, profile_length=profile_length)
|
kernel = kernel_detection_box(image, mask, edge_threshold=edge_threshold, profile_length=profile_length)
|
||||||
|
|
||||||
test_blurred = cv2.imread(image_file, cv2.IMREAD_GRAYSCALE).astype(np.float32) / 255.0
|
|
||||||
|
# Apply Richardson-Lucy to each channel
|
||||||
|
num_iter = 30
|
||||||
|
deblurred_channels = []
|
||||||
|
for i in range(3): # R, G, B
|
||||||
|
channel = image_rgb[..., i]
|
||||||
|
deconv = richardson_lucy(channel, kernel, num_iter=num_iter)
|
||||||
|
deblurred_channels.append(deconv)
|
||||||
|
|
||||||
|
# Stack back into an RGB image
|
||||||
|
deblurred_rgb = np.stack(deblurred_channels, axis=2)
|
||||||
|
deblurred_rgb = np.clip(deblurred_rgb, 0, 1)
|
||||||
|
|
||||||
deconvolved = richardson_lucy(test_blurred, kernel, num_iter=30)
|
|
||||||
|
|
||||||
# Display results
|
# Show result
|
||||||
plt.figure(figsize=(12, 4))
|
plt.figure(figsize=(10, 5))
|
||||||
plt.subplot(1, 3, 1)
|
plt.subplot(1, 2, 1)
|
||||||
|
plt.imshow(image_rgb)
|
||||||
plt.title("Blurred Image")
|
plt.title("Blurred Image")
|
||||||
plt.imshow(test_blurred, cmap='gray')
|
|
||||||
plt.axis('off')
|
plt.axis('off')
|
||||||
|
|
||||||
plt.subplot(1, 3, 2)
|
plt.subplot(1, 2, 2)
|
||||||
plt.title("Estimated Kernel")
|
plt.imshow(deblurred_rgb)
|
||||||
plt.imshow(kernel, cmap='hot')
|
|
||||||
plt.axis('off')
|
|
||||||
|
|
||||||
plt.subplot(1, 3, 3)
|
|
||||||
plt.title("Deconvolved Image")
|
plt.title("Deconvolved Image")
|
||||||
plt.imshow(deconvolved, cmap='gray')
|
|
||||||
plt.axis('off')
|
plt.axis('off')
|
||||||
|
|
||||||
plt.tight_layout()
|
|
||||||
plt.show()
|
plt.show()
|
||||||
|
|
||||||
|
|
||||||
@ -253,4 +302,4 @@ if __name__ == "__main__":
|
|||||||
img_file = "assets/real_test.jpg"
|
img_file = "assets/real_test.jpg"
|
||||||
|
|
||||||
#demo("assets/omas.png")
|
#demo("assets/omas.png")
|
||||||
deconvolution(img_file, edge_threshold=10)
|
deconvolution(img_file, edge_threshold=5)
|
||||||
|
Loading…
x
Reference in New Issue
Block a user