Skip to content

Instantly share code, notes, and snippets.

@chooblarin
Created September 7, 2018 18:52
Show Gist options
  • Save chooblarin/54244bbad4120e77997a4a3fbf09c6ed to your computer and use it in GitHub Desktop.
Save chooblarin/54244bbad4120e77997a4a3fbf09c6ed to your computer and use it in GitHub Desktop.
1D Cellular Automaton
<!--
originated from
https://github.com/alifelab/alife_book_src/blob/master/chap02/cellular_automata_1d.py
-->
<p id="time">t = 0</p>
<canvas id="sketch"></canvas>
<div class="desc">Press Space Key to increment time</div>
console.clear();
const timeParagraph = document.querySelector('#time');
const canvas = document.querySelector('#sketch');
const context = canvas.getContext('2d');
const canvasWidth = 500;
const canvasHeight = 50;
const dpr = window.devicePixelRatio;
canvas.width = canvasWidth;
canvas.height = canvasHeight;
canvas.clientWidth = canvasWidth * dpr;
canvas.clientHeight = canvasHeight * dpr;
const cellCount = 10;
const cellWidth = canvasWidth / 10;
const cellHeight = canvasHeight;
const update = (current, rule) => {
const next = [];
for (let i = 0; i < current.length; i += 1) {
let center = current[i];
let left;
let right;
if (i === 0) {
left = current[current.length - 1];
right = current[i + 1];
} else if (i === current.length - 1) {
left = current[i - 1];
right = current[0];
} else {
left = current[i - 1];
right = current[i + 1];
}
const neighborCellCode = 4 * left + 2 * center + right;
const s = (rule >> neighborCellCode & 1) ? 1 : 0;
next.push(s);
}
return next;
};
const render = (state) => {
context.clearRect(0, 0, canvasWidth, canvasHeight);
for (let i = 0; i < state.length; i += 1) {
const s = state[i];
if (s === 0) {
context.fillStyle = 'white';
} else {
context.fillStyle = 'black';
}
context.fillRect(i * cellWidth, 0, (i + 1) * cellWidth, cellHeight);
}
};
const rule = 30;
let t = 0;
// let cellStates = Array(cellCount).fill().map(_ => Math.random() * 2 | 0);
let cellStates = Array(cellCount).fill().map( (_, i) => i === (cellCount / 2 | 0) ? 1 : 0);
render(cellStates);
const step = () => {
t += 1;
cellStates = update(cellStates, rule);
timeParagraph.textContent = `t = ${t}`;
render(cellStates);
};
window.addEventListener('keydown', ev => {
if (ev.key === ' ') {
step();
}
});
* {
margin: 0;
padding: 0;
border: 0;
}
body {
display: flex;
flex-direction: column;
justify-content: center;
align-items: center;
height: 100vh;
background: #f8f8f8;
}
p {
font-size: 2rem;
margin-bottom: 1rem;
}
#sketch {
background: white;
width: 500px;
height: 50px;
border: 1px solid #777;
}
.desc {
color: #aaa;
position: fixed;
bottom: 40px;
left: 40px;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment