aboutsummaryrefslogtreecommitdiff
path: root/src/spectate/main.ts
diff options
context:
space:
mode:
Diffstat (limited to 'src/spectate/main.ts')
-rw-r--r--src/spectate/main.ts51
1 files changed, 41 insertions, 10 deletions
diff --git a/src/spectate/main.ts b/src/spectate/main.ts
index 4d508b6..422a2c6 100644
--- a/src/spectate/main.ts
+++ b/src/spectate/main.ts
@@ -6,10 +6,15 @@ type Packet = "tick"
| { pos: { id: number, x: number, y: number } }
| { game: { width: number, height: number } }
| { player: { id: number, name: string } }
+ | { die: number[] }
class Snake {
parts: { x: number, y: number, dx: number, dy: number }[] = []
- constructor(public name: string) { }
+ color: string
+ dead = false
+ constructor(public name: string) {
+ this.color = name_color(name)
+ }
add_part(x: number, y: number) {
if (!this.parts.length) return this.parts.push({ x, y, dx: 0, dy: 0 })
const last = this.parts[this.parts.length - 1]
@@ -17,12 +22,12 @@ class Snake {
if (x > last.x + 1 || x < last.x - 1) dx *= -1, dx /= Math.abs(dx)
if (y > last.y + 1 || y < last.y - 1) dy *= -1, dy /= Math.abs(dy)
this.parts.push({ x, y, dx, dy })
- console.log(this.parts);
-
}
}
+
let size = 0
-let snakes = new Map<number, Snake>()
+let tick_anim = 0;
+const snakes = new Map<number, Snake>()
let canvas: HTMLCanvasElement
let ctx: CanvasRenderingContext2D
@@ -59,27 +64,49 @@ function redraw() {
for (let i = 0; i < snake.parts.length; i++) {
const p = snake.parts[i];
ctx.moveTo(p.x - p.dx, p.y - p.dy)
- ctx.lineTo(p.x, p.y)
+ if (i == snake.parts.length - 1)
+ ctx.lineTo(tick_lerp(p.x - p.dx, p.x), tick_lerp(p.y - p.dy, p.y))
+ else ctx.lineTo(p.x, p.y)
}
ctx.lineCap = "round"
ctx.lineJoin = "round"
- ctx.lineWidth = 0.6;
- ctx.strokeStyle = "red"
+ if (snake.dead) ctx.lineWidth = tick_lerp(0.6, 0)
+ else ctx.lineWidth = 0.6;
+ ctx.strokeStyle = snake.color
ctx.stroke()
}
ctx.restore()
}
ctx.restore()
-
+ tick_anim += 0.1
+ tick_anim = Math.min(1, tick_anim)
requestAnimationFrame(redraw)
}
+function tick_lerp(f: number, t: number) {
+ return (1 - tick_anim) * f + tick_anim * t
+}
+
+function name_color(name: string): string {
+ let hash = 0;
+ for (let i = 0; i < name.length; i++) {
+ hash = ((hash << 5) - hash) + name.charCodeAt(i);
+ hash |= 0;
+ }
+ return `hsl(${hash % 360}deg 100% 50%)`;
+}
+
ws.onerror = console.error
ws.onmessage = message => {
const p = JSON.parse(message.data) as Packet
console.log(p);
if (p == "tick") {
-
+ tick_anim = 0
+ const d = []
+ for (const [k, s] of snakes) {
+ if (s.dead) d.push(k)
+ }
+ d.forEach(k => snakes.delete(k))
} else if ("game" in p) {
snakes.clear()
size = p.game.width
@@ -87,7 +114,11 @@ ws.onmessage = message => {
snakes.set(p.player.id, new Snake(p.player.name))
} else if ("pos" in p) {
snakes.get(p.pos.id)?.add_part(p.pos.x, p.pos.y)
+ } else if ("die" in p) {
+ for (const d of p.die) {
+ const s = snakes.get(d)
+ if (s) s.dead = true
+ }
}
-
}