42d65b0d25
Add fill_seg_dropouts: where ViTMatte's alpha is ~0 but BiRefNet confidently asserts foreground, restore a faint alpha from the mask (strength * seg_mask). This recovers green-contaminated wisps that ViTMatte cuts because they are nearly the background colour, while leaving ViTMatte's sharper edges elsewhere untouched (gated to true dropouts) and not refilling the finger gap (low mask). On the TestImage2 shoulder, faint wisps ViTMatte cut drop from 72% to 33%; the finger gap stays transparent. The rescued wisps are still green-tinted -- the recolor pass (next) restores their colour. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
107 lines
3.3 KiB
Python
107 lines
3.3 KiB
Python
from __future__ import annotations
|
|
|
|
from dataclasses import dataclass
|
|
|
|
|
|
@dataclass(frozen=True)
|
|
class ChromaSettings:
|
|
green_margin: float = 0.08
|
|
min_green_value: float = 0.22
|
|
min_saturation: float = 0.20
|
|
hue_low: float = 35.0
|
|
hue_high: float = 95.0
|
|
border_ratio: float = 0.04
|
|
min_samples: int = 2048
|
|
hue_sigma_min: float = 7.0
|
|
lab_sigma_min: float = 10.0
|
|
rgb_sigma_min: float = 0.08
|
|
|
|
|
|
@dataclass(frozen=True)
|
|
class TrimapSettings:
|
|
sure_bg_threshold: float = 0.92
|
|
sure_fg_threshold: float = 0.12
|
|
unknown_radius_ratio: float = 0.012
|
|
fg_safe_radius_ratio: float = 0.006
|
|
min_unknown_radius: int = 4
|
|
min_fg_safe_radius: int = 2
|
|
# Semantic fusion thresholds (used by fuse_trimap when segmentation is on).
|
|
seg_core_threshold: float = 0.60
|
|
seg_loose_threshold: float = 0.08
|
|
|
|
|
|
@dataclass(frozen=True)
|
|
class AlphaPostSettings:
|
|
min_component_area_ratio: float = 0.00001
|
|
fill_hole_area_ratio: float = 0.00002
|
|
alpha_floor: float = 0.002
|
|
alpha_ceil: float = 0.998
|
|
# Chroma-guided alpha suppression: in the unknown band, pull alpha toward 0
|
|
# where background (green) confidence is high, clearing spill in gaps/holes.
|
|
chroma_suppress: bool = True
|
|
chroma_suppress_bg_low: float = 0.35
|
|
chroma_suppress_bg_high: float = 0.80
|
|
chroma_suppress_strength: float = 1.0
|
|
# Segmentation dropout-fill: rescue alpha where ViTMatte cut a region the
|
|
# semantic mask asserts is foreground (green-contaminated wisps it cannot see).
|
|
seg_fill: bool = True
|
|
seg_fill_alpha_max: float = 0.10
|
|
seg_fill_seg_min: float = 0.10
|
|
seg_fill_strength: float = 0.70
|
|
|
|
|
|
@dataclass(frozen=True)
|
|
class ForegroundSettings:
|
|
enabled: bool = True
|
|
method: str = "ml" # "ml" (pymatting) or "unmix" (legacy heuristic)
|
|
fallback_to_unmix: bool = True
|
|
ml_regularization: float = 1e-5
|
|
# Legacy "unmix" method parameters (used only when method == "unmix").
|
|
edge_low: float = 0.005
|
|
edge_high: float = 0.995
|
|
min_unmix_alpha: float = 0.08
|
|
unmix_strength: float = 0.70
|
|
local_strength: float = 0.45
|
|
local_blur_radius: int = 11
|
|
local_alpha_threshold: float = 0.92
|
|
local_bg_confidence_max: float = 0.20
|
|
green_excess_margin: float = 0.015
|
|
bg_confidence_weight: float = 0.70
|
|
|
|
|
|
@dataclass(frozen=True)
|
|
class DespillSettings:
|
|
enabled: bool = True
|
|
edge_low: float = 0.005
|
|
strength: float = 0.92
|
|
green_excess_margin: float = 0.015
|
|
edge_expand_radius: int = 2
|
|
alpha_weight_floor: float = 0.35
|
|
|
|
|
|
@dataclass(frozen=True)
|
|
class ModelSettings:
|
|
model_name: str = "hustvl/vitmatte-small-composition-1k"
|
|
device: str = "cuda"
|
|
matting_method: str = "vitmatte"
|
|
fallback_to_chroma_alpha: bool = False
|
|
|
|
|
|
@dataclass(frozen=True)
|
|
class SegmentationSettings:
|
|
enabled: bool = True
|
|
model_name: str = "ZhengPeng7/BiRefNet"
|
|
device: str = "cuda"
|
|
input_size: int = 1024
|
|
|
|
|
|
@dataclass(frozen=True)
|
|
class PipelineSettings:
|
|
chroma: ChromaSettings = ChromaSettings()
|
|
trimap: TrimapSettings = TrimapSettings()
|
|
alpha_post: AlphaPostSettings = AlphaPostSettings()
|
|
foreground: ForegroundSettings = ForegroundSettings()
|
|
despill: DespillSettings = DespillSettings()
|
|
model: ModelSettings = ModelSettings()
|
|
segmentation: SegmentationSettings = SegmentationSettings()
|