Javascript敌人的角度/方向

时间:2018-02-01 21:36:45

标签: javascript html

我制作了一个有3个物体的小游戏

玩家:可以使用WASD移动

子弹:由点击

的事件监听器移动

敌人:像僵尸一样跟随玩家。

如何制作僵尸的角度是他移动的方向,而不是总是面对玩家对象?

Fiddle

    tick: function() {
     enemy.angle = Math.atan2(player.y - enemy.y, player.x - enemy.x);// * (180 / Math.PI);
    },

以上是我用来让敌人面对玩家的代码

1 个答案:

答案 0 :(得分:0)

我理解你想要问的是什么,但实际上,现在僵尸总是直接进入玩家,所以如果它看起来像其他方式它实际上会很奇怪。你需要做的是让僵尸慢慢转身并在它上面行走,而不仅仅是减少它与玩家之间的欧氏距离。

第一个干,我将为你做的一个是计算旋转。我们不得不立即转向正确的角度,而是慢慢转动每一个嘀嗒声:

    tick: function() {
        // 1 degree per tick
        const rotationSpeed = (1/180)*Math.PI;
        // the angle we want - facing the player
        const desiredAngle = Math.atan2(player.y - enemy.y, player.x - enemy.x)
        // transition angle will be explained below 
        enemy.angle = transitionAngle(enemy.angle, desiredAngle,rotationSpeed );
    },

这并不像听起来那么容易,因为你需要计算它是否能够更快地左转或右转再次面对玩家。幸运的是,一旦你知道你需要什么,这很容易谷歌。我的功能基于this answer

function transitionAngle(fromAngle, toAngle, speed) {
    // normalize the angles to 0-360 range
    const rad360 = 2*Math.PI;
    fromAngle = fromAngle % rad360;
    toAngle = toAngle % rad360;



    if (fromAngle < toAngle) {
        if (Math.abs(fromAngle - toAngle) < Math.PI)
            fromAngle += speed;
        else fromAngle -= speed;
    }

    else {
        if (Math.abs(fromAngle - toAngle) < Math.PI)
            fromAngle -= speed;
        else fromAngle += speed;
    }
    return fromAngle;
}

有了这个,僵尸慢慢减速,看起来已经好一点了。

