正在分析视频
AI 正在定位足球和踢球队员
基于 IFAB 足球规则 2025/26

AI 智能假动作检测

上传点球视频,AI 自动识别踢球队员和足球位置,判断是否存在假动作犯规。无需手动标定,拖拽即用。

三步完成假动作识别

无需手动标定门线或框选人员,上传视频即可在 40 秒内得到结果。

第一步:定位足球

YOLO 目标检测模型逐帧搜索足球位置,通过网格聚类算法排除画面边缘的误检,精确定位足球坐标。

🧍

第二步:追踪踢球队员

裁剪放大策略对画面中每个人做姿态估计,每帧独立选取足部离球最近的人作为踢球队员。

第三步:判定假动作

当踢球队员的足部接近球不足 80 像素,而球的位置始终未发生显著移动,即判定为假动作犯规。

拖拽点球视频开始分析

支持 MP4、AVI、MOV、MKV 格式,文件大小不超过 200MB。

📁

拖拽视频文件到此处

或点击选择本地文件

MP4 / AVI / MOV / MKV / WebM(最大 200MB)

技术原理与系统设计

完整的技术架构、算法流程与参数配置说明。

算法流程图

开始用户上传点球视频系统按 1/80 比例抽取视频帧(自动适配 FPS,最多采样 ~80 帧) ↓ 逐帧调用 YOLOv26 双模型 ├── YOLOv26-Detect → 检测足球位置(class=32, sports ball) └── YOLOv26-Pose → 提取人体 17 关键点 ↓ 80px 网格聚类找球,排除边缘误检 ↓ 逐帧裁剪放大 3x → 姿态检测 → 提取脚踝关键点计算足部-足球像素距离 ├── 距离 < 80px → 假动作(摆腿接近但未触球) ├── 距离 80-200px → 接近中 └── 距离 > 200px → 未接近 ↓ 去重(相邻假动作帧 ≤ 5 帧合并为一个事件) ↓ 生成判罚结论 + 标注截图(球 / 足 / 连线 / 距离) ↓ 结束

软件基础设置信息

字段说明
功能名称FeintGuard — AI 假动作检测系统
适用场景足球点球 / 罚球场景中,AI 自动识别踢球人是否做出摆腿假动作(feinting),辅助裁判判罚
开发语言Python 3.12+
核心依赖Flask ultralytics opencv-python numpy Pillow PyYAML
AI 模型YOLOv26-Detect(目标检测,80 类)+ YOLOv26-Pose(17 关键点姿态估计),双模型协同推理
前端技术原生 HTML5 / CSS3 / JavaScript,FeintGuard Unicorn 暗色风格 UI
上传限制MAX_CONTENT_LENGTH = 200MB,支持 MP4 / AVI / MOV / MKV / WebM 格式
任务管理单次请求同步处理(上传 → 抽帧 → 检测 → 判罚 → 截图 → 返回 JSON),前端同步等待结果

软件系统设计

1. 目录结构与路径管理

项目根目录/ ├── 后端/ │ ├── app.py ← Flask 主入口,create_app() 工厂模式 │ ├── config.yaml ← 模型路径 + 假动作阈值参数 │ ├── routes/ │ │ └── analyze.py ← POST /upload_and_analyze 全自动分析 │ ├── services/ │ │ ├── ball_finder.py ← 球检测 + 80px 网格聚类 │ │ ├── kicker_tracker.py← 人体检测 + 裁剪放大 3x + 姿态提取足部 │ │ └── feint_judge.py ← 假动作判定 + 判罚结论 + 截图标注 │ ├── static/weights/ │ │ ├── yolo26n-pose.pt ← 姿态估计模型 (7.8MB) │ │ └── yolo26n.pt ← 目标检测模型 (5.5MB) │ └── data/ │ ├── uploads/ ← 用户上传视频(按 task_id 隔离) │ └── results/ ← 分析结果截图(按 task_id 分子目录) └── 前端/ └── templates/ └── index.html ← FeintGuard 主界面

2. 视频抽帧引擎

基于 OpenCV VideoCapture 实现,自动检测视频 FPS。按 step = total_frames // 80 策略采样,最多处理 ~80 帧。使用 imencode 编码绕过中文路径兼容性问题。原始分辨率不缩放,直接传递 YOLO 模型。

3. YOLOv26 双模型协同检测

Pass 1 — 球检测 + 聚类(services/ball_finder.py)

  • detect_balls(): YOLOv26-Detect 逐帧检测 class=32(sports ball),过滤 conf < 0.2
  • 画面四边 100px margin 内的检测结果直接丢弃(排除边缘误检)
  • find_ball_cluster(): 80px 网格聚类,选最大簇的均值中心作为足球最终位置
  • 排除边缘簇(mean_x < 50 或 > 1230,mean_y < 50 或 > 670)

