{"version":3,"file":"ngx-mazes.mjs","sources":["../../../projects/ngx-mazes/src/lib/maze-algorithms.model.ts","../../../projects/ngx-mazes/src/lib/algorithms/aldousBroderMaze.model.ts","../../../projects/ngx-mazes/src/lib/algorithms/primsMaze.model.ts","../../../projects/ngx-mazes/src/public-api.ts","../../../projects/ngx-mazes/src/ngx-mazes.ts"],"sourcesContent":["import { Subject } from \"rxjs\";\r\n\r\nexport interface Maze2D {\r\n\twidth: number; height: number;\r\n\ttiles: Tile[][];\r\n}\r\n\r\nexport interface Tile {\r\n  id: string, passable: {l:boolean,r:boolean,t:boolean,b:boolean}; speed: number; wall: boolean;\r\n}\r\n\r\nexport interface IterationData {\r\n  maze: Maze2D; i: number; o: number; iteration: number, timeTaken: number, finalIteration: boolean\r\n}\r\n\r\nexport interface MazeGraph {\r\n  nodes: MazeNode[]\r\n}\r\n\r\nexport interface MazeNode {\r\n  x: number; y: number; id: string; connections: string[]\r\n}\r\n\r\n// delete when appropriate...\r\nexport interface MazeStatsData {\r\n  width: number; height: number; iterations: { min: number; actual: number }; efficiency: number; time: number; maxIterationsPerSecond: number;\r\n}\r\n\r\nexport abstract class MazeAlgorithms {\r\n\r\n  // values which return data\r\n  currentData = new Subject<IterationData>();\r\n\r\n  // control of the process\r\n  play: boolean = true;\r\n\r\n  abstract generateMaze(width: number, height: number, iterationsPerSecond?: number): void;//{ maze: Maze2D, executionTime: number, iterationCount: number };\r\n\r\n  constructor() {}\r\n\r\n  public playMaze():void { this.play = true; }\r\n  public pauseMaze():void { this.play = false; }\r\n\r\n  /**\r\n   * Generates a Maze2D object for the algorithm to use.\r\n   * @param width\r\n   * @param height\r\n   * @returns\r\n   */\r\n  generateMazeStructure(width: number, height: number, makeWalled: boolean = false, passable: boolean = false): Maze2D {\r\n     // make a new maze object\r\n     let maze: Maze2D = { width, height, tiles: [] };\r\n     // build the maze...\r\n     for(let i = 0 ; i < height ; i++) {\r\n       // start a new row\r\n       maze.tiles.push([]);\r\n       // and add the columns...\r\n       for(let o = 0 ; o < width ; o++) {\r\n         // i is the column\r\n         // o is the row\r\n         maze.tiles[i][o] = { id: this.generateRandomString(5), passable: {l:passable,r:passable,t:passable,b:passable}, speed: 1, wall: makeWalled };\r\n       }\r\n     }\r\n     return maze;\r\n  }\r\n\r\n /**\r\n   * Creates a mazegraph out of a maze2d.\r\n   * This is essentially a series of nodes with connectionsbetween adjacent tiles\r\n   * with no wall between them. It can be used for navigation fo the maze\r\n   * @param maze\r\n   * @returns\r\n   */\r\n  generateMazeGraph(maze: Maze2D): MazeGraph {\r\n    let graph: MazeGraph = { nodes: [] };\r\n    for(let i = 0 ; i < maze.tiles.length ; i++) {\r\n      // each row\r\n      for(let o = 0 ; o < maze.tiles[i].length ; o++) {\r\n        // each columns in row i\r\n        const mazeSection: Tile = maze.tiles[i][o];\r\n\r\n        let connections: string[] = [];\r\n\r\n        // connections can only be up down left right, so.\r\n        mazeSection.passable.l && maze.tiles[i][o-1].passable.r && !maze.tiles[i][o-1].wall   ? connections.push(maze.tiles[i][o-1].id) : null;\r\n        mazeSection.passable.r && maze.tiles[i][o+1].passable.l && !maze.tiles[i][o+1].wall   ? connections.push(maze.tiles[i][o+1].id) : null;\r\n        mazeSection.passable.t && maze.tiles[i-1][o].passable.b && !maze.tiles[i-1][o].wall   ? connections.push(maze.tiles[i-1][o].id) : null;\r\n        mazeSection.passable.b && maze.tiles[i+1][o].passable.t && !maze.tiles[i+1][o].wall   ? connections.push(maze.tiles[i+1][o].id) : null;\r\n        // build the node\r\n        const node: MazeNode = { x: o, y: i, id: mazeSection.id, connections: connections }\r\n        graph.nodes.push(node);\r\n      }\r\n    }\r\n    return graph;\r\n  }\r\n\r\n    /**\r\n   * Generates a random stribg of length 'length'\r\n   * Usually used for IDs\r\n   * @param length\r\n   * @returns\r\n   */\r\n     generateRandomString(length: number, alphabet: string = \"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz1234567890\"): string {\r\n      let randomString: string = \"\";\r\n\r\n      for(let i = 0 ; i < length ; i++) {\r\n        let randomNumber: number = Math.floor(Math.random() * alphabet.length);\r\n        randomString += alphabet.charAt(randomNumber);\r\n      }\r\n\r\n      return randomString;\r\n    }\r\n\r\n    /**\r\n     * Makes thick walls throughout the maze so there are no sharp turns.\r\n     * Useful for game mazes.\r\n     * Elegant? No. Working? Yeah!\r\n     * @param maze\r\n     * @returns\r\n     */\r\n    makeWallsThick(maze: Maze2D): Maze2D {\r\n      // new maze is twice as thick as the last\r\n      let thickMaze: Maze2D = this.generateMazeStructure((maze.width * 2) + 1, (maze.height * 2) + 1, true, true);\r\n      const impassible = { t: false, b: false, l: false, r: false };\r\n\r\n      // need multiple iterations because the maze is being rebuilt and no true forward lookup is available...\r\n      for(let i = 0 ; i < maze.height ; i++) {\r\n        //each row\r\n        for(let o = 0 ; o < maze.width ; o++) {\r\n          // each column\r\n          const tile: Tile = maze.tiles[i][o];\r\n\r\n          // set this tile as open\r\n          thickMaze.tiles[2*i][2*o].wall = false;\r\n          thickMaze.tiles[2*i][2*o].wall = false;\r\n\r\n          // to make thickmaze essentially if the cell is passable tot he right, duplicate this tile right, and the same in the y direction\r\n          // if it is NOT passable, make thay adjacent cell a wall...\r\n          if(2*i + 1 <= thickMaze.height - 1) { tile.passable.b ? thickMaze.tiles[(2*i)+1][2*o] = { ...tile, id: this.generateRandomString(5)} : thickMaze.tiles[(2*i)+1][2*o] = { ...thickMaze.tiles[(2*i)+1][2*o], wall: true, passable: impassible} }\r\n          if(2*o + 1 <= thickMaze.width - 1) { tile.passable.r ? thickMaze.tiles[2*i][(2*o)+1] = { ...tile, id: this.generateRandomString(5)} : thickMaze.tiles[2*i][(2*o)+1] = { ...thickMaze.tiles[2*i][(2*o)+1], wall: true, passable: impassible} }\r\n        }\r\n      }\r\n\r\n      // and add walls to cell where needed (helps build the graphs...)\r\n      for(let t = 0 ; t < thickMaze.height ; t++) {\r\n        for(let s = 0 ; s < thickMaze.width ; s++) {\r\n          thickMaze.tiles[t][s].passable = thickMaze.tiles[t][s].wall\r\n                                              ? { t: false, b: false, l: false, r: false }\r\n                                              : {\r\n                                                  b: t + 1 <= thickMaze.height - 1  ? !thickMaze.tiles[t+1][s].wall ? true : false : false,\r\n                                                  t: t - 1 >= 0                     ? !thickMaze.tiles[t-1][s].wall ? true : false : false,\r\n                                                  r: s + 1 <= thickMaze.width - 1   ? !thickMaze.tiles[t][s+1].wall ? true : false : false,\r\n                                                  l: s - 1 >= 0                     ? !thickMaze.tiles[t][s-1].wall ? true : false : false\r\n                                                };\r\n        }\r\n      }\r\n\r\n      for(let t = 0 ; t < thickMaze.height ; t++) {\r\n        thickMaze.tiles[t].unshift(thickMaze.tiles[t][thickMaze.tiles[t].length - 1]);\r\n        thickMaze.tiles[t].splice(thickMaze.tiles[t].length - 1, 1);\r\n      }\r\n\r\n      // make the top a wall and the bottom only have a single line of wall.\r\n      thickMaze.tiles.unshift(thickMaze.tiles[thickMaze.tiles.length - 1]);\r\n      thickMaze.tiles.splice(thickMaze.tiles.length - 1, 1);\r\n\r\n      return thickMaze;\r\n    }\r\n\r\n    /**\r\n     * Takes a maze object and mirrors it in the x direction, adding the same again in a mirror position tot he right hand side\r\n     * @param maze\r\n     * @returns\r\n     */\r\n    mirrorMazeXDirection(maze: Maze2D, timesMirrored?: number): Maze2D {\r\n      let longMaze: Maze2D;\r\n\r\n      // wait for better support to implement\r\n      // try {\r\n      //   longMaze = structuredClone(maze);\r\n      // } catch(e) {\r\n        longMaze = JSON.parse(JSON.stringify(maze));\r\n      // }\r\n\r\n      longMaze.width = maze.width*2;\r\n\r\n      // iterate the rows...\r\n      for(let i = 0 ; i < maze.tiles.length ; i++) {\r\n        // store the value for the tile length or it might end up going forever as it grows itself.\r\n        const rowLength: number = maze.tiles[i].length;\r\n        // iterate over cols...\r\n        for(let o = 0 ; o < rowLength ; o++) {\r\n          // now work backwards from the RHS adding to the array.\r\n          let oldTile: Tile = {...maze.tiles[i][rowLength - 1 - o]};\r\n          let newTile: Tile = {...oldTile};\r\n          // generate a new unique id for the new tile\r\n          newTile.id = this.generateRandomString(5);\r\n          // flip the passables to be a mirror...\r\n          newTile.passable = { l: oldTile.passable.r, r: oldTile.passable.l, t: oldTile.passable.t, b: oldTile.passable.b };\r\n          // and push to the main array...\r\n          longMaze.tiles[i].push({...newTile});\r\n        }\r\n      }\r\n      // open a hole in the right hand side of the maze...\r\n      let randomHeight = Math.floor(Math.random() * longMaze.tiles.length);\r\n      longMaze.tiles[randomHeight][Math.floor(longMaze.tiles[randomHeight].length / 2) -1].passable.r = true;\r\n      longMaze.tiles[randomHeight][Math.floor(longMaze.tiles[randomHeight].length / 2)].passable.l = true;\r\n\r\n      return longMaze;\r\n    }\r\n\r\n    /**\r\n     * Takes a maze object and mirrors in the y direction, doubling the height. Provides one door\r\n     * @param maze\r\n     * @returns\r\n     */\r\n    mirrorMazeYDirection(maze: Maze2D, timesMirrored: number = 2): Maze2D {\r\n        let highMaze: Maze2D;\r\n\r\n        // wait for better support to implement\r\n        // try {\r\n        //   highMaze = structuredClone(maze);\r\n        // } catch(e) {\r\n          highMaze = JSON.parse(JSON.stringify(maze));\r\n        // }\r\n\r\n        highMaze.height = maze.height * 2;\r\n\r\n        const mazeHeight: number = maze.tiles.length;\r\n        // iterate the rows...\r\n        for(let i = mazeHeight - 1 ; i >= 0 ; i--) {\r\n            // copy the row\r\n            let mazeLength: number = maze.tiles[i].length;\r\n            let newRow : Tile[] = [];\r\n            // iterate over and flip the up and down walls...\r\n            for(let o = 0 ; o < mazeLength ; o++) {\r\n              let newTile: Tile = {...maze.tiles[i][o]};\r\n              newTile.passable = { t: maze.tiles[i][o].passable.b, b: maze.tiles[i][o].passable.t, l: maze.tiles[i][o].passable.l, r: maze.tiles[i][o].passable.r };\r\n              newTile.id = this.generateRandomString(5);\r\n              newRow.push(newTile);\r\n            }\r\n            // and put it back onto the array...\r\n            highMaze.tiles.push(newRow);\r\n        }\r\n        // open a hole in the bottom!\r\n        if(timesMirrored) {\r\n            // the maze has already had multiple mirrors\r\n            let division: number = Math.floor(highMaze.tiles[0].length / timesMirrored);\r\n            for(let i = 0 ; i < timesMirrored ; i+=2) {\r\n                highMaze.tiles[Math.floor(highMaze.tiles.length / 2)-1][i*division].passable.b = true;\r\n                highMaze.tiles[Math.floor(highMaze.tiles.length / 2)][i*division].passable.t = true;\r\n                highMaze.tiles[Math.floor(highMaze.tiles.length / 2)-1][highMaze.tiles[0].length - i*division - 1].passable.b = true;\r\n                highMaze.tiles[Math.floor(highMaze.tiles.length / 2)][highMaze.tiles[0].length - i*division - 1].passable.t = true;\r\n            }\r\n        } else {\r\n            let randomPosition: number = Math.floor(Math.random() * highMaze.tiles[0].length);\r\n            highMaze.tiles[Math.floor(highMaze.tiles.length / 2) - 1][randomPosition].passable.b = true;\r\n            highMaze.tiles[Math.floor(highMaze.tiles.length / 2)][randomPosition].passable.t = true;\r\n        }\r\n\r\n        return highMaze;\r\n    }\r\n\r\n\r\n    /**\r\n     * Doors can be made manually...\r\n     * @param maze\r\n     * @param width\r\n     * @param height\r\n     * @param xCenter\r\n     * @param yCenter\r\n     * @returns\r\n     */\r\n    addRoom(maze: Maze2D,  width: number = 5, height: number = 4, xCenter?: number, yCenter?: number): Maze2D {\r\n\r\n      // place it in the middle if center is not defined...\r\n      if(!xCenter) xCenter = maze.tiles[0].length / 2;\r\n      if(!yCenter) yCenter = maze.tiles.length / 2;\r\n\r\n      let xStart: number = xCenter - (width / 2);\r\n      let yStart: number = yCenter - (height / 2);\r\n\r\n      if(xStart % 1 !== 0) { xStart -= 0.5; width += 1; }\r\n      if(yStart % 1 !== 0) { yStart -= 0.5; height += 1; }\r\n\r\n      for(let i = 0 ; i < height ; i++) {\r\n        for(let o = 0 ; o < width ; o++) {\r\n          maze.tiles[i+yStart][(o+xStart)].passable = { l: true, r: true, t: true, b: true };\r\n          maze.tiles[i+yStart][(o+xStart)].wall = false;\r\n\r\n          if((i+yStart) === yStart) { maze.tiles[i+yStart][o+xStart].passable.t = false;  maze.tiles[i+yStart-1][o+xStart].passable.b = false; }\r\n          if((o+xStart) === xStart) { maze.tiles[i+yStart][o+xStart].passable.l = false; maze.tiles[i+yStart][o+xStart-1].passable.r = false;}\r\n          if((i+yStart+1) === yStart + height) { maze.tiles[i+yStart][o+xStart].passable.b = false; maze.tiles[i+yStart+1][o+xStart].passable.t = false;}\r\n          if((o+xStart+1) === xStart + width) { maze.tiles[i+yStart][o+xStart].passable.r = false; maze.tiles[i+yStart][o+xStart+1].passable.l = false;}\r\n        }\r\n      }\r\n\r\n      return maze;\r\n    }\r\n}\r\n","import { Maze2D, MazeAlgorithms } from \"../maze-algorithms.model\";\r\n\r\nexport interface AldousBroderProperties {\r\n  visitedCells: number;\r\n}\r\n\r\nexport class AldousBroderMaze extends MazeAlgorithms {\r\n\r\n  constructor() {\r\n    super();\r\n  }\r\n\r\n  /**\r\n   * Generate an Aldous Broder  Maze\r\n   * INFO: https://weblog.jamisbuck.org/2011/1/17/maze-generation-aldous-broder-algorithm\r\n   *\r\n   * @param width\r\n   * @param height\r\n   * @returns\r\n   */\r\n  generateMaze(width: number, height: number, iterationsPerSecond: number = 0): void {//{ maze: Maze2D, executionTime: number, iterationCount: number } {\r\n    // make a new maze object\r\n    let maze: Maze2D = this.generateMazeStructure(width, height);\r\n    // start the performance indicator...\r\n    const startingTime: number = performance.now();\r\n\r\n    // Psuedo Algorithm\r\n    // https://people.cs.ksu.edu/~ashley78/wiki.ashleycoleman.me/index.php/Aldous-Broder_Algorithm.html\r\n    //\r\n    // 1. Select a random cell and add it to the list visited cells. This is the current cell\r\n    // 2. Randomly choose an adjacent cell, this cell is now the current cell\r\n    //      If the cell is not in the list of visited cells\r\n    //        Add it to the list of visited cells\r\n    //        Remove the edge between the current cell and the previous cell\r\n    //      Else\r\n    //        Do nothing\r\n    // 3. Repeat step 2 until all cells have been visited\r\n\r\n    let visitedCells: { i: number, o: number }[] = [];\r\n    let currentCell: { i: number, o: number } = { i: Math.floor(Math.random() * height), o: Math.floor(Math.random() * width ) };\r\n    let iterationCount: number = 0;\r\n    let timer: number;\r\n    let lastTime: number = 0;\r\n    let pausedTime: number = 0;\r\n\r\n    // until all cells have been visited...\r\n    if(iterationsPerSecond > 0) {\r\n\r\n      timer = window.setTimeout(() => { fn(); }, (1 / iterationsPerSecond) * 1000);\r\n\r\n      const fn = () => {\r\n        if((visitedCells.length < (width * height))) {\r\n          if(this.play) {\r\n            iterationCount++;\r\n            [maze, currentCell, visitedCells] = this.iteration(maze, currentCell, visitedCells, width, height)\r\n            // send out updated coordinates...\r\n            lastTime = performance.now();\r\n            this.currentData.next({maze, i: currentCell.i, o: currentCell.o, iteration: iterationCount, timeTaken: lastTime - startingTime - pausedTime, finalIteration: visitedCells.length === ((width * height) - 2)});\r\n          } else {\r\n            pausedTime += performance.now() - lastTime;\r\n            lastTime = performance.now();\r\n          }\r\n          timer = window.setTimeout(() => { fn(); }, (1 / iterationsPerSecond) * 1000);\r\n        }\r\n      }\r\n\r\n    } else {\r\n      while(visitedCells.length < (width * height)) {\r\n        iterationCount++;\r\n        [maze, currentCell, visitedCells] = this.iteration(maze, currentCell, visitedCells, width, height)\r\n      }\r\n      // push the maze to the user\r\n      this.currentData.next({maze, i: currentCell.i, o: currentCell.o, iteration: 1, timeTaken: performance.now() - startingTime, finalIteration: true});\r\n    }\r\n\r\n\r\n  }\r\n\r\n  /**\r\n   * One iteration of the algorithm\r\n   *\r\n   * @param maze\r\n   * @param currentCell\r\n   * @param visitedCells\r\n   * @param width\r\n   * @param height\r\n   * @returns\r\n   */\r\n  iteration(maze: Maze2D, currentCell: { i: number, o: number }, visitedCells: { i: number, o: number }[], width: number, height: number): [Maze2D, { i: number, o: number }, { i: number, o: number }[]] {\r\n      // select a random adjacent cell\r\n      // 1 2 3\r\n      // 4 5 6\r\n      // 7 8 9\r\n      // Where only 2 4 6 and 8 are considered adjacent as we cant move through a corner...\r\n      let randomAdjacentCell: number = (Math.floor(Math.random() * 4) * 2) + 2;\r\n      let adji: number= currentCell.i;\r\n      let adjo: number= currentCell.o;\r\n\r\n      // set the adjacent coordinates...\r\n      switch(randomAdjacentCell) {\r\n        case 2:\r\n          adji = currentCell.i - 1 >= 0 ? currentCell.i - 1 : currentCell.i;\r\n          adjo = currentCell.o;\r\n          break;\r\n        case 4:\r\n          adji = currentCell.i;\r\n          adjo = currentCell.o - 1 >= 0 ? currentCell.o - 1 : currentCell.o;\r\n          break;\r\n        case 6:\r\n          adji = currentCell.i;\r\n          adjo = currentCell.o + 1 <= width - 1 ? currentCell.o + 1 : currentCell.o;\r\n          break;\r\n        case 8:\r\n          adji = currentCell.i + 1 <= height - 1 ? currentCell.i + 1 : currentCell.i;\r\n          adjo = currentCell.o;\r\n          break;\r\n      }\r\n\r\n      // check if the new cell is inside of the grid, and if so continue the iteration, otherwise reiterate...\r\n      if(adji !== currentCell.i || adjo !== currentCell.o) {\r\n        // find if its in the list of visited cells...\r\n        let isItVisited: boolean = !!visitedCells.find(temp => temp.i === adji && temp.o === adjo);\r\n\r\n        if(!isItVisited) {\r\n          maze.tiles[currentCell.i][currentCell.o].passable = {\r\n            l: randomAdjacentCell === 4 ? true : maze.tiles[currentCell.i][currentCell.o].passable.l,\r\n            r: randomAdjacentCell === 6 ? true : maze.tiles[currentCell.i][currentCell.o].passable.r,\r\n            t: randomAdjacentCell === 2 ? true : maze.tiles[currentCell.i][currentCell.o].passable.t,\r\n            b: randomAdjacentCell === 8 ? true : maze.tiles[currentCell.i][currentCell.o].passable.b\r\n          };\r\n\r\n          // set the passables...\r\n          maze.tiles[adji][adjo].passable = {\r\n            l: randomAdjacentCell === 6 ? true : maze.tiles[adji][adjo].passable.l,\r\n            r: randomAdjacentCell === 4 ? true : maze.tiles[adji][adjo].passable.r,\r\n            t: randomAdjacentCell === 8 ? true : maze.tiles[adji][adjo].passable.t,\r\n            b: randomAdjacentCell === 2 ? true : maze.tiles[adji][adjo].passable.b\r\n          };\r\n          maze.tiles[adji][adjo].speed = 1;\r\n\r\n          visitedCells.push({ i: adji, o: adjo });\r\n        }\r\n\r\n        // set it as the current cell\r\n        currentCell = { i: adji, o: adjo };\r\n      }\r\n    return [maze, currentCell, visitedCells];\r\n  }\r\n\r\n}\r\n","import { Maze2D, MazeAlgorithms } from \"../maze-algorithms.model\";\r\n\r\nexport class PrimsMaze extends MazeAlgorithms {\r\n\r\n  constructor() {\r\n    super();\r\n  }\r\n\r\n  /**\r\n   * Generate a Prims Maze\r\n   * INFO: https://weblog.jamisbuck.org/2011/1/10/maze-generation-prim-s-algorithm\r\n   *\r\n   * @param width\r\n   * @param height\r\n   * @returns\r\n   */\r\n  generateMaze(width: number, height: number, iterationsPerSecond: number = 0): void {//{ maze: Maze2D, executionTime: number, iterationCount: number } {\r\n    // make a new maze object\r\n    let maze: Maze2D = this.generateMazeStructure(width, height);\r\n    // start the performance indicator...\r\n    const startingTime: number = performance.now();\r\n\r\n    // Psuedo Algorithm\r\n    // https://people.cs.ksu.edu/~ashley78/wiki.ashleycoleman.me/index.php/Prim's_Algorithm.html\r\n    //\r\n    // Choose a cell at random and add it to the list of visited cells. This is the current cell.\r\n    // Mark all cells adjacent to the current cell\r\n    // Randomly select a marked cell and remove its connecting edge to a cell from the list of visited cells. This is now the current cell.\r\n    // Repeat 2 until no adjacent wall can be selected\r\n    // While there are marked cells remaining go to 2\r\n\r\n    let currentCell: { i: number, o: number } = { i: Math.floor(Math.random() * height), o: Math.floor(Math.random() * width) };\r\n    let visitedCells: { i: number, o: number }[] = [currentCell];\r\n    let markedCells: { i: number, o: number }[] = [];\r\n\r\n    // set the initial cells around the current cell as marked.\r\n    if(currentCell.o - 1 >= 0) markedCells.push({ o: currentCell.o - 1, i: currentCell.i });\r\n    if(currentCell.o + 1 <= width - 1) markedCells.push({ o: currentCell.o + 1, i: currentCell.i });\r\n    if(currentCell.i - 1 >= 0) markedCells.push({ o: currentCell.o, i: currentCell.i - 1 });\r\n    if(currentCell.i + 1 <= height - 1) markedCells.push({ o: currentCell.o, i: currentCell.i + 1 });\r\n\r\n    // stats\r\n    let iterationCount: number = 0;\r\n    let timer: number;\r\n    let lastTime: number = 0;\r\n    let pausedTime: number = 0;\r\n\r\n    // until all cells have been visited...\r\n    if(iterationsPerSecond > 0) {\r\n\r\n      timer = window.setTimeout(() => { fn(); }, (1 / iterationsPerSecond) * 1000);\r\n\r\n      const fn = (): void => {\r\n        if(markedCells.length > 0) {\r\n          if(this.play) {\r\n            iterationCount++;\r\n            [maze, currentCell, markedCells, visitedCells] = this.iteration(maze, currentCell, markedCells, visitedCells, width, height)\r\n            // send out updated coordinates...\r\n            lastTime = performance.now();\r\n            this.currentData.next({maze, i: currentCell.i, o: currentCell.o, iteration: iterationCount, timeTaken: lastTime - startingTime - pausedTime, finalIteration: visitedCells.length === ((width * height) - 2)});\r\n          } else {\r\n            pausedTime += performance.now() - lastTime;\r\n            lastTime = performance.now();\r\n          }\r\n          timer = window.setTimeout(() => { fn(); }, (1 / iterationsPerSecond) * 1000);\r\n        }\r\n      }\r\n\r\n    } else {\r\n      while(markedCells.length > 0) {\r\n        iterationCount++;\r\n        [maze, currentCell, markedCells, visitedCells] = this.iteration(maze, currentCell, markedCells, visitedCells, width, height)\r\n      }\r\n      // push the maze to the user\r\n      this.currentData.next({maze, i: currentCell.i, o: currentCell.o, iteration: 1, timeTaken: performance.now() - startingTime, finalIteration: true});\r\n    }\r\n\r\n\r\n  }\r\n\r\n  /**\r\n   * One iteration of the algorithm\r\n   *\r\n   * @param maze\r\n   * @param currentCell\r\n   * @param visitedCells\r\n   * @param width\r\n   * @param height\r\n   * @returns\r\n   */\r\n  iteration(maze: Maze2D, currentCell: { i: number, o: number }, markedCells: { i: number, o: number }[], visitedCells: { i: number, o: number }[], width: number, height: number): [Maze2D, { i: number, o: number }, { i: number, o: number }[], { i: number, o: number }[]] {\r\n\r\n      // select a random marked cell\r\n      let cell: { i: number, o: number } = markedCells[Math.floor(Math.random() * markedCells.length)];\r\n\r\n      // find adjacent tiles in the possible visited category.\r\n      let possibleVisited: { i: number, o: number }[] = visitedCells.filter(temp =>\r\n        (temp.i === cell.i && temp.o === (cell.o - 1)) ||\r\n        (temp.i === cell.i && temp.o === (cell.o + 1)) ||\r\n        (temp.i === (cell.i - 1) && temp.o === cell.o ) ||\r\n        (temp.i === (cell.i + 1) && temp.o === cell.o )\r\n        );\r\n      let cellVisited: { i: number, o: number } = possibleVisited[Math.floor(Math.random() * possibleVisited.length)]\r\n\r\n      // remove the connecting edges...\r\n      if(cell.i === cellVisited.i && cell.o === cellVisited.o - 1) {\r\n        maze.tiles[cell.i][cell.o].passable.r = true;\r\n        maze.tiles[cellVisited.i][cellVisited.o].passable.l = true;\r\n      } else if(cell.i === cellVisited.i && cell.o === cellVisited.o + 1) {\r\n        maze.tiles[cell.i][cell.o].passable.l = true;\r\n        maze.tiles[cellVisited.i][cellVisited.o].passable.r = true;\r\n      } else if(cell.i === cellVisited.i - 1 && cell.o === cellVisited.o) {\r\n        maze.tiles[cell.i][cell.o].passable.b = true;\r\n        maze.tiles[cellVisited.i][cellVisited.o].passable.t = true;\r\n      } else if(cell.i === cellVisited.i + 1 && cell.o === cellVisited.o) {\r\n        maze.tiles[cell.i][cell.o].passable.t = true;\r\n        maze.tiles[cellVisited.i][cellVisited.o].passable.b = true;\r\n      }\r\n      // set current cell to the last cell...\r\n      currentCell = cell;\r\n\r\n      // set the initial cells around the current cell as marked.\r\n      if(currentCell.o - 1 >= 0)            markedCells.push({ o: currentCell.o - 1, i: currentCell.i });\r\n      if(currentCell.o + 1 <= width - 1)    markedCells.push({ o: currentCell.o + 1, i: currentCell.i });\r\n      if(currentCell.i - 1 >= 0)            markedCells.push({ o: currentCell.o, i: currentCell.i - 1 });\r\n      if(currentCell.i + 1 <= height - 1)   markedCells.push({ o: currentCell.o, i: currentCell.i + 1 });\r\n\r\n      // get rid of duplicates from the marked cells\r\n      markedCells = markedCells.filter((value, index, self) => { return index === self.findIndex((t) => { return t.i === value.i && t.o === value.o; }) });\r\n\r\n      // add the cell to the visited list\r\n      visitedCells.push(cell);\r\n\r\n      // filter all the visited cells from the marked cells.\r\n      markedCells = markedCells.filter((value) =>{ return visitedCells.findIndex(temp => temp.i === value.i && temp.o === value.o) === -1 })\r\n      // filter out of marked cells the one we just added to the visited cell\r\n      markedCells = markedCells.filter(temp => temp.i !== currentCell.i || temp.o !== currentCell.o);\r\n\r\n      return [maze, currentCell, markedCells, visitedCells];\r\n  }\r\n\r\n}\r\n","/*\n * Public API Surface of ngx-mazes\n */\n\nexport * from './lib/maze-algorithms.model';\nexport * from './lib/algorithms/aldousBroderMaze.model';\nexport * from './lib/algorithms/primsMaze.model';\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './public-api';\n"],"names":[],"mappings":"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"}