&#13;
&#13;
      var canvas = document.getElementById('canvas');
      var context = canvas.getContext('2d');
      var bounds = canvas.getBoundingClientRect();
      var mouseX = 0.0;
      var mouseY = 0.0;
      var pressingDown = false;
      var pressingUp = false;
      var pressingLeft = false;
      var pressingRight = false;

      var player = {
        x: 210,
        y: 250,
        radius: 17.5,
        angle: 0.0,
        tick: function() {
          this.angle = Math.atan2(mouseY - this.y, mouseX - this.x);
        },

        draw: function() {
          context.fillStyle = "darkred";
          context.strokeStyle = "black";
          context.translate(this.x, this.y);
          context.rotate(this.angle);
          context.beginPath();
          context.moveTo(this.radius, 0.0);
          context.lineTo(-0.5 * this.radius, 0.5 * this.radius);
          context.lineTo(-0.5 * this.radius, -0.5 * this.radius);
          context.lineTo(this.radius, 0.0);
          context.fill();
          context.stroke();
          context.rotate(-this.angle);
          context.translate(-this.x, -this.y);
        },

        updatePlayerPosition: function() {
          if (pressingRight)
            player.x += 1;
          if (pressingLeft)
            player.x -= 1;
          if (pressingDown)
            player.y += 1;
          if (pressingUp)
            player.y -= 1;
        }

      }

      var bullet = {
        x: player.x,
        y: player.y,
        dx: 0.0,
        dy: 0.0,
        radius: 5.0,

        tick: function() {
          this.x += this.dx;
          this.y += this.dy;

          if (this.x + this.radius < 0.0 || this.x - this.radius > canvas.width || this.y + this.radius < 0.0 || this.y - this.radius > canvas.height) {
            this.dx = 0.0;
            this.dy = 0.0;
          }
        },

        render: function() {
          context.fillStyle = "darkcyan";
          context.strokeStyle = "white";
          context.beginPath();
          context.arc(this.x, this.y, this.radius, 0.0, 2.0 * Math.PI, false);
          context.fill();
          context.stroke();
        }
      };
	
  	var enemy = {       
    		x: 200,
        y: 300,
        radius: 17.5,
        angle: 0.0,
        tick: function() {
            // 1 degree per tick
            const rotationSpeed = (1/180)*Math.PI;
            const desiredAngle = Math.atan2(player.y - enemy.y, player.x - enemy.x)
            enemy.angle = transitionAngle(enemy.angle, desiredAngle,rotationSpeed );
        },

        draw: function() {
          context.fillStyle = "Green";
          context.strokeStyle = "darkgreen";
          context.translate(this.x, this.y);
          context.rotate(this.angle);
          context.beginPath();
          context.moveTo(this.radius, 0.0);
          context.lineTo(-0.5 * this.radius, 0.5 * this.radius);
          context.lineTo(-0.5 * this.radius, -0.5 * this.radius);
          context.lineTo(this.radius, 0.0);
          context.fill();
          context.stroke();
          context.rotate(-this.angle);
          context.translate(-this.x, -this.y);
        },
        drawEnemy: function(something){
          var diffX = player.x - something.x;
          var diffY = player.y - something.y

        if (diffX > 0)
          something.x += .3
        else
          something.x -= .3;

        if (diffY > 0)
          something.y += .3
        else
          something.y -= .3;
      }
        
        }





      function Refresh() {
        context.clearRect(0, 0, canvas.width, canvas.height);
        bullet.render();
        bullet.tick();
        player.draw();
        player.tick();
        player.updatePlayerPosition();
        enemy.draw();
        enemy.tick();
        enemy.drawEnemy(enemy);

      }
      

      setInterval(Refresh, 0)

      window.onmousemove = function(e) {
        mouseX = e.clientX - bounds.left;
        mouseY = e.clientY - bounds.top;
      }

      document.onkeydown = function(event) {
        if (event.keyCode === 83) //s
          pressingDown = true;
        else if (event.keyCode === 87) //w
          pressingUp = true;
        else if (event.keyCode === 65) //a
          pressingLeft = true;
        else if (event.keyCode === 68) //d
          pressingRight = true;
      }

      document.onkeyup = function(event) {
        if (event.keyCode === 83) //s
          pressingDown = false;
        else if (event.keyCode === 87) //w
          pressingUp = false;
        else if (event.keyCode === 65) //a
          pressingLeft = false;
        else if (event.keyCode === 68) //d
          pressingRight = false;
      }

      window.onmousedown = function(e) {
        // The mouse pos - the player pos gives a vector
        // that points from the player toward the mouse
        var x = mouseX - player.x;
        var y = mouseY - player.y;

        // Using pythagoras' theorm to find the distance (the length of the vector)
        var l = Math.sqrt(x * x + y * y);

        // Dividing by the distance gives a normalized vector whose length is 1
        x = x / l;
        y = y / l;

        // Reset bullet position
        bullet.x = player.x;
        bullet.y = player.y;

        // Get the bullet to travel towards the mouse pos with a new speed of 10.0 (you can change this)
        bullet.dx = x * 10.0;
        bullet.dy = y * 10.0;
      }

function transitionAngle(fromAngle, toAngle, speed) {
    // normalize the angles to 0-360 range
    const rad360 = 2*Math.PI;
    fromAngle = fromAngle % rad360;
    toAngle = toAngle % rad360;
    
    
    
    if (fromAngle < toAngle) {
        if (Math.abs(fromAngle - toAngle) < Math.PI)
            fromAngle += speed;
        else fromAngle -= speed;
    }

    else {
        if (Math.abs(fromAngle - toAngle) < Math.PI)
            fromAngle -= speed;
        else fromAngle += speed;
    }
    return fromAngle;
}
&#13;
<canvas id="canvas" style="border:2px solid darkred" width="700" height="500"></canvas>
&#13;
&#13;
&#13;

这份工作的第二部分 - 我将这一部分留给你 - 就是让僵尸实际上走向它所面对的方向。为此,请为其指定步行速度,然后使用僵尸角度的sincos乘以速度来获得X和Y偏移。同样,谷歌是你的朋友,只需键入&#34; 按速度和角度移动javascript &#34;。