Neikar
Neikar

Reputation: 55

How to make this move longer without pauses

I've got this code which work perfectly if I want to move one block, but when I will keep the key pressed, animation will work but with those pauses. I figured out that multiply speed and distance will work, but I have no idea how to add this "live" to animation. Can you give me some advice?

var Xpos = 0;
var Ypos = 0;
var spd = 250;
var dstnc = 100;

$(document).keydown(function(e) {
  if (e.keyCode == 87) {
    $('#movThs').animate({
      top: -dstnc + Ypos + 'px'
    }, spd);
    Ypos = Ypos - dstnc;
  }
  if (e.keyCode == 68) {
    $('#movThs').animate({
      left: dstnc + Xpos + 'px'
    }, spd);
    Xpos = Xpos + dstnc;
  }
  if (e.keyCode == 83) {
    $('#movThs').animate({
      top: dstnc + Ypos + 'px'
    }, spd);
    Ypos = Ypos + dstnc;
  }
  if (e.keyCode == 65) {
    $('#movThs').animate({
      left: -dstnc + Xpos + 'px'
    }, spd);
    Xpos = Xpos - dstnc;
  }
});
#movThs {
  background-color: #ff0000;
  width: 100px;
  height: 100px;
  position: relative;
  border-radius: 90%;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div id="movThs"></div>

Upvotes: 4

Views: 95

Answers (3)

Tolgahan Albayrak
Tolgahan Albayrak

Reputation: 3206

If you consider not using JQuery but pure JS, I would suggest giving a try to below snippet.

Regards

document.addEventListener("DOMContentLoaded", () => {
if (document.animationInitialized) {
    return;
}

document.animationInitialized = true;

const movThs = document.getElementById("movThs");
const UP = "W".charCodeAt(0);
const DOWN = "S".charCodeAt(0);
const RIGHT = "D".charCodeAt(0);
const LEFT = "A".charCodeAt(0);
const XMAX = 50;
const YMAX = 50;

let x = 0;
let y = 0;
let ax = 0;
let ay = 0;
let cx = 0;
let cy = 0;

function clamp(v, min, max) {
    return v < min ? min : v > max ? max : v;
}

window.requestAnimationFrame(function onAnimation() {
    if (!x) {
        if (ax) {
            ax += -Math.sign(ax);
        }
    } else {
        ax += x;
        ax = clamp(ax, -XMAX, XMAX);
    }
    cx += ax / 100;

    if (!y) {
        if (ay) {
            ay += -Math.sign(ay);
        }
    } else {
        ay += y;
        ay = clamp(ay, -YMAX, YMAX);
    }
    cy += ay / 100;

    movThs.style.transform = `translate3d(${cx}rem,${cy}rem,0)`

    window.requestAnimationFrame(onAnimation);
});

document.addEventListener("keydown", (event) => {
    switch (event.which) {
        case UP:
            y = -1;
            break;
        case LEFT:
            x = -1;
            break;
        case RIGHT:
            x = 1;
            break;
        case DOWN:
            y = 1;
            break;
    }
}, false);

document.addEventListener("keyup", (event) => {
    switch (event.which) {
        case UP:
        case DOWN:
            y = 0;
            break;
        case LEFT:
        case RIGHT:
            x = 0;
            break;
    }
}, false);

});

if (document.readyState === "complete") {
document.dispatchEvent(new Event("DOMContentLoaded"));
}
#movThs {
  background-color: #ff0000;
  width: 100px;
  height: 100px;
  position: relative;
  border-radius: 90%;
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<div id="movThs"></div>

Upvotes: 0

ne1410s
ne1410s

Reputation: 7082

I'm not sure of the exact easing behaviour you wish to implement, but one handy hint to making things smoother is to stop() before re-animating.

It ends up with non-discrete positioning; with the stop(), you can now be left between two positions, which may not be what you want. What it does do is prevent animation-queues from building up (without sacrificing the original smoothness).

<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<style>
  #movThs {
    background-color: #ff0000;
    width: 100px;
    height: 100px;
    position: relative;
    border-radius: 90%;
  }
</style>

<div id="movThs"></div>
<script>
  var Xpos = 0;
  var Ypos = 0;
  var spd = 250;
  var dstnc = 100;

  $(document).keydown(function(e) {
    if (e.keyCode == 87) {
      $('#movThs').stop().animate({
        top: -dstnc + Ypos + 'px'
      }, spd);
      Ypos = Ypos - dstnc;
    }
    if (e.keyCode == 68) {
      $('#movThs').stop().animate({
        left: dstnc + Xpos + 'px'
      }, spd);
      Xpos = Xpos + dstnc;
    }
    if (e.keyCode == 83) {
      $('#movThs').stop().animate({
        top: dstnc + Ypos + 'px'
      }, spd);
      Ypos = Ypos + dstnc;
    }
    if (e.keyCode == 65) {
      $('#movThs').stop().animate({
        left: -dstnc + Xpos + 'px'
      }, spd);
      Xpos = Xpos - dstnc;
    }
  });
</script>

Upvotes: 2

The Bomb Squad
The Bomb Squad

Reputation: 4337

The variable spd is really the time it takes for an operation to complete

The variable dstnc is the distance to travel in said time for the operation

My Answer is below, has spd which really is time to do operation to 10 milliseconds

<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<style>
  #movThs {
    background-color: #ff0000;
    width: 100px;
    height: 100px;
    position: relative;
    border-radius: 90%;
  }
</style>

<div id="movThs"></div>
<script>
  var Xpos = 0;
  var Ypos = 0;
  var spd = 10; //the amount of time it takes (milliseconds)
  var dstnc = 100; //the distance to travel (pixels)

  $(document).keydown(function(e) {
    if (e.keyCode == 87) {
      $('#movThs').animate({
        top: -dstnc + Ypos + 'px'
      }, spd);
      Ypos = Ypos - dstnc;
    }
    if (e.keyCode == 68) {
      $('#movThs').animate({
        left: dstnc + Xpos + 'px'
      }, spd);
      Xpos = Xpos + dstnc;
    }
    if (e.keyCode == 83) {
      $('#movThs').animate({
        top: dstnc + Ypos + 'px'
      }, spd);
      Ypos = Ypos + dstnc;
    }
    if (e.keyCode == 65) {
      $('#movThs').animate({
        left: -dstnc + Xpos + 'px'
      }, spd);
      Xpos = Xpos - dstnc;
    }
  });
</script>

Upvotes: 0

Related Questions