explorata/src/components/CanvasBoard.vue

143 lines
3.7 KiB
Vue

<template>
<main id="mainContent">
<CanvasBoard
id="canvas-board"
ref="canvas-board"
:width="canvasWidth"
:height="canvasHeight"
/>
</main>
</template>
<script>
import {
create1dState,
create1dStateOneCell,
create2dState,
createBoard,
conwayRules,
evolve2d,
} from "../modules/automata.js";
import { getRandomInt, sleep } from "../modules/common.js";
import { mapGetters } from "vuex";
export default {
name: "CanvasBoard",
data() {
return {
canvas: null,
ctx: null,
};
},
computed: {
...mapGetters({
cellProperties: "getCellProperties",
rules: "get1dRules",
drawing: "isDrawing",
canvasWidth: "getCanvasWidth",
canvasHeight: "getCanvasHeight",
refreshRate: "getRefreshRate",
initial1dState: "getInitial1dState",
drawingDirection: "getDrawingDirection",
lastBoard: "getLastBoard",
}),
boardWidth: function () {
return Math.floor(this.canvasWidth / this.cellProperties.size);
},
boardHeight: function () {
return Math.floor(this.canvasHeight / this.cellProperties.size);
},
},
mounted() {
this.canvas = this.$refs["canvas"];
this.ctx = this.canvas.getContext("2d");
this.$store.commit("setCanvasWidth", this.canvas.parentElement.clientWidth);
this.$store.commit(
"setCanvasHeight",
this.canvas.parentElement.clientHeight
);
this.$root.$on("draw1d", () => {
this.draw1d();
});
this.$root.$on("draw2dNew", () => {
this.draw2dNew();
});
this.$root.$on("draw2dLast", () => {
this.draw2dLast();
});
this.$root.$on("reset", () => {
this.reset();
});
this.$root.$on("stop", () => {
this.stop();
});
},
methods: {
drawCanvas(board) {
const props = this.cellProperties;
board.map((row, y) => {
const d = props.size;
return row.map((cell, x) => {
this.ctx.fillStyle = (() => {
if (cell === 1) return props.liveColor;
return props.deadColor;
})();
if (this.drawingDirection === "x")
this.ctx.fillRect(y * d, x * d, d, d);
else this.ctx.fillRect(x * d, y * d, d, d);
return cell;
});
});
},
compute1dInitialState() {
if (this.initial1dState === "onecell")
return create1dStateOneCell(this.boardWidth);
return create1dState(this.boardWidth, getRandomInt, [0, 2]);
},
async draw1d() {
const initialState = this.compute1dInitialState();
const board = createBoard(initialState, this.rules, this.boardWidth);
this.$store.commit("setLastBoard", board);
this.drawCanvas(board);
},
async draw2d(board) {
if (this.drawing === 0) return;
const draw2dNext = async (b) => {
if (this.drawing === 0) return;
const newBoard = evolve2d(b, conwayRules);
this.drawCanvas(b, this.cellProperties);
await sleep(this.refreshRate);
draw2dNext(newBoard);
};
return draw2dNext(board);
},
async draw2dNew() {
const initialState = create2dState(
this.boardWidth,
this.boardHeight,
getRandomInt,
[0, 2]
);
const board = evolve2d(initialState, conwayRules);
this.$store.commit("setLastBoard", board);
this.draw2d(board);
},
async draw2dLast() {
console.log(this.lastBoard);
this.draw2d(this.lastBoard);
},
stop() {
this.$store.commit("setDrawingStatus", 0);
},
reset() {
this.stop();
this.ctx.clearRect(0, 0, this.canvas.width, this.canvas.height);
},
},
};
</script>
<style>
#mainContent {
min-width: 70%;
}
</style>