Files
functional-programming-snake/js/solutions/browser.js
T

37 lines
1.2 KiB
JavaScript

// Browser glue: turns a canvas and a window into a Platform. Impure by nature; not part of the exercises' logic.
const PREVENT = new Set(['ArrowUp', 'ArrowDown', 'ArrowLeft', 'ArrowRight', ' '])
export const browserPlatform = (canvas, win) => {
const ctx = canvas.getContext('2d')
// Keys that scroll the page should only steer the game.
const onKey = (cb) => (e) => {
if (PREVENT.has(e.key)) e.preventDefault()
cb(e.key)
}
return {
fillRect: (x, y, w, h, color) => {
ctx.fillStyle = color
ctx.fillRect(x, y, w, h)
},
fillText: (x, y, text, color, size, align) => {
ctx.fillStyle = color
ctx.font = `${size}px monospace`
ctx.textAlign = align
ctx.fillText(text, x, y)
},
randomSeed: () => crypto.getRandomValues(new Uint32Array(1))[0],
// t is the number of milliseconds since the first frame.
startClock: (onTime) => {
const frame = (start) => (now) => {
const t0 = start ?? now
onTime(now - t0)
win.requestAnimationFrame(frame(t0))
}
win.requestAnimationFrame(frame(undefined))
},
onKeyDown: (cb) => win.addEventListener('keydown', onKey(cb)),
onKeyUp: (cb) => win.addEventListener('keyup', onKey(cb)),
}
}