Search code examples
javascriptjqueryhtmlcssjsfiddle

Why does my application keep running?


I'm making a Whack-A-Mole game and i'm currently stuck with this problem : My game keeps running after lives are < 0 , I'm just wondering if anyone wants to take a look at my code ( the inAction boolean in particular) and can tell me what I'm doing wrong , I'm just learning :) Here is my code :

#moleWorld {
  height: 330px;
  width: 1500px;
  margin: 0 auto;
  border: 1px solid black;
}

.field {
  display: inline-block;
  width: 21%;
  margin: 27px;
  height: 21%;
  border: 1px solid black;
  background: red;
}

.mole {
  display: inline-block;
  width: 21%;
  margin: 27px;
  height: 21%;
  border: 1px solid black;
  background-color: green;
}

#generalInformation {
  height: 40px;
  width: 330px;
  margin: 0 auto;
  background: lightblue;
}

#level-display,
#lifes-display {
  margin-left: 30px;
}

#beginEasyClick,
#beginNormalClick,
#beginHardClick {
  margin: 40px 45%;
  width: 70px;
  height: 30px
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.1.1/jquery.min.js"></script>
<script type="text/javascript" src="../jquery-3.1.1.js">
    "use strict";

    var currentScore = 2;
    var niveau = 0;
    var currentLives = 3;
    var inAction = false;
    var moleworld = "#moleWorld";
    var beginEasyClick = document.getElementById("beginEasyClick");
    var beginNormalClick = document.getElementById("beginNormalClick");
    var beginHardClick = document.getElementById("beginHardClick");
    var displayScore = document.getElementById("_displayScore");
    var $field = $(moleworld).find(class = "field")

    var getrandomInt(function(min, max) {
      return Math.floor(Math.random() * (max - min - 1)) + min
    })

    function randomField() {
      return Math.floor(Math.random() * 8)
    }
  </script>


  <script>
    var moleworld = "#moleWorld";
    var $moleworld = $(moleworld);
    
    currentScore = 0;
    currentLives = 5;
    inAction = false;
    
    "use strict";
    
    $().ready(function() {

      $(beginEasyClick).click(function() {
      
          if (!inAction) {
          
            inAction = true
            
            setInterval(function() {
              spawnMole();
            }, 1400);

            showScore();
            isThisTheMole();

          }
          
        });

      function spawnMole() {
      
        var oldScore = currentScore;
        var allFields = new Array();
        allFields = document.getElementsByClassName("field")
        var target = $(allFields[Math.floor(Math.random() * allFields.length)])
        target.addClass("mole");

        setTimeout(function() {
        
          target.removeClass("mole")
          
          if (oldScore === currentScore) {
            currentLives--;
            checkLives();
          }
          showScore();
          
        }, 1000)

      }

      function showScore() {

        document.getElementById("_displayScore").innerHTML = "<span> Score : " + currentScore + " Lives : " + currentLives + "</span>"

      }

      $(beginNormalClick).click(function() {
        // $("#car").css("background-color" , "green");
        inAction = false;

      });

      function isThisTheMole() {

        $("div>div").click(function() {


          var clickedField = $(this);

          if (clickedField.hasClass("mole")) {
            currentScore++;

            clickedField.removeClass("mole");

          } else {
            currentLives--;

          }
          showScore();
          checkLives();

        })
      }


      function checkLives() {
      
        if (currentLives === 0) {
          alert("")

          inAction = false;
        }
        
      }

    });
  </script>
  
  <p id="car" class="kes">blablacar</p>
  <p class="kes">carblabla </p>
  <div id="StartMenu"></div>
  <button id="beginEasyClick"> Easy </button>
  <button id="beginNormalClick"> Normal </button>
  <button id="beginHardClick"> Hard </button>
  <div id="generalInformation">
    <p id="_displayScore"> </p>
  </div>

  <div id="moleWorld">

    <div class="field"> </div>
    <div class="field"> </div>
    <div class="field"> </div>
    <div class="field"> </div>
    <div class="field"> </div>
    <div class="field"> </div>
    <div class="field"> </div>
    <div class="field"> </div>

