why when I click the “Gioca di nuovo” button and play another game, it sends 2 times the same score?

‘When I press the “Gioca di nuovo” button to start a new game, my game sends the score to the server twice, resulting in duplicate records. I believe the issue might be in the sendScoreToServer and resetGame functions, as these are responsible for managing the game restart. The sendScoreToServer function is called when the game ends, and resetGame is invoked to reset game parameters and prepare for a new game. How can I modify these functions to ensure that the score is sent to the server only once, and avoid duplicate records in the leaderboard?’


function startGame() {
    gameStarted = true;
    document.getElementById('login-form').style.display = 'none';  // Nascondi il form di login
    document.addEventListener("keydown", moveShip);
    document.addEventListener("keyup", shoot);
    createDaleks();  // Crea i Dalek
    startDalekBulletTimer(); // Avvia il timer per i proiettili dei Dalek
    requestAnimationFrame(update);  // Avvia il ciclo di aggiornamento
}

function update() {
    if (!gameStarted) {
        return;
    }

    // Mostra il punteggio finale
    let finalScore = document.getElementById('final-score');
    finalScore.innerText = `Score: ${score}`;

    // Mostra il messaggio di game over
    if (gameOver) {
        endGame(); // Chiamata al metodo endGame per gestire la fine del gioco
        return; // Interrompe il ciclo di aggiornamento
    }

    // Disegna lo sfondo
    context.drawImage(spaceImg, 0, 0, boardWidth, boardHeight);

    // Disegna la navicella
    context.drawImage(tardisImg, ship.x, ship.y, ship.width, ship.height);

    // Aggiorna e disegna i Dalek
    for (let i = 0; i < daleksArray.length; i++) {
        let dalek = daleksArray[i];
        if (dalek.alive) {
            dalek.x += dalekVelocityX;

            if (dalek.x + dalek.width >= board.width || dalek.x <= 0) {
                dalekVelocityX *= -1;
                dalek.x += dalekVelocityX * 2;

                for (let j = 0; j < daleksArray.length; j++) {
                    daleksArray[j].y += daleksHeight;
                }
            }

            context.drawImage(dalekImg, dalek.x, dalek.y, dalek.width, dalek.height);

            if (dalek.y >= ship.y) {
                gameOver = true;
                document.getElementById('score').innerText = `Score: ${score} (Game Over)`;
            }
        }
    }

    // Gestione dei proiettili dei Dalek
    for (let i = 0; i < dalekBulletArray.length; i++) {
        let bullet = dalekBulletArray[i];
        bullet.y += dalekBulletVelocityY;  // I proiettili dei Dalek si muovono verso il basso
        context.fillStyle = "red";
        context.fillRect(bullet.x, bullet.y, bullet.width, bullet.height);

        // Verifica se il proiettile colpisce la navicella
        if (detectCollision(bullet, ship)) {
            score -= 50;  // Sottrai 50 punti
            bullet.used = true;  // Marca il proiettile come utilizzato
            if (score < 0) {
                score = 0;
                gameOver = true;
            }
            document.getElementById('score').innerText = `Score: ${score} (Game Over)`;
        }
    }

    while (dalekBulletArray.length > 0 && (dalekBulletArray[0].y > board.height || dalekBulletArray[0].used)) {
        dalekBulletArray.shift();
    }

    // Gestione dei proiettili del giocatore
    for (let i = 0; i < bulletArray.length; i++) {
        let bullet = bulletArray[i];
        bullet.y += tardisBulletVelocity;
        context.fillStyle = "white";
        context.fillRect(bullet.x, bullet.y, bullet.width, bullet.height);

        for (let j = 0; j < daleksArray.length; j++) {
            let dalek = daleksArray[j];
            if (!bullet.used && dalek.alive && detectCollision(bullet, dalek)) {
                bullet.used = true;
                dalek.alive = false;
                dalekCount--;
                score += 100;
                context.fillStyle = "red";
                context.fillRect(dalek.x, dalek.y, dalek.width, dalek.height);
            }
        }
    }

    while (bulletArray.length > 0 && (bulletArray[0].used || bulletArray[0].y < 0)) {
        bulletArray.shift();
    }

    if (dalekCount == 0) {
        score += dalekColumns * dalekRows * 100;
        dalekColumns = Math.min(dalekColumns + 1, rows - 4);
        dalekVelocityX += (dalekVelocityX > 0) ? 0.2 : -0.2;
        daleksArray = [];
        bulletArray = [];
        dalekBulletArray = []; // Resetta i proiettili dei Dalek
        createDaleks();
    }

    document.getElementById('score').innerText = `Score: ${score}`;
    requestAnimationFrame(update);
}

function detectCollision(obj1, obj2) {
    return obj1.x < obj2.x + obj2.width &&
           obj1.x + obj1.width > obj2.x &&
           obj1.y < obj2.y + obj2.height &&
           obj1.y + obj1.height > obj2.y;
}

function shoot(e) {
    if (e.code === "Space" && !gameOver) {
        let bullet = {
            x: ship.x + ship.width / 2 - 2,
            y: ship.y,
            width: 4,
            height: 10,
            used: false
        };
        bulletArray.push(bullet);
    }
}

function moveShip(e) {
    if (gameOver) {
        return;
    }

    if (e.code === "ArrowLeft" && ship.x > 0) {
        ship.x -= shipVelocityX;
    } else if (e.code === "ArrowRight" && ship.x < boardWidth - shipWidth) {
        ship.x += shipVelocityX;
    }
}

