game over stats
This commit is contained in:
		
							
								
								
									
										73
									
								
								app.js
									
									
									
									
									
								
							
							
						
						
									
										73
									
								
								app.js
									
									
									
									
									
								
							@ -122,6 +122,10 @@ class MinoesTable {
 | 
			
		||||
        this.table = document.getElementById(id)
 | 
			
		||||
        this.rows = this.table.rows.length
 | 
			
		||||
        this.columns = this.table.rows[0].childElementCount
 | 
			
		||||
        this.init()
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    init() {
 | 
			
		||||
        this._piece = null
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -161,6 +165,10 @@ MinoesTable.prototype.init_center = [2, 2]
 | 
			
		||||
class NextQueue extends MinoesTable {
 | 
			
		||||
    constructor() {
 | 
			
		||||
        super("nextTable")
 | 
			
		||||
        this.init()
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    init() {
 | 
			
		||||
        this.pieces = this.init_centers.map(center => {
 | 
			
		||||
            let piece = new Tetromino.pick()
 | 
			
		||||
            piece.center = Array.from(center)
 | 
			
		||||
@ -191,6 +199,10 @@ NextQueue.prototype.init_centers = [[2, 2], [2, 5], [2, 8], [2, 11], [2, 14]]
 | 
			
		||||
class Matrix extends MinoesTable {
 | 
			
		||||
    constructor() {
 | 
			
		||||
        super("matrixTable")
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    init() {
 | 
			
		||||
        super.init()
 | 
			
		||||
        this.blocks = Array(this.rows).fill().map(() => Array(this.columns))
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
@ -378,11 +390,11 @@ class Settings {
 | 
			
		||||
    constructor() {
 | 
			
		||||
        this.form = settingsForm
 | 
			
		||||
        this.load()
 | 
			
		||||
        this.form.onsubmit = newGame
 | 
			
		||||
        this.modal = new bootstrap.Modal('#settingsModal')
 | 
			
		||||
        document.getElementById('settingsModal').addEventListener('shown.bs.modal', () => {
 | 
			
		||||
            resumeButton.focus()
 | 
			
		||||
        })
 | 
			
		||||
        this.init()
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    load() {
 | 
			
		||||
@ -391,6 +403,14 @@ class Settings {
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    init() {
 | 
			
		||||
        this.form.onsubmit = newGame
 | 
			
		||||
        levelInput.name = "startLevel"
 | 
			
		||||
        levelInput.disabled = false
 | 
			
		||||
        titleHeader.innerHTML = "QUATRIS"
 | 
			
		||||
        resumeButton.innerHTML = "Jouer"
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    show() {
 | 
			
		||||
        resumeButton.disabled = false
 | 
			
		||||
        settings.form.classList.remove('was-validated')
 | 
			
		||||
@ -432,9 +452,19 @@ function changeKey(input) {
 | 
			
		||||
class Stats {
 | 
			
		||||
    constructor() {
 | 
			
		||||
        this.highScore = Number(localStorage["highScore"]) || 0
 | 
			
		||||
        this.init()
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    init() {
 | 
			
		||||
        this.combo = 0
 | 
			
		||||
        this.b2b = 0
 | 
			
		||||
        this.startTime = new Date()
 | 
			
		||||
        this.lockDelay = 0
 | 
			
		||||
        this.totalClearedLines = 0
 | 
			
		||||
        this.nbQuatris = 0
 | 
			
		||||
        this.nbTSpin = 0
 | 
			
		||||
        this.maxCombo = 0
 | 
			
		||||
        this.maxB2B = 0
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    set score(score) {
 | 
			
		||||
@ -494,6 +524,10 @@ class Stats {
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    lockDown(nbClearedLines, tSpin) {
 | 
			
		||||
        this.totalClearedLines += nbClearedLines
 | 
			
		||||
        if (nbClearedLines == 4) this.nbQuatris++
 | 
			
		||||
        if (tSpin == T_SPIN.T_SPIN) this.nbTSpin++
 | 
			
		||||
 | 
			
		||||
        // Cleared lines & T-Spin
 | 
			
		||||
        let awardedLineClears = AWARDED_LINE_CLEARS[tSpin][nbClearedLines]
 | 
			
		||||
        let patternScore = 100 * this.level * awardedLineClears
 | 
			
		||||
@ -517,6 +551,7 @@ class Stats {
 | 
			
		||||
        // Combo
 | 
			
		||||
        if (nbClearedLines) {
 | 
			
		||||
            this.combo++
 | 
			
		||||
            if (this.combo > this.maxCombo) this.maxCombo = this.combo
 | 
			
		||||
            if (this.combo >= 1) {
 | 
			
		||||
                let comboScore = (nbClearedLines == 1 ? 20 : 50) * this.combo * this.level
 | 
			
		||||
                if (this.combo == 1) {
 | 
			
		||||
@ -541,6 +576,7 @@ class Stats {
 | 
			
		||||
        // Back to back sequence
 | 
			
		||||
        if ((nbClearedLines == 4) || (tSpin && nbClearedLines)) {
 | 
			
		||||
            this.b2b++
 | 
			
		||||
            if (this.b2b > this.maxB2B) this.maxB2B = this.b2b
 | 
			
		||||
            if (this.b2b >= 1) {
 | 
			
		||||
                let b2bScore = patternScore / 2
 | 
			
		||||
                if (this.b2b == 1) {
 | 
			
		||||
@ -596,11 +632,7 @@ let holdQueue = new MinoesTable("holdTable")
 | 
			
		||||
let matrix = new Matrix()
 | 
			
		||||
let nextQueue = new NextQueue()
 | 
			
		||||
let playing = false
 | 
			
		||||
 | 
			
		||||
function init() {
 | 
			
		||||
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
let gameOverModal = new bootstrap.Modal('#gameOverModal')
 | 
			
		||||
 | 
			
		||||
function pauseSettings() {
 | 
			
		||||
    scheduler.clearInterval(fall)
 | 
			
		||||
@ -828,12 +860,29 @@ function gameOver() {
 | 
			
		||||
    scheduler.clearInterval(ticktack)
 | 
			
		||||
    playing = false
 | 
			
		||||
 | 
			
		||||
    messagesSpan.onanimationend = null
 | 
			
		||||
    messagesSpan.addNewChild("div", {
 | 
			
		||||
        className: "game-over-animation",
 | 
			
		||||
        style: "opacity: 100%",
 | 
			
		||||
        innerHTML: "<h1>FIN</h1>"
 | 
			
		||||
    })
 | 
			
		||||
    goScoreCell.innerText = stats.score.toLocaleString()
 | 
			
		||||
    goHighScoreCell.innerText = stats.highScore.toLocaleString()
 | 
			
		||||
    goLevelCell.innerText = stats.level
 | 
			
		||||
    let time = stats.time
 | 
			
		||||
    goTimeCell.innerText = stats.timeFormat.format(time)
 | 
			
		||||
    gototalClearedLines.innerText = stats.totalClearedLines
 | 
			
		||||
    gototalClearedLinesPM.innerText = (stats.totalClearedLines * 60 / time).toFixed(2)
 | 
			
		||||
    goNbQuatris.innerText = stats.nbQuatris
 | 
			
		||||
    goNbTSpin.innerText = stats.nbTSpin
 | 
			
		||||
    goMaxCombo.innerText = stats.maxCombo
 | 
			
		||||
    goMaxB2B.innerText = stats.maxB2B
 | 
			
		||||
    gameOverModal.show()
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
function restart() {
 | 
			
		||||
    gameOverModal.hide()
 | 
			
		||||
    holdQueue.init()
 | 
			
		||||
    stats.init()
 | 
			
		||||
    matrix.init()
 | 
			
		||||
    matrix.redraw()
 | 
			
		||||
    nextQueue.init()
 | 
			
		||||
    settings.init()
 | 
			
		||||
    pauseSettings()
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
window.onbeforeunload = function(event) {
 | 
			
		||||
 | 
			
		||||
							
								
								
									
										49
									
								
								index.html
									
									
									
									
									
								
							
							
						
						
									
										49
									
								
								index.html
									
									
									
									
									
								
							@ -1,4 +1,5 @@
 | 
			
		||||
<html lang="fr">
 | 
			
		||||
 | 
			
		||||
  <head>
 | 
			
		||||
    <meta charset="utf-8" />
 | 
			
		||||
    <title>QUATRIS</title>
 | 
			
		||||
@ -16,7 +17,9 @@
 | 
			
		||||
    <link rel="icon" type="image/png" sizes="16x16" href="favicons/favicon-16x16.png">
 | 
			
		||||
    <link rel="manifest" href="manifest.json">
 | 
			
		||||
  </head>
 | 
			
		||||
 | 
			
		||||
  <body data-bs-theme="dark">
 | 
			
		||||
 | 
			
		||||
    <div class="modal fade" id="settingsModal" data-bs-backdrop="static" data-bs-keyboard="false">
 | 
			
		||||
      <div class="modal-dialog modal-dialog-centered">
 | 
			
		||||
        <div class="modal-content">
 | 
			
		||||
@ -108,7 +111,9 @@
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
 | 
			
		||||
    <div class="container-fluid d-flex h-100 justify-content-center d-flex align-items-center">
 | 
			
		||||
 | 
			
		||||
      <div class="row row-cols-auto align-items-start gap-2">
 | 
			
		||||
        <div class="col d-flex flex-column align-items-end">
 | 
			
		||||
          <div class="card mb-4">
 | 
			
		||||
@ -124,17 +129,18 @@
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
          <div class="card">
 | 
			
		||||
            <table id="statsTable" class="table mb-0 align-middle">
 | 
			
		||||
              <tr><td>Score</td><th id="scoreCell" class="text-end">0</th></tr>
 | 
			
		||||
              <tr><td>Meilleur</td><th id="highScoreCell" class="text-end">
 | 
			
		||||
            <table id="statsTable" class="table mb-0">
 | 
			
		||||
              <tr><th>Score</th>    <td id="scoreCell">0</td>    </tr>
 | 
			
		||||
              <tr><th>Meilleur</th> <td id="highScoreCell">
 | 
			
		||||
                <script>document.write(Number(localStorage["highScore"]) || 0)</script>
 | 
			
		||||
              </th></tr>
 | 
			
		||||
              <tr><td>Niveau</td><th id="levelCell" class="text-end">0</th></tr>
 | 
			
		||||
              <tr><td>But</td><th id="goalCell" class="text-end">0</th></tr>
 | 
			
		||||
              <tr><td>Temps</td><th id="timeCell" class="text-end">00:00</th></tr>
 | 
			
		||||
              </td></tr>
 | 
			
		||||
              <tr><th>Niveau</th>   <td id="levelCell">0</td>    </tr>
 | 
			
		||||
              <tr><th>But</th>      <td id="goalCell">0</td>     </tr>
 | 
			
		||||
              <tr><th>Temps</th>    <td id="timeCell">00:00</td> </tr>
 | 
			
		||||
            </table>
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
 | 
			
		||||
        <div class="col position-relative">
 | 
			
		||||
          <div class="card">
 | 
			
		||||
            <table id="matrixTable" class="minoes-table" style="--buffer-zone-rows: 5">
 | 
			
		||||
@ -167,6 +173,7 @@
 | 
			
		||||
          </div>
 | 
			
		||||
          <span id="messagesSpan"></span>
 | 
			
		||||
        </div>
 | 
			
		||||
 | 
			
		||||
        <div class="col">
 | 
			
		||||
          <div class="card">
 | 
			
		||||
            <div class="card-header text-center"><strong>NEXT</strong></div>
 | 
			
		||||
@ -194,6 +201,34 @@
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
 | 
			
		||||
    </div>
 | 
			
		||||
 | 
			
		||||
    <div class="modal fade" id="GameOverModal" tabindex="-1">
 | 
			
		||||
      <div class="modal-dialog modal-dialog-centered">
 | 
			
		||||
        <div class="modal-dialog">
 | 
			
		||||
          <div class="modal-content">
 | 
			
		||||
            <div class="modal-header">
 | 
			
		||||
              <h1 class="modal-title w-100 text-center">Fin</h1>
 | 
			
		||||
              <button type="button" class="btn-close" data-bs-dismiss="modal"></button>
 | 
			
		||||
            </div>
 | 
			
		||||
            <div class="modal-body p-0">
 | 
			
		||||
              <table class="table mb-0">
 | 
			
		||||
                <tr><th>Score</th>                    <td id="goScoreCell"></td>         <th>Niveau</th>                  <td id="goLevelCell"></td>           </tr>
 | 
			
		||||
                <tr><th>Meilleur score</th>           <td id="goHighScoreCell"></td>     <th>Temps</th>                   <td id="goTimeCell"></td>            </tr>
 | 
			
		||||
                <tr><th>Lignes</th>                   <td id="gototalClearedLines"></td> <th>Lignes par minutes</th>      <td id="gototalClearedLinesPM"></td> </tr>
 | 
			
		||||
                <tr><th>Quatris</th>                  <td id="goNbQuatris"></td>         <th>Pirouettes</th>              <td id="goNbTSpin"></td>             </tr>
 | 
			
		||||
                <tr><th>Plus grand enchaînement</th>  <td id="goMaxCombo"></td>          <th>Plus grand bout à bout</th>  <td id="goMaxB2B"></td>              </tr>
 | 
			
		||||
              </table>
 | 
			
		||||
            </div>
 | 
			
		||||
            <div class="modal-footer">
 | 
			
		||||
              <button type="button" class="btn btn-primary" onclick="restart()">Rejouer ?</button>
 | 
			
		||||
            </div>
 | 
			
		||||
          </div>
 | 
			
		||||
        </div>
 | 
			
		||||
      </div>
 | 
			
		||||
    </div>
 | 
			
		||||
    
 | 
			
		||||
 | 
			
		||||
    <script src="https://cdn.jsdelivr.net/npm/bootstrap@5.3.0-alpha3/dist/js/bootstrap.bundle.min.js" integrity="sha384-ENjdO4Dr2bkBIFxQpeoTz1HIcje39Wm4jDKdf19U8gI4ddQ3GYNS7NTKfAdVQSZe" crossorigin="anonymous"></script>
 | 
			
		||||
    <script src="app.js"></script>
 | 
			
		||||
    <script>
 | 
			
		||||
 | 
			
		||||
		Reference in New Issue
	
	Block a user