import createjs from "./createjs-2015.11.26.combined"; import Matter from "matter-js"; function rule(t, e) { return !!( [0, 1, 2, 3, 4, 5, 6].includes(t) && ((e %= 180), e < 0 && (e += 180), (e >= 0 && e <= 65) || (e >= 115 && e <= 180)) ); } function segmentsIntr(t, e, i, r) { var n = (t.x - i.x) * (e.y - i.y) - (t.y - i.y) * (e.x - i.x), s = (t.x - r.x) * (e.y - r.y) - (t.y - r.y) * (e.x - r.x); if (n * s >= 0) return !1; var a = (i.x - t.x) * (r.y - t.y) - (i.y - t.y) * (r.x - t.x), o = a + n - s; return !(a * o >= 0); } function stopUnusual(t, e, i, r) { var n = 1e-4; return Math.abs(t) <= n && Math.abs(e) <= n; } export default class Ring { constructor(x, y, r, id, waterful) { this.active = true; this.color = id.replace("ring_", ""); this.r = r; const sprite = new createjs.SpriteSheet({ images: [waterful._queue.getResult(id)], frames: { width: 62, height: 62 }, animations: { normal: { frames: [ 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 10, 9, 8, 7, 6, 5, 4, 3, 2, 1, 0, ], speed: 0.3, }, prepare: { frames: [0, 1, 2, 3, 4, 5, 6, 5, 4, 3, 2, 1, 0], speed: 0.1, }, }, }); this.texture = new createjs.Sprite(sprite, "normal"); const bounds = this.texture.getBounds(); this.texture.regX = bounds.width / 2; this.texture.regY = bounds.height / 2; this.texture.stop(); this.texture.x = x; this.texture.y = y; this.texture.scaleX = (r * 2) / bounds.width; this.texture.scaleY = (r * 2) / bounds.height; this.texture.on("animationend", function (e) { var target = e.currentTarget; target.y < 528 ? e.target.gotoAndPlay("prepare") : e.target.gotoAndPlay("normal"); }); this.body = Matter.Bodies.circle(this.texture.x, this.texture.y, r, { frictionAir: 0.02, restitution: 0.15, }); } update(waterful) { const { texture, body, r } = this; const { x, y, rotation } = texture; const { position, angle, velocity } = body; const innerRadius = texture.scaleX * 16; const startPoint = { x: x - innerRadius * Math.cos(rotation * (Math.PI / 180)), y: y - innerRadius * Math.sin(rotation * (Math.PI / 180)), }; const endPoint = { x: x + innerRadius * Math.cos(-rotation * (Math.PI / 180)), y: y + innerRadius * Math.sin(rotation * (Math.PI / 180)), }; const m = { x: 616, y: 264 }; const n = { x: 616, y: 700 }; const u = { x: 1196, y: 264 }; const v = { x: 1196, y: 700 }; if ( segmentsIntr(startPoint, endPoint, m, n) && this.afterCollision(waterful, "left") ) return; if ( segmentsIntr(startPoint, endPoint, u, v) && this.afterCollision(waterful, "right") ) return; const x1 = Math.round(x); const x2 = Math.round(position.x); const y1 = Math.round(y); const y2 = Math.round(position.y); if (x1 !== x2 || y1 !== y2) { texture.paused && texture.play(); texture.rotation = (180 * angle) / Math.PI; } else { !texture.paused && texture.stop(); } if (stopUnusual(velocity.x, velocity.y, x1, y1)) { var factor = 1; if (x1 < 206 || (x1 > 400 && x1 < 455)) { factor = -1; } Matter.Body.applyForce( body, { x: position.x, y: position.y }, { x: 0.05 * factor, y: 0 } ); } texture.x = body.position.x; texture.y = body.position.y; } afterCollision(waterful, dir) { const { texture } = this; const { currentFrame, rotation } = texture; const followRule = rule(currentFrame, rotation); if ( !followRule || waterful._score[dir].length > 8 || this.body.velocity.y <= 0 ) return false; const scores = waterful._score[dir].length; createjs.Tween.get(this.texture) .to({ y: 666 - 30 * scores }, (666 - 30 * scores) / 0.21) .call(function () { waterful._staticRings.push(this); }); Matter.World.remove(waterful._engine.world, this.body); this.body = null; this.active = false; this.update = () => { const { texture } = this; const { currentFrame } = texture; var t = this.texture, e = t.currentFrame; if (0 === currentFrame) texture.gotoAndStop(0); else { if (!this.frameCounter) this.frameCounter = 5; texture.gotoAndStop(--texture.currentFrame); this.frameCounter--; if (texture.x < 582) ++texture.x; if (texture.x > 660 && texture.x < 660 + 80) --texture.x; if (texture.x > 1242) --texture.x; if (texture.x > 1162 && texture.x < 1206) ++texture.x; } let angle = Math.round(texture.rotation) % 180; angle < 0 && (angle += 180); angle > 0 && angle <= 90 ? (texture.rotation = angle - 1) : angle > 90 && angle < 180 ? (texture.rotation = angle + 1) : 0 === currentFrame && (this.update = function () {}); }; waterful.score(dir, this.color); return true; } }