Home > Software engineering >  Circle moving out of window
Circle moving out of window

Time:01-10

var circle = document.getElementById("circle");


function moveUp() {
  var top = circle.offsetTop;
  newTop = top - 10;
  circle.style.top = newTop   "px";
  console.log("moveUP Called")
}

function moveDown() {
  var top = circle.offsetTop;
  newTop = top   10;
  circle.style.top = newTop   "px";


  console.log("moveDown Called")
}

function moveLeft() {
  var left = circle.offsetLeft;
  newLeft = left - 10;
  circle.style.left = newLeft   "px";


  console.log("moveLeft Called")
}

function moveRight() {
  var left = circle.offsetLeft;
  newLeft = left   10;
  circle.style.left = newLeft   "px";


  console.log("moveRight Called")
}


window.addEventListener("keypress", (event) => {

  if (event.key == 'w') {
    moveUp();
  } else if (event.key == 's') {
    moveDown();
  } else if (event.key == 'a') {
    moveLeft();
  } else if (event.key == 'd') {
    moveRight();
  }
})
body {
  margin: 2px;
  background-color: aquamarine;
}

#circle {
  height: 100px;
  width: 100px;
  background-color: blue;
  border-radius: 50%;
  position: absolute;
}

In the above code where on key press circle moves, for example on 'w' it moves up, for 's' it moves down and so on.

But the problem is that the circle even moves out of the window, how do I fix it and what is the problem??

CodePudding user response:

var circle = document.getElementById("circle");
console.log(window.innerWidth, window.innerHeight)

function moveUp() {
  var top = circle.offsetTop;
  console.log(top)
  newTop = top - 10;
  if(newTop < 0) {
    newTop = 0;
  }
  circle.style.top = newTop   "px";
 
}

function moveDown() {
  var top = circle.offsetTop;
  var height = circle.offsetHeight   top;
  if((height   10) >= window.innerHeight) {
  return;
  }
  newTop = top   10;
  circle.style.top = newTop   "px";


  /* console.log("moveDown Called") */
}

function moveLeft() {
  var left = circle.offsetLeft;
  
  newLeft = left - 10;
  if(newLeft<0) {
  newLeft = 0;
  }
  circle.style.left = newLeft   "px";


 
}

function moveRight() {
  var left = circle.offsetLeft;
  newLeft = left   10;
  if(newLeft > window.innerWidth - 100 ) {
    newLeft = window.innerWidth - 100 ;
  }
  circle.style.left = newLeft   "px";


 
}


window.addEventListener("keypress", (event) => {

  if (event.key == 'w') {
    moveUp();
  } else if (event.key == 's') {
    moveDown();
  } else if (event.key == 'a') {
    moveLeft();
  } else if (event.key == 'd') {
    moveRight();
  }
})
body{
    margin:2px;
    background-color: aquamarine;   
}

#circle{
    height: 100px;
    width: 100px;
    background-color: blue;
    border-radius: 50%;
    position: absolute;
    overflow: hidden;
}
<div id="circle">

</div>

Explaination

for moveup() if the position is a negative number that means the div is going out of the viewport. So with the if condition new position will be always set to 0 preventing the div to go negative position.
for moveDown() first you get the offsetTop which means how far is the box from top position along with the offsetHeight which represents the height of the box. So add these two to get the total height. Now simply check if this height is going over the innerHeight the distance(10) you are going with each move. If it is more than the innerHeight simply return. otherwise move the box.
moveLeft() is same as moveUp().
moveRight() is also same as moveDown() but here we're calculating the innerWidth. Subtract it with the box width so it doesn't go outside the viewport. Now simple condition check and set the new right position.

hope it helped

CodePudding user response:

What is the problem?

There is no problem. CSS does exactly what you told it to do.

For example, you can click on 'w' couple of times, which will set left property for your absolutely positioned circle to, let's say, -160px. This will instruct the browser to move your element to the left, away from the viewport, i.e. to position it -160px of the left edge of the initial containing block or nearest positioned ancestor. More about left property: https://developer.mozilla.org/en-US/docs/Web/CSS/left

I would not say that it is a problem, because it is exactly what left is used for - move elements to whatever position you like. Sometimes you can hide elements by setting their position: absolute; left: -10000px;

How do I fix it?

If you don't want your circle to move away from the viewport, you need to check if your circle is 'touching' the viewport. I will use example with the left, but the same logic can be applied to top, right and bottom.

So for the left, this will consist of two parts:

  1. Check what is the initial distance from your circle to the left edge of the viewport.
  2. Check if absolute value of your new left value is not greater than this distance.

For example, for the left method:

var elDistanceToLeft = window.pageXOffset   circle.getBoundingClientRect().left;

function moveLeft() {
  let left = circle.offsetLeft;
  newLeft = Math.abs(left - 10) <= elDistanceToLeft ? left - 10 : -elDistanceToLeft;
  circle.style.left = newLeft   "px";
}

In this case your circle will move all way to the left (on pressing 'a') until it 'touches' the viewport (screen). Then it will stop.

Here is a code snippet

var elDistanceToLeft = window.pageXOffset   circle.getBoundingClientRect().left

function moveLeft() {
  let left = circle.offsetLeft;
  newLeft = Math.abs(left - 10) <= elDistanceToLeft ? left - 10 : -elDistanceToLeft;
  circle.style.left = newLeft   "px";
}

window.addEventListener("keypress", (ev) => { if (ev.key == 'a') { moveLeft();} })
#circle {
    height: 100px;
    width: 100px;
    background-color: blue;
    border-radius: 50%;
    position: absolute;
}

#parent {
 position: relative;
 padding: 200px;
}
<div id="parent">
  <div id="circle"></div>
</div>

  • Related