function createDaleks() {
    daleksArray = [];
    dalekCount = 0;

    for (let i = 0; i < dalekRows; i++) {
        for (let j = 0; j < dalekColumns; j++) {
            daleksArray.push({
                x: dalekX + j * (daleksWidth + tileSize),
                y: dalekY + i * (daleksHeight + tileSize),
                width: daleksWidth,
                height: daleksHeight,
                alive: true
            });
            dalekCount++;
        }
    }
}

let dalekBulletTimerId; 

function startDalekBulletTimer() {
    if (dalekBulletTimerId) return;

    dalekBulletTimerId = setInterval(() => {
        if (gameOver) {
            clearInterval(dalekBulletTimerId); 
            dalekBulletTimerId = null;
            return;
        }

        let aliveDaleks = daleksArray.filter(dalek => dalek.alive);
        if (aliveDaleks.length > 0) {
            let randomDalek = aliveDaleks[Math.floor(Math.random() * aliveDaleks.length)];
            let bullet = {
                x: randomDalek.x + randomDalek.width / 2 - 2,
                y: randomDalek.y + randomDalek.height,
                width: 4,
                height: 10,
                used: false
            };
            dalekBulletArray.push(bullet);
        }
    }, 1000); 
}



function endGame() {
    document.removeEventListener("keydown", moveShip);
    document.removeEventListener("keyup", shoot);

    document.getElementById('game-over-message').style.display = 'block';
    document.getElementById('end-buttons').style.display = 'block';

    let finalScore = document.getElementById('final-score');
    finalScore.innerText = `Final Score: ${score}`;

    // Ferma la musica di sottofondo
    backgroundMusic.pause();
    backgroundMusic.currentTime = 0; // Riavvolgi la musica all'inizio

    // Recupera l'username dal form di login
    let username = document.getElementById('username').value;

    // Invia il punteggio al server
    if (username) {
        sendScoreToServer(username, score);
    }
}

document.getElementById('view-leaderboard').addEventListener('click', function () {
    showLeaderboard();
});

document.getElementById('back-button').addEventListener('click', function () {
    hideLeaderboard();
});

function showLeaderboard() {
    // Nascondi solo il testo di Game Over e il punteggio
    document.getElementById('game-over-text').style.display = 'none';
    document.getElementById('final-score').style.display = 'none';
    document.getElementById('end-buttons').style.display = 'none';
    document.getElementById('game-over-message').style.display = 'none';

    // Mostra il contenitore della classifica
    document.getElementById('leaderboard-container').style.display = 'flex';
    document.getElementById('back-button').style.display = 'block'; // Mostra il bottone "Indietro"

    // Recupera la classifica dal server
    fetch('../php/space.php')
        .then(response => response.json()) // Converti la risposta in JSON
        .then(data => {
            // Costruisci la tabella dinamicamente
            console.log("sei nella generazione tabella" + data);
            let tabella = `
                <table id="classifica">
                    <thead>
                        <tr>
                            <th>Posizione</th>
                            <th>Username</th>
                            <th>Punteggio</th>
                            <th>Data e ora</th>
                        </tr>
                    </thead>
                    <tbody>
                        ${generaRighe(data)}
                    </tbody>
                </table>
            `;

            let tabellaContainer = document.querySelector("#leaderboard-container");
            tabellaContainer.insertAdjacentHTML('beforeend', tabella);
        })
        .catch(error => console.error('Error:', error));
}




document.getElementById('view-leaderboard').addEventListener('click', function () {
    // Rimuovi la tabella esistente (se presente)
    let oldTable = document.querySelector("#leaderboard-container table");
    if (oldTable) {
        oldTable.remove();
    }
    // (Il resto della funzione rimane invariato)
});

document.getElementById('play-again').addEventListener('click', function () {
    resetGame();
    startGame();
});

function sendScoreToServer(username, score) {
    fetch('../php/save_score.php', {
        method: 'POST',
        headers: {
            'Content-Type': 'application/json'
        },
        body: JSON.stringify({ username: username, score: score })
    })
        .then(response => response.text())
        .then(data => console.log(data))
        .catch(error => console.error('Error:', error));
}

function resetGame() {
    // Nascondi la schermata di Game Over e la classifica
    document.getElementById('game-over-message').style.display = 'none';
    document.getElementById('end-buttons').style.display = 'none';
    document.getElementById('leaderboard-container').style.display = 'none';

    // Resetta i parametri del gioco
    score = 0;
    gameOver = false;
    daleksArray = [];
    bulletArray = [];
    dalekBulletArray = [];

    // Ripristina la navicella alla posizione iniziale
    ship.x = shipX;
    ship.y = shipY;

    dalekColumns = 3;
    dalekVelocityX = 1;
    dalekBulletVelocityY = 10;

    // Ripristina la musica di sottofondo
    backgroundMusic.currentTime = 0; 
    backgroundMusic.play();

    // Rimuovi gli event listeners esistenti per evitare conflitti
    document.removeEventListener("keydown", moveShip);
    document.removeEventListener("keyup", shoot);

    // Pulisci il timer dei proiettili dei Dalek se esiste
    if (dalekBulletTimerId) {
        clearInterval(dalekBulletTimerId);
        dalekBulletTimerId = null;
    }

    // Riavvia gli event listeners per il gioco
    document.addEventListener("keydown", moveShip);
    document.addEventListener("keyup", shoot);

    // Crea nuovi Dalek e avvia il timer dei proiettili dei Dalek
    createDaleks();
    startDalekBulletTimer(); 

    // Avvia il ciclo di aggiornamento
    requestAnimationFrame(update);

}
this is the javascript code.'