This commit is contained in:
syuilo 2019-05-11 11:47:47 +09:00
parent ede93ade11
commit 5ac502d401
No known key found for this signature in database
GPG key ID: BDC4C49D06AB9D69
3 changed files with 34 additions and 9 deletions

View file

@ -2,6 +2,10 @@ import * as gen from 'random-seed';
import { CellType } from './maze'; import { CellType } from './maze';
const cellVariants = { const cellVariants = {
void: {
digg: { left: null, right: null, top: null, bottom: null },
cross: { left: false, right: false, top: false, bottom: false },
},
empty: { empty: {
digg: { left: 'left', right: 'right', top: 'top', bottom: 'bottom' }, digg: { left: 'left', right: 'right', top: 'top', bottom: 'bottom' },
cross: { left: false, right: false, top: false, bottom: false }, cross: { left: false, right: false, top: false, bottom: false },
@ -77,6 +81,8 @@ export function genMaze(seed) {
const rand = gen.create(seed); const rand = gen.create(seed);
const mazeSize = 11 + rand(21); const mazeSize = 11 + rand(21);
const donut = rand(3) === 0;
const donutWidth = mazeSize / 3;
// maze (filled by 'empty') // maze (filled by 'empty')
const maze: CellType[][] = new Array(mazeSize); const maze: CellType[][] = new Array(mazeSize);
@ -84,10 +90,15 @@ export function genMaze(seed) {
maze[i] = new Array(mazeSize).fill('empty'); maze[i] = new Array(mazeSize).fill('empty');
} }
const origin = { if (donut) {
x: rand(mazeSize), for (let y = 0; y < mazeSize; y++) {
y: rand(mazeSize), for (let x = 0; x < mazeSize; x++) {
}; if (x >= donutWidth && x < mazeSize - donutWidth && y >= donutWidth && y < mazeSize - donutWidth) {
maze[x][y] = 'void';
}
}
}
}
function checkDiggable(x: number, y: number, dir: Dir) { function checkDiggable(x: number, y: number, dir: Dir) {
if (cellVariants[maze[x][y]].digg[dir] === null) return false; if (cellVariants[maze[x][y]].digg[dir] === null) return false;
@ -102,6 +113,7 @@ export function genMaze(seed) {
if (newPos.x < 0 || newPos.y < 0 || newPos.x >= mazeSize || newPos.y >= mazeSize) return false; if (newPos.x < 0 || newPos.y < 0 || newPos.x >= mazeSize || newPos.y >= mazeSize) return false;
const cell = maze[newPos.x][newPos.y]; const cell = maze[newPos.x][newPos.y];
if (cell === 'void') return false;
if (cell === 'empty') return true; if (cell === 'empty') return true;
if (cellVariants[cell].cross[dir] && checkDiggable(newPos.x, newPos.y, dir)) return true; if (cellVariants[cell].cross[dir] && checkDiggable(newPos.x, newPos.y, dir)) return true;
@ -148,7 +160,20 @@ export function genMaze(seed) {
} }
} }
diggFrom(origin.x, origin.y); //#region start digg
const nonVoidCells = [];
for (let y = 0; y < mazeSize; y++) {
for (let x = 0; x < mazeSize; x++) {
const cell = maze[x][y];
if (cell !== 'void') nonVoidCells.push([x, y]);
}
}
const origin = nonVoidCells[rand(nonVoidCells.length)];
diggFrom(origin[0], origin[1]);
//#endregion
let hasEmptyCell = true; let hasEmptyCell = true;
while (hasEmptyCell) { while (hasEmptyCell) {
@ -157,7 +182,7 @@ export function genMaze(seed) {
for (let y = 0; y < mazeSize; y++) { for (let y = 0; y < mazeSize; y++) {
for (let x = 0; x < mazeSize; x++) { for (let x = 0; x < mazeSize; x++) {
const cell = maze[x][y]; const cell = maze[x][y];
if (cell !== 'empty' && cell !== 'cross') nonEmptyCells.push([x, y]); if (cell !== 'empty' && cell !== 'void' && cell !== 'cross') nonEmptyCells.push([x, y]);
} }
} }

View file

@ -1 +1 @@
export type CellType = 'empty' | 'left' | 'right' | 'top' | 'bottom' | 'leftTop' | 'leftBottom' | 'rightTop' | 'rightBottom' | 'leftRightTop' | 'leftRightBottom' | 'leftTopBottom' | 'rightTopBottom' | 'leftRight' | 'topBottom' | 'cross'; export type CellType = 'void' | 'empty' | 'left' | 'right' | 'top' | 'bottom' | 'leftTop' | 'leftBottom' | 'rightTop' | 'rightBottom' | 'leftRightTop' | 'leftRightBottom' | 'leftTopBottom' | 'rightTopBottom' | 'leftRight' | 'topBottom' | 'cross';

View file

@ -29,8 +29,8 @@ export function renderMaze(seed, maze: CellType[][], stream: fs.WriteStream): Pr
// Draw // Draw
function drawCell(ctx, x, y, size, left, right, top, bottom, mark) { function drawCell(ctx, x, y, size, left, right, top, bottom, mark) {
const wallThickness = size / 8; const wallThickness = size / 6;
const margin = size / 5; const margin = size / 6;
const markerMargin = size / 3; const markerMargin = size / 3;
ctx.fillStyle = colors.road; ctx.fillStyle = colors.road;