157 lines
4.1 KiB
JavaScript
157 lines
4.1 KiB
JavaScript
p5.disableFriendlyErrors = true;
|
|
|
|
var canvasWidth = 720;
|
|
var canvasHeight = 720;
|
|
var mazeWidth = 18, mazeHeight = 18;
|
|
var shiftpop = 0;
|
|
var colorfg, colorbg, borderWeight;
|
|
var showOverlay = true;
|
|
var showCurrent = true;
|
|
|
|
var canvas;
|
|
// 3d array, cells[x][y] = [top wall, right wall, bottom wall, left wall, available, in stack]
|
|
var cells;
|
|
var stack;
|
|
var cx, cy;
|
|
var done;
|
|
var bias = 0;
|
|
|
|
function setup() {
|
|
canvas = createCanvas(canvasWidth+0.5, canvasHeight+0.5);
|
|
canvas.parent('canvas-wrapper');
|
|
canvas.id('maze-canvas');
|
|
setupSelects();
|
|
colorfg = color(0);
|
|
colorbg = color(255);
|
|
borderWeight = 2;
|
|
resetMaze();
|
|
frameRate(30);
|
|
}
|
|
|
|
function resetMaze() {
|
|
background(colorbg);
|
|
cells = []; stack = []; done = false;
|
|
for(var x = 0; x < mazeWidth; x++) {
|
|
cells.push([]);
|
|
for(var y = 0; y < mazeHeight; y++) {
|
|
cells[x][y] = [true, true, true, true, true, false];
|
|
}
|
|
}
|
|
cx = floor(random(mazeWidth));
|
|
cy = floor(random(mazeHeight));
|
|
cells[cx][cy][4] = false;
|
|
elem('status').innerHTML = 'Generating...';
|
|
}
|
|
|
|
|
|
function draw() {
|
|
background(colorbg);
|
|
drawCells();
|
|
chooseNextCell();
|
|
}
|
|
|
|
function drawCells() {
|
|
stroke(colorfg);
|
|
strokeWeight(borderWeight);
|
|
var cw = canvasWidth/mazeWidth;
|
|
var ch = canvasHeight/mazeHeight;
|
|
var x, y, c
|
|
// Show overlay
|
|
if(!done && showOverlay) {
|
|
noStroke();
|
|
for(x = 0; x < mazeWidth; x++) {
|
|
for(y = 0; y < mazeHeight; y++) {
|
|
c = cells[x][y];
|
|
// Fill with blue if visited & on stack
|
|
if(!c[4] && c[5])
|
|
{fill( 99, 99, 255); rect(x*cw, y*ch, cw, ch);}
|
|
// Fill with light blue if visited but not on stack
|
|
if(!c[4] && !c[5])
|
|
{fill(150, 180, 255); rect(x*cw, y*ch, cw, ch);}
|
|
}
|
|
}
|
|
stroke(colorfg);
|
|
}
|
|
if(!done && showCurrent) {
|
|
noStroke();
|
|
var d = false;
|
|
var x, y;
|
|
for(x = 0; x < mazeWidth; x++) {
|
|
for(y = 0; y < mazeHeight; y++) {
|
|
// Fill with green if current cell
|
|
if(cx == x && cy == y)
|
|
{fill(0, 230, 50); rect(x*cw, y*ch, cw, ch); d=true; break; }
|
|
}
|
|
if(d) break;
|
|
}
|
|
stroke(colorfg);
|
|
}
|
|
for(x = 0; x < mazeWidth; x++) {
|
|
for(y = 0; y < mazeHeight; y++) {
|
|
c = cells[x][y];
|
|
if(c[0]) line(x*cw, y*ch, x*cw+cw, y*ch);
|
|
if(c[1]) line(x*cw+cw, y*ch, x*cw+cw, y*ch+ch);
|
|
if(c[2]) line(x*cw, y*ch+ch, x*cw+cw, y*ch+ch);
|
|
if(c[3]) line(x*cw, y*ch, x*cw, y*ch+ch);
|
|
}
|
|
}
|
|
if(done) noLoop();
|
|
}
|
|
|
|
function chooseNextCell() {
|
|
var choices = [];
|
|
// Check left, right, up, and down
|
|
if(cells[cx-1] && cells[cx-1][cy] && cells[cx-1][cy][4]) {
|
|
choices.push([cx-1, cy, 3]);
|
|
if(bias > 0) {choices.push([cx-1, cy, 3]); choices.push([cx-1, cy, 3]);}
|
|
}
|
|
if(cells[cx+1] && cells[cx+1][cy] && cells[cx+1][cy][4]) {
|
|
choices.push([cx+1, cy, 1]);
|
|
if(bias > 0) {choices.push([cx+1, cy, 1]); choices.push([cx+1, cy, 1]);}
|
|
}
|
|
if(cells[cx] && cells[cx][cy-1] && cells[cx][cy-1][4]) {
|
|
choices.push([cx, cy-1, 0]);
|
|
if(bias < 0) {choices.push([cx, cy-1, 0]); choices.push([cx, cy-1, 0]);}
|
|
}
|
|
if(cells[cx] && cells[cx][cy+1] && cells[cx][cy+1][4]) {
|
|
choices.push([cx, cy+1, 2]);
|
|
if(bias < 0) {choices.push([cx, cy+1, 2]); choices.push([cx, cy+1, 2]);}
|
|
}
|
|
if(choices.length > 0){
|
|
// Push current cell to stack
|
|
stack.push([cx, cy]);
|
|
cells[cx][cy][5] = true;
|
|
// Choose randomly if choices
|
|
var choice = random(choices);
|
|
// Remove wall
|
|
cells[cx][cy][choice[2]] = false;
|
|
// Move to new cell
|
|
cx = choice[0];
|
|
cy = choice[1];
|
|
// Remove wall
|
|
cells[cx][cy][(choice[2]+2)%4] = false;
|
|
// Mark cell as visited
|
|
cells[cx][cy][4] = false;
|
|
} else if(stack.length > 0) {
|
|
// Otherwise, pop the stack
|
|
var n;
|
|
if(shiftpop == 0)
|
|
n = stack.pop();
|
|
else if(shiftpop == 1)
|
|
n = stack.shift();
|
|
else {
|
|
var rand = random();
|
|
if(rand > shiftpop)
|
|
n = stack.pop();
|
|
else
|
|
n = stack.shift();
|
|
}
|
|
cx = n[0];
|
|
cy = n[1];
|
|
cells[cx][cy][5] = false;
|
|
} else {
|
|
// If stack is empty, we're done
|
|
done = true;
|
|
elem('status').innerHTML = 'Done!';
|
|
}
|
|
}
|