Spaces:
Paused
Paused
File size: 2,017 Bytes
bb75e0a | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 | """The ONE entrypoint a tool author edits.
`process(file_url, engine, radius, strength)` runs Noise2Void self-supervised
denoising on a noisy 2D image and returns a noisy/denoised/clean summary plus a
report (PSNR/SSIM when the clean ground-truth sidecar is available).
"""
from __future__ import annotations
import os
import numpy as np
from . import n2v, viz
from .io import load_image_from_any
ENGINES = n2v.ENGINES
def _to_gray01(arr: np.ndarray) -> np.ndarray:
a = np.asarray(arr)
if a.ndim == 3:
a = a[..., :3].mean(-1)
a = a.astype(np.float32)
return np.clip((a - a.min()) / max(a.max() - a.min(), 1e-6), 0, 1)
def simulate_full(image_path, engine: str = "fast", radius: int = 2,
strength: float = 1.0) -> dict:
if engine not in ENGINES:
raise ValueError(f"Unknown engine '{engine}'. Choose one of {ENGINES}.")
noisy = _to_gray01(load_image_from_any(image_path))
clean = None
# Clean ground-truth sidecar, saved next to the baked example as a hidden file
# (leading dot) so it is never mistaken for an input image.
if isinstance(image_path, str):
base = os.path.splitext(image_path)[0]
d, name = os.path.split(base)
for side in (base + "_clean.npy", os.path.join(d, "." + name + "_clean.npy")):
if os.path.exists(side):
try:
clean = np.load(side)
except Exception: # noqa: BLE001
clean = None
break
res = n2v.analyze(noisy, engine=engine, radius=int(radius),
strength=float(strength), clean=clean)
return {"summary": viz.summary_image(res), "report": res["report"], "res": res}
def process(image_path, engine: str = "fast", radius: int = 2,
strength: float = 1.0) -> tuple[np.ndarray, dict]:
"""Returns (noisy/denoised/clean summary RGB, report dict)."""
r = simulate_full(image_path, engine, radius, strength)
return r["summary"], r["report"]
|