ngx-snake
Version:
Snake game as an angular component, its only the core of the game... you need to add everything around it (controls, score...) yourself :)
1 lines • 21.8 kB
Source Map (JSON)
{"version":3,"file":"ngx-snake.mjs","sources":["../../../projects/ngx-snake/src/lib/definitions.ts","../../../projects/ngx-snake/src/lib/services/game-manager.service.ts","../../../projects/ngx-snake/src/lib/components/tile/tile.component.ts","../../../projects/ngx-snake/src/lib/components/board/board.component.ts","../../../projects/ngx-snake/src/lib/components/board/board.component.html","../../../projects/ngx-snake/src/lib/ngx-snake.component.ts","../../../projects/ngx-snake/src/lib/ngx-snake.module.ts","../../../projects/ngx-snake/src/public-api.ts","../../../projects/ngx-snake/src/ngx-snake.ts"],"sourcesContent":["export type GameGrid = Array<Array<TileState>>;\n\nexport enum GameState {\n Paused = 0,\n Started = 1,\n Over = 2\n}\n\nexport enum TileState {\n Free = 'free',\n Head = 'head',\n Body = 'body',\n Tail = 'tail',\n Wall = 'wall',\n Food = 'food'\n}\n\nexport enum MoveDirections {\n UP,\n RIGHT,\n DOWN,\n LEFT\n}\n","import {Injectable, OnDestroy} from '@angular/core';\nimport {BehaviorSubject, interval, ReplaySubject, Subject, Subscription} from 'rxjs';\nimport {GameGrid, MoveDirections, TileState} from '../definitions';\nimport {filter, switchMap, take, tap} from 'rxjs/operators';\n\ninterface Part {\n x: number, y: number\n}\n\nconst INITIAL_SPEED = 700;\n\n@Injectable()\nexport class GameManagerService implements OnDestroy {\n private _grid: GameGrid = [];\n private _grid$ = new ReplaySubject<GameGrid>(1);\n public grid$ = this._grid$.asObservable();\n\n private _gameOver$ = new Subject();\n public gameOver$ = this._gameOver$;\n\n private _foodEaten$ = new Subject();\n public foodEaten$ = this._foodEaten$;\n\n\n private _gridSize = {\n h: 10,\n w: 10\n }\n\n private _snake: Array<Part> = [];\n private _nextMoveDir: MoveDirections = MoveDirections.RIGHT;\n private _moveDir: MoveDirections = MoveDirections.RIGHT;\n\n private _food: Part | null = null;\n\n private _interval$ = new BehaviorSubject(INITIAL_SPEED);\n private _paused = true;\n private _playable = true;\n private _signalSub: Subscription;\n public signal$ = this._interval$\n .asObservable()\n .pipe(\n switchMap((period) => interval(period)),\n filter(() => !this._paused),\n tap(() => this._gameCycle()),\n );\n\n initialize(height: number, width: number) {\n this._gridSize.w = width;\n this._gridSize.h = height;\n\n this._buildEmptyGrid();\n this._initSnake();\n this._drawSnake();\n\n this._gridChanged();\n\n this._signalSub = this.signal$.subscribe();\n }\n\n ngOnDestroy() {\n if (this._signalSub) {\n this._signalSub.unsubscribe();\n }\n }\n\n public start() {\n if (this._playable) {\n this._paused = false;\n }\n }\n\n public changeSpeed(period: number): void {\n this._interval$.next(period);\n }\n\n public pause() {\n this._paused = true;\n }\n\n public reset() {\n this.pause();\n this._playable = true;\n this._moveDir = MoveDirections.RIGHT;\n this._nextMoveDir = this._moveDir;\n this._interval$.next(INITIAL_SPEED);\n\n this._buildEmptyGrid();\n this._initSnake();\n this._drawSnake();\n\n this._gridChanged();\n }\n\n public up() { this._moveDir !== MoveDirections.DOWN ? this._nextMoveDir = MoveDirections.UP : this._moveDir }\n public right() { this._moveDir !== MoveDirections.LEFT ? this._nextMoveDir = MoveDirections.RIGHT : this._moveDir }\n public down() { this._moveDir !== MoveDirections.UP ? this._nextMoveDir = MoveDirections.DOWN : this._moveDir }\n public left() { this._moveDir !== MoveDirections.RIGHT ? this._nextMoveDir = MoveDirections.LEFT : this._moveDir }\n\n private _endGame() {\n this._playable = false;\n this.pause();\n\n this._gameOver$.next();\n }\n\n private _buildEmptyGrid() {\n const newGrid = [];\n for(let y = 0; y <= this._gridSize.h; y++) {\n const row = [];\n for(let x = 0; x <= this._gridSize.w; x++) {\n row.push(TileState.Free);\n }\n\n newGrid.push(row);\n }\n\n this._grid = newGrid;\n }\n\n private _gridChanged() {\n this._grid$.next(this._grid)\n }\n\n private _initSnake() {\n this._snake = [];\n\n const xCenter = Math.floor(this._gridSize.w / 2);\n const yCenter = Math.floor(this._gridSize.h / 2);\n\n this._snake.push({ x: xCenter, y: yCenter });\n this._snake.push({ x: xCenter - 1, y: yCenter });\n this._snake.push({ x: xCenter - 2, y: yCenter });\n }\n\n private _spawnFood() {\n if (!this._food) {\n const eligibleFields = [];\n for(let y = 1; y <= this._gridSize.h - 1; y++) {\n for(let x = 1; x <= this._gridSize.w - 1 ; x++) {\n if (this._grid[y][x] === TileState.Free) {\n eligibleFields.push({\n x, y\n })\n }\n }\n }\n\n const shuffled = eligibleFields.sort((a, b) => 0.5 - Math.random());\n this._food = shuffled[0];\n\n }\n\n this._grid[this._food.y][this._food.x] = TileState.Food;\n }\n\n private _drawSnake() {\n const head = this._snake[0];\n const tail = this._snake[this._snake.length - 1];\n\n this._grid[head.y][head.x] = TileState.Head;\n\n for(let i = 1; i < this._snake.length - 1; i++) {\n const part = this._snake[i];\n this._grid[part.y][part.x] = TileState.Body;\n }\n\n this._grid[tail.y][tail.x] = TileState.Tail;\n }\n\n private _gameCycle() {\n const head = this._snake[0];\n let newHead: Part;\n this._moveDir = this._nextMoveDir;\n if (this._moveDir === MoveDirections.UP) {\n newHead = { x: head.x, y: head.y - 1 };\n\n } else if (this._moveDir === MoveDirections.RIGHT) {\n newHead = { x: head.x + 1, y: head.y };\n\n } else if (this._moveDir === MoveDirections.DOWN) {\n newHead = { x: head.x, y: head.y + 1 };\n\n } else {\n // Moving left\n newHead = { x: head.x - 1, y: head.y };\n }\n\n if (this._willCrash(newHead)) {\n return this._endGame();\n }\n\n // position new head\n this._snake.unshift(newHead);\n\n if (this._willGrow(newHead)) {\n this._increaseSpeed();\n this._foodEaten$.next();\n this._food = null;\n\n } else {\n // drop old tail\n this._snake.pop();\n }\n\n this._buildEmptyGrid();\n this._drawSnake();\n this._spawnFood();\n this._gridChanged();\n }\n\n /**\n * Checks if field is not currently occupied (is free to take)\n * @param newHead\n * @private\n */\n private _willCrash(newHead: Part): boolean {\n // Gets out of the board\n if (newHead.x < 0 || newHead.y < 0 || newHead.x > this._gridSize.w || newHead.y > this._gridSize.h) {\n return true;\n }\n\n const CRASHABLE_FIELDS: Array<TileState> = [\n TileState.Body,\n TileState.Wall\n ];\n if (CRASHABLE_FIELDS.includes(this._grid[newHead.y][newHead.x])) {\n return true;\n }\n\n // If crashing with tail then check if tail will move...\n if (this._grid[newHead.y][newHead.x] === TileState.Tail && this._willGrow(newHead)) {\n return true;\n }\n\n return false;\n }\n\n private _willGrow(newHead: Part): boolean {\n if (this._food && this._food.y === newHead.y && this._food.x === newHead.x) {\n return true;\n }\n return false;\n }\n\n private _increaseSpeed() {\n this._interval$\n .pipe(take(1))\n .subscribe((current) => {\n if (current >= 600) {\n this._interval$.next(current - 100);\n\n } else if (current >= 500) {\n this._interval$.next(current - 30);\n\n } else if (current >= 400) {\n this._interval$.next(current - 20);\n\n } else {\n this._interval$.next(current - 10);\n }\n })\n }\n}\n","import {\n ChangeDetectionStrategy,\n Component,\n ElementRef,\n Input,\n OnInit,\n Renderer2,\n ViewEncapsulation\n} from '@angular/core';\nimport {TileState} from '../../definitions';\n\n@Component({\n selector: 'ngx-snake-tile',\n template: `<div></div>`,\n styleUrls: ['./tile.component.scss'],\n encapsulation: ViewEncapsulation.None,\n changeDetection: ChangeDetectionStrategy.OnPush,\n})\nexport class TileComponent implements OnInit {\n @Input() state: TileState;\n\n constructor(\n public el: ElementRef,\n private _renderer: Renderer2\n ) {\n }\n\n ngOnInit() {\n if (this.state) {\n this._renderer.addClass(this.el.nativeElement, this.state);\n }\n\n }\n\n}\n","import {Component, Input, OnInit} from '@angular/core';\nimport {GameGrid} from '../../definitions';\n\n@Component({\n selector: 'ngx-snake-board',\n templateUrl: './board.component.html',\n styleUrls: ['./board.component.scss']\n})\nexport class BoardComponent implements OnInit {\n @Input() data: GameGrid|null;\n\n constructor() {\n }\n\n ngOnInit(): void {\n }\n\n}\n","<div class=\"ngx-snake-board-row\" *ngFor=\"let row of data\">\n <ngx-snake-tile *ngFor=\"let tileState of row\"\n [state]=\"tileState\"></ngx-snake-tile>\n</div>\n","import {Component, Input, OnInit, Output} from '@angular/core';\nimport {GameManagerService} from './services/game-manager.service';\n\n@Component({\n selector: 'ngx-snake',\n template: `\n <ngx-snake-board\n [data]=\"grid$ | async\"></ngx-snake-board>\n `,\n styles: [],\n providers: [GameManagerService]\n})\nexport class NgxSnakeComponent implements OnInit {\n @Input() boardHeight: number = 10;\n @Input() boardWidth: number = 10;\n\n @Output() foodEaten = this._manager.foodEaten$;\n @Output() gameOver = this._manager.gameOver$;\n\n public grid$ = this._manager.grid$;\n\n constructor(\n private _manager: GameManagerService\n ) {\n }\n\n ngOnInit(): void {\n this._manager.initialize(this.boardHeight, this.boardWidth);\n }\n\n public actionUp() { this._manager.up(); }\n public actionRight() { this._manager.right(); }\n public actionDown() { this._manager.down(); }\n public actionLeft() { this._manager.left(); }\n\n\n public actionStart() {\n this._manager.start();\n }\n\n public actionStop() {\n this._manager.pause();\n }\n\n public actionReset() {\n this._manager.reset();\n }\n\n}\n","import {ModuleWithProviders, NgModule} from '@angular/core';\nimport {NgxSnakeComponent} from './ngx-snake.component';\n\n\nimport {BoardComponent} from './components/board/board.component';\nimport {TileComponent} from './components/tile/tile.component';\nimport {CommonModule} from '@angular/common';\n\n@NgModule({\n declarations: [\n NgxSnakeComponent,\n BoardComponent,\n TileComponent\n ],\n imports: [\n CommonModule\n ],\n exports: [\n NgxSnakeComponent\n ]\n})\nexport class NgxSnakeModule {\n static forRoot(): ModuleWithProviders<NgxSnakeModule> {\n return {\n ngModule: NgxSnakeModule\n };\n }\n}\n","/*\n * Public API Surface of ngx-snake\n */\n\nexport * from './lib/ngx-snake.component';\nexport * from './lib/ngx-snake.module';\n","/**\n * Generated bundle index. Do not edit.\n */\n\nexport * from './public-api';\n"],"names":[],"mappings":"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"}