File

src/app/services/game-engine.service.ts

Index

Properties
Methods

Methods

blocksInTheWay
blocksInTheWay(shape: any[], board: any[], row: number, col: number)
Parameters :
Name Type Optional
shape any[] No
board any[] No
row number No
col number No
Returns : any
Public boardRows
boardRows(board: any[])
Parameters :
Name Type Optional
board any[] No
Returns : any
Public evalMovesForFinalRowCount
evalMovesForFinalRowCount(moves: any[])
Parameters :
Name Type Optional
moves any[] No
Returns : any
Public evalMovesForRow
evalMovesForRow(moves: any[])
Parameters :
Name Type Optional
moves any[] No
Returns : number
flatten
flatten(acc: string | any[], val: any)
Parameters :
Name Type Optional
acc string | any[] No
val any No
Returns : any
getColor
getColor()
Returns : any
Public getColorBoard
getColorBoard(moves: any[])
Parameters :
Name Type Optional
moves any[] No
Returns : {}
incompleteColorRows
incompleteColorRows(row: any[])
Parameters :
Name Type Optional
row any[] No
Returns : {}
incompleteRows
incompleteRows(row: any[])
Parameters :
Name Type Optional
row any[] No
Returns : {}
joinRemainingBoardRows
joinRemainingBoardRows(board: any[])
Parameters :
Name Type Optional
board any[] No
Returns : any
Public rowCount
rowCount(board: string | any[])
Parameters :
Name Type Optional
board string | any[] No
Returns : any
Public rowNumbers
rowNumbers(board: any)
Parameters :
Name Type Optional
board any No
Returns : {}

Properties

Public colors
Type : []
Default value : ['#3F51B5', '#ABA9BB', '#777586', '#659F9D', '#E8D5B5', '#ABA9BB', '#AD2234', '#EB5D63', '#E8D5B5']
currentColorIndex
Type : number
Default value : 0
Public Shapes
Type : object
Default value : { Q: [0, 1, 10, 11], Z: [1, 2, 10, 11], S: [0, 1, 11, 12], T: [1, 10, 11, 12], I: [0, 1, 2, 3], L: [0, 1, 10, 20], J: [0, 1, 11, 21] }
import { Injectable } from '@angular/core';

export interface GameResult {
  moves: string;
  finalRows: number;
}

@Injectable({
  providedIn: 'root'
})
export class GameEngineService {

  public colors = ['#3F51B5', '#ABA9BB', '#777586', '#659F9D', '#E8D5B5', '#ABA9BB', '#AD2234', '#EB5D63', '#E8D5B5'];
  currentColorIndex = 0;

  public Shapes = {
    Q: [0, 1, 10, 11],
    Z: [1, 2, 10, 11],
    S: [0, 1, 11, 12],
    T: [1, 10, 11, 12],
    I: [0, 1, 2, 3],
    L: [0, 1, 10, 20],
    J: [0, 1, 11, 21]
  };

  public evalMovesForFinalRowCount(moves: any[]) {
    let board = [];
    moves.forEach((move: (string | number)[]) => { // e.g. Q4
      const shape = this.Shapes[move[0]];   // move[0] is the letter
      const col = +move[1];                 // move[1] is the col position from left to start the drop

      if (shape && col < 10 && col >= 0) {
        let row = board.length ? this.rowCount(board) + 1 : 0;         // start at the top of the board, if it has any blocks
        while (row > 0 && !this.blocksInTheWay(shape, board, (row - 1), col)) { row--; }   // move down until you hit a block
        shape.forEach((block: number) => { board[10 * row + col + block] = 1; });          // write the block to the board
        board = this.joinRemainingBoardRows([...this.boardRows(board).filter(this.incompleteRows)]); // remove complete rows
      }
    });

    return this.rowCount(board);
  }

  public rowCount(board: string | any[]) { return Math.ceil(board.length / 10); }

  incompleteRows(row: any[]) {
    return (row && row.length > 0) ? row.reduce((acc: number, val: any) => acc + val) !== 10 : [];
  }

  flatten(acc: string | any[], val: any) { return acc.concat(val); }

  joinRemainingBoardRows(board: any[]) {
    return (board === undefined || board.length === 0) ? [] : board.reduce(this.flatten);
  }

  public rowNumbers(board: any) { return [...Array(this.rowCount(board)).keys()]; } // e.g. 0,1,2,3

  public boardRows(board: any[]) { // an array of the data for the rows of the board, in slices of 10
    return (board && board.length > 0) ?  // again this has a few safety features
      this.rowNumbers(board).map(rowNum => board.slice(rowNum * 10, rowNum * 10 + 10)) : [];
  }

  blocksInTheWay(shape: any[], board: any[], row: number, col: number) {
    return shape.some((block: any) => board[10 * row + col + block]);
  }


  // minor  variations for vizualizations

  public getColorBoard(moves: any[]) {
    this.currentColorIndex = 0;
    const boards = [];
    let board = [];
    moves.forEach((move, index) => {            // e.g. Q4
      const shape = this.Shapes[move[0]];   // move[0] is the letter
      const col = +move[1];                 // move[1] is the col position from left to start the drop

      if (shape) {
        const color = this.getColor();
        let row = board.length ? this.rowCount(board) + 1 : 0;         // start at the top of the board, if it has any blocks
        while (row > 0 && !this.blocksInTheWay(shape, board, (row - 1), col)) { row--; }   // move down until you hit a block
        shape.forEach((block: number) => { board[10 * row + col + block] = color; });          // write the block to the board

        const before = JSON.stringify(board);
        if (index === moves.length - 1) {
          boards.push(JSON.parse(before));
        }

        board = this.joinRemainingBoardRows([...this.boardRows(board).filter(this.incompleteColorRows)]); // remove complete rows
        if (index === moves.length - 1) {
          const after = JSON.stringify(board);
          if (before !== after) { boards.push(JSON.parse(JSON.stringify(board))); }
        }
      }
    });

    return boards;
  }

  getColor() {
    if (this.currentColorIndex > this.colors.length - 1) { this.currentColorIndex = 0; }
    return this.colors[this.currentColorIndex++];
  }

  incompleteColorRows(row: any[]) {
    let total = 0;
    row.forEach(val => {
      total += +(val && val.length > 0 ? 1 : 0);
    });

    return (row && row.length > 0) ? total !== 10 : [];
  }

  // for animation

  public evalMovesForRow(moves: any[]) {
    let board = [];
    let row: number;
    moves.forEach((move: (string | number)[]) => {            // e.g. Q4
      const shape = this.Shapes[move[0]];   // move[0] is the letter
      const col = +move[1];                 // move[1] is the col position from left to start the drop

      if (shape) {
        row = board.length ? this.rowCount(board) + 1 : 0;         // start at the top of the board, if it has any blocks
        while (row > 0 && !this.blocksInTheWay(shape, board, (row - 1), col)) { row--; }   // move down until you hit a block
        shape.forEach((block: number) => { board[10 * row + col + block] = 1; });          // write the block to the board
        board = this.joinRemainingBoardRows([...this.boardRows(board).filter(this.incompleteRows)]); // remove complete rows
      }
    });

    return row;
  }


}

result-matching ""

    No results matching ""