carlosriverat's picture
Update app.py
b883a76 verified
raw
history blame
3.31 kB
import gradio as gr
import cv2
import numpy as np
from skimage.metrics import structural_similarity as ssim
def preprocess_image(image, blur_value):
# Convert to grayscale
gray = cv2.cvtColor(image, cv2.COLOR_BGR2GRAY)
# Apply Gaussian blur to reduce noise
blurred = cv2.GaussianBlur(gray, (blur_value, blur_value), 0)
return blurred
def compare_images(image1, image2, blur_value, technique, threshold_value):
# Preprocess images
gray1 = preprocess_image(image1, blur_value)
gray2 = preprocess_image(image2, blur_value)
# Compute SSIM between the two images
score, diff = ssim(gray1, gray2, full=True)
diff = (diff * 255).astype("uint8")
if technique == "Adaptive Threshold":
_, thresh = cv2.threshold(diff, 30, 255, cv2.THRESH_BINARY_INV)
elif technique == "Otsu's Threshold":
_, thresh = cv2.threshold(diff, 0, 255, cv2.THRESH_BINARY_INV | cv2.THRESH_OTSU)
else: # Simple Binary
_, thresh = cv2.threshold(diff, threshold_value, 255, cv2.THRESH_BINARY)
# Find contours of differences
contours, _ = cv2.findContours(thresh, cv2.RETR_EXTERNAL, cv2.CHAIN_APPROX_SIMPLE)
# Filter out small noise using contour area threshold
filtered_contours = [cnt for cnt in contours if cv2.contourArea(cnt) > 500]
# Create a mask to isolate only the significant added object
mask = np.zeros_like(image1)
cv2.drawContours(mask, filtered_contours, -1, (255, 255, 255), thickness=cv2.FILLED)
# Apply the mask to highlight the object added in the second image
highlighted = cv2.bitwise_and(image2, mask)
# Overlay the difference in magenta over the first image
diff_colored = cv2.cvtColor(diff, cv2.COLOR_GRAY2BGR)
diff_colored[:, :, 1:] = 0 # Keep only red channel for magenta effect
overlayed = cv2.addWeighted(image1, 0.7, diff_colored, 0.3, 0)
return highlighted, overlayed
def update_threshold_visibility(technique):
return gr.update(visible=(technique == "Simple Binary"))
with gr.Blocks() as demo:
gr.Markdown("# Object Difference Highlighter\nUpload two images: one without an object and one with an object. The app will highlight only the newly added object and show the real differences in magenta overlayed on the original image.")
with gr.Row():
img1 = gr.Image(type="numpy", label="Image Without Object")
img2 = gr.Image(type="numpy", label="Image With Object")
blur_slider = gr.Slider(minimum=1, maximum=15, step=2, value=5, label="Gaussian Blur")
technique_dropdown = gr.Dropdown(["Adaptive Threshold", "Otsu's Threshold", "Simple Binary"], label="Thresholding Technique", value="Adaptive Threshold", interactive=True)
threshold_slider = gr.Slider(minimum=0, maximum=255, step=1, value=50, label="Threshold Value", visible=False)
technique_dropdown.change(update_threshold_visibility, inputs=[technique_dropdown], outputs=[threshold_slider])
output1 = gr.Image(type="numpy", label="Highlighted Differences")
output2 = gr.Image(type="numpy", label="Raw Difference Overlay (Magenta)")
btn = gr.Button("Process")
btn.click(compare_images, inputs=[img1, img2, blur_slider, technique_dropdown, threshold_slider], outputs=[output1, output2])
demo.launch()