import { CONTAINER_HEIGHT, CONTAINER_WIDTH } from '../../config'; import { Game } from '../../game'; import { calculateCollision } from '../calculateCollision/calculateCollision'; import { calculateDirection } from '../calculateDirection/calculateDirection'; /** * Функция для вычисления взаимодействий сущностей игры в зависимости от времени из Ticker * @param {Game} game экземпляр класса игры * @param {number} containerWidth ширина игрового контейнера в пикселях * @param {number} containerHeight высота игрового контейнера в пикселях * @param {number} deltaTime изменение времени из Ticker */ export function tick(game, containerWidth, containerHeight, deltaTime) { try { if (!(game instanceof Game)) { throw new Error('Аргумент game должен быть экземпляром класса игры'); } if ([containerWidth, containerHeight].some((element) => typeof element !== 'number')) { throw new Error('Значения размеров игрового контейнера должены являться числами'); } if (containerWidth <= 0 || containerHeight <= 0) { throw new Error('Размеры игрового контейнера должены быть положительными числами'); } if (typeof deltaTime !== 'number' || deltaTime <= 0) { throw new Error('Значение изменения времени должно быть положительным числом'); } const { ball, paddle, bricks } = game; ball.moveForward(deltaTime); const leftBoundary = ball.radius; const rightBoundary = containerWidth - ball.radius; const topBoundary = ball.radius; const bottomBoundary = containerHeight - ball.radius; // Не даем мячу выйти за границы стен слева / справав и меняем направление if (ball.x <= leftBoundary || ball.x >= rightBoundary) { ball.x = ball.x <= leftBoundary ? leftBoundary : rightBoundary; ball.horizontalSpeed *= -1; } // Не даем мячу выйти за границы стен сверху / снизу и меняем направление if (ball.y <= topBoundary || ball.y >= bottomBoundary) { ball.y = ball.y <= topBoundary ? topBoundary : bottomBoundary; ball.verticalSpeed *= -1; } // Базоввое взаимодействие мяча и кирпича for (const row of bricks) { for (const brick of row) { if (!brick.alive) { continue; } const ballLeft = ball.x - ball.radius; const ballRight = ball.x + ball.radius; const ballTop = ball.y - ball.radius; const ballBottom = ball.y + ball.radius; const brickLeft = brick.x; const brickRight = brick.x + brick.width; const brickTop = brick.y; const brickBottom = brick.y + brick.height; const ballObject = { left: ballLeft, right: ballRight, top: ballTop, bottom: ballBottom }; const brickObject = { left: brickLeft, right: brickRight, top: brickTop, bottom: brickBottom }; const isCollided = calculateCollision(ballObject, brickObject); if (isCollided) { const directions = calculateDirection(ballObject, brickObject); if (directions !== null) { ball.horizontalSpeed *= directions[0]; ball.verticalSpeed *= directions[1]; brick.kill(); break; } } } } // Базоввое взаимодействие мяча и ракетки if ( ball.verticalSpeed > 0 && ball.y + ball.radius >= paddle.y && ball.x >= paddle.x && ball.x <= paddle.x + paddle.width ) { verticalSpeed *= -1; } } catch (err) { console.error(err); return null; } }