Skip to content

Commit

Permalink
🚸 Make it easier to turn quickly by adding key presses to a queue
Browse files Browse the repository at this point in the history
  • Loading branch information
Vages committed Nov 13, 2021
1 parent 3931684 commit 8e20ea9
Show file tree
Hide file tree
Showing 2 changed files with 51 additions and 21 deletions.
19 changes: 13 additions & 6 deletions src/App.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -5,10 +5,12 @@
import GameOverModal from "./GameOverModal.svelte";
import {
DIRECTION_VECTORS,
DIRECTION_NAMES,
getNewApplePosition,
getNewDirectionFromEventKey,
getNextSnake,
is180Turn,
isStraightOr180Turn,
getNextHeadDirectionAndQueue,
isEqual,
isInsideBoard,
isSnakeEatingItself,
Expand All @@ -34,6 +36,7 @@
let score;
let snake;
let willGrow;
let headDirectionQueue;
function resetGame() {
const initialSnake = [
Expand All @@ -43,16 +46,23 @@
];
apple = getNewApplePosition(BOARD_DIMENSIONS, initialSnake);
gameState = GAME_STATES.START_SCREEN;
headDirection = "SOUTH";
headDirection = DIRECTION_NAMES.SOUTH;
score = 0;
snake = initialSnake;
willGrow = false;
headDirectionQueue = [];
}
resetGame();
// Snake logic
function moveSnake() {
const [nextQueue, nextDirection] = getNextHeadDirectionAndQueue(
headDirectionQueue,
headDirection
);
headDirectionQueue = nextQueue;
headDirection = nextDirection;
snake = getNextSnake(snake, DIRECTION_VECTORS[headDirection], willGrow);
willGrow = false;
}
Expand Down Expand Up @@ -95,10 +105,7 @@
if (!keyDirection) {
return;
}
if (!is180Turn(snake, keyDirection)) {
headDirection = keyDirection;
}
headDirectionQueue = [...headDirectionQueue, keyDirection];
}
}
Expand Down
53 changes: 38 additions & 15 deletions src/utils.js
Original file line number Diff line number Diff line change
@@ -1,8 +1,20 @@
export const DIRECTION_NAMES = Object.freeze({
NORTH: "NORTH",
EAST: "EAST",
SOUTH: "SOUTH",
WEST: "WEST",
});

const OPPOSITE_DIRECTIONS = [
[DIRECTION_NAMES.NORTH, DIRECTION_NAMES.SOUTH],
[DIRECTION_NAMES.EAST, DIRECTION_NAMES.WEST],
];

export const DIRECTION_VECTORS = Object.freeze({
NORTH: { x: 0, y: -1 },
SOUTH: { x: 0, y: 1 },
EAST: { x: 1, y: 0 },
WEST: { x: -1, y: 0 },
[DIRECTION_NAMES.NORTH]: { x: 0, y: -1 },
[DIRECTION_NAMES.SOUTH]: { x: 0, y: 1 },
[DIRECTION_NAMES.EAST]: { x: 1, y: 0 },
[DIRECTION_NAMES.WEST]: { x: -1, y: 0 },
});

export function add(coordinateA, coordinateB) {
Expand Down Expand Up @@ -48,14 +60,12 @@ export function isSnakeEatingItself(snake) {
return snake.slice(1).some((snakeSpace) => isEqual(snakeSpace, headPosition));
}

export function is180Turn(snake, newDirectionFromEventKey) {
const head = snake[0];
const neck = snake[1];
const headWouldEatNeck = isEqual(
add(head, DIRECTION_VECTORS[newDirectionFromEventKey]),
neck
export function isStraightOr180Turn(currentDirection, nextDirection) {
return OPPOSITE_DIRECTIONS.some(
(directionAndOpposite) =>
directionAndOpposite.includes(currentDirection) &&
directionAndOpposite.includes(nextDirection)
);
return headWouldEatNeck;
}

export function getNewDirectionFromEventKey(key) {
Expand All @@ -64,19 +74,32 @@ export function getNewDirectionFromEventKey(key) {
case "ArrowUp":
case "w":
case ",":
return "NORTH";
return DIRECTION_NAMES.NORTH;
case "ArrowDown":
case "s":
case "o":
return "SOUTH";
return DIRECTION_NAMES.SOUTH;
case "ArrowLeft":
case "a":
return "WEST";
return DIRECTION_NAMES.WEST;
case "ArrowRight":
case "d":
case "e":
return "EAST";
return DIRECTION_NAMES.EAST;
default:
return null;
}
}

export function getNextHeadDirectionAndQueue(queue, currentDirection) {
const foundIndex = queue.findIndex(
(direction) => !isStraightOr180Turn(currentDirection, direction)
);

const noNextDirectionFound = foundIndex === -1;
if (noNextDirectionFound) {
return [[], currentDirection];
} else {
return [queue.slice(foundIndex + 1), queue[foundIndex]];
}
}

0 comments on commit 8e20ea9

Please sign in to comment.