# Smoke test: guided filter przez cv2.boxFilter (zamiennik cv2.ximgproc.guidedFilter, # ktorego brak w opencv-python-headless) + porownanie z bilateralFilter. import time import cv2 import numpy as np from PIL import Image IMG = r"C:\xampp\htdocs\vilmax\vilmax-cockpit\data\hall-audit\preview\p-6419.jpg" def guided_filter(guide: np.ndarray, src: np.ndarray, radius: int, eps: float) -> np.ndarray: """Klasyczny guided filter (He et al.) — tylko boxFilter, bez contrib.""" I = guide.astype(np.float32) p = src.astype(np.float32) ksize = (2 * radius + 1, 2 * radius + 1) mean_I = cv2.boxFilter(I, -1, ksize, normalize=True) mean_p = cv2.boxFilter(p, -1, ksize, normalize=True) corr_I = cv2.boxFilter(I * I, -1, ksize, normalize=True) corr_Ip = cv2.boxFilter(I * p, -1, ksize, normalize=True) var_I = corr_I - mean_I * mean_I cov_Ip = corr_Ip - mean_I * mean_p a = cov_Ip / (var_I + eps) b = mean_p - a * mean_I return cv2.boxFilter(a, -1, ksize, normalize=True) * I + cv2.boxFilter(b, -1, ksize, normalize=True) rgb = np.asarray(Image.open(IMG).convert("RGB"), dtype=np.uint8) gray = cv2.cvtColor(rgb, cv2.COLOR_RGB2GRAY).astype(np.float32) / 255.0 # symulacja: szumna maska alfa (gladka + krawedzie) alpha = (gray < 0.55).astype(np.float32) alpha = cv2.GaussianBlur(alpha, (0, 0), 3) noise = np.random.default_rng(0).normal(0, 0.03, alpha.shape).astype(np.float32) alpha_n = np.clip(alpha + noise, 0, 1) t = time.time() g = guided_filter(gray, alpha_n, radius=8, eps=1e-3) t_g = (time.time() - t) * 1000 t = time.time() b = cv2.bilateralFilter(alpha_n, d=17, sigmaColor=0.1, sigmaSpace=8) t_b = (time.time() - t) * 1000 # metryka krawedzi: ostrosc przejscia 10-90% na profilu poziomym def edge_width(a_img, y): row = a_img[y] xs = np.nonzero(np.abs(np.diff(row)) > 0.05)[0] return len(xs) print(f"guidedFilter(boxFilter impl): {t_g:.1f} ms shape={g.shape}") print(f"bilateralFilter: {t_b:.1f} ms") print(f"residual |guided-src| mean: {float(np.abs(g-alpha).mean()):.4f}") print(f"residual |bilat-src| mean: {float(np.abs(b-alpha).mean()):.4f}") # wycieki przez krawedz: ile sygnalu alfa przechodzi na jasne tlo po prawej stronie for name, m in (("raw", alpha_n), ("guided", g), ("bilateral", b)): print(f"{name:>9}: mean na tle (gray>0.7): {float(m[gray > 0.7].mean()):.4f}")