import cv2 import gradio as gr import numpy as np def original_image(input_image): return input_image def grayscale(input_image): gray_image = cv2.cvtColor(input_image, cv2.COLOR_BGR2GRAY) return gray_image def edge_detection(input_image): edges = cv2.Canny(input_image, 100, 200) return edges def sobel_edge_detection(input_image): gray_image = cv2.cvtColor(input_image, cv2.COLOR_BGR2GRAY) sobel_x = cv2.Sobel(gray_image, cv2.CV_64F, 1, 0, ksize=5) sobel_y = cv2.Sobel(gray_image, cv2.CV_64F, 0, 1, ksize=5) sobel_magnitude = cv2.magnitude(sobel_x, sobel_y) sobel_magnitude = np.uint8(255 * sobel_magnitude / np.max(sobel_magnitude)) return sobel_magnitude def invert_colors(input_image): inverted_image = cv2.bitwise_not(input_image) return inverted_image def erosion(input_image, iterations): kernel = np.ones((5, 5), np.uint8) eroded_image = cv2.erode(input_image, kernel, iterations=iterations) return eroded_image def dilation(input_image, dilation_iterations): kernel = np.ones((5, 5), np.uint8) dilated_image = cv2.dilate(input_image, kernel, iterations=dilation_iterations) return dilated_image def gaussian_blur(image, blur_degree): blur_degree = int(blur_degree) | 1 result = cv2.GaussianBlur(image, (blur_degree, blur_degree), 0) return result def custom_filter(input_image): kernel = np.array([[-1, -1, -1], [-1, 9, -1], [-1, -1, -1]]) return cv2.filter2D(input_image, -1, kernel) def mosaic(image, block_size): if image is None: return None height, width = image.shape[:2] for y in range(0, height, block_size): for x in range(0, width, block_size): # Define the region of interest (ROI), ensuring it doesn't go out of bounds roi = image[y:min(y + block_size, height), x:min(x + block_size, width)] # Compute the average color of the ROI color = np.mean(roi, axis=(0, 1)).astype(int) # Set the block region to the average color image[y:min(y + block_size, height), x:min(x + block_size, width)] = color return image def apply_opencv_methods(input_image, method, iterations, blur_degree, dilation_iterations, mosaic_block_size): if method == "default": return original_image(input_image) elif method == "erosion": return erosion(input_image, iterations) elif method == "dilation": return dilation(input_image, dilation_iterations) elif method == "邊緣檢測1(Sobel)": return sobel_edge_detection(input_image) elif method == "風格變換": return custom_filter(input_image) elif method == "模糊": return gaussian_blur(input_image, blur_degree) elif method == "馬賽克": return mosaic(input_image,mosaic_block_size) else: methods = { "灰階": grayscale, "邊緣檢測2(Canny)": edge_detection, "反轉顏色": invert_colors, } return methods[method](input_image) def update_slider_visibility(method): return ( gr.update(visible=(method == "erosion")), gr.update(visible=(method == "模糊")), gr.update(visible=(method == "dilation")), gr.update(visible=(method == "馬賽克")) ) css=""" @import url('https://fonts.googleapis.com/css2?family=LXGW+WenKai+TC&display=swap'); .gradio-container { font-family: 'LXGW WenKai TC', sans-serif; /* 將字體套用到整個 Gradio 介面 */ } .gradio-container h1 { /* 修改 title 標題樣式 */ font-family: 'LXGW WenKai TC', sans-serif; /* 字體 */ font-size: 32px; /* 字體大小 */ color: #F5F5DC; /* 字體顏色 */ text-align: center; /* 置中對齊 */ } .dark-light-toggle { /* 隱藏主題切換按鈕 */ display: none !important; } """ with gr.Blocks(css=css) as demo: input_image = gr.Image(type="numpy", label="input image") method = gr.Radio( choices=["default", "灰階", "反轉顏色", "erosion", "dilation", "模糊", "馬賽克" ,"邊緣檢測1(Sobel)", "邊緣檢測2(Canny)", "風格變換"], value="default", label="選擇操作方法") iterations = gr.Slider(minimum=0, maximum=10, step=1, value=1, label="參數大小", visible=False) blur_degree = gr.Slider(minimum=1, maximum=25, step=2, value=1, label="模糊程度", visible=False) dilation_iterations = gr.Slider(minimum=0, maximum=10, step=1, value=1, label="參數大小", visible=False) mosaic_block_size = gr.Slider(minimum=5, maximum=50, step=5, value=5, label="馬賽克塊大小", visible=False) output_image = gr.Image(type="numpy", label="output image") method.change( fn=update_slider_visibility, inputs=[method], outputs=[iterations, blur_degree, dilation_iterations, mosaic_block_size] ) gr.Interface( fn=apply_opencv_methods, inputs=[input_image, method, iterations, blur_degree, dilation_iterations, mosaic_block_size], outputs=output_image, live=True, title="各種影像處理", description="上傳一張圖片並選擇想要處理影像的方法", ) examples = gr.Examples( examples=[ ["chikawa.jpg", "erosion", 2, None, None, None], ["cat.jpg", "風格變換", None, None, None, None], ["pui.jpg", "模糊", None, 15, None, None] ], inputs=[input_image, method, iterations, blur_degree, dilation_iterations, mosaic_block_size], label="example", ) demo.launch()