import logging from PIL import Image, ImageFilter import scipy.signal import numpy as np logging.getLogger(__name__) sobel_x_kernel = np.array(( (1, 0, -1), (2, 0, -2), (1, 0, -1) )) sobel_y_kernel = np.transpose(sobel_x_kernel) def difference_of_gaussians(img: Image.Image, blur_strength_1: float | None = 1.0, blur_strength_2: float | None = 1.2, threshold: int | None = 128*3) -> Image.Image: blur_1 = img.filter(ImageFilter.GaussianBlur(blur_strength_1)) blur_2 = img.filter(ImageFilter.GaussianBlur(blur_strength_2)) w, h = img.size dog = Image.new(img.mode, img.size) for pixel_y in range(h): for pixel_x in range(w): coords = (pixel_x, pixel_y) p1 = blur_1.getpixel(coords) p2 = blur_2.getpixel(coords) p1 = np.array(p1) p2 = np.array(p2) new_pixel = p2 - p1 # if new_pixel.sum() < threshold: # new_pixel = np.zeros(3).astype(np.uint8) dog.putpixel(coords, tuple(new_pixel.tolist())) return dog def sobel(img: Image.Image, gradient_threshold: int | None = 20) -> tuple[Image.Image, np.ndarray]: logging.debug(img.size) img = img.convert('L') img.save('debug/test-L.png') logging.debug('Sobel Operator') logging.debug(img.size) pixels = np.array(img) logging.debug(f'pixels size: {pixels.size}') dx = scipy.signal.correlate(pixels, sobel_x_kernel, mode='same') dy = scipy.signal.correlate(pixels, sobel_y_kernel, mode='same') logging.debug(f'dx size: {dx.size}') edges = np.sqrt(np.square(dx) + np.square(dy)) edges[edges>255] = 255 logging.debug(f'edges size: {edges.size}') gradient = np.arctan2(dy.flatten(), dx.flatten()) gradient = np.absolute(gradient) print(gradient) print(np.average(gradient)) gradient[gradient > gradient_threshold] = 0 pil_edges = edges.astype(np.uint8) newimg = Image.fromarray(pil_edges, mode='L') logging.debug(f'New Img Size: {newimg.size}') return (newimg, gradient) def average_colors(colors: list) -> tuple: colors = np.array(colors) np.average(colors) sum = np.zeros(len(colors[0])) for c in colors: sum += c sum /= len(colors) return tuple(sum.astype(np.uint8).tolist())