Implemented simple rooms. Fixed #14
This commit is contained in:
parent
eef0fc6c0b
commit
eaa2c78d8c
|
@ -8,6 +8,7 @@ use mapgen::dungeon::{
|
||||||
starting_point::{AreaStartingPosition, XStart, YStart},
|
starting_point::{AreaStartingPosition, XStart, YStart},
|
||||||
cull_unreachable::CullUnreachable,
|
cull_unreachable::CullUnreachable,
|
||||||
distant_exit::DistantExit,
|
distant_exit::DistantExit,
|
||||||
|
rooms_corridors_nearest::NearestCorridors,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
@ -47,6 +48,7 @@ impl World {
|
||||||
pub fn new_random_rooms(width: u32, height: u32, seed: u32) -> World {
|
pub fn new_random_rooms(width: u32, height: u32, seed: u32) -> World {
|
||||||
let mut rng = StdRng::seed_from_u64(seed as u64);
|
let mut rng = StdRng::seed_from_u64(seed as u64);
|
||||||
let map = MapBuilder::new(Box::new(RandomRoomsGen::new()))
|
let map = MapBuilder::new(Box::new(RandomRoomsGen::new()))
|
||||||
|
.with(NearestCorridors::new())
|
||||||
.build_map_with_rng(width as usize, height as usize, &mut rng);
|
.build_map_with_rng(width as usize, height as usize, &mut rng);
|
||||||
let tiles = (0..map.tiles.len())
|
let tiles = (0..map.tiles.len())
|
||||||
.map(|i| if map.tiles[i] == TileType::Floor {Cell::Floor} else {Cell::Wall})
|
.map(|i| if map.tiles[i] == TileType::Floor {Cell::Floor} else {Cell::Wall})
|
||||||
|
|
|
@ -4,11 +4,11 @@
|
||||||
/*!*****************************!*\
|
/*!*****************************!*\
|
||||||
!*** ../pkg/mapgen_demo.js ***!
|
!*** ../pkg/mapgen_demo.js ***!
|
||||||
\*****************************/
|
\*****************************/
|
||||||
/*! exports provided: World, __wbindgen_object_drop_ref, __wbg_getTime_29addd71c7089c47, __wbg_new0_a3af66503e735141, __wbindgen_throw */
|
/*! exports provided: Cell, World, __wbindgen_throw */
|
||||||
/***/ (function(module, __webpack_exports__, __webpack_require__) {
|
/***/ (function(module, __webpack_exports__, __webpack_require__) {
|
||||||
|
|
||||||
"use strict";
|
"use strict";
|
||||||
eval("__webpack_require__.r(__webpack_exports__);\n/* harmony import */ var _mapgen_demo_bg_wasm__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! ./mapgen_demo_bg.wasm */ \"../pkg/mapgen_demo_bg.wasm\");\n/* harmony import */ var _mapgen_demo_bg_js__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ./mapgen_demo_bg.js */ \"../pkg/mapgen_demo_bg.js\");\n/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, \"World\", function() { return _mapgen_demo_bg_js__WEBPACK_IMPORTED_MODULE_1__[\"World\"]; });\n\n/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, \"__wbindgen_object_drop_ref\", function() { return _mapgen_demo_bg_js__WEBPACK_IMPORTED_MODULE_1__[\"__wbindgen_object_drop_ref\"]; });\n\n/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, \"__wbg_getTime_29addd71c7089c47\", function() { return _mapgen_demo_bg_js__WEBPACK_IMPORTED_MODULE_1__[\"__wbg_getTime_29addd71c7089c47\"]; });\n\n/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, \"__wbg_new0_a3af66503e735141\", function() { return _mapgen_demo_bg_js__WEBPACK_IMPORTED_MODULE_1__[\"__wbg_new0_a3af66503e735141\"]; });\n\n/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, \"__wbindgen_throw\", function() { return _mapgen_demo_bg_js__WEBPACK_IMPORTED_MODULE_1__[\"__wbindgen_throw\"]; });\n\n\n\n\n//# sourceURL=webpack:///../pkg/mapgen_demo.js?");
|
eval("__webpack_require__.r(__webpack_exports__);\n/* harmony import */ var _mapgen_demo_bg_wasm__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! ./mapgen_demo_bg.wasm */ \"../pkg/mapgen_demo_bg.wasm\");\n/* harmony import */ var _mapgen_demo_bg_js__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! ./mapgen_demo_bg.js */ \"../pkg/mapgen_demo_bg.js\");\n/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, \"Cell\", function() { return _mapgen_demo_bg_js__WEBPACK_IMPORTED_MODULE_1__[\"Cell\"]; });\n\n/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, \"World\", function() { return _mapgen_demo_bg_js__WEBPACK_IMPORTED_MODULE_1__[\"World\"]; });\n\n/* harmony reexport (safe) */ __webpack_require__.d(__webpack_exports__, \"__wbindgen_throw\", function() { return _mapgen_demo_bg_js__WEBPACK_IMPORTED_MODULE_1__[\"__wbindgen_throw\"]; });\n\n\n\n\n//# sourceURL=webpack:///../pkg/mapgen_demo.js?");
|
||||||
|
|
||||||
/***/ }),
|
/***/ }),
|
||||||
|
|
||||||
|
@ -16,11 +16,11 @@ eval("__webpack_require__.r(__webpack_exports__);\n/* harmony import */ var _map
|
||||||
/*!********************************!*\
|
/*!********************************!*\
|
||||||
!*** ../pkg/mapgen_demo_bg.js ***!
|
!*** ../pkg/mapgen_demo_bg.js ***!
|
||||||
\********************************/
|
\********************************/
|
||||||
/*! exports provided: World, __wbindgen_object_drop_ref, __wbg_getTime_29addd71c7089c47, __wbg_new0_a3af66503e735141, __wbindgen_throw */
|
/*! exports provided: Cell, World, __wbindgen_throw */
|
||||||
/***/ (function(module, __webpack_exports__, __webpack_require__) {
|
/***/ (function(module, __webpack_exports__, __webpack_require__) {
|
||||||
|
|
||||||
"use strict";
|
"use strict";
|
||||||
eval("__webpack_require__.r(__webpack_exports__);\n/* WEBPACK VAR INJECTION */(function(module) {/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, \"World\", function() { return World; });\n/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, \"__wbindgen_object_drop_ref\", function() { return __wbindgen_object_drop_ref; });\n/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, \"__wbg_getTime_29addd71c7089c47\", function() { return __wbg_getTime_29addd71c7089c47; });\n/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, \"__wbg_new0_a3af66503e735141\", function() { return __wbg_new0_a3af66503e735141; });\n/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, \"__wbindgen_throw\", function() { return __wbindgen_throw; });\n/* harmony import */ var _mapgen_demo_bg_wasm__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! ./mapgen_demo_bg.wasm */ \"../pkg/mapgen_demo_bg.wasm\");\n\n\nconst heap = new Array(32).fill(undefined);\n\nheap.push(undefined, null, true, false);\n\nfunction getObject(idx) { return heap[idx]; }\n\nlet heap_next = heap.length;\n\nfunction dropObject(idx) {\n if (idx < 36) return;\n heap[idx] = heap_next;\n heap_next = idx;\n}\n\nfunction takeObject(idx) {\n const ret = getObject(idx);\n dropObject(idx);\n return ret;\n}\n\nconst lTextDecoder = typeof TextDecoder === 'undefined' ? (0, module.require)('util').TextDecoder : TextDecoder;\n\nlet cachedTextDecoder = new lTextDecoder('utf-8', { ignoreBOM: true, fatal: true });\n\ncachedTextDecoder.decode();\n\nlet cachegetUint8Memory0 = null;\nfunction getUint8Memory0() {\n if (cachegetUint8Memory0 === null || cachegetUint8Memory0.buffer !== _mapgen_demo_bg_wasm__WEBPACK_IMPORTED_MODULE_0__[\"memory\"].buffer) {\n cachegetUint8Memory0 = new Uint8Array(_mapgen_demo_bg_wasm__WEBPACK_IMPORTED_MODULE_0__[\"memory\"].buffer);\n }\n return cachegetUint8Memory0;\n}\n\nfunction getStringFromWasm0(ptr, len) {\n return cachedTextDecoder.decode(getUint8Memory0().subarray(ptr, ptr + len));\n}\n\nfunction addHeapObject(obj) {\n if (heap_next === heap.length) heap.push(heap.length + 1);\n const idx = heap_next;\n heap_next = heap[idx];\n\n heap[idx] = obj;\n return idx;\n}\n/**\n*/\nclass World {\n\n static __wrap(ptr) {\n const obj = Object.create(World.prototype);\n obj.ptr = ptr;\n\n return obj;\n }\n\n free() {\n const ptr = this.ptr;\n this.ptr = 0;\n\n _mapgen_demo_bg_wasm__WEBPACK_IMPORTED_MODULE_0__[\"__wbg_world_free\"](ptr);\n }\n /**\n * @param {number} width\n * @param {number} height\n * @returns {World}\n */\n static new(width, height) {\n var ret = _mapgen_demo_bg_wasm__WEBPACK_IMPORTED_MODULE_0__[\"world_new\"](width, height);\n return World.__wrap(ret);\n }\n /**\n * @returns {number}\n */\n width() {\n var ret = _mapgen_demo_bg_wasm__WEBPACK_IMPORTED_MODULE_0__[\"world_width\"](this.ptr);\n return ret >>> 0;\n }\n /**\n * @returns {number}\n */\n height() {\n var ret = _mapgen_demo_bg_wasm__WEBPACK_IMPORTED_MODULE_0__[\"world_height\"](this.ptr);\n return ret >>> 0;\n }\n /**\n * @returns {number}\n */\n tiles() {\n var ret = _mapgen_demo_bg_wasm__WEBPACK_IMPORTED_MODULE_0__[\"world_tiles\"](this.ptr);\n return ret;\n }\n}\n\nconst __wbindgen_object_drop_ref = function(arg0) {\n takeObject(arg0);\n};\n\nconst __wbg_getTime_29addd71c7089c47 = function(arg0) {\n var ret = getObject(arg0).getTime();\n return ret;\n};\n\nconst __wbg_new0_a3af66503e735141 = function() {\n var ret = new Date();\n return addHeapObject(ret);\n};\n\nconst __wbindgen_throw = function(arg0, arg1) {\n throw new Error(getStringFromWasm0(arg0, arg1));\n};\n\n\n/* WEBPACK VAR INJECTION */}.call(this, __webpack_require__(/*! ./../www/node_modules/webpack/buildin/harmony-module.js */ \"./node_modules/webpack/buildin/harmony-module.js\")(module)))\n\n//# sourceURL=webpack:///../pkg/mapgen_demo_bg.js?");
|
eval("__webpack_require__.r(__webpack_exports__);\n/* WEBPACK VAR INJECTION */(function(module) {/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, \"Cell\", function() { return Cell; });\n/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, \"World\", function() { return World; });\n/* harmony export (binding) */ __webpack_require__.d(__webpack_exports__, \"__wbindgen_throw\", function() { return __wbindgen_throw; });\n/* harmony import */ var _mapgen_demo_bg_wasm__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! ./mapgen_demo_bg.wasm */ \"../pkg/mapgen_demo_bg.wasm\");\n\n\nconst lTextDecoder = typeof TextDecoder === 'undefined' ? (0, module.require)('util').TextDecoder : TextDecoder;\n\nlet cachedTextDecoder = new lTextDecoder('utf-8', { ignoreBOM: true, fatal: true });\n\ncachedTextDecoder.decode();\n\nlet cachegetUint8Memory0 = null;\nfunction getUint8Memory0() {\n if (cachegetUint8Memory0 === null || cachegetUint8Memory0.buffer !== _mapgen_demo_bg_wasm__WEBPACK_IMPORTED_MODULE_0__[\"memory\"].buffer) {\n cachegetUint8Memory0 = new Uint8Array(_mapgen_demo_bg_wasm__WEBPACK_IMPORTED_MODULE_0__[\"memory\"].buffer);\n }\n return cachegetUint8Memory0;\n}\n\nfunction getStringFromWasm0(ptr, len) {\n return cachedTextDecoder.decode(getUint8Memory0().subarray(ptr, ptr + len));\n}\n/**\n*/\nconst Cell = Object.freeze({ Floor:0,\"0\":\"Floor\",Wall:1,\"1\":\"Wall\", });\n/**\n*/\nclass World {\n\n static __wrap(ptr) {\n const obj = Object.create(World.prototype);\n obj.ptr = ptr;\n\n return obj;\n }\n\n free() {\n const ptr = this.ptr;\n this.ptr = 0;\n\n _mapgen_demo_bg_wasm__WEBPACK_IMPORTED_MODULE_0__[\"__wbg_world_free\"](ptr);\n }\n /**\n * @param {number} width\n * @param {number} height\n * @param {number} seed\n * @returns {World}\n */\n static new_cellular_automata(width, height, seed) {\n var ret = _mapgen_demo_bg_wasm__WEBPACK_IMPORTED_MODULE_0__[\"world_new_cellular_automata\"](width, height, seed);\n return World.__wrap(ret);\n }\n /**\n * @param {number} width\n * @param {number} height\n * @param {number} seed\n * @returns {World}\n */\n static new_random_rooms(width, height, seed) {\n var ret = _mapgen_demo_bg_wasm__WEBPACK_IMPORTED_MODULE_0__[\"world_new_random_rooms\"](width, height, seed);\n return World.__wrap(ret);\n }\n /**\n * @returns {number}\n */\n width() {\n var ret = _mapgen_demo_bg_wasm__WEBPACK_IMPORTED_MODULE_0__[\"world_width\"](this.ptr);\n return ret >>> 0;\n }\n /**\n * @returns {number}\n */\n height() {\n var ret = _mapgen_demo_bg_wasm__WEBPACK_IMPORTED_MODULE_0__[\"world_height\"](this.ptr);\n return ret >>> 0;\n }\n /**\n * @returns {number}\n */\n tiles() {\n var ret = _mapgen_demo_bg_wasm__WEBPACK_IMPORTED_MODULE_0__[\"world_tiles\"](this.ptr);\n return ret;\n }\n}\n\nconst __wbindgen_throw = function(arg0, arg1) {\n throw new Error(getStringFromWasm0(arg0, arg1));\n};\n\n\n/* WEBPACK VAR INJECTION */}.call(this, __webpack_require__(/*! ./../www/node_modules/webpack/buildin/harmony-module.js */ \"./node_modules/webpack/buildin/harmony-module.js\")(module)))\n\n//# sourceURL=webpack:///../pkg/mapgen_demo_bg.js?");
|
||||||
|
|
||||||
/***/ }),
|
/***/ }),
|
||||||
|
|
||||||
|
@ -28,7 +28,7 @@ eval("__webpack_require__.r(__webpack_exports__);\n/* WEBPACK VAR INJECTION */(f
|
||||||
/*!**********************************!*\
|
/*!**********************************!*\
|
||||||
!*** ../pkg/mapgen_demo_bg.wasm ***!
|
!*** ../pkg/mapgen_demo_bg.wasm ***!
|
||||||
\**********************************/
|
\**********************************/
|
||||||
/*! exports provided: memory, __wbg_world_free, world_new, world_width, world_height, world_tiles */
|
/*! exports provided: memory, __wbg_world_free, world_new_cellular_automata, world_new_random_rooms, world_width, world_height, world_tiles */
|
||||||
/***/ (function(module, exports, __webpack_require__) {
|
/***/ (function(module, exports, __webpack_require__) {
|
||||||
|
|
||||||
eval("\"use strict\";\n// Instantiate WebAssembly module\nvar wasmExports = __webpack_require__.w[module.i];\n__webpack_require__.r(exports);\n// export exports from WebAssembly module\nfor(var name in wasmExports) if(name != \"__webpack_init__\") exports[name] = wasmExports[name];\n// exec imports from WebAssembly module (for esm order)\n/* harmony import */ var m0 = __webpack_require__(/*! ./mapgen_demo_bg.js */ \"../pkg/mapgen_demo_bg.js\");\n\n\n// exec wasm module\nwasmExports[\"__webpack_init__\"]()\n\n//# sourceURL=webpack:///../pkg/mapgen_demo_bg.wasm?");
|
eval("\"use strict\";\n// Instantiate WebAssembly module\nvar wasmExports = __webpack_require__.w[module.i];\n__webpack_require__.r(exports);\n// export exports from WebAssembly module\nfor(var name in wasmExports) if(name != \"__webpack_init__\") exports[name] = wasmExports[name];\n// exec imports from WebAssembly module (for esm order)\n/* harmony import */ var m0 = __webpack_require__(/*! ./mapgen_demo_bg.js */ \"../pkg/mapgen_demo_bg.js\");\n\n\n// exec wasm module\nwasmExports[\"__webpack_init__\"]()\n\n//# sourceURL=webpack:///../pkg/mapgen_demo_bg.wasm?");
|
||||||
|
@ -43,7 +43,7 @@ eval("\"use strict\";\n// Instantiate WebAssembly module\nvar wasmExports = __we
|
||||||
/***/ (function(module, __webpack_exports__, __webpack_require__) {
|
/***/ (function(module, __webpack_exports__, __webpack_require__) {
|
||||||
|
|
||||||
"use strict";
|
"use strict";
|
||||||
eval("__webpack_require__.r(__webpack_exports__);\n/* harmony import */ var mapgen_demo__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! mapgen-demo */ \"../pkg/mapgen_demo.js\");\n/* harmony import */ var mapgen_demo_mapgen_demo_bg__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! mapgen-demo/mapgen_demo_bg */ \"../pkg/mapgen_demo_bg.wasm\");\n\n\n\nconst CELL_SIZE = 12;\nconst GRID_COLOR = \"#CCCCCC\";\nconst DEAD_COLOR = \"#FFFFFF\";\nconst ALIVE_COLOR = \"#000000\";\n\nconst world = mapgen_demo__WEBPACK_IMPORTED_MODULE_0__[\"World\"].new(80, 50);\nconst width = world.width();\nconst height = world.height();\n\n// Give the canvas room for all of our cells and a 1px border\n// around each of them.\nconst canvas = document.getElementById(\"mapgen-canvas\");\ncanvas.height = (CELL_SIZE + 1) * height + 1;\ncanvas.width = (CELL_SIZE + 1) * width + 1;\n\nconst ctx = canvas.getContext('2d');\n\nconst renderLoop = () => {\n // universe.tick();\n\n drawGrid();\n drawCells();\n\n requestAnimationFrame(renderLoop);\n};\n\nconst drawGrid = () => {\n ctx.beginPath();\n ctx.strokeStyle = GRID_COLOR;\n\n // Vertical lines.\n for (let i = 0; i <= width; i++) {\n ctx.moveTo(i * (CELL_SIZE + 1) + 1, 0);\n ctx.lineTo(i * (CELL_SIZE + 1) + 1, (CELL_SIZE + 1) * height + 1);\n }\n\n // Horizontal lines.\n for (let j = 0; j <= height; j++) {\n ctx.moveTo(0, j * (CELL_SIZE + 1) + 1);\n ctx.lineTo((CELL_SIZE + 1) * width + 1, j * (CELL_SIZE + 1) + 1);\n }\n\n ctx.stroke();\n};\n\nconst getIndex = (row, column) => {\n return row * width + column;\n};\n\nconst drawCells = () => {\n const tilesPtr = world.tiles();\n const tiles = new Uint8Array(mapgen_demo_mapgen_demo_bg__WEBPACK_IMPORTED_MODULE_1__[\"memory\"].buffer, tilesPtr, width * height);\n\n ctx.beginPath();\n\n for (let row = 0; row < height; row++) {\n for (let col = 0; col < width; col++) {\n const idx = getIndex(row, col);\n\n ctx.fillStyle = tiles[idx]\n ? DEAD_COLOR\n : ALIVE_COLOR;\n\n ctx.fillRect(\n col * (CELL_SIZE + 1) + 1,\n row * (CELL_SIZE + 1) + 1,\n CELL_SIZE,\n CELL_SIZE\n );\n }\n }\n\n ctx.stroke();\n};\n\ndrawGrid();\ndrawCells();\nrequestAnimationFrame(renderLoop);\n\n//# sourceURL=webpack:///./index.js?");
|
eval("__webpack_require__.r(__webpack_exports__);\n/* harmony import */ var mapgen_demo__WEBPACK_IMPORTED_MODULE_0__ = __webpack_require__(/*! mapgen-demo */ \"../pkg/mapgen_demo.js\");\n/* harmony import */ var mapgen_demo_mapgen_demo_bg__WEBPACK_IMPORTED_MODULE_1__ = __webpack_require__(/*! mapgen-demo/mapgen_demo_bg */ \"../pkg/mapgen_demo_bg.wasm\");\n\n\n\nconst CELL_SIZE = 12;\nconst GRID_COLOR = \"#CCCCCC\";\nconst DEAD_COLOR = \"#FFFFFF\";\nconst ALIVE_COLOR = \"#000000\";\n\nvar world = null;\nconst width = 80;\nconst height = 50;\n\nconst infoDiv = document.getElementById('map-info');\n// Give the canvas room for all of our cells and a 1px border\n// around each of them.\nconst canvas = document.getElementById(\"mapgen-canvas\");\ncanvas.height = (CELL_SIZE + 1) * height + 1;\ncanvas.width = (CELL_SIZE + 1) * width + 1;\n\nconst ctx = canvas.getContext('2d');\n\n// Map generators\nfunction newCellularAutomata() {\n var seed = Date.now();\n world = mapgen_demo__WEBPACK_IMPORTED_MODULE_0__[\"World\"].new_cellular_automata(width, height, seed);\n requestAnimationFrame(renderLoop);\n infoDiv.textContent = \"Cellular Automata with the seed: \" + seed;\n}\n\nfunction newSimpleRooms() {\n var seed = Date.now();\n world = mapgen_demo__WEBPACK_IMPORTED_MODULE_0__[\"World\"].new_random_rooms(width, height, seed);\n requestAnimationFrame(renderLoop);\n infoDiv.textContent = \"Random Rooms with the seed: \" + seed;\n}\n\nconst renderLoop = () => {\n // universe.tick();\n\n drawGrid();\n drawCells();\n\n requestAnimationFrame(renderLoop);\n};\n\nconst drawGrid = () => {\n ctx.beginPath();\n ctx.strokeStyle = GRID_COLOR;\n\n // Vertical lines.\n for (let i = 0; i <= width; i++) {\n ctx.moveTo(i * (CELL_SIZE + 1) + 1, 0);\n ctx.lineTo(i * (CELL_SIZE + 1) + 1, (CELL_SIZE + 1) * height + 1);\n }\n\n // Horizontal lines.\n for (let j = 0; j <= height; j++) {\n ctx.moveTo(0, j * (CELL_SIZE + 1) + 1);\n ctx.lineTo((CELL_SIZE + 1) * width + 1, j * (CELL_SIZE + 1) + 1);\n }\n\n ctx.stroke();\n};\n\nconst getIndex = (row, column) => {\n return row * width + column;\n};\n\nconst drawCells = () => {\n const tilesPtr = world.tiles();\n const tiles = new Uint8Array(mapgen_demo_mapgen_demo_bg__WEBPACK_IMPORTED_MODULE_1__[\"memory\"].buffer, tilesPtr, width * height);\n\n ctx.beginPath();\n\n for (let row = 0; row < height; row++) {\n for (let col = 0; col < width; col++) {\n const idx = getIndex(row, col);\n\n ctx.fillStyle = tiles[idx] == mapgen_demo__WEBPACK_IMPORTED_MODULE_0__[\"Cell\"].Floor\n ? DEAD_COLOR\n : ALIVE_COLOR;\n\n ctx.fillRect(\n col * (CELL_SIZE + 1) + 1,\n row * (CELL_SIZE + 1) + 1,\n CELL_SIZE,\n CELL_SIZE\n );\n }\n }\n\n ctx.stroke();\n};\n\nnewCellularAutomata();\n\n// Connect UI element\ndocument.getElementById('cellular-automata-option').addEventListener('click', newCellularAutomata);\ndocument.getElementById('simple-rooms-option').addEventListener('click', newSimpleRooms);\n\n\n//# sourceURL=webpack:///./index.js?");
|
||||||
|
|
||||||
/***/ }),
|
/***/ }),
|
||||||
|
|
||||||
|
|
BIN
docs/bbf7fe2631d06e11148e.module.wasm
Normal file
BIN
docs/bbf7fe2631d06e11148e.module.wasm
Normal file
Binary file not shown.
11
docs/bootstrap.js
vendored
11
docs/bootstrap.js
vendored
|
@ -55,15 +55,6 @@
|
||||||
/******/ "../pkg/mapgen_demo_bg.wasm": function() {
|
/******/ "../pkg/mapgen_demo_bg.wasm": function() {
|
||||||
/******/ return {
|
/******/ return {
|
||||||
/******/ "./mapgen_demo_bg.js": {
|
/******/ "./mapgen_demo_bg.js": {
|
||||||
/******/ "__wbindgen_object_drop_ref": function(p0i32) {
|
|
||||||
/******/ return installedModules["../pkg/mapgen_demo_bg.js"].exports["__wbindgen_object_drop_ref"](p0i32);
|
|
||||||
/******/ },
|
|
||||||
/******/ "__wbg_getTime_29addd71c7089c47": function(p0i32) {
|
|
||||||
/******/ return installedModules["../pkg/mapgen_demo_bg.js"].exports["__wbg_getTime_29addd71c7089c47"](p0i32);
|
|
||||||
/******/ },
|
|
||||||
/******/ "__wbg_new0_a3af66503e735141": function() {
|
|
||||||
/******/ return installedModules["../pkg/mapgen_demo_bg.js"].exports["__wbg_new0_a3af66503e735141"]();
|
|
||||||
/******/ },
|
|
||||||
/******/ "__wbindgen_throw": function(p0i32,p1i32) {
|
/******/ "__wbindgen_throw": function(p0i32,p1i32) {
|
||||||
/******/ return installedModules["../pkg/mapgen_demo_bg.js"].exports["__wbindgen_throw"](p0i32,p1i32);
|
/******/ return installedModules["../pkg/mapgen_demo_bg.js"].exports["__wbindgen_throw"](p0i32,p1i32);
|
||||||
/******/ }
|
/******/ }
|
||||||
|
@ -168,7 +159,7 @@
|
||||||
/******/ promises.push(installedWasmModuleData);
|
/******/ promises.push(installedWasmModuleData);
|
||||||
/******/ else {
|
/******/ else {
|
||||||
/******/ var importObject = wasmImportObjects[wasmModuleId]();
|
/******/ var importObject = wasmImportObjects[wasmModuleId]();
|
||||||
/******/ var req = fetch(__webpack_require__.p + "" + {"../pkg/mapgen_demo_bg.wasm":"bf853f7fb17b7aed38db"}[wasmModuleId] + ".module.wasm");
|
/******/ var req = fetch(__webpack_require__.p + "" + {"../pkg/mapgen_demo_bg.wasm":"bbf7fe2631d06e11148e"}[wasmModuleId] + ".module.wasm");
|
||||||
/******/ var promise;
|
/******/ var promise;
|
||||||
/******/ if(importObject instanceof Promise && typeof WebAssembly.compileStreaming === 'function') {
|
/******/ if(importObject instanceof Promise && typeof WebAssembly.compileStreaming === 'function') {
|
||||||
/******/ promise = Promise.all([WebAssembly.compileStreaming(req), importObject]).then(function(items) {
|
/******/ promise = Promise.all([WebAssembly.compileStreaming(req), importObject]).then(function(items) {
|
||||||
|
|
|
@ -3,11 +3,54 @@
|
||||||
<head>
|
<head>
|
||||||
<meta charset="utf-8">
|
<meta charset="utf-8">
|
||||||
<title>Mapgen demo</title>
|
<title>Mapgen demo</title>
|
||||||
|
<link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.5.2/css/bootstrap.min.css"
|
||||||
|
integrity="sha384-JcKb8q3iqJ61gNV9KGb8thSsNjpSL0n8PARn9HuZOnIxN0hoP+VmmDGMN5t9UJ0Z" crossorigin="anonymous">
|
||||||
|
<style>
|
||||||
|
body {
|
||||||
|
background-color: lightgrey;
|
||||||
|
}
|
||||||
|
canvas {
|
||||||
|
padding-left: 0;
|
||||||
|
padding-right: 0;
|
||||||
|
margin-left: auto;
|
||||||
|
margin-right: auto;
|
||||||
|
display: block;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
|
<script src="./bootstrap.js"></script>
|
||||||
</head>
|
</head>
|
||||||
<body>
|
<body>
|
||||||
<h1>Mapgen demo</h1>
|
<nav class="navbar navbar-expand-lg navbar-light bg-light">
|
||||||
|
<a class="navbar-brand" href="#">Mapgen demo</a>
|
||||||
|
<button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarSupportedContent"
|
||||||
|
aria-controls="navbarSupportedContent" aria-expanded="false" aria-label="Toggle navigation">
|
||||||
|
<span class="navbar-toggler-icon"></span>
|
||||||
|
</button>
|
||||||
|
|
||||||
|
<div class="collapse navbar-collapse" id="navbarSupportedContent">
|
||||||
|
<ul class="navbar-nav mr-auto">
|
||||||
|
<li class="nav-item dropdown">
|
||||||
|
<a class="nav-link dropdown-toggle" href="#" id="navbarDropdown" role="button" data-toggle="dropdown"
|
||||||
|
aria-haspopup="true" aria-expanded="false">
|
||||||
|
Select generator
|
||||||
|
</a>
|
||||||
|
<div class="dropdown-menu" aria-labelledby="navbarDropdown">
|
||||||
|
<a class="dropdown-item" href="#" id="cellular-automata-option">Cellular Automata</a>
|
||||||
|
<a class="dropdown-item" id="simple-rooms-option">Simple Rooms</a>
|
||||||
|
</div>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
</nav>
|
||||||
|
|
||||||
<canvas id="mapgen-canvas"></canvas>
|
<canvas id="mapgen-canvas"></canvas>
|
||||||
<noscript>This page contains webassembly and javascript content, please enable javascript in your browser.</noscript>
|
<div id="map-info" style="text-align: center"></div>
|
||||||
<script src="./bootstrap.js"></script>
|
|
||||||
|
<script src="https://code.jquery.com/jquery-3.5.1.slim.min.js"
|
||||||
|
integrity="sha384-DfXdz2htPH0lsSSs5nCTpuj/zy4C+OGpamoFVy38MVBnE+IbbVYUew+OrCXaRkfj" crossorigin="anonymous"></script>
|
||||||
|
<script src="https://cdn.jsdelivr.net/npm/popper.js@1.16.1/dist/umd/popper.min.js"
|
||||||
|
integrity="sha384-9/reFTGAW83EW2RDu2S0VKaIzap3H66lZH81PoYlFhbGU+6BZp6G7niu735Sk7lN" crossorigin="anonymous"></script>
|
||||||
|
<script src="https://stackpath.bootstrapcdn.com/bootstrap/4.5.2/js/bootstrap.min.js"
|
||||||
|
integrity="sha384-B4gt1jrGC7Jh4AgTPSdUtOBvfO8shuf57BaghqFfPlYxofvL8/KUEfYiJOMMV+rV" crossorigin="anonymous"></script>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
|
|
@ -14,6 +14,11 @@ impl Point {
|
||||||
Point {x, y}
|
Point {x, y}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Create new point from i32 coords
|
||||||
|
pub fn new_i32(x: i32, y: i32) -> Point {
|
||||||
|
Point::new(x as usize, y as usize)
|
||||||
|
}
|
||||||
|
|
||||||
/// Euclidean distance to a given point
|
/// Euclidean distance to a given point
|
||||||
pub fn distance_to(self, point: &Point) -> f32 {
|
pub fn distance_to(self, point: &Point) -> f32 {
|
||||||
let a = (self.x as f32 - point.x as f32).powf(2.0);
|
let a = (self.x as f32 - point.x as f32).powf(2.0);
|
||||||
|
@ -41,8 +46,8 @@ impl Rect {
|
||||||
self.x1 <= other.x2 && self.x2 >= other.x1 && self.y1 <= other.y2 && self.y2 >= other.y1
|
self.x1 <= other.x2 && self.x2 >= other.x1 && self.y1 <= other.y2 && self.y2 >= other.y1
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn center(&self) -> (i32, i32) {
|
pub fn center(&self) -> Point {
|
||||||
((self.x1 + self.x2)/2, (self.y1 + self.y2)/2)
|
Point::new_i32((self.x1 + self.x2)/2, (self.y1 + self.y2)/2)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -23,7 +23,9 @@ pub struct Map {
|
||||||
pub width : usize,
|
pub width : usize,
|
||||||
pub height : usize,
|
pub height : usize,
|
||||||
pub starting_point: Option<Point>,
|
pub starting_point: Option<Point>,
|
||||||
pub exit_point: Option<Point>
|
pub exit_point: Option<Point>,
|
||||||
|
pub rooms: Vec<Rect>,
|
||||||
|
pub corridors: Vec<Vec<Point>>,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl Map {
|
impl Map {
|
||||||
|
@ -37,6 +39,8 @@ impl Map {
|
||||||
height,
|
height,
|
||||||
starting_point: None,
|
starting_point: None,
|
||||||
exit_point: None,
|
exit_point: None,
|
||||||
|
rooms: Vec::new(),
|
||||||
|
corridors: Vec::new()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -105,12 +109,36 @@ impl Map {
|
||||||
|
|
||||||
/// Create room on the map at given location
|
/// Create room on the map at given location
|
||||||
/// Room is created by setting all tiles in the room to the Floor
|
/// Room is created by setting all tiles in the room to the Floor
|
||||||
pub fn create_room(&mut self, rect: &Rect) {
|
pub fn add_room(&mut self, rect: Rect) {
|
||||||
for x in rect.x1..rect.x2 {
|
for x in rect.x1..rect.x2 {
|
||||||
for y in rect.y1..rect.y2 {
|
for y in rect.y1..rect.y2 {
|
||||||
self.set_tile(x as usize, y as usize, TileType::Floor);
|
self.set_tile(x as usize, y as usize, TileType::Floor);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
self.rooms.push(rect);
|
||||||
|
}
|
||||||
|
|
||||||
|
pub fn add_corridor(&mut self, from: Point, to:Point) {
|
||||||
|
let mut corridor = Vec::new();
|
||||||
|
let mut x = from.x;
|
||||||
|
let mut y = from.y;
|
||||||
|
|
||||||
|
while x != to.x || y != to.y {
|
||||||
|
if x < to.x {
|
||||||
|
x += 1;
|
||||||
|
} else if x > to.x {
|
||||||
|
x -= 1;
|
||||||
|
} else if y < to.y {
|
||||||
|
y += 1;
|
||||||
|
} else if y > to.y {
|
||||||
|
y -= 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
if self.at(x, y) != TileType::Floor {
|
||||||
|
corridor.push(Point::new(x, y));
|
||||||
|
self.set_tile(x, y, TileType::Floor);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -183,7 +211,7 @@ mod tests {
|
||||||
#[test]
|
#[test]
|
||||||
fn test_create_room() {
|
fn test_create_room() {
|
||||||
let mut map = Map::new(5, 5);
|
let mut map = Map::new(5, 5);
|
||||||
map.create_room(&Rect::new(1, 1, 3, 3));
|
map.add_room(Rect::new(1, 1, 3, 3));
|
||||||
for x in 0..map.width {
|
for x in 0..map.width {
|
||||||
for y in 0..map.height {
|
for y in 0..map.height {
|
||||||
if x == 0 || y == 0 || x == 4 || y == 4 {
|
if x == 0 || y == 0 || x == 4 || y == 4 {
|
||||||
|
@ -195,4 +223,23 @@ mod tests {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn test_add_corridor() {
|
||||||
|
let map_str = "
|
||||||
|
##########
|
||||||
|
# # #
|
||||||
|
##########
|
||||||
|
";
|
||||||
|
let mut map = Map::from_string(map_str);
|
||||||
|
let expected_map_str = "
|
||||||
|
##########
|
||||||
|
# #
|
||||||
|
##########
|
||||||
|
";
|
||||||
|
let expected_map = Map::from_string(expected_map_str);
|
||||||
|
|
||||||
|
map.add_corridor(Point::new(1, 1), Point::new(8, 1));
|
||||||
|
|
||||||
|
assert_eq!(map.tiles, expected_map.tiles);
|
||||||
|
}
|
||||||
}
|
}
|
|
@ -31,6 +31,7 @@ pub mod cellular_automata;
|
||||||
pub mod cull_unreachable;
|
pub mod cull_unreachable;
|
||||||
pub mod distant_exit;
|
pub mod distant_exit;
|
||||||
pub mod random_rooms;
|
pub mod random_rooms;
|
||||||
|
pub mod rooms_corridors_nearest;
|
||||||
pub mod starting_point;
|
pub mod starting_point;
|
||||||
mod dijkstra;
|
mod dijkstra;
|
||||||
|
|
||||||
|
|
|
@ -50,7 +50,6 @@ impl RandomRoomsGen {
|
||||||
|
|
||||||
fn build_rooms(&self, width: usize, height: usize, rng : &mut StdRng) -> Map {
|
fn build_rooms(&self, width: usize, height: usize, rng : &mut StdRng) -> Map {
|
||||||
let mut map = Map::new(width, height);
|
let mut map = Map::new(width, height);
|
||||||
let mut rooms : Vec<Rect> = Vec::new();
|
|
||||||
|
|
||||||
// Create room dimensions
|
// Create room dimensions
|
||||||
for _ in 0..self.max_rooms {
|
for _ in 0..self.max_rooms {
|
||||||
|
@ -59,17 +58,12 @@ impl RandomRoomsGen {
|
||||||
let x = random::random_range(rng, 1, width - w);
|
let x = random::random_range(rng, 1, width - w);
|
||||||
let y = random::random_range(rng, 1, height - h);
|
let y = random::random_range(rng, 1, height - h);
|
||||||
let new_room = Rect::new(x as i32, y as i32, w as i32, h as i32);
|
let new_room = Rect::new(x as i32, y as i32, w as i32, h as i32);
|
||||||
let intersects = rooms.iter().any(|r| new_room.intersect(r));
|
let intersects = map.rooms.iter().any(|r| new_room.intersect(r));
|
||||||
if !intersects {
|
if !intersects {
|
||||||
rooms.push(new_room);
|
map.add_room(new_room);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Apply rooms to the map
|
|
||||||
for room in rooms {
|
|
||||||
map.create_room(&room);
|
|
||||||
}
|
|
||||||
|
|
||||||
map
|
map
|
||||||
}
|
}
|
||||||
}
|
}
|
47
src/dungeon/rooms_corridors_nearest.rs
Normal file
47
src/dungeon/rooms_corridors_nearest.rs
Normal file
|
@ -0,0 +1,47 @@
|
||||||
|
//! Connect nearest rooms on the map with corridors
|
||||||
|
//!
|
||||||
|
use rand::prelude::StdRng;
|
||||||
|
use super::MapModifier;
|
||||||
|
use super::map::Map;
|
||||||
|
use std::collections::HashSet;
|
||||||
|
|
||||||
|
|
||||||
|
pub struct NearestCorridors {}
|
||||||
|
|
||||||
|
impl MapModifier for NearestCorridors {
|
||||||
|
fn modify_map(&self, _: &mut StdRng, map: &Map) -> Map {
|
||||||
|
self.corridors(map)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
impl NearestCorridors {
|
||||||
|
|
||||||
|
pub fn new() -> Box<NearestCorridors> {
|
||||||
|
Box::new(NearestCorridors{})
|
||||||
|
}
|
||||||
|
|
||||||
|
fn corridors(&self, map: &Map) -> Map {
|
||||||
|
let mut new_map = map.clone();
|
||||||
|
|
||||||
|
let mut connected : HashSet<usize> = HashSet::new();
|
||||||
|
for (i,room) in map.rooms.iter().enumerate() {
|
||||||
|
let mut room_distance : Vec<(usize, f32)> = Vec::new();
|
||||||
|
let room_center = room.center();
|
||||||
|
for (j,other_room) in new_map.rooms.iter().enumerate() {
|
||||||
|
if i != j && !connected.contains(&j) {
|
||||||
|
let other_center = other_room.center();
|
||||||
|
let distance = room_center.distance_to(&other_center);
|
||||||
|
room_distance.push((j, distance));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if !room_distance.is_empty() {
|
||||||
|
room_distance.sort_by(|a,b| a.1.partial_cmp(&b.1).unwrap() );
|
||||||
|
let dest_center = new_map.rooms[room_distance[0].0].center();
|
||||||
|
new_map.add_corridor(room_center, dest_center);
|
||||||
|
connected.insert(i);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
new_map
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in New Issue
Block a user