segmentation
sleap_nn.inference.segmentation
¶
Inference utilities for bottom-up instance segmentation.
Classes:
| Name | Description |
|---|---|
BottomUpSegmentationInferenceModel |
Inference model for bottom-up instance segmentation. |
CenteredInstanceMaskInferenceModel |
Stage-2 holder for top-down (crop-centered) instance segmentation (#622). |
SemanticSegmentationInferenceModel |
Inference model for whole-frame semantic (foreground/background) segmentation. |
Functions:
| Name | Description |
|---|---|
find_center_peaks |
Find instance-center peaks robustly (plateau-aware). |
group_instances_from_offsets |
Group foreground pixels into instances using center-offset predictions. |
merge_instances |
Fuse over-segmented fragments of one animal via a RAG over candidate masks. |
BottomUpSegmentationInferenceModel
¶
Bases: LightningModule
Inference model for bottom-up instance segmentation.
Wraps a trained model and post-processing into a single forward pass.
Input images should already be padded to stride before being passed to this
model (handled by the predictor's _run_inference_on_batch).
Attributes:
| Name | Type | Description |
|---|---|---|
torch_model |
Callable model that returns head output dict. |
|
fg_threshold |
Threshold for foreground binarization. |
|
peak_threshold |
Minimum peak value for center detection. |
|
output_stride |
Stride of the model output maps. |
|
min_mask_area |
Minimum mask area (original-image pixels) carried through
to |
|
max_instances |
Optional cap on instances per frame (highest-scoring
centers kept). Carried through to |
|
center_nms_kernel |
Odd window size for center-peak NMS. Default |
|
mask_cleanup |
Keep-largest-CC + hole-fill per mask. Default |
Methods:
| Name | Description |
|---|---|
__init__ |
Initialize the inference model. |
forward |
Run inference on a batch of images. |
Source code in sleap_nn/inference/segmentation.py
785 786 787 788 789 790 791 792 793 794 795 796 797 798 799 800 801 802 803 804 805 806 807 808 809 810 811 812 813 814 815 816 817 818 819 820 821 822 823 824 825 826 827 828 829 830 831 832 833 834 835 836 837 838 839 840 841 842 843 844 845 846 847 848 849 850 851 852 853 854 855 856 857 858 859 860 861 862 863 864 865 866 867 868 869 870 871 872 873 874 875 876 877 878 879 880 881 882 883 884 885 886 887 888 889 890 891 892 893 894 895 896 897 898 899 900 901 902 903 904 | |
__init__(torch_model, fg_threshold=0.5, peak_threshold=0.2, output_stride=2, input_scale=1.0, min_mask_area=0, max_instances=None, center_nms_kernel=3, mask_cleanup=False, mask_cleanup_radius=0, distance_gate_alpha=None, merge_fragments=False, merge_method='greedy', merge_thresholds=(0.85, 0.6, 0.4), merge_w_valley=1.0, merge_w_offset=0.25, merge_dilate=1, full_res_masks=False, mask_output='mask', polygon_epsilon=0.01)
¶
Initialize the inference model.
Source code in sleap_nn/inference/segmentation.py
forward(batch)
¶
Run inference on a batch of images.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
batch
|
Dict
|
Dict with "image" key. Shape: (B, C, H, W). Images should already be padded to the model's max stride. |
required |
Returns:
| Type | Description |
|---|---|
List[List[Dict]]
|
List of instance lists (one per batch element). Each instance is a dict with "mask", "center", and "score" keys. |
Source code in sleap_nn/inference/segmentation.py
CenteredInstanceMaskInferenceModel
¶
Bases: LightningModule
Stage-2 holder for top-down (crop-centered) instance segmentation (#622).
A thin attribute bag (no real forward — the modern composed
:class:~sleap_nn.inference.layers.topdown_segmentation.TopDownSegmentationLayer
drives the run) carrying the per-crop seg model + the knobs the layer
builder reads off it. Mirrors how the legacy FindInstancePeaks is used
purely as an attribute holder by the modern top-down layer builder.
Attributes:
| Name | Type | Description |
|---|---|---|
torch_model |
Per-crop seg Lightning module; |
|
output_stride |
Head-map → crop-pixel stride. |
|
input_scale |
Input scale the model was trained with (applied to crops). |
|
max_stride |
Backbone max stride (crops padded to a multiple of it). |
|
fg_threshold |
Foreground probability threshold for binarization. |
|
mask_output |
/ polygon_epsilon
|
Output-packaging knobs (read by the
layer builder and forwarded to |
Methods:
| Name | Description |
|---|---|
__init__ |
Stash the per-crop seg model + knobs. |
Source code in sleap_nn/inference/segmentation.py
__init__(torch_model, output_stride=2, input_scale=1.0, max_stride=1, fg_threshold=0.5, mask_output='mask', polygon_epsilon=0.01)
¶
Stash the per-crop seg model + knobs.
Source code in sleap_nn/inference/segmentation.py
SemanticSegmentationInferenceModel
¶
Bases: LightningModule
Inference model for whole-frame semantic (foreground/background) segmentation.
A lone :class:~sleap_nn.architectures.heads.SegmentationHead on the WHOLE
frame (no crop, no instance grouping). The trained model's forward returns
{"SegmentationHead": prob} with the sigmoid ALREADY applied (mirroring
:class:BottomUpSegmentationLightningModule, whose foreground head is
sigmoided in forward — required so tiled inference stitches probabilities,
not logits). postprocess thresholds the foreground map into ONE mask per
frame; there is no center/offset field and no group_instances_from_offsets.
Like :class:BottomUpSegmentationInferenceModel, this is primarily an
attribute bag whose .torch_model + packaging knobs are read off it by
_build_semantic_segmentation_layer (via getattr); the real inference
run is driven by the composed
:class:~sleap_nn.inference.layers.segmentation.SemanticSegmentationLayer.
forward is provided for training-viz / GPU mask-eval parity and emits raw
output-stride masks (min_mask_area / full_res_masks / packaging knobs
are applied later, in the layer's postprocess).
Attributes:
| Name | Type | Description |
|---|---|---|
torch_model |
Callable model returning |
|
fg_threshold |
Foreground probability threshold for binarization. |
|
output_stride |
Stride of the seg head map relative to the model input. |
|
input_scale |
Input scale the model was trained with (applied to frames). |
|
min_mask_area |
Minimum mask area (ORIGINAL-image pixels) carried through
to |
|
full_res_masks |
/ mask_output / polygon_epsilon
|
Output-packaging knobs
read by the layer builder and forwarded to the layer / |
Methods:
| Name | Description |
|---|---|
__init__ |
Stash the whole-frame seg model + packaging knobs. |
forward |
Threshold the foreground map into ONE mask per batch element. |
Source code in sleap_nn/inference/segmentation.py
317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 404 405 406 407 | |
__init__(torch_model, fg_threshold=0.5, output_stride=2, input_scale=1.0, min_mask_area=0, full_res_masks=False, mask_output='mask', polygon_epsilon=0.01)
¶
Stash the whole-frame seg model + packaging knobs.
Source code in sleap_nn/inference/segmentation.py
forward(batch)
¶
Threshold the foreground map into ONE mask per batch element.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
batch
|
Dict
|
Dict with an |
required |
Returns:
| Type | Description |
|---|---|
List[List[Dict]]
|
List (one per batch element) of instance lists. Each element is either
empty (no foreground above threshold) or a single-item list
|
Source code in sleap_nn/inference/segmentation.py
find_center_peaks(center_heatmap, threshold=0.2, kernel_size=3)
¶
Find instance-center peaks robustly (plateau-aware).
Strict-greater non-maximum suppression (find_local_peaks_rough) drops a
peak whose maximum spans 2+ tied pixels — which happens routinely for the
synthetic center heatmap when a centroid lands exactly between grid points
(the +stride/2 convention). This detector instead keeps every pixel
equal to its neighborhood max (>=) and collapses each connected
plateau of tied maxima to a single representative (its argmax pixel), so a
flat-topped peak yields exactly one center.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
center_heatmap
|
Tensor
|
|
required |
threshold
|
float
|
Minimum peak value. |
0.2
|
kernel_size
|
int
|
Odd window size for the max-pool NMS. Larger values suppress
nearby duplicate centers (a lever against over-segmentation from a
single instance producing two close center peaks). Default |
3
|
Returns:
| Type | Description |
|---|---|
Tuple[Tensor, Tensor]
|
|
Source code in sleap_nn/inference/segmentation.py
group_instances_from_offsets(foreground, center_heatmap, offsets, fg_threshold=0.5, peak_threshold=0.2, output_stride=2, max_instances=None, center_nms_kernel=3, mask_cleanup=False, mask_cleanup_radius=0, distance_gate_alpha=None, distance_gate_iters=3)
¶
Group foreground pixels into instances using center-offset predictions.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
foreground
|
Tensor
|
Foreground probability map. Shape: (1, 1, H, W). |
required |
center_heatmap
|
Tensor
|
Center heatmap. Shape: (1, 1, H, W). |
required |
offsets
|
Tensor
|
Offset field (dx, dy). Shape: (1, 2, H, W). |
required |
fg_threshold
|
float
|
Threshold for foreground binarization. |
0.5
|
peak_threshold
|
float
|
Minimum peak value for center detection. |
0.2
|
output_stride
|
int
|
Stride of the output maps relative to the input image. |
2
|
max_instances
|
Optional[int]
|
Optional cap on the number of instances per frame. When
more centers than this are detected, only the |
None
|
center_nms_kernel
|
int
|
Odd window size for center-peak NMS (passed to
:func: |
3
|
mask_cleanup
|
bool
|
When |
False
|
mask_cleanup_radius
|
int
|
When |
0
|
distance_gate_alpha
|
Optional[float]
|
Adaptive distance-gate strength. When |
None
|
distance_gate_iters
|
int
|
Number of adaptive re-estimation iterations for the
distance gate (only used when |
3
|
Returns:
| Type | Description |
|---|---|
List[Dict]
|
List of dicts, each with: - "mask": (H, W) boolean numpy array (at output stride resolution) - "center": (x, y) tuple in original pixel coordinates - "score": float confidence score (peak value) |
Source code in sleap_nn/inference/segmentation.py
63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 | |
merge_instances(instances, center_heatmap, offsets, output_stride, *, method='greedy', dilate_iters=1, w_valley=1.0, w_offset=0.25, thresholds=(0.85, 0.6, 0.4), join_bias=0.5)
¶
Fuse over-segmented fragments of one animal via a RAG over candidate masks.
Builds a region-adjacency graph over the candidate masks (edge affinity =
contact-gate * a center-valley-ridge / offset-agreement blend), then runs the
chosen agglomeration. Two genuinely-touching distinct animals are kept apart
by the valley term (a deep heatmap valley between their centers vetoes the
merge). Operates at output-stride (grid) resolution, BEFORE upsample and
min_mask_area, on the dicts returned by
:func:group_instances_from_offsets.
Parameters:
| Name | Type | Description | Default |
|---|---|---|---|
instances
|
List[Dict]
|
|
required |
center_heatmap
|
ndarray
|
|
required |
offsets
|
ndarray
|
|
required |
output_stride
|
int
|
Stride of the head maps relative to the model input. |
required |
method
|
str
|
|
'greedy'
|
dilate_iters
|
int
|
Dilation iterations for the contact test (default |
1
|
w_valley
|
float
|
Weight on the center-valley ridge term (default |
1.0
|
w_offset
|
float
|
Weight on the offset-agreement term (default |
0.25
|
thresholds
|
Sequence[float]
|
Decreasing affinity thresholds per greedy phase. |
(0.85, 0.6, 0.4)
|
join_bias
|
float
|
Multicut decision boundary (affinity > this => attractive). |
0.5
|
Returns:
| Type | Description |
|---|---|
List[Dict]
|
A NEW list of merged |