Spaces:
Running
Running
import cv2 | |
import numpy as np | |
import scipy as sp | |
import scipy.sparse.linalg | |
from numba import njit, prange | |
import gradio as gr | |
def neighbours(y, x, max_y, max_x): | |
neighbors = [] | |
if y > 0: | |
neighbors.append((y-1, x)) | |
if y < max_y: | |
neighbors.append((y+1, x)) | |
if x > 0: | |
neighbors.append((y, x-1)) | |
if x < max_x: | |
neighbors.append((y, x+1)) | |
return neighbors | |
def build_poisson_matrix(img, alpha, img_h, img_w): | |
im2var = np.arange(img_h * img_w).reshape(img_h, img_w) | |
A_data = np.zeros(img_h * img_w * 5, dtype=np.float64) | |
A_row = np.zeros(img_h * img_w * 5, dtype=np.int32) | |
A_col = np.zeros(img_h * img_w * 5, dtype=np.int32) | |
b = np.zeros(img_h * img_w * 5, dtype=np.float64) | |
e = 0 | |
for y in range(img_h): | |
for x in range(img_w): | |
A_data[e] = 1 | |
A_row[e] = e | |
A_col[e] = im2var[y, x] | |
b[e] = img[y, x] | |
e += 1 | |
for n_y, n_x in neighbours(y, x, img_h-1, img_w-1): | |
A_data[e] = 1 | |
A_row[e] = e | |
A_col[e] = im2var[y, x] | |
e += 1 | |
A_data[e] = -1 | |
A_row[e] = e - 1 | |
A_col[e] = im2var[n_y, n_x] | |
b[e-1] = alpha * (img[y, x] - img[n_y, n_x]) | |
e += 1 | |
return A_data[:e], A_row[:e], A_col[:e], b[:e], e | |
def poisson_sharpening(img: np.ndarray, alpha: float) -> np.ndarray: | |
img_h, img_w = img.shape | |
A_data, A_row, A_col, b, e = build_poisson_matrix(img, alpha, img_h, img_w) | |
A = sp.sparse.csr_matrix((A_data, (A_row, A_col)), shape=(e, img_h * img_w)) | |
v = sp.sparse.linalg.lsqr(A, b)[0] | |
return np.clip(v.reshape(img_h, img_w), 0, 1) | |
def sharpen_image_channels(img, alpha): | |
sharpen_img = np.zeros_like(img) | |
for b in range(3): | |
sharpen_img[:,:,b] = poisson_sharpening(img[:,:,b], alpha) | |
return sharpen_img | |
def get_image(img): | |
return cv2.cvtColor(img, cv2.COLOR_BGR2RGB).astype('float32') / 255.0 | |
def sharpen_image(input_img, alpha): | |
img = get_image(input_img) | |
sharpen_img = sharpen_image_channels(img, alpha) | |
return (sharpen_img * 255).astype(np.uint8) | |
# Create examples list | |
examples = [ | |
["img1.jpg", 9.0], | |
["img2.PNG", 7.0], | |
] | |
# Create the Gradio interface | |
iface = gr.Interface( | |
fn=sharpen_image, | |
inputs=[ | |
gr.Image(label="Input Image", type="numpy"), | |
gr.Slider(minimum=1.0, maximum=15.0, step=0.01, value=9.0, label="Sharpening Strength (alpha)") | |
], | |
outputs=gr.Image(label="Sharpened Image"), | |
title="Poisson Image Sharpening", | |
description="Upload an image or choose from the examples, then adjust the sharpening strength to enhance edges and details.", | |
theme='bethecloud/storj_theme', | |
examples=examples, | |
cache_examples=True | |
) | |
iface.launch() |