0

I am developing a basic HTML / Javascript game where one entity (ie. zombie) is trying to capture another entity (ie. brain). The zombie operates by using the keypad and the brain is rendered in the DOM.

My goal is when the zombie div touches the brain div, the score increments +1.

Note The commented-out function "collision($zombie, $brain)" was an alternative method I tried that did not work. Also note, when the code snippet is run, the dom is blank because I cannot include the image folder. Images used

function docReady(){
         window.addEventListener('keydown', moveZombie);
         window.addEventListener('keydown', collision);
 /*eventListner can tell a key is pressed, and then call the function  moveZombie*/
       }

function moveZombie(evt) {        /* create a function call it moveZombie*/
 switch (evt.keyCode) {          /*keyCode is used to identify which key is  pressed*/
 case 37:leftArrowPressed();
 break;                          /* call the function leftArrowPressed()*/
 case 39: rightArrowPressed();
 break;
 case 38: upArrowPressed();
 break;
 case 40: downArrowPressed();
 break;
 }
}

function leftArrowPressed(){             /*define a function and call it leftArrowPressed()*/

 var leftZombie = document.getElementById('zombie');

 leftZombie.style.left = parseInt(leftZombie.style.left) - 15 + 'px';
 /*when left Arrow Pressed move the zombie 10 px to the left*/
}

function rightArrowPressed(){
 var rightZombie = document.getElementById('zombie');
 rightZombie.style.left= parseInt(rightZombie.style.left) + 15 + 'px';

}

function upArrowPressed(){
 var upZombie = document.getElementById('zombie');
 upZombie.style.top= parseInt(upZombie.style.top) - 20 +'px';

}

function downArrowPressed() {
 var downZombie = document.getElementById('zombie');
 downZombie.style.top = parseInt(downZombie.style.top) + 15 + 'px';
}

function collision(){

  var zombie = document.getElementById('zombie');
  var brain = document.getElementById('brain');

  var zomLeft = zombie.x;
  var zomRight = zombie.x + (zombie.width);
  var zomTop = zombie.y;
  var zomBottom = zombie.y + (zombie.height);

  var brainLeft = brain.x;
  var brainRight = brain.x + (brain.width);
  var brainTop = brain.y;
  var brainBottom = brain.y + (brain.height);
  var crash = false;

  if ((zomBottom > brainTop) || (zomTop < brainBottom) || (zomRight > brainLeft) || (zomLeft < brainRight)) {
      crash = true;
  }

return crash;


}

/*function collision($zombie, $brain) {
     var x1 = $zombie.offset().left;
     var y1 = $zombie.offset().top;
     var h1 = $zombie.outerHeight(true);
     var w1 = $zombie.outerWidth(true);
     var b1 = y1 + h1;
     var r1 = x1 + w1;
     var x2 = $brain.offset().left;
     var y2 = $brain.offset().top;
     var h2 = $brain.outerHeight(true);
     var w2 = $brain.outerWidth(true);
     var b2 = y2 + h2;
     var r2 = x2 + w2;

     var crash = false;

     
     if (b1 < y2 || y1 > b2 || r1 < x2 || x1 > r2) crash = true;

     return crash;

   } */

function scoreBoard(){
var score =0;
var scoreBoard = "Score: " + score;

if(collison==true){
score= score+1;
}
else
return scoreBoard;

}
h1{
color:red;
font-style: italic;
}

/*Our png picture is 2000px * 312px, then each frame is 200px * 312px*/

 #zombie {
/*Our png picture is 2000px * 312px, then each frame is 200px * 312px*/

    width: 200px;
    height: 312px;
    background-image: url("../img/walkingdead.png");
 animation: plays 1.8s steps(10) infinite;
 position: relative;
 margin:auto;
 top:50%;

}

#brain{
  width: 130px;
  height: 130px;
  background-image: url("../img/brain.png");
  position: fixed;
  margin: auto;
  top: 50%;

}

#wrapper{
 width: 600px;
    height: 200px;
 position: relative;
 animation: move 4s infinite ;
}

#score{
  color:red;
  font-style: italic;

}

@keyframes plays {
 from { background-position:    0px;  }
 to { background-position: -2000px;  }
}
<!DOCTYPE�html>
<head>
<title>Zombie</title>
<link rel="stylesheet" type="text/css" href="css/styles.css">
</head>

