javascript - 为什么 "crab"(一个实体)不像 "monster"(也是一个实体)那样可触摸?

标签 javascript canvas

我正在开发一款游戏,我想知道为什么“螃蟹”(一个实体)不能像“怪物”(也是一个实体)一样被杀死。我的意思是,如果我触摸妖精怪物,我就会得到一分,但我只是走过螃蟹。 我尝试添加一个 if..else,但随后玩家每秒获得数千分。 我做错了什么?

// Create the canvas
var canvas = document.createElement("canvas");
var ctx = canvas.getContext("2d");
canvas.width = 512;
canvas.height = 480;
document.body.appendChild(canvas);

// Background image
var bgReady = false;
var bgImage = new Image();
bgImage.onload = function() {
  bgReady = true;
};
bgImage.src = "images/background.png";

// Hero image
var heroReady = false;
var heroImage = new Image();
heroImage.onload = function() {
  heroReady = true;
};
heroImage.src = "images/hero.png";

// Monster image
var monsterReady = false;
var monsterImage = new Image();
monsterImage.onload = function() {
  monsterReady = true;
};
monsterImage.src = "images/monster.png";

// Crab image
var crabReady = false;
var crabImage = new Image();
crabImage.onload = function() {
  crabReady = true;
};
crabImage.src = "images/old/hero.png";

// Game objects
var hero = {
  speed: 300 // movement in pixels per second
};
var monster = {};
var crab = {};
var monstersCaught = 0;

// Handle keyboard controls
var keysDown = {};

addEventListener("keydown", function(e) {
  keysDown[e.keyCode] = true;
}, false);

addEventListener("keyup", function(e) {
  delete keysDown[e.keyCode];
}, false);

// Reset the game when the player catches a monster
var reset = function() {
  hero.x = canvas.width / 2;
  hero.y = canvas.height / 2;

  // Throw the monster somewhere on the screen randomly
  monster.x = 32 + (Math.random() * (canvas.width - 64));
  monster.y = 32 + (Math.random() * (canvas.height - 64));

  // Throw the crab somewhere on the screen randomly
  crab.x = 32 + (Math.random() * (canvas.width - 64));
  crab.y = 32 + (Math.random() * (canvas.height - 64));
};

// Update game objects
var update = function(modifier) {
  if (38 in keysDown) { // Player holding up
    hero.y -= hero.speed * modifier;
  }
  if (40 in keysDown) { // Player holding down
    hero.y += hero.speed * modifier;
  }
  if (37 in keysDown) { // Player holding left
    hero.x -= hero.speed * modifier;
  }
  if (39 in keysDown) { // Player holding right
    hero.x += hero.speed * modifier;
  }

  // Are they touching?
  if (
    hero.x <= (monster.x + 32) && monster.x <= (hero.x + 32) && hero.y <= (monster.y + 32) && monster.y <= (hero.y + 32)
  ) {
    ++monstersCaught;
    reset();
  }
};

// Draw everything
var render = function() {
  if (bgReady) {
    ctx.drawImage(bgImage, 0, 0);
  }

  if (heroReady) {
    ctx.drawImage(heroImage, hero.x, hero.y);
  }

  if (monsterReady) {
    ctx.drawImage(monsterImage, monster.x, monster.y);
  }

  if (crabReady) {
    ctx.drawImage(crabImage, crab.x, crab.y);
  }

  // Score
  ctx.fillStyle = "rgb(250, 250, 250)";
  ctx.font = "24px Helvetica";
  ctx.textAlign = "left";
  ctx.textBaseline = "top";
  ctx.fillText("Mobs killed: " + monstersCaught, 32, 32);
};

// The main game loop
var main = function() {
  var now = Date.now();
  var delta = now - then;

  update(delta / 1000);
  render();

  then = now;

  // Request to do this again ASAP
  requestAnimationFrame(main);
};

// Cross-browser support for requestAnimationFrame
var w = window;
requestAnimationFrame = w.requestAnimationFrame || w.webkitRequestAnimationFrame || w.msRequestAnimationFrame || w.mozRequestAnimationFrame;

// Let's play this game!
var then = Date.now();
reset();
main();
<!DOCTYPE html>
<html>
 <head>
  <title>Underbound</title>
  <link rel="stylesheet" type="text/css" href="style.css">
 </head>
 <body>
  <div class="game">
   <script src="js/game.js"></script>
  </div>
 </body>
</html>

最佳答案

因为你只是检查英雄是否与怪物发生碰撞。

hero.x <= (monster.x + 32) && monster.x <= (hero.x + 32) && hero.y <= (monster.y + 32) && monster.y <= (hero.y + 32)

相反,您可能应该创建一个函数来检查它们是否发生冲突:

function isColliding(a, b) {
  return a.x <= (b.x + 32) && b.x <= (a.x + 32) &&
         a.y <= (b.y + 32) && b.y <= (a.y + 32);
}

if (isColliding(hero, monster)) { ...

然后还可以检查它们是否与crab发生碰撞。

if (isColliding(hero, crab)) { ...

如果你将所有“怪物”放入一个数组中,然后检查数组中的每个怪物,那么它会更可持续(直到你有很多怪物)。

至于快速获得大量积分的问题:你必须将怪物(或螃蟹)从游戏区域中移走,并在更新阶段停止检查碰撞,否则玩家将继续与螃蟹碰撞并获得积分。

对此的一个解决方案是为你的怪物提供一个active(或类似的属性)。默认情况下,这是 true,但是当玩家与它们碰撞时,这将是 false。然后,您只需绘制它们并在 active 为 true 时检查碰撞。

关于javascript - 为什么 "crab"(一个实体)不像 "monster"(也是一个实体)那样可触摸?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35161046/

相关文章:

javascript - 如何将ISO8601 json转换为正常日期格式

javascript - Typescript私有(private)方法 "is not a function"

JavaScript Canvas ,获得平坦的线条

javascript - 了解在 Canvas 弧中为端点完成的数学运算

javascript - Canvas 颜色和拖放

javascript - 如何从ajax调用 Controller 并发送$_POST

javascript - Google 可视化 API — 百分比条

javascript - React 中的状态管理

javascript - Canvas Shiny 星星背景性能问题

javascript - 使用 HTML5/Canvas/JavaScript 在浏览器中截屏