Files
fxl.codes.Weather/src/state.ts
T

90 lines
2.6 KiB
TypeScript

import Crack from "./crack"
export default class State {
readonly canvas: HTMLCanvasElement
readonly maxCracks: number
readonly grid: number[][]
colors: number[]
seeds: {x: number, y: number}[]
cracks: Crack[]
colorIndex: number = 0
constructor(colors: number[], maxCracks: number, canvas: HTMLCanvasElement) {
this.canvas = canvas
this.maxCracks = maxCracks
this.grid = []
this.colors = colors
this.cracks = []
this.seeds = []
this.init()
}
init(colors?: number[]) {
if (colors) this.colors = colors
this.cracks.length = 0
this.grid.length = 0
this.seeds.length = 0
this.colorIndex = 0
const height = this.canvas.height
const width = this.canvas.width
const context = this.canvas.getContext("2d")
context.fillStyle = "rgb(255 255 255 / 95%)"
context.fillRect(0, 0, width, height)
for (let x = 0; x < width; x++) {
this.grid[x] = []
for (let y = 0; y < height; y++) {
this.grid[x][y] = 10001
}
}
for (let i = 0; i < 3; i++) {
const x = Math.floor(Math.random() * width)
const y = Math.floor(Math.random() * height)
const angle = Math.floor(Math.random() * 360)
this.cracks.push(new Crack(this, x, y, angle))
this.grid[x][y] = angle
}
}
addCrack() {
if (this.cracks.length >= this.maxCracks) return
const {x, y, angle} = this.getNewEntry()
this.cracks.push(new Crack(this, x, y, angle))
}
getNextColor(): number {
return this.colors[this.colorIndex++ % this.colors.length]
}
isWithinBoundary(x: number, y: number): boolean {
return x >= 0 && x < this.canvas.width && y >= 0 && y < this.canvas.height
}
getNewEntry(): {x: number, y: number, angle: number} {
if (!this.seeds.length) {
const x = Math.floor(Math.random() * this.canvas.width)
const y = Math.floor(Math.random() * this.canvas.height)
let angle = this.grid[x][y]
if (angle > 10000) {
angle = Math.floor(Math.random() * 360)
this.grid[x][y] = angle
}
return {x, y, angle}
}
const randomIndex = Math.floor(Math.random() * this.seeds.length)
const entry = this.seeds.splice(randomIndex, 1)[0]
return {
x: entry.x,
y: entry.y,
angle: this.grid[entry.x][entry.y]
}
}
}