<script src="game.js"></script>

<body onload="docReady()" background ="./img/graveyard.png">
  <h1>Zombie Game</h1>
  <div id="wrapper">
      <div id ="zombie" style="position:absolute; left:800px; top:200px"></div>

  </div>
  <div id = "brain"> </div>

<div id="score" style= "position:fixed; left 1000px; top:100px" >
  
</div>
</body>

</html>
  • Welcome to the small world of game developement. Ur question was already asked a thousand times, here is one so link https://stackoverflow.com/questions/5419134/how-to-detect-if-two-divs-touch-with-jquery – Doomenik Oct 19 '17 at 04:38
  • @Doomenik Thank you for your response! As I mentioned, I already tried to implement that solution in my project (its the commented out function). If you could provide any insight as to why that solution doesn't work I would appreciate it. –  Oct 19 '17 at 04:42
  • @JimM33, `var zomLeft = zombie.x;` doesn't give you the position of zombie. `zombie` variable contains a DOM element and it has no `x` property. – DylanYi Oct 19 '17 at 05:06

2 Answers2

3

Try this.

var score = 0;

function checkCollision(elm1, elm2) {
  var elm1Rect = elm1.getBoundingClientRect();
  var elm2Rect = elm2.getBoundingClientRect();

  return (elm1Rect.right >= elm2Rect.left &&
      elm1Rect.left <= elm2Rect.right) &&
    (elm1Rect.bottom >= elm2Rect.top &&
      elm1Rect.top <= elm2Rect.bottom);
}

function moveZombie(evt) {
  var key;

  var zombie = document.getElementById('zombie');
  var brain = document.getElementById('brain');
  var scoreDiv = document.getElementById('score');

  var x = parseInt(zombie.style.left);
  var y = parseInt(zombie.style.top);

  switch (evt.keyCode) {
    case 37:
      zombie.style.left = `${x+-15}px`;
      break;
    case 39:
      zombie.style.left = `${x+15}px`;
      break;
    case 38:
      zombie.style.top = `${y+-15}px`;
      break;
    case 40:
      zombie.style.top = `${y+15}px`;
      break;
  }


  setTimeout(function() {

    if (checkCollision(brain, zombie)) {
      scoreDiv.innerHTML = ++score;
    }
  }, 150);


}

window.addEventListener('keydown', moveZombie);
#score {
  position: fixed;
  top: 0;
  right: 0;
  width: 80px;
  height: 40px;
  border-radius: 5px;
  box-shadow: 0 4px 20px 4px rgba(0, 20, 60, .1), 0 4px 80px -8px rgba(0, 20, 60, .2);
  text-align: center;
  color: green;
  font-size: 1.3em;
  line-height: 1.8;
}

#zombie {
  position: absolute;
  width: 100px;
  height: 100px;
  background: #fa0000;
  color: white;
  text-align: center;
  font-size: 1.5em;
  transition: all 0.1s ease-in-out;
}

#brain {
  width: 100px;
  height: 100px;
  position: fixed;
  left: 400px;
  top: 100px;
  background: #e5ac5e;
  text-align: center;
  font-size: 1.5em;
}

#buttons {
  position: fixed;
  bottom: 0;
}

#buttons>button {
  width: 80px;
  height: 30px;
}
<div id="score"></div>
<div id="zombie" style="left:0; top:0">Zombie</div>
<div id="brain">brain</div>
  • Sorry bro, my English is bad that is why I didn't go to explanation. – Ibrahim Al Khalil Oct 19 '17 at 08:42
  • @IbrahimAlKhalil Thank you for this answer! It worked. I up-voted but don't have a 15 reputation, in case others were wondering if this solution works. –  Oct 19 '17 at 17:49
1

If all you need is just to check rectangular area crossing, getBoundingClientRect DOM method would be fine:

var r1 = zombie.getBoundingClientRect();
var r2 = brain.getBoundingClientRect();
var crash = r1.left <= r2.right && r2.left <= r1.right
            && r1.bottom <= r2.top && r2.bottom <= r1.top;

For finer hit-testing irregular shapes, you need more specialized logic.

DylanYi
  • 196
  • 1
  • 10