Thank you very much for reading!


Solution

  • You need to reset your interval with clearInterval():

    var currentScore = 0;
    var currentLives = 0;
    var inAction = false;
    var interval = null;
    var allFields = document.getElementsByClassName("field");
    
    function start(lives) {
    	if (inAction) {
    		console.log('Already in action, ignore request');
    		return;
    	}
    	currentScore = 0;
    	currentLives = lives;
    	inAction = true;
    	console.log('Start interval');
    	// Store interval id to be able to clear it later
    	interval = setInterval(function () {
    		spawnMole();
    	}, 1400);
    
    	showScore();
    	isThisTheMole();
    }
    
    function stop() {
    	console.log('Stop interval');
    	inAction = false;
    	clearInterval(interval);
    }
    
    function spawnMole() {
    	var oldScore = currentScore;
    	var target = $(allFields[Math.floor(Math.random() * allFields.length)]);
    	target.addClass("mole");
    
    	setTimeout(function () {
    		target.removeClass("mole");
    		if (oldScore === currentScore) {
    			currentLives--;
    			checkLives();
    		}
    		showScore();
    	}, 1000);
    }
    
    function showScore() {
    	// Use jQuery as it's already loaded
    	$("#displayScore").html("<span> Score : " + currentScore + " Lives : " + currentLives + "</span>");
    }
    
    function isThisTheMole() {
    	// Only listen on relevant divs
    	$("div#moleWorld > div.field").click(function () {
    		// Ignore click if the game is running
    		if (!inAction) return;
    		var clickedField = $(this);
    		if (clickedField.hasClass("mole")) {
    			currentScore++;
    			clickedField.removeClass("mole");
    		} else {
    			currentLives--; // Double penalty
    		}
    		showScore();
    		checkLives();
    	})
    }
    
    function checkLives() {
    	if (currentLives <= 0) { // lives could be below zero in case of double penalty
    		console.log('No more lifes remaining');
    		stop();
    	}
    }
    
    $(function() {
    	// Use jQuery as it's already loaded
    	$('#beginEasyClick').click(function () {
    		start(5);
    	});
    
    	$('#beginNormalClick').click(function () {
    		start(2);
    	});
    });
    #moleWorld {
    	height: 330px;
    	width: 1500px;
    	margin: 0 auto;
    	border: 1px solid black;
    }
    
    .field {
    	display: inline-block;
    	width: 21%;
    	margin: 27px;
    	height: 21%;
    	border: 1px solid black;
    	background: red;
    }
    
    .mole {
    	display: inline-block;
    	width: 21%;
    	margin: 27px;
    	height: 21%;
    	border: 1px solid black;
    	background-color: green;
    }
    
    #generalInformation {
    	height: 40px;
    	width: 330px;
    	margin: 0 auto;
    	background: lightblue;
    }
    
    #level-display, #lifes-display {
    	margin-left: 30px;
    }
    
    #beginEasyClick , #beginNormalClick, #beginHardClick {
    	margin: 40px 45%; width: 70px;height: 30px
    }
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
    <p id="car" class="kes">blablacar</p>
    <p class="kes">carblabla </p>
    <div id="StartMenu"></div>
    <button id="beginEasyClick"> Easy </button>
    <button id="beginNormalClick"> Normal </button>
    <button id="beginHardClick"> Hard </button>
    <div id="generalInformation"><p id="displayScore"></p></div>
    <div id="moleWorld">
    	<div class="field"> </div>
    	<div class="field"> </div>
    	<div class="field"> </div>
    	<div class="field"> </div>
    	<div class="field"> </div>
    	<div class="field"> </div>
    	<div class="field"> </div>
    	<div class="field"> </div>
    </div>

    (I've removed some unused stuff)