Pass 2 — 踢球人追踪(services/kicker_tracker.py)

  • detect_persons_with_foot(): YOLOv26-Detect 找 person(class=0, conf ≥ 0.5
  • 每人裁剪放大:margin_x = bbox_w × 2, margin_y_top = bbox_h × 1.5
  • 裁剪区域放大 3 倍(INTER_CUBIC 插值)后送入 YOLOv26-Pose 姿态检测
  • 提取脚踝关键点(R_ankle → L_ankle → R_knee → L_knee 优先级),需 ≥ 5 个关键点置信度 > 0.3
  • collect_kicker_foot_data(): 每帧选足部距球最近的人作为踢球队员(距离 < 300px 才纳入)

4. 假动作判定与容错(services/feint_judge.py)

判定逻辑

  • detect_feints(): 足-球像素距离 < min_dist_threshold(默认 80px)→ 判定为假动作
  • 去重:相邻假动作帧间隔 ≤ 5 帧视为同一事件,合并
  • make_verdict(): 根据检测结果生成四种判罚结论

判罚结论枚举

Verdict含义触发条件
FEINT检测到假动作足-球距离 < 80px, dedup 后 ≥ 1 次
CLEAN正常踢球有采样数据但未触发假动作条件
NO_KICKER未检测到踢球人足-球距离序列为空
NO_APPROACH踢球人未接近球最近距离 > 200px
NO_BALL未检测到足球球检测聚类失败

截图标注

  • 黄圈标注 BALL + 红圈标注 FOOT + 绿线连接 + 距离(px)标注
  • 判罚标签 "FEINT!" 叠加在画面左上角
  • JPEG quality=85,通过 Pillow 保存,绕过 OpenCV 中文路径问题

5. 字段映射与容错

API 响应 JSON 中内置多种容错处理:

  • 球位置为 None → 返回 NO_BALL 判罚而非崩溃
  • 姿态检测无有效关键点 → 该帧跳过踢球人追踪
  • 所有异常被 try/except 捕获,返回 {"error": "..."} 而非 500
  • 前端 showErr() 函数在分析失败时恢复页面操作区,不会卡死在 loading 状态

参数配置

配置文件 config.yaml,位于 后端/ 目录下,启动时由 create_app() 读取。

models.pose
static/weights/yolo26n-pose.pt
YOLOv26 姿态估计模型,输出 17 关键点(COCO 格式)
models.detect
static/weights/yolo26n.pt
YOLOv26 目标检测模型,输出 80 类目标(class=32 为球)
feint.foot_ball_threshold_px
80
假动作判定阈值(像素)。1280×720 画面中约等于画面宽度的 6.25%
feint.ball_cluster_grid_size
80
球位置聚类网格大小(像素),越大去噪效果越强
feint.ball_edge_margin
100
画面四边排除宽度(像素),过滤边框误检球
feint.sampling_step_divisor
80
采样密度控制,步长 = 总帧数 / 80,最多 ~80 帧采样
feint.dedup_frame_gap
5
假动作去重窗口(帧),间隔 ≤ 5 帧的事件合并为一个

核心模块说明

球检测模块(services/ball_finder.py)

BALL_CLASS=32。每帧 YOLOv26-Detect 推理 → 过滤 conf≥0.2 且位于 margin 内的检测 → 80px 网格聚类 → 取最大簇均值作为足球最终位置。返回 (mean_cx, mean_cy, cluster_size) 或 None。

踢球人追踪模块(services/kicker_tracker.py)

对 YOLOv26-Detect 找到的每个 person(conf≥0.5)做裁剪放大→3x 放大→YOLOv26-Pose 姿态检测→提取脚踝关键点。每帧选足部距球最近者。关键点优先级: R_ankle(16) → L_ankle(15) → R_knee(14) → L_knee(13)。需 ≥5 个关键点置信度 > 0.3 才采用。最终收集足-球距离时间序列。

假动作判定模块(services/feint_judge.py)

detect_feints() 遍历足-球距离序列,距离 < 80px 标记为假动作,5 帧窗口去重。make_verdict() 根据 feint 数量 / 有无采样 / 最近距离生成 FEINT / CLEAN / NO_KICKER / NO_APPROACH 判罚。generate_screenshots() 在原始帧上绘制球(黄圈)、足(红圈)、连线(绿线)、距离标注、判罚标签,JPEG 压缩后返回 URL 列表。

模块依赖关系

app.py (Flask 入口, create_app 工厂) ├── config.yaml ────────────────────── 模型路径 + 阈值参数 ├── static/weights/yolo26n.pt ──────── YOLO Detect 模型 ├── static/weights/yolo26n-pose.pt ─── YOLO Pose 模型 └── routes/analyze.py (Blueprint: /upload_and_analyze) ├── services/ball_finder.py │ ├── detect_balls() 逐帧检测 class=32 球 │ └── find_ball_cluster() 80px 网格聚类定位 ├── services/kicker_tracker.py │ ├── detect_persons_with_foot() 裁剪放大 3x + 姿态提取 │ └── collect_kicker_foot_data() 足-球距离时间序列 └── services/feint_judge.py ├── detect_feints() 距离 < 80px 判定 ├── make_verdict() 生成判罚结论 └── generate_screenshots() 标注截图输出

学术支撑

本文系统引用以下学术成果与技术标准。

[1] IFAB (2025)
Laws of the Game 2025/26, Law 14: The Penalty Kick. 国际足球协会理事会官方规则,定义假动作犯规与守门员站位要求。
[2] Jocher et al. (2024)
Ultralytics YOLOv8: State-of-the-Art Object Detection and Image Segmentation. 本项目使用的目标检测与姿态估计核心框架。
[3] Cioppa et al. (2022)
SoccerNet: Action Spotting in Soccer Videos. arXiv:2211.04134. 足球视频动作时序检测方法,踢球时刻检测的方法论基础。
[4] Giancola et al. (2023)
SoccerNet 2023: Pose, Action, and Re-identification. arXiv:2304.03447. 足球场景姿态估计基线,人体关键点检测参考。
[5] Akyon et al. (2022)
SAHI: Slicing Aided Hyper Inference for Small Object Detection. IEEE ICIP 2022. 大图切片推理方法,本项目裁剪放大策略的理论依据。
[6] Deliege et al. (2024)
SoccerNet Challenge 2024: Broadcast Video Understanding. arXiv:2406.04265. 广播视频中的足球犯规检测技术参考。