| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250 | 
							- import o0 from "./o0.js"
 
- module.exports = {
 
- 	SandbagAlgorithm: class {
 
- 		constructor(option) {
 
- 			let {
 
- 				frameHitCapacity,
 
- 				slopeArr
 
- 			} = option;
 
- 			this.stableAcc = new o0.Vector2(0, 0);
 
- 			this.stableGyr = new o0.Vector2(0, 0);
 
- 			this.stableCount = 0;
 
- 			this.stableCountMax = 3000;
 
- 			this.frameCapacity = 6;
 
- 			this.frame = [];
 
- 			this.frameLength = 5;
 
- 			this.frameOffset = 0;
 
- 			// this.frameHitCapacity = 11;
 
- 			this.frameHitCapacity = frameHitCapacity;
 
- 			this.slopeArr = slopeArr;
 
- 			console.log("init frameHitCapacity:" + this.frameHitCapacity + ",slopeArr:" + this
 
- 				.slopeArr);
 
- 			this.frameHit = []; //打击后的n帧
 
- 			for (var i = 0; i < this.frameCapacity; ++i) {
 
- 				var o = new Object();
 
- 				o.acc = new o0.Vector2(0, 0);
 
- 				o.gyr = new o0.Vector2(0, 0);
 
- 				o.timeGap = 20;
 
- 				o.accFixed = 0;
 
- 				o.accSlope = 0;
 
- 				o.pos = new o0.Vector2(0, 0);
 
- 				o.predict = new o0.Vector2(0, 0);
 
- 				o.shake = 0;
 
- 				o.shakeFixed = 0;
 
- 				o.shakeSlope = 0;
 
- 				o.hit = 0;
 
- 				this.frame.push(o);
 
- 			}
 
- 			this.quitHitCount = 0;
 
- 		}
 
- 		//这个函数不建议外部调用
 
- 		GetDirection() {
 
- 			var direction = new o0.Vector2(0, 0);
 
- 			var directionDistance = 0.0;
 
- 			for (var fi = 0; fi < this.frameHit.length - 1; ++fi) {
 
- 				for (var li = fi + 1; li < this.frameHit.length; ++li) {
 
- 					var newDirection = this.frameHit[li].gyr.minus(this.frameHit[fi].gyr);
 
- 					var newDirectionDistance = newDirection.length;
 
- 					if (directionDistance < newDirectionDistance) {
 
- 						directionDistance = newDirectionDistance;
 
- 						direction = newDirection.multiply(this.frameHit[this.frameHit.length - 1].time -
 
- 							this.frameHit[0].time);
 
- 					} else {
 
- 						//cout << "false" << endl;
 
- 					}
 
- 				}
 
- 			}
 
- 			return direction;
 
- 		}
 
- 		// 输入俯视的平面坐标系下的xy轴坐标 的 加速计向量/陀螺仪向量。
 
- 		// timeGap 代表当前帧读取传感器与上一帧读取传感器 之间的时间差
 
- 		Update(accX, accY, gyrX, gyrY, timeGap) {
 
- 			var rawAcc = new o0.Vector2(accX, accY);
 
- 			var rawGyr = new o0.Vector2(gyrX, gyrY);
 
- 			let lastFrame = this.frame[(this.frameOffset + this.frameLength - 1) % this.frameCapacity];
 
- 			let last2Frame = this.frame[(this.frameOffset + this.frameLength - 2) % this.frameCapacity];
 
- 			let last3Frame = this.frame[(this.frameOffset + this.frameLength - 3) % this.frameCapacity];
 
- 			let last4Frame = this.frame[(this.frameOffset + this.frameLength - 4) % this.frameCapacity];
 
- 			let last5Frame = this.frame[(this.frameOffset + this.frameLength - 5) % this.frameCapacity];
 
- 			var newFrame = this.frame[(this.frameOffset + this.frameLength) % this.frameCapacity];
 
- 			newFrame.timeGap = timeGap;
 
- 			newFrame.acc = rawAcc.minus(this.stableAcc);
 
- 			newFrame.gyr = rawGyr.minus(this.stableGyr);
 
- 			if (this.stableCount < this.stableCountMax) {
 
- 				this.stableCount += 1;
 
- 			}
 
- 			this.stableAcc = this.stableAcc.multiply((this.stableCount - 1.0) / this.stableCount).plus(
 
- 				rawAcc.multiply(1 / this.stableCount));
 
- 			this.stableGyr = this.stableGyr.multiply((this.stableCount - 1.0) / this.stableCount).plus(
 
- 				rawGyr.multiply(1 / this.stableCount));
 
- 			//////////////////////////////////////////////////////////////////////////////////
 
- 			newFrame.accFixed = newFrame.acc.length * 100;
 
- 			if (newFrame.accFixed < lastFrame.accFixed * 0.85) {
 
- 				newFrame.accFixed = lastFrame.accFixed * 0.85;
 
- 			}
 
- 			lastFrame.accFixed = Math.max(lastFrame.accFixed, Math.min(newFrame.accFixed, last2Frame
 
- 				.accFixed), Math.min(newFrame.accFixed, last3Frame.accFixed));
 
- 			///////////////////////////////////////////////////////////////////////
 
- 			//newFrame.pos = lastFrame.pos.plus(lastFrame.acc.plus(newFrame.acc).multiply(timeGap/60)).multiply(Math.max(1-timeGap/200,0));
 
- 			newFrame.pos = lastFrame.pos.plus(newFrame.acc.multiply(timeGap / 30)).multiply(Math.max(1 -
 
- 				timeGap / 1000, 0));
 
- 			////////////////////////////////////////////
 
- 			newFrame.accSlope = Math.max(newFrame.accFixed - lastFrame.accFixed, 0);
 
- 			var lastI = this.frame.length - 1;
 
- 			var t2 = this.frame[lastI - 1].timeGap;
 
- 			var t3 = this.frame[lastI].timeGap + t2;
 
- 			var t4 = newFrame.timeGap + t3;
 
- 			newFrame.predict = new o0.Vector2(
 
- 				new o0.QuadraticEquation(0, this.frame[lastI - 2].pos.x, t2, this.frame[lastI - 1].pos
 
- 					.x, t3, this.frame[lastI].pos.x).y(t4),
 
- 				new o0.QuadraticEquation(0, this.frame[lastI - 2].pos.y, t2, this.frame[lastI - 1].pos
 
- 					.y, t3, this.frame[lastI].pos.y).y(t4)); /** */
 
- 			newFrame.shake = o0.distance2(newFrame.predict, newFrame.pos) * 100;
 
- 			if (isNaN(newFrame.shake)) {
 
- 				newFrame.shake = 0.0;
 
- 			}
 
- 			newFrame.shakeFixed = lastFrame.shakeFixed * 0.85;
 
- 			if (newFrame.shake > newFrame.shakeFixed) {
 
- 				newFrame.shakeFixed = newFrame.shake;
 
- 			} /* */
 
- 			lastFrame.shakeFixed = Math.max(lastFrame.shakeFixed, Math.min(newFrame.shakeFixed, last2Frame
 
- 				.shakeFixed), Math.min(newFrame.shakeFixed, last3Frame.shakeFixed));
 
- 			////////////////////////////////////////////////////////////////
 
- 			newFrame.shakeSlope = Math.max(newFrame.shakeFixed - lastFrame.shakeFixed, 0);
 
- 			///////////////////////////////////////////////////////////////
 
- 			var direction = undefined;
 
- 			//15 20 20 40 , 13 17 17 35
 
- 			// let slopeArr = [15, 20, 20, 40];
 
- 			// let slopeArr = this.slopeArr;// [13, 17, 17, 35];
 
- 			if (lastFrame.hit == 0 &&
 
- 				last2Frame.hit == 0 &&
 
- 				last3Frame.hit == 0 &&
 
- 				last4Frame.hit == 0 &&
 
- 				last5Frame.hit == 0 &&
 
- 				(newFrame.accSlope >= this.slopeArr[0] || lastFrame.accSlope >= this.slopeArr[1]) &&
 
- 				(newFrame.shakeSlope >= this.slopeArr[2] || lastFrame.shakeSlope >= this.slopeArr[3])) {
 
- 				newFrame.hit = 1;
 
- 				if (this.frameHit.length < this.frameHitCapacity && this.frameHit.length !=
 
- 					0) { //判断到第二次hit,但还未输出第一次hit的方向,强制输出方向
 
- 					direction = this.GetDirection();
 
- 				} /**/
 
- 				this.frameHit = [];
 
- 				/*
 
- 				var o3 = new Object();
 
- 				o3.time = 0;
 
- 				o3.gyr = lastFrame3.gyr;
 
- 				this.frameHit.push(o3);/* */
 
- 				var o2 = new Object();
 
- 				o2.time = last2Frame.timeGap;
 
- 				o2.gyr = last2Frame.gyr;
 
- 				this.frameHit.push(o2);
 
- 				var o = new Object();
 
- 				o.time = last2Frame.timeGap + lastFrame.timeGap;
 
- 				o.gyr = lastFrame.gyr;
 
- 				this.frameHit.push(o);
 
- 			} else {
 
- 				newFrame.hit = 0;
 
- 			}
 
- 			if (this.frameHit.length < this.frameHitCapacity && this.frameHit.length != 0) {
 
- 				var o = new Object();
 
- 				o.time = this.frameHit[this.frameHit.length - 1].time + newFrame.timeGap;
 
- 				//o.gyr = this.frameHit[this.frameHit.length-1].gyr.plus(newFrame.gyr);
 
- 				o.gyr = newFrame.gyr;
 
- 				this.frameHit.push(o);
 
- 				if (this.frameHit.length == this.frameHitCapacity) { //累计达到设定的延迟帧数,输出方向
 
- 					direction = this.GetDirection();
 
- 				}
 
- 			}
 
- 			if ((this.frameOffset += 1) >= this.frameCapacity) {
 
- 				this.frameOffset -= this.frameCapacity;
 
- 			}
 
- 			return [newFrame.hit, direction];
 
- 		}
 
- 		getTempValue(curDirection) {
 
- 			let result = Math.atan2(curDirection.y, curDirection.x) * 180 / (Math.PI);
 
- 			result = Math.round(result);
 
- 			let curAngle = result > 0 ? result : (360 + result);
 
- 			let directionPunch = "all",
 
- 				name = "击中",
 
- 				ename = "hit";
 
- 			let positiveMidSlope = [70, 110]; //min max
 
- 			let negativeMidSlope = [250, 290]; //min max
 
- 			if (curAngle < positiveMidSlope[1] && curAngle >= positiveMidSlope[0]) {
 
- 				directionPunch = "straightPunch";
 
- 				name = "正向的直拳";
 
- 				ename = "front-straight";
 
- 			} else if (curAngle < positiveMidSlope[0] && curAngle >= 0) {
 
- 				directionPunch = "rightPunch";
 
- 				name = "正向的右拳";
 
- 				ename = "front-right";
 
- 			} else if (curAngle <= 180 && curAngle >= positiveMidSlope[1]) {
 
- 				directionPunch = "leftPunch";
 
- 				name = "正向的左拳";
 
- 				ename = "front-left";
 
- 			}
 
- 			//相反方向击打
 
- 			//正方向
 
- 			else if (curAngle <= negativeMidSlope[1] && curAngle > negativeMidSlope[0]) {
 
- 				directionPunch = "straightPunch";
 
- 				name = "负向的直拳";
 
- 				ename = "back-straight";
 
- 			} else if (curAngle <= negativeMidSlope[0] && curAngle > 180) {
 
- 				directionPunch = "rightPunch";
 
- 				name = "负向的右拳";
 
- 				ename = "back-right";
 
- 			} else if (curAngle <= 360 && curAngle > negativeMidSlope[1]) {
 
- 				directionPunch = "leftPunch";
 
- 				name = "负向的左拳";
 
- 				ename = "back-left";
 
- 			}
 
- 			this.quitHitCount++;
 
- 			let temp = {
 
- 				type: 'hit',
 
- 				hit: curDirection.length,
 
- 				hitCount: this.quitHitCount,
 
- 				direction: directionPunch,
 
- 				directionVect: {
 
- 					'x': curDirection.x,
 
- 					'y': curDirection.y
 
- 				},
 
- 				angle: curAngle,
 
- 				name: name,
 
- 				ename: ename
 
- 			}
 
- 			return temp;
 
- 		}
 
- 	}
 
- };
 
 
  |