From ce4cbdc1947d0e9fc4ea6a4b4a6ca83f4f53355b Mon Sep 17 00:00:00 2001 From: Nikita Iryupin Date: Wed, 2 Jun 2021 08:19:54 +0200 Subject: [PATCH] Destroying blocks by shots --- src/Blocks/types/block.js | 39 ++++++++++++++++++++++++++++++- src/Blocks/types/brick.js | 20 ++++++++++++++-- src/GameLogic/collisionManager.js | 35 +++++++++++++++++++++------ src/GameLogic/gameField.js | 15 +++++++++++- src/KeyAdapters/tankKeyAdapter.js | 1 - src/Tanks/shotElement.js | 11 +++++---- src/constants.js | 1 + 7 files changed, 105 insertions(+), 17 deletions(-) diff --git a/src/Blocks/types/block.js b/src/Blocks/types/block.js index 2fca9e2..288b538 100644 --- a/src/Blocks/types/block.js +++ b/src/Blocks/types/block.js @@ -1,4 +1,13 @@ +import { isThursday } from "date-fns"; +import { DirectionEnum } from "../../Tanks/directionEnum"; + export class Block { + + /** + * + * @param {Box[]} boxes + * @param {Tile} tile + */ constructor(boxes, tile) { this._boxes = boxes; this._tile = tile; @@ -10,7 +19,7 @@ export class Block { } } - resolveAttack(){ + resolveAttack(boxId, direction) { return; } @@ -26,6 +35,9 @@ export class Box { this._yBox = yBox; this._wBox = wBox; this._hBox = hBox; + + this._hOriginBox = hBox; + this._wOriginBox = wBox; } draw(ctx, x, y, tile){ @@ -47,4 +59,29 @@ export class Box { getYMax() { return this._yBox + this._hBox; } + + /** + * + * @param {DirectionEnum} directionOfShot + */ + getHit(directionOfShot) { + switch (directionOfShot) { + case DirectionEnum.Left: + this._wBox = this._wBox - (this._wOriginBox / 2); + break; + case DirectionEnum.Right: + this._xBox = this._xBox + (this._wOriginBox / 2); + this._wBox = this._wBox - (this._wOriginBox / 2); + break; + + case DirectionEnum.Up: + this._hBox = this._hBox - (this._hOriginBox / 2); + break; + case DirectionEnum.Down: + this._yBox = this._yBox + (this._hOriginBox / 2); + this._hBox = this._hBox - (this._hOriginBox / 2); + break; + } + console.log(this._hBox + " " + this._wBox); + } } \ No newline at end of file diff --git a/src/Blocks/types/brick.js b/src/Blocks/types/brick.js index 598f33d..0c98ecf 100644 --- a/src/Blocks/types/brick.js +++ b/src/Blocks/types/brick.js @@ -1,9 +1,25 @@ -import {Block} from "./block" +import { DirectionEnum } from "../../Tanks/directionEnum"; +import { Block, Box } from "./block" export class Brick extends Block { + constructor(boxes, tile) { super(boxes, tile); } - + /** + * + * @param {Box} box + * @param {DirectionEnum} direction + */ + resolveAttack(boxId, direction) { + let boxToResolve = this._boxes[boxId]; + + if (boxToResolve) + boxToResolve.getHit(direction); + + this._boxes = this._boxes.filter((e) => e._hBox != 0 && e._wBox != 0); + } + + } \ No newline at end of file diff --git a/src/GameLogic/collisionManager.js b/src/GameLogic/collisionManager.js index fc68367..32b6bf8 100644 --- a/src/GameLogic/collisionManager.js +++ b/src/GameLogic/collisionManager.js @@ -1,6 +1,5 @@ import { Constants } from "../constants"; import { Map } from "../Graphics/Map/map"; -import { CollisionTypeEnum } from "./collisionType"; export class CollisionManager { /** @@ -16,13 +15,30 @@ export class CollisionManager { } checkCollisionForTank(xMin, xMax, yMin, yMax) { + if (!this._map) + return false; + return (this._checkTankCollision(xMin, xMax, yMin, yMax) != null) || (this._checkBoundaries(xMin, xMax, yMin, yMax) != null) || (this._checkBlockCollision(xMin, xMax, yMin, yMax) != null); } - checkCollisionForShots(xMin, xMax, yMin, yMax) { + checkCollisionForShots(xMin, xMax, yMin, yMax, direction) { + if (!this._map) + return false; + + let blockColl = this._checkBlockCollision(xMin, xMax, yMin, yMax); + + if (blockColl) { + for (let blockInfo of blockColl) { + blockInfo.block.resolveAttack(blockInfo.boxId, direction); + } + return true; + } + + return this._checkBoundaries(xMin, xMax, yMin, yMax) != null; + } _checkTankCollision(xMin, xMax, yMin, yMax) { @@ -34,26 +50,31 @@ export class CollisionManager { const tilesize = Constants.TILE_SIZE.getValue(); if (xMin < 0 || yMin < 0 || xMax > this._map.width * tilesize || yMax > this._map.height * tilesize) - return CollisionTypeEnum.Edge; + return []; return null; } _checkBlockCollision(xMin, xMax, yMin, yMax) { const blocksToCheck = this._getAllElementsOfMapOn(xMin, xMax, yMin, yMax); const tilesize = Constants.TILE_SIZE.getValue(); + let blockColl = new Set(); for (let i = 0; i < blocksToCheck.length; i++) { - let boxes = blocksToCheck[i]["block"].getAllBoxes(); - let x = blocksToCheck[i]["xPos"]; - let y = blocksToCheck[i]["yPos"]; + let boxes = blocksToCheck[i].block.getAllBoxes(); + let x = blocksToCheck[i].xPos; + let y = blocksToCheck[i].yPos; for (let j = 0; j < boxes.length; j++) { const box = boxes[j]; if (this.intersect(xMin, xMax, yMin, yMax, x * tilesize + box.getXMin(), x * tilesize + box.getXMax(), - y * tilesize + box.getYMin(), y * tilesize + box.getYMax())) return CollisionTypeEnum.Block; + y * tilesize + box.getYMin(), y * tilesize + box.getYMax())) blockColl.add({block:blocksToCheck[i].block, boxId:j}); } } + if (blockColl.size != 0){ + return blockColl.values(); + } + return null; } diff --git a/src/GameLogic/gameField.js b/src/GameLogic/gameField.js index 724a37f..d59169a 100644 --- a/src/GameLogic/gameField.js +++ b/src/GameLogic/gameField.js @@ -4,6 +4,7 @@ import { Constants } from "../constants" import { BlockTypeEnum } from "../Blocks/blockTypeEnum" import { MapParser } from "../Graphics/Map/mapParser"; import { CollisionManager } from "./collisionManager"; +import { Forest } from "./../Blocks/types/forest"; export class GameField { constructor(width = 512, height = 512, ctx, canvas) { @@ -58,17 +59,29 @@ export class GameField { this.collisionManager.attachMap(this.map); } + let lateDraw = []; + for (let x = 0; x < this.map.width; x += 1) { for (let y = 0; y < this.map.height; y += 1) { this.ctx.fillStyle = "black"; this.ctx.fillRect(x * Constants.TILE_SIZE.getValue(), y * Constants.TILE_SIZE.getValue(), Constants.TILE_SIZE.getValue(), Constants.TILE_SIZE.getValue()); - this.map.getElement(x, y).draw(this.ctx, x * Constants.TILE_SIZE.getValue(), y * Constants.TILE_SIZE.getValue()); + + let element = this.map.getElement(x, y); + if (element instanceof Forest){ + lateDraw.push({element, x, y}); + } else + { + element.draw(this.ctx, x * Constants.TILE_SIZE.getValue(), y * Constants.TILE_SIZE.getValue()); + } } } this.tank.draw(this.tileset, this.ctx); + for (let el of lateDraw) { + el.element.draw(this.ctx, el.x * Constants.TILE_SIZE.getValue(), el.y * Constants.TILE_SIZE.getValue()); + } requestAnimationFrame(() => this.drawField()); } diff --git a/src/KeyAdapters/tankKeyAdapter.js b/src/KeyAdapters/tankKeyAdapter.js index 14211d0..9545033 100644 --- a/src/KeyAdapters/tankKeyAdapter.js +++ b/src/KeyAdapters/tankKeyAdapter.js @@ -9,7 +9,6 @@ export class TankKeyAdapter extends GameKeyAdapterInterface { } handleEvent(event) { - console.log(event.key); switch (event.key) { case "ArrowLeft": this.tank.move(DirectionEnum.Left); diff --git a/src/Tanks/shotElement.js b/src/Tanks/shotElement.js index d5fca2d..f45dea2 100644 --- a/src/Tanks/shotElement.js +++ b/src/Tanks/shotElement.js @@ -9,30 +9,31 @@ class Shot { this.x = x; this.y = y; this.speed = Constants.SHOT_SPEED.getValue(); + this.size = Constants.SHOT_SIZE.getValue(); } move() { switch (this.direction) { case DirectionEnum.Up: - if (!this.shotManager.checkCollision(this.x, this.x + 4, this.y - this.speed, this.y + 4 - this.speed)) + if (!this.shotManager.checkCollision(this.x, this.x + this.size, this.y - this.speed, this.y + this.size - this.speed)) this.y -= this.speed; else this.shotManager.destroyShot(); break; case DirectionEnum.Left: - if (!this.shotManager.checkCollision(this.x - this.speed, this.x + 4 - this.speed, this.y, this.y + 4)) + if (!this.shotManager.checkCollision(this.x - this.speed, this.x + this.size - this.speed, this.y, this.y + this.size)) this.x -= this.speed; else this.shotManager.destroyShot(); break; case DirectionEnum.Right: - if (!this.shotManager.checkCollision(this.x + this.speed, this.x + 4 + this.speed, this.y, this.y + 4)) + if (!this.shotManager.checkCollision(this.x + this.speed, this.x + this.size + this.speed, this.y, this.y + this.size)) this.x += this.speed; else this.shotManager.destroyShot(); break; case DirectionEnum.Down: - if (!this.shotManager.checkCollision(this.x, this.x + 4, this.y + this.speed, this.y + 4 + this.speed)) + if (!this.shotManager.checkCollision(this.x, this.x + this.size, this.y + this.speed, this.y + this.size + this.speed)) this.y += this.speed; else this.shotManager.destroyShot(); break; @@ -55,7 +56,7 @@ export class ShotManager { } checkCollision(minX, maxX, minY, maxY) { - return this.collisionManager.checkCollisionForTank(minX, maxX, minY, maxY); + return this.collisionManager.checkCollisionForShots(minX, maxX, minY, maxY, this.shot.direction); } destroyShot() { diff --git a/src/constants.js b/src/constants.js index 4434f09..1d13182 100644 --- a/src/constants.js +++ b/src/constants.js @@ -3,6 +3,7 @@ export class Constants { static TANK_SIZE = new Constants(24); static TANK_COLL_OFFSET = new Constants(0.125); static SHOT_SPEED = new Constants(3.0); + static SHOT_SIZE = new Constants(5); constructor(value){ this._value = value;