调用电脑前置摄像头,本地实时监测坐姿与久坐时长,提醒你保持良好姿势、及时起身活动。
长期伏案工作 / 学习时,我们很难察觉自己逐渐前倾、低头或连续几小时不动。青松坐姿 PinEase 打开电脑前置摄像头,在浏览器本地(无需后端、无需上传画面)完成:
- 姿势监测:实时检测低头前倾、身体前倾、身体侧倾三类不良坐姿,画面上叠加人体关键点骨架;
- 姿势提醒:判定为不良姿势时,通过提示音、系统桌面通知、页面弹窗提醒你调整;
- 久坐提醒:检测到你在座位上即开始计时,连续坐满设定时长(默认 45 分钟)提醒起身活动;
- 统计回顾:按天累计坐姿时长、良好占比与提醒次数,展示近 7 天趋势图。
当前版本是前端实现;后端由使用者自行接入(见下方接口约定),前端已预留上报开关,默认关闭、数据不出本机。
| 模块 | 功能说明 | 状态 |
|---|---|---|
| 监督模式 | 休闲 / 严格 / 康复三档预设,一键切换提醒强度,可再手动微调 | 已实现 |
| 实时监测 | 摄像头采集 + 本地关键点检测 + 骨架叠加 + 实时角度展示 | 已实现 |
| 姿势提醒 | 低头 / 前倾 / 侧倾判定(连续帧去抖),声音 + 通知 + 弹窗 | 已实现 |
| 久坐提醒 | 坐姿计时、到点提醒、剩余时间环形进度 | 已实现 |
| 眨眼提醒 | 定时(10/15/20/30 分)提醒眨眼与远眺,保护眼睛 | 已实现 |
| 统计回顾 | 今日概览 + 近 7 天坐姿/良好时长与提醒次数趋势图 | 已实现 |
| 设置 | 提醒间隔、开关、灵敏度阈值、摄像头选择、后端上报地址(预留) | 已实现 |
| 后端上报 | POST {baseUrl}/api/stats 每日统计(默认关闭) |
预留 |
本项目不是医疗器械,也不提供任何医学诊断。角度判定基于 2D 投影近似,仅用于日常姿势习惯提醒与健康教育。如有长期疼痛或明显体态异常,请及时前往正规医疗机构检查,并以医生意见为准。
- React 19 + TypeScript + Vite
- Tailwind CSS 4
- MediaPipe Tasks Vision(PoseLandmarker):浏览器本地人体关键点检测,无需后端
- Recharts:统计趋势图
- Lucide React:图标
npm install
npm run dev
# http://localhost:3003
npm run build
# 生产构建
npm run preview
# 构建产物本地预览:http://localhost:3004
npm run lint # tsc --noEmit 类型检查
⚠️ 注意:上面代码块里的#是 bash 注释。不要把注释写进package.json的scripts里(例如"build": "vite build # 生产构建")——Windows 下 npm 用 cmd 执行脚本,#不是注释而是参数,会导致 Vite 报错(如 "Could not resolve entry module '#/index.html'")。
- 点击「开始监测」,允许摄像头权限(首次还会询问是否允许桌面通知);
- 无需联网:人体模型已随仓库打包,wasm 由
predev/prebuild自动从 node_modules 复制到本地; - 坐回电脑前,调整摄像头角度让上半身完整入画;
- 保持好姿势即可;收到姿势 / 久坐提醒时调整坐姿或起身活动;
- 若判定不准,到「设置 → 姿势判定灵敏度」调整角度阈值,并参考监测页左下角的实时角度数值。
.
├── public/ # 静态资源与 PWA 配置
├── src/
│ ├── config.ts # 品牌名 / 模型地址 / 默认设置 / 后端配置(集中在此)
│ ├── types.ts # 姿势状态、统计等类型定义
│ ├── lib/
│ │ ├── camera.ts # 摄像头枚举与启停
│ │ ├── pose.ts # MediaPipe 模型加载、关键点检测、骨架绘制
│ │ ├── posture.ts # 角度计算与姿势判定(核心算法)
│ │ ├── reminder.ts # 提示音(Web Audio)与桌面通知
│ │ ├── stats.ts # 按天统计的 localStorage 存储
│ │ └── api.ts # 后端上报接口(预留)
│ ├── hooks/
│ │ └── usePostureMonitor.ts # 监测循环:摄像头 + 检测 + 状态机 + 计时 + 提醒
│ └── pages/
│ ├── Monitor.tsx # 主监测页(摄像头画面 + 实时状态 + 久坐计时)
│ ├── Stats.tsx # 统计趋势
│ ├── Settings.tsx # 提醒 / 灵敏度 / 摄像头 / 后端配置
│ └── About.tsx # 原理、隐私与免责声明
├── index.html
└── README.md
基于 MediaPipe 33 个人体关键点,取耳、肩、髋三组关键点计算三个角度:
| 特征 | 计算方式 | 默认阈值(可调) |
|---|---|---|
| 头部角 | 耳→肩连线偏离竖直方向的角度 | 38° |
| 躯干角 | 肩→髋连线偏离竖直方向的角度 | 15° |
| 侧倾角 | 双肩连线偏离水平方向的角度 | 10° |
超过阈值后,再借助关键点的深度(z)区分方向:头部/肩膀比基准点更靠近摄像头判为低头/前倾,更远判为仰头/后仰;深度差太小时方向不可判,按前向处理以免漏提醒。
连续 6 帧判定一致才切换状态(抑制抖动);同一不良状态在冷却期(默认 60 秒)内不重复提醒。
前端默认不上报任何数据。在「设置 → 后端上报」中开启并填写地址后,前端会每 5 秒发送一次当日统计快照:
POST {baseUrl}/api/stats
Content-Type: application/json
{
"app": "pinease",
"date": "2026-01-01", // 本地时区日期
"stats": { "sitSeconds": 3600, "goodSeconds": 2400, "postureAlerts": 5, "sitAlerts": 1 },
"clientTime": "2026-01-01T10:00:00.000Z"
}后端未就绪或请求失败时前端自动跳过,不影响本地功能。实现你自己的后端时,只需按此契约接收即可(也可自行扩展,如拉取提醒参数下发)。
- 摄像头画面与检测数据只在本机内存与 localStorage 中处理,默认不发送任何网络请求;
- MediaPipe 的 wasm 与人体模型均本地打包(
public/vendor/),运行无需联网; - 关闭监测或离开页面即释放摄像头;
- 本仓库不含任何个人数据采集逻辑。
本项目许可证沿用 Apache-2.0(见源码头部声明)。欢迎 fork、修改与贡献。