Swimmer Head Detection (Face Blurring) Models
Object detection models that locate the head of a swimmer in video frames. They were trained as part of the SWIM-360 / DIVE project, a collaboration between the University of Malta and the Aquatic Sports Association of Malta, and are intended to support face anonymisation (blurring) of swimmers in swimming footage.
This repository contains several detectors from two model families, so they can be compared on accuracy and speed:
| Family | Architectures | GitHub |
|---|---|---|
| Ultralytics YOLO | YOLO11m, YOLO26m, YOLO26L | ultralytics/ultralytics |
| Roboflow RF-DETR | RF-DETR Small, RF-DETR Large | roboflow/rf-detr |
Repository structure
.
βββ Ultralytics/
β βββ YOLO11m/
β β βββ swimmer_head_detection_yolo11m_exp1.pt
β βββ YOLO26m/
β β βββ swimmer_head_detection_yolo26m_exp2.pt
β β βββ swimmer_head_detection_yolo26m_with_augmentations_exp4.pt
β βββ YOLO26L/
β βββ swimmer_head_detection_yolo26L_exp3.pt
βββ Roboflow/
βββ RF-DETR Small/
β βββ swimmer_head_detection_rfdetr_small_best_ema_exp5.pth
β βββ swimmer_head_detection_rfdetr_small_checkpoint_best_total_exp5.pth
βββ RF-DETR Large/
βββ swimmer_head_detection_rfdetr_large_best_ema_exp6.pth
βββ swimmer_head_detection_rfdetr_large_checkpoint_best_total_exp6.pth
Available models
| Experiment | Model | File | Notes |
|---|---|---|---|
| exp1 | YOLO11m | Ultralytics/YOLO11m/swimmer_head_detection_yolo11m_exp1.pt |
First experiment |
| exp2 | YOLO26m | Ultralytics/YOLO26m/swimmer_head_detection_yolo26m_exp2.pt |
Baseline |
| exp3 | YOLO26L | Ultralytics/YOLO26L/swimmer_head_detection_yolo26L_exp3.pt |
Larger YOLO26 variant |
| exp4 | YOLO26m | Ultralytics/YOLO26m/swimmer_head_detection_yolo26m_with_augmentations_exp4.pt |
YOLO26m (best model out of "exp1" - "exp3"). Trained with geometric augmentations |
| exp5 | RF-DETR Small | Roboflow/RF-DETR Small/..._best_ema_exp5.pth and ..._checkpoint_best_total_exp5.pth |
Best EMA weights / best overall checkpoint |
| exp6 | RF-DETR Large | Roboflow/RF-DETR Large/..._best_ema_exp6.pth and ..._checkpoint_best_total_exp6.pth |
Best EMA weights / best overall checkpoint |
For the RF-DETR models, two checkpoints are provided per experiment: the best EMA weights and the best total checkpoint saved during training.
Task
- Task: object detection
- Class:
face(a single class: the swimmer's head) - Input: RGB video frames of swimmers, recorded on 120fps and 4k resolution; 3840x2160.
- Output: bounding boxes around swimmers' heads with confidence scores
Usage
Ultralytics YOLO
pip install ultralytics huggingface_hub
from huggingface_hub import hf_hub_download
from ultralytics import YOLO
weights = hf_hub_download(
repo_id="UM-SWIM-360/swimmer-head-detection-face-blurring",
filename="Ultralytics/YOLO26m/swimmer_head_detection_yolo26m_with_augmentations_exp4.pt",
)
model = YOLO(weights)
results = model.predict("swimmer.jpg", conf=0.25)
for box in results[0].boxes:
print(box.xyxy, box.conf)
RF-DETR
pip install rfdetr huggingface_hub
from huggingface_hub import hf_hub_download
from rfdetr import RFDETRSmall # or RFDETRLarge for the Large models
from PIL import Image
weights = hf_hub_download(
repo_id="UM-SWIM-360/swimmer-head-detection-face-blurring",
filename="Roboflow/RF-DETR Small/swimmer_head_detection_rfdetr_small_best_ema_exp5.pth",
)
model = RFDETRSmall(pretrain_weights=weights)
detections = model.predict(Image.open("swimmer.jpg"), threshold=0.5)
print(detections.xyxy, detections.confidence)
Example: blur detected heads
import cv2
from ultralytics import YOLO
model = YOLO("swimmer_head_detection_yolo26m_with_augmentations_exp4.pt")
frame = cv2.imread("swimmer.jpg")
for box in model.predict(frame, conf=0.25)[0].boxes.xyxy.int().tolist():
x1, y1, x2, y2 = box
roi = frame[y1:y2, x1:x2]
frame[y1:y2, x1:x2] = cv2.GaussianBlur(roi, (0, 0), sigmaX=15)
cv2.imwrite("swimmer_blurred.jpg", frame)
Training data
Models were trained on video frames with the ground truth located on a swimmer's head. The dataset included frames from the dynamic camera setup and a static camera setup datasets ; frames that do not have a swimmer's head visible are completely discarded.
Evaluation on Test Set
Best model (Based on mAP@50): YOLO26m
Worst model (Based on mAP@50): RF-DETR Small
| Model | Experiment | Precision | Recall | mAP@50 | mAP@50-95 | Inference speed |
|---|---|---|---|---|---|---|
| YOLO11m | exp1 | 0.895 | 0.882 | 0.904 | 0.597 | 49.7 ms (20.1 FPS) |
| YOLO26m | exp2 | 0.895 | 0.880 | 0.912 | 0.607 | 49.0 ms (20.4 FPS) |
| YOLO26L | exp3 | 0.905 | 0.881 | 0.905 | 0.604 | 54.1 ms (18.5 FPS) |
| YOLO26m + augmentations | exp4 | 0.887 | 0.886 | 0.909 | 0.562 | 51.1 ms (19.6 FPS) |
| RF-DETR Small | exp5 | 0.902 | 0.871 | 0.871 | 0.519 | 50.7 ms (19.7 FPS) |
| RF-DETR Large | exp6 | 0.916 | 0.882 | 0.890 | 0.545 | 53.0 ms (18.9 FPS) |
Citation
@misc{swim360facedetectionmodels2026,
author = {Camilleri, Vanessa and Seychell, Dylan and Montebello, Matthew and Azzopardi, Liam and Bartolo, Matthias and Camilleri, Reno Yuri and Pace, Daniel and Fialovszky, Mark and Gineste, Thomas and Scicluna, Justine and Aquilina, Gianluca},
title = {{SWIM-360 Swimmer Head Detection Face Blurring Models}},
year = {2026},
publisher = {Hugging Face},
howpublished = {\url{https://huggingface.co/UM-SWIM-360/swimmer-head-detection-face-blurring}},
note = {Accessed: 2026-09-10}
}
Model tree for UM-SWIM-360/swimmer-head-detection-face-blurring
Base model
Roboflow/rf-detr-large