MediaPipe手势识别快速入门:Flask后端API服务搭建与测试

张开发
2026/4/15 7:01:19 15 分钟阅读

分享文章

MediaPipe手势识别快速入门:Flask后端API服务搭建与测试
MediaPipe手势识别快速入门Flask后端API服务搭建与测试1. 项目概述1.1 技术背景MediaPipe Hands是Google开发的高精度手部关键点检测模型能够从RGB图像中实时定位21个3D关键点。本教程将展示如何基于该模型构建一个完整的Flask后端服务提供手势识别API接口。1.2 核心功能支持单/双手21个3D关键点检测创新的彩虹骨骼可视化每根手指不同颜色提供RESTful API接口纯CPU运行无需GPU支持1.3 适用场景人机交互应用虚拟现实控制智能家居手势控制教育领域的互动教学2. 环境准备2.1 系统要求Python 3.7支持的操作系统Windows/Linux/macOS内存建议4GB以上存储空间500MB可用空间2.2 依赖安装创建并激活Python虚拟环境python -m venv venv source venv/bin/activate # Linux/macOS venv\Scripts\activate # Windows安装所需依赖pip install flask2.3.3 opencv-python4.8.0.74 mediapipe0.10.9 numpy1.24.33. 核心代码实现3.1 项目结构hand_tracking_api/ ├── app.py ├── utils/ │ └── hand_tracker.py ├── static/ │ └── uploads/ └── templates/ └── index.html3.2 手势识别模块utils/hand_tracker.py实现核心识别逻辑import cv2 import mediapipe as mp import numpy as np class HandTracker: def __init__(self): self.mp_hands mp.solutions.hands self.hands self.mp_hands.Hands( static_image_modeTrue, max_num_hands2, min_detection_confidence0.6 ) # 手指颜色定义(BGR格式) self.finger_colors [ (0, 255, 255), # 拇指(黄色) (128, 0, 128), # 食指(紫色) (255, 255, 0), # 中指(青色) (0, 255, 0), # 无名指(绿色) (0, 0, 255) # 小指(红色) ] # 手指关键点范围 self.finger_segments [(1,4), (5,8), (9,12), (13,16), (17,20)] def draw_rainbow_skeleton(self, image, landmarks): h, w image.shape[:2] points [(int(lm.x*w), int(lm.y*h)) for lm in landmarks] # 绘制白色关节点 for pt in points: cv2.circle(image, pt, 5, (255,255,255), -1) # 绘制彩色骨骼线 for idx, (start, end) in enumerate(self.finger_segments): color self.finger_colors[idx] for i in range(start, end): cv2.line(image, points[i], points[i1], color, 2) return image def process_image(self, image_path): image cv2.imread(image_path) if image is None: return {error: 无法读取图像} rgb_image cv2.cvtColor(image, cv2.COLOR_BGR2RGB) results self.hands.process(rgb_image) if not results.multi_hand_landmarks: return {landmarks: [], message: 未检测到手部} output_image image.copy() all_landmarks [] for hand_landmarks in results.multi_hand_landmarks: landmarks [{x: lm.x, y: lm.y, z: lm.z} for lm in hand_landmarks.landmark] all_landmarks.append(landmarks) output_image self.draw_rainbow_skeleton( output_image, hand_landmarks.landmark) output_path image_path.replace(uploads/, uploads/result_) cv2.imwrite(output_path, output_image) return { landmarks: all_landmarks, result_image: output_path, hand_count: len(all_landmarks) }3.3 Flask应用实现app.py主程序代码from flask import Flask, request, jsonify, send_file import os from utils.hand_tracker import HandTracker app Flask(__name__) tracker HandTracker() UPLOAD_FOLDER static/uploads os.makedirs(UPLOAD_FOLDER, exist_okTrue) app.config[UPLOAD_FOLDER] UPLOAD_FOLDER app.route(/api/track, methods[POST]) def track_hand(): if file not in request.files: return jsonify({error: 缺少文件字段}), 400 file request.files[file] if not file.filename: return jsonify({error: 未选择文件}), 400 if file: filename file.filename filepath os.path.join(app.config[UPLOAD_FOLDER], filename) file.save(filepath) try: result tracker.process_image(filepath) if error in result: return jsonify(result), 400 return jsonify(result) except Exception as e: return jsonify({error: str(e)}), 500 app.route(/result/filename) def get_result_image(filename): return send_file(fstatic/uploads/{filename}) if __name__ __main__: app.run(host0.0.0.0, port5000)4. 服务部署与测试4.1 启动服务python app.py服务将在http://localhost:5000启动4.2 API接口测试使用curl测试APIcurl -X POST -F filetest.jpg http://localhost:5000/api/track成功响应示例{ hand_count: 1, landmarks: [ [ {x: 0.52, y: 0.61, z: -0.03}, {x: 0.48, y: 0.59, z: -0.02}, ... ] ], result_image: static/uploads/result_test.jpg }4.3 Web界面测试创建templates/index.html简单测试页面!DOCTYPE html html headtitle手势识别测试/title/head body h2上传手部图片/h2 form action/api/track methodpost enctypemultipart/form-data input typefile namefile acceptimage/* required button typesubmit分析手势/button /form /body /html访问http://localhost:5000即可使用Web界面测试5. 生产环境建议5.1 性能优化图像预处理调整输入图像大小至640x480批处理支持同时处理多张图片缓存机制缓存常用手势检测结果5.2 安全增强# 在app.py中添加文件校验 ALLOWED_EXTENSIONS {png, jpg, jpeg} def allowed_file(filename): return . in filename and \ filename.rsplit(., 1)[1].lower() in ALLOWED_EXTENSIONS # 修改上传处理 if file and allowed_file(file.filename): # 处理文件 else: return jsonify({error: 文件类型不支持}), 4005.3 部署选项使用Gunicorn或uWSGI部署配置Nginx反向代理容器化部署(Docker)6. 总结6.1 关键要点回顾本教程实现了基于MediaPipe Hands的高精度手势识别创新的彩虹骨骼可视化完整的Flask REST API服务简单易用的Web测试界面6.2 扩展方向添加手势分类功能支持视频流处理开发移动端应用集成到智能家居系统获取更多AI镜像想探索更多AI镜像和应用场景访问 CSDN星图镜像广场提供丰富的预置镜像覆盖大模型推理、图像生成、视频生成、模型微调等多个领域支持一键部署。

更多文章