682 lines
21 KiB
XML
682 lines
21 KiB
XML
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||
<svg viewBox="-200 -150 400 300" version="1.1" xmlns="http://www.w3.org/2000/svg">
|
||
<style>
|
||
#frames {
|
||
position: absolute;
|
||
right: 0px;
|
||
}
|
||
|
||
p {
|
||
border: 1px solid black;
|
||
box-size: border-box;
|
||
}
|
||
|
||
rect#bg {
|
||
fill: gray;
|
||
}
|
||
|
||
.ship rect {
|
||
fill: green;
|
||
}
|
||
|
||
.ship circle {
|
||
fill: white;
|
||
}
|
||
|
||
#crosshair {
|
||
opacity: 0.5;
|
||
}
|
||
|
||
circle.bullet {
|
||
fill: yellow;
|
||
}
|
||
|
||
#frames {
|
||
padding: 1px;
|
||
font-size: 4pt;
|
||
font-family: courier;
|
||
}
|
||
|
||
#triangles {
|
||
opacity: 0.5;
|
||
}
|
||
|
||
#triangles line {
|
||
stroke: limegreen;
|
||
stroke-width: 0.5px;
|
||
}
|
||
|
||
#triangles polygon {
|
||
fill-opacity: 0.2;
|
||
stroke-width: 0.5px;
|
||
fill: none;
|
||
stroke: none;
|
||
}
|
||
|
||
#triangles polygon.clockwise-orientation {
|
||
fill: white;
|
||
stroke: red;
|
||
}
|
||
|
||
#lines line {
|
||
stroke: gold;
|
||
}
|
||
|
||
#legs {
|
||
display: none;
|
||
}
|
||
</style>
|
||
|
||
<rect id="bg" x="-200" y="-150" width="400" height="300"/>
|
||
|
||
<g>
|
||
<g class="hitbox">
|
||
<g class="ship">
|
||
<line id="cannon" x1="0" y1="0" x2="0" y2="8" stroke="black"/>
|
||
<circle id="body" cx="0" cy="0" r="5"/>
|
||
<g id="legs">
|
||
<path d="M 3 2 l 2 2 v 2 m -2 0 h 4" stroke="black" fill="none" />
|
||
<path d="M -3 2 l -2 2 v 2 m -2 0 h 4" stroke="black" fill="none" />
|
||
</g>
|
||
</g>
|
||
</g>
|
||
|
||
<polygon id="wall" points="-10,-30 -10,-40 30,-50 60,-30 80,0 150,0 150,10 60,50 -10,40 -20,20 20,20 20,-20" />
|
||
<!-- <rect id="rect1" x="30" y="30" width="20" height="20"/> -->
|
||
<g id="triangles">
|
||
</g>
|
||
<g id="lines">
|
||
</g>
|
||
|
||
<g id="bullets"></g>
|
||
</g>
|
||
|
||
<foreignObject x="-200" y="-150" width="100%" height="100%">
|
||
<div id="frames" xmlns="http://www.w3.org/1999/xhtml">
|
||
<span id="time" xmlns="http://www.w3.org/1999/xhtml">0</span> s
|
||
<span id="fps" xmlns="http://www.w3.org/1999/xhtml">0</span> fps
|
||
</div>
|
||
|
||
<!-- <button id="turn-left" xmlns="http://www.w3.org/1999/xhtml">🡐</button> -->
|
||
<!-- <button id="move-backward" xmlns="http://www.w3.org/1999/xhtml">🡑</button> -->
|
||
<!-- <button id="move-forward" xmlns="http://www.w3.org/1999/xhtml">🡓</button> -->
|
||
<!-- <button id="turn-right" xmlns="http://www.w3.org/1999/xhtml">🡒</button> -->
|
||
<!-- <button id="rotate-ccw" xmlns="http://www.w3.org/1999/xhtml">⟲</button> -->
|
||
<!-- <button id="rotate-cw" xmlns="http://www.w3.org/1999/xhtml">⟳</button> -->
|
||
<!-- <button id="fire" xmlns="http://www.w3.org/1999/xhtml">Fire</button> -->
|
||
<pre id="debug" xmlns="http://www.w3.org/1999/xhtml"></pre>
|
||
</foreignObject>
|
||
|
||
<script type="text/javascript">//<![CDATA[
|
||
const namespaceURIsvg = 'http://www.w3.org/2000/svg';
|
||
const degsRegex = /(-?\d*\.{0,1}\d+)deg/g;
|
||
const regex = /(-?\d*\.{0,1}\d+)px/g;
|
||
const bullets = [];
|
||
|
||
let previous, zero, frameCount = 0;
|
||
let position = [0, 0]; // meters
|
||
let velocity = [0, 0]; // meters per second
|
||
let acceleration = [0, 0]; // meters per second per second
|
||
// let friction = 7.5;
|
||
let friction = 0;
|
||
let rotate = 0;
|
||
let rotationSpeed = 0.25;
|
||
const maxSpeed = 100;
|
||
|
||
const fps = document.querySelector("#fps");
|
||
const time = document.querySelector("#time");
|
||
const info = document.querySelector("#debug");
|
||
const ship = document.querySelector(".ship");
|
||
const gun = ship.querySelector('#cannon');
|
||
const shipBody = ship.querySelector("circle");
|
||
|
||
const hitbox = document.querySelector(".hitbox");
|
||
const bulletsContainer = document.querySelector("#bullets");
|
||
|
||
const leftTurnButton = document.querySelector("#turn-left");
|
||
const rightTurnButton = document.querySelector("#turn-right");
|
||
const reverseMoveButton = document.querySelector("#move-backward");
|
||
const forwardMoveButton = document.querySelector("#move-forward");
|
||
|
||
const rotateCWButton = document.querySelector("#rotate-cw");
|
||
const rotateCCWButton = document.querySelector("#rotate-ccw");
|
||
|
||
const fireButton = document.querySelector("#fire");
|
||
const pt = document.querySelector('svg').createSVGPoint();
|
||
const cornerPt = document.querySelector('svg').createSVGPoint();
|
||
const wall = document.querySelector('#wall');
|
||
|
||
const points = wall.getAttribute('points').split(' ').map(coords => {
|
||
const [x, y] = coords.split(',');
|
||
return [+x, +y];
|
||
});
|
||
|
||
const triangleContainer = document.querySelector('#triangles');
|
||
const lineContainer = document.querySelector('#lines');
|
||
const trianglePts = points.map((pt, i) => [pt, points[(i + 1) % points.length]]);
|
||
|
||
|
||
function drawEdges() {
|
||
const lpts = wall.getAttribute('points').split(' ');
|
||
let edges = lpts.map((pt, i) => [pt, lpts[(i + 1) % lpts.length]]).map(e => e.join(' '));
|
||
// console.log(edges);
|
||
|
||
edges.forEach(e => {
|
||
const [x, y] = e.split(' ');
|
||
const [x1, y1] = x.split(',');
|
||
const [x2, y2] = y.split(',');
|
||
const el = document.createElementNS(namespaceURIsvg, 'line');
|
||
// const attr = `${x1},${y1} ${x2},${y2} ${positionX},${positionY}`
|
||
// const attr = `${x1},${y1} ${x2},${y2} ${positionX},${positionY}`
|
||
el.setAttribute('x1', x1);
|
||
el.setAttribute('y1', y1);
|
||
el.setAttribute('x2', x2);
|
||
el.setAttribute('y2', y2);
|
||
lineContainer.appendChild(el)
|
||
});
|
||
}
|
||
// const edges = lpts.map((pt, i) => [pt.split(','), lpts[(i + 1) % lpts.length].split(',')]);
|
||
|
||
drawEdges();
|
||
|
||
function drawTriangles(container, pts, [positionX, positionY]) {
|
||
pts.forEach(([[x1, y1], [x2, y2]]) => {
|
||
const el = document.createElementNS(namespaceURIsvg, 'polygon');
|
||
const attr = `${x1},${y1} ${x2},${y2} ${positionX},${positionY}`
|
||
el.setAttribute('points', attr);
|
||
container.appendChild(el)
|
||
});
|
||
}
|
||
|
||
drawTriangles(triangleContainer, trianglePts, [0, 0]);
|
||
const triangles = triangleContainer.querySelectorAll('polygon');
|
||
|
||
function updateTriangles([positionX, positionY]) {
|
||
const delim = ' ';
|
||
const className = 'clockwise-orientation';
|
||
const visible = [];
|
||
const PI = Math.PI / 2;
|
||
|
||
triangles.forEach(t => {
|
||
const attr = t.getAttribute('points').split(delim);
|
||
const [[xa, ya], [xb, yb], [xc, yc]] = attr.map(t => t.split(','));
|
||
|
||
// https://en.wikipedia.org/wiki/Curve_orientation#Practical_considerations
|
||
// Determinant for a convex polygon
|
||
const det = (+xb - +xa) * (+yc - +ya) - (+xc - +xa) * (+yb - +ya);
|
||
|
||
const pos = `${positionX},${positionY}`;
|
||
const cwOrientation = det < 0;
|
||
const isClockwise = det < 0;
|
||
let isAcute = false;
|
||
|
||
if (isClockwise) {
|
||
const [[ax, ay], [bx, by], [shipx, shipy]] =
|
||
t.getAttribute('points').split(' ').map(n => n.split(',').map(n => +n));
|
||
|
||
const da = distance(ax, ay, shipx, shipy);
|
||
const db = distance(bx, by, shipx, shipy);
|
||
const dc = distance(ax, ay, bx, by);
|
||
|
||
// https://en.wikipedia.org/wiki/Law_of_cosines
|
||
// Solve for angles α and β with inverse cosine (arccosine)
|
||
const α = Math.acos((db ** 2 + dc ** 2 - da ** 2) / (2 * db * dc));
|
||
const β = Math.acos((da ** 2 + dc ** 2 - db ** 2) / (2 * da * dc));
|
||
isAcute = α < PI && β < PI;
|
||
}
|
||
|
||
if (pos !== attr.pop()) {
|
||
attr.push(pos);
|
||
t.setAttribute('points', attr.join(delim));
|
||
}
|
||
|
||
t.classList[isClockwise && isAcute ? "add" : "remove"](className);
|
||
if (isClockwise && isAcute) visible.push(t);
|
||
});
|
||
|
||
return visible;
|
||
}
|
||
|
||
function wrapPos(positionX, positionY) {
|
||
let x, y;
|
||
|
||
if (positionY > 150) y = positionY - 300;
|
||
else if (positionY < -150) y = positionY + 300;
|
||
else y = positionY;
|
||
|
||
if (positionX > 200) x = positionX - 400;
|
||
else if (positionX < -200) x = positionX + 400;
|
||
else x = positionX;
|
||
|
||
return [x, y];
|
||
}
|
||
|
||
function fireBullet(x, y, velocity) {
|
||
const degrees = getRotate(gun);
|
||
const radians = degrees * Math.PI / 180; // toFixed(15)?
|
||
const speed = 200; // meters per second
|
||
const vx = -Math.sin(radians);
|
||
const vy = Math.cos(radians);
|
||
const bulletTimeout = 5000; // miliseconds
|
||
const cannonLength = 8;
|
||
|
||
const el = document.createElementNS(namespaceURIsvg, 'circle');
|
||
el.classList.add('bullet');
|
||
el.setAttribute('r', 1);
|
||
el.setAttribute('cx', 0);
|
||
el.setAttribute('cy', 0);
|
||
|
||
const bullet = {
|
||
x: x + vx * cannonLength,
|
||
y: y + vy * cannonLength,
|
||
vx: vx * speed + velocity[0],
|
||
vy: vy * speed + velocity[1],
|
||
time: bulletTimeout,
|
||
node: bulletsContainer.appendChild(el)
|
||
}
|
||
|
||
bullets.push(bullet);
|
||
}
|
||
|
||
function getTranslate(el) {
|
||
let x, y;
|
||
|
||
if (el.style.transform.length === 0) {
|
||
x = 0;
|
||
y = 0;
|
||
} else {
|
||
[[, x], [, y] = ["0px", "0"]] = [...el.style.transform.matchAll(regex)];
|
||
}
|
||
|
||
return [+x, +y];
|
||
}
|
||
|
||
function getRotate(el) {
|
||
let [[, degrees] = ["0deg", "0"]] = [...el.style.transform.matchAll(degsRegex)];
|
||
return +degrees;
|
||
}
|
||
|
||
function updateBullets(elapsed) {
|
||
const deleteCount = 1;
|
||
const pt = document.querySelector('svg').createSVGPoint();
|
||
|
||
[...bullets].forEach((bullet, index) => {
|
||
bullet.time -= elapsed;
|
||
const x = bullet.x + 0.001 * elapsed * bullet.vx;
|
||
const y = bullet.y + 0.001 * elapsed * bullet.vy;
|
||
pt.x = x;
|
||
pt.y = y;
|
||
|
||
if (bullet.time > 0 && !wall.isPointInFill(pt)) {
|
||
[bullet.x, bullet.y] = wrapPos(x, y);
|
||
bullet.node.style.transform = `translate(${bullet.x}px, ${bullet.y}px)`;
|
||
} else {
|
||
bullet.node.remove();
|
||
bullets.splice(index, deleteCount);
|
||
}
|
||
});
|
||
}
|
||
|
||
function updateLines([positionX, positionY]) {
|
||
lines.forEach(line => {
|
||
line.setAttribute('x2', positionX);
|
||
line.setAttribute('y2', positionY);
|
||
|
||
// let slope = (+line.getAttribute('y2') - +line.getAttribute('y1')) / (+line.getAttribute('x2') - +line.getAttribute('x1'));
|
||
// slope = +slope.toFixed(15);
|
||
// console.log('slope', slope);
|
||
|
||
const firstP = line.getPointAtLength(1);
|
||
if (polygon.isPointInFill(firstP)) {
|
||
line.setAttribute('x2', line.getAttribute('x1'));
|
||
line.setAttribute('y2', line.getAttribute('y1'));
|
||
}
|
||
});
|
||
}
|
||
|
||
requestAnimationFrame(firstFrame);
|
||
|
||
|
||
let start;
|
||
let restart = false;
|
||
function firstFrame(timestamp) {
|
||
zero = timestamp;
|
||
zeroForTimer = timestamp;
|
||
previous = timestamp;
|
||
animate(timestamp);
|
||
}
|
||
|
||
function distance(x1, y1, x2, y2) {
|
||
return Math.sqrt((x2 - x1) ** 2 + (y2 - y1) ** 2);
|
||
}
|
||
|
||
const startingTrianglePts = ["-20,20 20,20", "20,20 20,-20", "20,-20 -10,-30"];
|
||
|
||
function animate(timestamp) {
|
||
const delta = timestamp - zero;
|
||
time.innerText = ((timestamp - zeroForTimer) * 0.001).toFixed(3);
|
||
// time.innerText = time.inner
|
||
const elapsed = timestamp - previous;
|
||
previous = timestamp;
|
||
|
||
if (delta >= 1000) {
|
||
fps.innerText = frameCount;
|
||
|
||
// info.innerText = `velocity ${velocity}\n`
|
||
// + 'bullets\nx\ty\tvx\tvy\n'
|
||
// + bullets.map(b => {
|
||
// return `${b.x.toFixed(2)}\t${b.y.toFixed(2)}\t${b.vx.toFixed(2)}\t${b.vy.toFixed(2)}`;
|
||
// }).join("\n");
|
||
|
||
zero = timestamp;
|
||
frameCount = 0;
|
||
} else {
|
||
frameCount++;
|
||
}
|
||
|
||
let degrees = getRotate(gun);
|
||
|
||
if (rotate > 0) gun.style.transform = `rotate(${(+degrees + rotationSpeed * elapsed) % 360}deg)`;
|
||
else if (rotate < 0) gun.style.transform = `rotate(${(+degrees - rotationSpeed * elapsed) % 360}deg)`;
|
||
|
||
let [velocityX, velocityY] = restart ? [0, 0] : velocity;
|
||
let [accelerationX, accelerationY] = restart ? [0, 0] : acceleration;
|
||
|
||
if (velocityX > 0) accelerationX += -friction;
|
||
else if (velocityX < 0) accelerationX += friction;
|
||
|
||
if (velocityY > 0) accelerationY += -friction;
|
||
else if (velocityY < 0) accelerationY += friction;
|
||
|
||
velocityX = velocityX > 0 && velocityX + accelerationX < 0 ? 0 : velocityX + accelerationX;
|
||
velocityY = velocityY > 0 && velocityY + accelerationY < 0 ? 0 : velocityY + accelerationY;
|
||
velocity = [velocityX, velocityY];
|
||
|
||
if (velocity[0] > maxSpeed) velocity[0] = maxSpeed;
|
||
else if (velocity[0] < -maxSpeed) velocity[0] = -maxSpeed
|
||
|
||
if (velocity[1] > maxSpeed) velocity[1] = maxSpeed;
|
||
else if (velocity[1] < -maxSpeed) velocity[1] = -maxSpeed
|
||
|
||
const changeX = 0.001 * elapsed * velocityX;
|
||
const changeY = 0.001 * elapsed * velocityY;
|
||
|
||
let [x, y] = getTranslate(hitbox);
|
||
let position = [positionX, positionY] = restart ? [0, 0] : wrapPos(changeX + x, changeY + y);
|
||
|
||
|
||
updateBullets(elapsed);
|
||
|
||
const visibleTriangles = updateTriangles(position);
|
||
const visibleTrianglePoints = [...visibleTriangles].map(p => p.getAttribute("points"));
|
||
const mappedEdges = visibleTrianglePoints.map(vt => {
|
||
vt = vt.split(' ');
|
||
vt.pop();
|
||
return vt.join(' ');
|
||
});
|
||
|
||
// console.log(mappedEdges);
|
||
[...lineContainer.children].forEach(l => {
|
||
const x1 = l.getAttribute('x1');
|
||
const y1 = l.getAttribute('y1');
|
||
const x2 = l.getAttribute('x2');
|
||
const y2 = l.getAttribute('y2');
|
||
const str = `${x1},${y1} ${x2},${y2}`;
|
||
if (mappedEdges.includes(str) && (lineContainer.childElementCount < 4 || !startingTrianglePts.includes(str))) {
|
||
l.remove();
|
||
}
|
||
});
|
||
|
||
|
||
if (restart) {
|
||
restart = false;
|
||
[...lineContainer.children].forEach(c => c.remove());;
|
||
drawEdges();
|
||
}
|
||
|
||
// edges = [...edges.filter(e => !mappedEdges.includes(e))]
|
||
|
||
// console.log(edges)
|
||
// info.innerText = [...visibleTriangles].map(t => {
|
||
// const [[ax, ay], [bx, by], [shipx, shipy]] =
|
||
// t.getAttribute('points').split(' ').map(n => n.split(',').map(n => +n));
|
||
//
|
||
// const da = distance(ax, ay, shipx, shipy);
|
||
// const db = distance(bx, by, shipx, shipy);
|
||
// const dc = distance(ax, ay, bx, by);
|
||
// const s = (1 / 2) * (da + db + dc);
|
||
// const hc = (2 / dc) * Math.sqrt(s * (s - da) * (s - db) * (s - dc));
|
||
//
|
||
// const alpha = Math.acos((db**2 + dc**2 - da**2) / (2 * db * dc));
|
||
// const beta = Math.acos((da**2 + dc**2 - db**2) / (2 * da * dc));
|
||
//
|
||
// const PI = Math.PI / 2;
|
||
// const acute = alpha < PI && beta < PI;
|
||
//
|
||
// return `${da.toFixed(2)} ${db.toFixed(2)} ${dc.toFixed(2)} ${hc.toFixed(2)} ${alpha.toFixed(2)} ${beta.toFixed(2)}`;
|
||
// }).join('\n');
|
||
|
||
// can do this after side collision detection
|
||
// const ts = updateTriangles(position);
|
||
// const corners = ts.reduce((acc, t) => {
|
||
// const [a, b,] = t.getAttribute('points').split(' ');
|
||
// // return p.map(t => t.split(','));
|
||
// // acc.push(a);
|
||
// // acc.push(b);
|
||
// return [a, b, ...acc];
|
||
// }, []);
|
||
//
|
||
// const uniqueCorners = [...new Set(corners)].map(n => n.split(',').map(n => +n));
|
||
|
||
const cornerCollision = points.some(([x, y]) => {
|
||
cornerPt.x = x - positionX;
|
||
cornerPt.y = y - positionY;
|
||
|
||
return shipBody.isPointInFill(cornerPt);
|
||
});
|
||
|
||
const PI = Math.PI / 2;
|
||
const shipRadius = 5;
|
||
const sideCollision = [...visibleTriangles].reduce((acc, t) => {
|
||
const [[ax, ay], [bx, by], [shipx, shipy]] =
|
||
t.getAttribute('points').split(' ').map(n => n.split(',').map(n => +n));
|
||
|
||
const da = distance(ax, ay, shipx, shipy);
|
||
const db = distance(bx, by, shipx, shipy);
|
||
const dc = distance(ax, ay, bx, by);
|
||
const s = (1 / 2) * (da + db + dc);
|
||
const hc = (2 / dc) * Math.sqrt(s * (s - da) * (s - db) * (s - dc));
|
||
const alpha = Math.acos((db**2 + dc**2 - da**2) / (2 * db * dc));
|
||
const beta = Math.acos((da**2 + dc**2 - db**2) / (2 * da * dc));
|
||
const acute = alpha < PI && beta < PI;
|
||
|
||
return acute ? [...acc, hc] : acc;
|
||
}, []).some(h => h <= shipRadius);
|
||
|
||
wall.setAttribute('fill', cornerCollision || sideCollision ? 'red' : 'black');
|
||
hitbox.style.transform = `translate(${positionX}px, ${positionY}px)`;
|
||
|
||
if (cornerCollision || sideCollision) {
|
||
// restart game
|
||
zeroForTimer = timestamp;
|
||
restart = true;
|
||
// position = [0, 0];
|
||
// acceleration = [0, 0];
|
||
}
|
||
|
||
// if (+y < 200)
|
||
// if (timestamp < 10000)
|
||
if (lineContainer.childElementCount > 0)
|
||
requestAnimationFrame(t => animate(t));
|
||
}
|
||
|
||
let force = 1;
|
||
|
||
let spacePressed = false;
|
||
let upPressed = false;
|
||
let downPressed = false;
|
||
let leftPressed = false;
|
||
let rightPressed = false;
|
||
let rotateCWPressed = false;
|
||
let rotateCCWPressed = false;
|
||
|
||
document.addEventListener("keydown", function(e) {
|
||
switch (e.code) {
|
||
case "Space":
|
||
if (!spacePressed) {
|
||
spacePressed = true;
|
||
const [x, y] = getTranslate(hitbox);
|
||
fireBullet(x, y, velocity);
|
||
}
|
||
break;
|
||
case "KeyW":
|
||
case "ArrowUp":
|
||
if (!upPressed) {
|
||
upPressed = true;
|
||
acceleration[1] += -force;
|
||
}
|
||
break;
|
||
case "KeyS":
|
||
case "ArrowDown":
|
||
if (!downPressed) {
|
||
downPressed = true;
|
||
acceleration[1] += force;
|
||
}
|
||
break;
|
||
case "KeyA":
|
||
case "ArrowLeft":
|
||
if (!leftPressed) {
|
||
leftPressed = true;
|
||
acceleration[0] += -force;
|
||
}
|
||
break;
|
||
case "KeyD":
|
||
case "ArrowRight":
|
||
if (!rightPressed) {
|
||
rightPressed = true;
|
||
acceleration[0] += force;
|
||
}
|
||
break;
|
||
case "KeyQ":
|
||
case "Comma":
|
||
if (!rotateCCWPressed) {
|
||
rotateCCWPressed = true;
|
||
rotate += -1;
|
||
}
|
||
break;
|
||
case "KeyE":
|
||
case "Period":
|
||
if (!rotateCWPressed) {
|
||
rotateCWPressed = true;
|
||
rotate += 1;
|
||
}
|
||
break;
|
||
}
|
||
});
|
||
|
||
document.addEventListener("keyup", function(e) {
|
||
switch (e.code) {
|
||
case "Space":
|
||
spacePressed = false;
|
||
break;
|
||
case "KeyW":
|
||
case "ArrowUp":
|
||
if (upPressed) {
|
||
upPressed = false;
|
||
acceleration[1] -= -force;
|
||
}
|
||
break;
|
||
case "KeyS":
|
||
case "ArrowDown":
|
||
if (downPressed) {
|
||
downPressed = false;
|
||
acceleration[1] -= force;
|
||
}
|
||
break;
|
||
case "KeyA":
|
||
case "ArrowLeft":
|
||
if (leftPressed) {
|
||
leftPressed = false;
|
||
acceleration[0] -= -force;
|
||
}
|
||
break;
|
||
case "KeyD":
|
||
case "ArrowRight":
|
||
if (rightPressed) {
|
||
rightPressed = false;
|
||
acceleration[0] -= force;
|
||
}
|
||
break;
|
||
case "KeyQ":
|
||
case "Comma":
|
||
if (rotateCCWPressed) {
|
||
rotateCCWPressed = false;
|
||
rotate -= -1;
|
||
}
|
||
break;
|
||
case "KeyE":
|
||
case "Period":
|
||
if (rotateCWPressed) {
|
||
rotateCWPressed = false;
|
||
rotate -= 1;
|
||
}
|
||
break;
|
||
}
|
||
});
|
||
|
||
// leftTurnButton.addEventListener("mousedown", function (e) {
|
||
// acceleration[0] = -force;
|
||
// });
|
||
//
|
||
// leftTurnButton.addEventListener("mouseup", function (e) {
|
||
// acceleration[0] = 0;
|
||
// });
|
||
//
|
||
// rightTurnButton.addEventListener("mousedown", function (e) {
|
||
// acceleration[0] = force;
|
||
// });
|
||
//
|
||
// rightTurnButton.addEventListener("mouseup", function (e) {
|
||
// acceleration[0] = 0;
|
||
// });
|
||
//
|
||
// reverseMoveButton.addEventListener("mousedown", function (e) {
|
||
// acceleration[1] = -force;
|
||
// });
|
||
//
|
||
// reverseMoveButton.addEventListener("mouseup", function (e) {
|
||
// acceleration[1] = 0;
|
||
// });
|
||
//
|
||
// forwardMoveButton.addEventListener("mousedown", function (e) {
|
||
// acceleration[1] = force;
|
||
// });
|
||
//
|
||
// forwardMoveButton.addEventListener("mouseup", function (e) {
|
||
// acceleration[1] = 0;
|
||
// });
|
||
//
|
||
// rotateCWButton.addEventListener("mousedown", function (e) {
|
||
// rotate = 1;
|
||
// });
|
||
//
|
||
// rotateCWButton.addEventListener("mouseup", function (e) {
|
||
// rotate = 0;
|
||
// });
|
||
//
|
||
// rotateCCWButton.addEventListener("mousedown", function (e) {
|
||
// rotate = -1;
|
||
// });
|
||
//
|
||
// rotateCCWButton.addEventListener("mouseup", function (e) {
|
||
// rotate = 0;
|
||
// });
|
||
//
|
||
// fireButton.addEventListener("click", function (e) {
|
||
// const [x, y] = getTranslate(hitbox);
|
||
// fireBullet(x, y, velocity);
|
||
// });
|
||
//]]></script>
|
||
</svg>
|
||
|