首页
学习
活动
专区
圈层
工具
发布
社区首页 >专栏 >【一步步开发AI运动APP】十二、自定义扩展新运动项目2

【一步步开发AI运动APP】十二、自定义扩展新运动项目2

原创
作者头像
alphaair
发布2025-10-09 09:07:54
发布2025-10-09 09:07:54
1060
举报

之前我们为您分享了【一步步开发AI运动小程序】开发系列博文,通过该系列博文,很多开发者开发出了很多精美的AI健身、线上运动赛事、AI学生体测、美体、康复锻炼等应用场景的AI运动小程序;为了帮助开发者继续深耕AI运动领域市场,今天开始我们将为您分享新系列【一步步开发AI运动APP】的博文,带您开发性能更强、体验更好的AI运动APP。

上一篇为您介绍了uni-app版运动识别插件的自定义扩展运动的基本架构、与小程序版运动识别插件的运动扩展差异,本篇我们就以双手并举为例带你来实现一个扩展运动。

一、动作姿态拆解

如上图所示,这个运动主要为手部摆动动,包含2个分动作姿态,起始动作姿态1为双手垂放于左右两侧站立,结束动作姿态2双手举过头顶撑直为结束动作,完成动作2时计数加一,如此反复运动。

二、定义运动检测规则

接下来我们为这两个拆解姿态分别构建检测规则,检测规则及自定义姿态的检测可以参考本系列博文的前面章节及插件的pose-calc指南文档。

  • 先构建动作姿态1手垂于两侧并站立的动作的检测规则: { name: '双手下垂', calc: '$and', rules: [{ name: '站立姿态', calc: 'stand', offset: 25 }, { name: '左腋夹角', calc: 'match-angle', angleKey: 'left_shoulder', secondKey: 'left_hip', thirdKey: 'left_wrist', angle: 30, offset: 30 }, { name: '左手下垂', calc: 'vertical', upperKey: 'left_shoulder', centerKey: 'left_elbow', lowerKey: 'left_wrist', offset: 25 }, { name: '右腋夹角', calc: 'match-angle', angleKey: 'right_shoulder', secondKey: 'right_hip', thirdKey: 'right_wrist', angle: 30, offset: 30 }, { name: '右手下垂', calc: 'vertical', upperKey: 'right_shoulder', centerKey: 'right_elbow', lowerKey: 'right_wrist', offset: 25 }] }
  • 再构建动作姿态2双手举过头顶伸直站立的检测规则:{ name: '双手上举', calc: '$and', rules: [{ name: '左手上举', calc: 'position', referenceKey: 'left_eye', positionKey: 'left_wrist', position: 'top', relaxed: true }, { name: '右手上举', calc: 'position', referenceKey: 'right_eye', positionKey: 'right_wrist', position: 'top', relaxed: true }] }
三、实现运动分析器

定义好动作姿态检测规则后,我们便可以实现此扩展运动的运动分析器了,完整代码如下:

代码语言:javascript
复制
/**
 * 双手并举运动分析器
 */
export class BothHandsUpSport {

	context = null;
	calculator = null; //ICalculator
	stateTran = -1;

	/**
	 * 初始化运动分析器
	 */
	constructor() {
		this.calculator = createCalculator();

		this.buildRules();
		const that = this;
		this.context = createExtendSportContext({
			key: 'both-hands-up',
			name: '自定义-双手并举',
			tickMode: true,
			view: 'front_back',
			start: () => that.start(),
			// reset: this.reset,
			// stop: this.stop,
			pushing: human => that.pushing(human)
		});
	}

	buildRules() {
		this.rules = {};
		this.rules.ups = {
			name: '双手上举',
			calc: '$and',
			rules: [{
				name: '左手上举',
				calc: 'position',
				referenceKey: 'left_eye',
				positionKey: 'left_wrist',
				position: 'top',
				relaxed: true
			}, {
				name: '右手上举',
				calc: 'position',
				referenceKey: 'right_eye',
				positionKey: 'right_wrist',
				position: 'top',
				relaxed: true
			}]
		};

		this.rules.downs = {
			name: '双手下垂',
			calc: '$and',
			rules: [{
				name: '站立姿态',
				calc: 'stand',
				offset: 25
			}, {
				name: '左腋夹角',
				calc: 'match-angle',
				angleKey: 'left_shoulder',
				secondKey: 'left_hip',
				thirdKey: 'left_wrist',
				angle: 30,
				offset: 30
			}, {
				name: '左手下垂',
				calc: 'vertical',
				upperKey: 'left_shoulder',
				centerKey: 'left_elbow',
				lowerKey: 'left_wrist',
				offset: 25
			}, {
				name: '右腋夹角',
				calc: 'match-angle',
				angleKey: 'right_shoulder',
				secondKey: 'right_hip',
				thirdKey: 'right_wrist',
				angle: 30,
				offset: 30
			}, {
				name: '右手下垂',
				calc: 'vertical',
				upperKey: 'right_shoulder',
				centerKey: 'right_elbow',
				lowerKey: 'right_wrist',
				offset: 25
			}]
		};
	}

	start() {
		this.stateTran = -1;
		console.log('运动启动', this);
	}

	pushing(fragment) {

		if (fragment.isNobody) {
			console.log('未识别到人体');
			return;
		}

		const human = fragment.human;
		if (this.stateTran != 1 && this.calculator.calculating(human, this.rules.downs)) {
			this.stateTran = 1;
			return;
		}

		if (this.stateTran == 1 && this.calculator.calculating(human, this.rules.ups)) {
			this.stateTran = 2;
			this.context.countTimes();
			this.context.emitTick(1);
		}
	}

	/**
	 * 获取当前扩展运动的原生分析器实例
	 * @returns 原生运动分析器实例
	 */
	getSportInstance() {
		return this.context.getSport();
	}

	/**
	 * 获取当前扩展运动描述
	 * 
	 * @returns  运动描述条目实例
	 */
	static getDescriptor() {
		let item = {
			key: 'both-hands-up',
			name: '自定义-双手并举'
		};

		return item;
	}
}

好了,本节就为您介绍到这,下一节我们将为您介绍将实现的自定义扩展运动列表的维护,敬请期待...

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

原创声明:本文系作者授权腾讯云开发者社区发表,未经许可,不得转载。

如有侵权,请联系 cloudcommunity@tencent.com 删除。

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 一、动作姿态拆解
  • 二、定义运动检测规则
  • 三、实现运动分析器
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档