amelioration jeu

This commit is contained in:
2025-12-01 22:46:43 +01:00
parent 502a462ec5
commit eab98868ef
3 changed files with 185 additions and 15 deletions

157
game.js
View File

@ -146,12 +146,16 @@ let maze = originalMaze.map(row => [...row]);
let score = 0;
let level = 1;
let gameRunning = true;
let isPaused = false;
let totalDots = 0;
let cherriesEaten = 0;
let isChangingLevel = false;
let cherryEatenRecently = false;
let cherryEatenTimer = 0;
let lives = 3;
let dotsRemainingElement = document.getElementById('dotsRemaining');
let pursuitIndicator = document.getElementById('pursuitIndicator');
let pursuitTimerElement = document.getElementById('pursuitTimer');
class Pacman {
constructor() {
@ -169,7 +173,7 @@ class Pacman {
}
update() {
if (!gameRunning) return;
if (!gameRunning || isPaused) return;
this.mouthAngle += 0.2;
if (this.mouthAngle > Math.PI * 2) {
@ -232,6 +236,9 @@ class Pacman {
score += 10;
scoreElement.textContent = score;
totalDots--;
if (dotsRemainingElement) {
dotsRemainingElement.textContent = totalDots;
}
} else if (maze[this.y][this.x] === BONUS_CHERRY) {
if (isChangingLevel) {
console.log('Changement de niveau en cours, cerise ignorée');
@ -248,6 +255,18 @@ class Pacman {
cherryEatenRecently = true;
cherryEatenTimer = Math.max(150, 300 - (level - 1) * 20);
// Rendre tous les fantômes vulnérables
const vulnerableTime = Math.max(180, 360 - (level - 1) * 30);
for (let ghost of ghosts) {
ghost.isVulnerable = true;
ghost.vulnerableTimer = vulnerableTime;
}
// Afficher l'indicateur de poursuite
if (pursuitIndicator) {
pursuitIndicator.style.display = 'block';
}
console.log('Après incrémentation, cherriesEaten:', cherriesEaten, 'isChangingLevel:', isChangingLevel);
if (cherriesEaten >= 4 && !isChangingLevel) {
@ -300,6 +319,10 @@ class Ghost {
this.pixelY = this.y * CELL_SIZE + CELL_SIZE / 2;
this.moveCounter = 0;
this.moveInterval = 30;
this.isVulnerable = false;
this.vulnerableTimer = 0;
this.startX = x;
this.startY = y;
}
updateSpeed() {
@ -307,12 +330,24 @@ class Ghost {
}
update() {
if (!gameRunning) return;
if (!gameRunning || isPaused) return;
// Gestion de la vulnérabilité
if (this.isVulnerable) {
this.vulnerableTimer--;
if (this.vulnerableTimer <= 0) {
this.isVulnerable = false;
}
}
if (cherryEatenTimer > 0) {
cherryEatenTimer--;
} else {
cherryEatenRecently = false;
// Rendre les fantômes vulnérables quand une cerise est mangée
if (!this.isVulnerable && cherryEatenTimer === 0) {
// La vulnérabilité est gérée dans collectDot()
}
}
this.moveInterval = Math.max(15, 30 - (level - 1) * 2);
@ -423,7 +458,13 @@ class Ghost {
const size = CELL_SIZE * 0.75;
ctx.fillStyle = this.color;
// Si vulnérable, afficher en bleu clignotant
if (this.isVulnerable) {
const flash = Math.floor(this.vulnerableTimer / 10) % 2;
ctx.fillStyle = flash === 0 ? '#0000ff' : '#ffffff';
} else {
ctx.fillStyle = this.color;
}
ctx.strokeStyle = '#000000';
ctx.lineWidth = 2;
@ -579,6 +620,10 @@ function countDots() {
}
}
}
// Mettre à jour l'affichage
if (dotsRemainingElement) {
dotsRemainingElement.textContent = totalDots;
}
}
function drawMaze() {
@ -611,7 +656,7 @@ function drawMaze() {
}
function checkCollisions() {
if (!gameRunning) return;
if (!gameRunning || isPaused) return;
for (let ghost of ghosts) {
const distance = Math.sqrt(
@ -620,16 +665,31 @@ function checkCollisions() {
);
if (distance < CELL_SIZE * 0.6) {
lives--;
updateLivesDisplay();
if (lives <= 0) {
gameRunning = false;
statusElement.textContent = 'Game Over !';
showGameOver();
saveScore();
if (ghost.isVulnerable) {
// Manger le fantôme
score += 200;
scoreElement.textContent = score;
ghost.isVulnerable = false;
ghost.vulnerableTimer = 0;
// Réinitialiser la position du fantôme
ghost.x = ghost.startX;
ghost.y = ghost.startY;
ghost.pixelX = ghost.x * CELL_SIZE + CELL_SIZE / 2;
ghost.pixelY = ghost.y * CELL_SIZE + CELL_SIZE / 2;
ghost.direction = Math.floor(Math.random() * 4);
} else {
restartCurrentLevel();
// Perdre une vie
lives--;
updateLivesDisplay();
if (lives <= 0) {
gameRunning = false;
statusElement.textContent = 'Game Over !';
showGameOver();
saveScore();
} else {
restartCurrentLevel();
}
}
}
}
@ -644,9 +704,40 @@ function gameLoop() {
}
drawMaze();
// Gestion de la pause
if (isPaused) {
ctx.fillStyle = 'rgba(0, 0, 0, 0.7)';
ctx.fillRect(0, 0, canvas.width, canvas.height);
ctx.fillStyle = '#ffd700';
ctx.font = 'bold 48px "Press Start 2P"';
ctx.textAlign = 'center';
ctx.textBaseline = 'middle';
ctx.fillText('PAUSE', canvas.width/2, canvas.height/2);
ctx.font = 'bold 16px "Press Start 2P"';
ctx.fillText('Appuyez sur ESPACE ou ECHAP', canvas.width/2, canvas.height/2 + 40);
requestAnimationFrame(gameLoop);
return;
}
pacman.update();
pacman.draw();
// Mettre à jour l'indicateur de poursuite
if (pursuitIndicator && cherryEatenTimer > 0) {
const seconds = Math.ceil(cherryEatenTimer / 60);
if (pursuitTimerElement) {
pursuitTimerElement.textContent = seconds;
}
// Vérifier si tous les fantômes sont encore vulnérables
const allVulnerable = ghosts.every(g => g.isVulnerable);
if (!allVulnerable && pursuitIndicator.style.display !== 'none') {
pursuitIndicator.style.display = 'none';
}
} else if (pursuitIndicator) {
pursuitIndicator.style.display = 'none';
}
for (let ghost of ghosts) {
ghost.update();
ghost.draw();
@ -705,11 +796,16 @@ function restartCurrentLevel() {
for (let ghost of ghosts) {
ghost.updateSpeed();
ghost.isVulnerable = false;
ghost.vulnerableTimer = 0;
}
cherriesEaten = 0;
cherryEatenRecently = false;
cherryEatenTimer = 0;
if (pursuitIndicator) {
pursuitIndicator.style.display = 'none';
}
statusElement.textContent = `Niveau ${level} - Recommencement !`;
statusElement.style.color = '#ff6b6b';
@ -796,8 +892,15 @@ function nextLevel() {
for (let ghost of ghosts) {
ghost.updateSpeed();
ghost.isVulnerable = false;
ghost.vulnerableTimer = 0;
}
cherryEatenTimer = 0;
if (pursuitIndicator) {
pursuitIndicator.style.display = 'none';
}
placeBonuses();
console.log('Bonus placés, nombre:', bonuses.length);
@ -1024,6 +1127,7 @@ function initGame() {
level = 1;
lives = 3;
cherriesEaten = 0;
isPaused = false;
scoreElement.textContent = score;
levelElement.textContent = level;
updateLivesDisplay();
@ -1032,6 +1136,9 @@ function initGame() {
statusElement.style.color = '#ffd700';
restartBtn.style.display = 'none';
hideGameOver();
if (pursuitIndicator) {
pursuitIndicator.style.display = 'none';
}
pacman = new Pacman();
pacman.speed = pacman.baseSpeed * (1 + (level - 1) * 0.05);
@ -1042,6 +1149,12 @@ function initGame() {
for (let ghost of ghosts) {
ghost.updateSpeed();
ghost.isVulnerable = false;
ghost.vulnerableTimer = 0;
}
if (pursuitIndicator) {
pursuitIndicator.style.display = 'none';
}
placeBonuses();
@ -1050,7 +1163,23 @@ function initGame() {
}
document.addEventListener('keydown', (e) => {
if (!gameRunning) return;
// Système de pause
if (e.key === 'Escape' || e.key === ' ') {
if (gameRunning && !isChangingLevel) {
isPaused = !isPaused;
if (isPaused) {
statusElement.textContent = 'PAUSE';
statusElement.style.color = '#ffd700';
} else {
statusElement.textContent = 'En jeu';
statusElement.style.color = '#ffd700';
}
e.preventDefault();
return;
}
}
if (!gameRunning || isPaused) return;
switch(e.key) {
case 'ArrowUp':