在 PixiJS 的帮助下重写 vanilla JS Pong

Rewrite of an vanilla JS Pong with the help of PixiJS

除了使用 PixiJS 之外,我还尝试重写一个普通的 JavaScript Pong 游戏,主要是因为我在调整大小方面遇到了 canvas 响应问题。

调整大小在 PixiJS 上运行良好,但所有对象开始都有尾随路径:Fiddle1

我认为那是因为在更新时添加了新实例而不是仅仅更新位置,所以我再次尝试从头开始返工。球员的移动到目前为止有效,但我无法让球正常工作......我有点迷失并且愿意学习。非常感谢帮助...非常感谢!

Fiddle2

import 'pixi.js';

// define gamne variables
const appWidth = window.innerWidth;
const appHeight = window.innerHeight;
const paddleWidth = 150;
const paddleHeight = 30;
const ballSize = 15;
const halfBall = ballSize / 2;
const appWidthHalf = appWidth / 2;
const appHeightHalf = appHeight / 2;
const paddleWidthHalf = paddleWidth / 2;
const pongColor = 0x57dfbf;
const bgColor = 0x282625;
const computerPositionX = appWidthHalf - paddleWidthHalf;
const computerPositionY = 50;
const playerPositionX = computerPositionX;
const playerPositionY = appHeight - computerPositionY - paddleHeight;
const ballPositionX = appWidthHalf - halfBall;
const ballPositionY = appHeightHalf - halfBall;
const playerSpeed = 4;
const computerSpeed = 4;
const ballSpeed = 3;

// Setup the ticker and the root stage PIXI.Container.
const app = new PIXI.Application(appWidth, appHeight, {
  antialias: false,
  backgroundColor: bgColor,
  transparent: false,
  resolution: 1,
});

// append app to body
document.body.appendChild(app.view);

// create graphic elements
const player = new PIXI.Graphics();
const computer = new PIXI.Graphics();
const ball = new PIXI.Graphics();

// Player
player
  .beginFill(pongColor)
  .drawRect(playerPositionX, playerPositionY, paddleWidth, paddleHeight)
  .endFill();

// Computer
computer
  .beginFill(pongColor)
  .drawRect(computerPositionX, computerPositionY, paddleWidth, paddleHeight)
  .endFill();

// Ball
ball
  .beginFill(pongColor)
  .drawRect(ballPositionX, ballPositionY, ballSize, ballSize)
  .endFill();

// Player Movement
player.update = function () {
  for (const key in keysDown) {
    const value = Number(key);
    if (value === 37) {
      player.move(-playerSpeed, 0);
    } else if (value === 39) {
      player.move(playerSpeed, 0);
    } else {
      player.move(0, 0);
    }
  }
};

player.move = function (x, y) {
  this.x += x;
  this.y += y;
  this.x_speed = x;
  this.y_speed = y;
  if (this.x < -appWidthHalf + paddleWidthHalf) {
    this.x = -appWidthHalf + paddleWidthHalf;
    this.x_speed = 0;
  } else if (this.x + this.width - paddleWidthHalf > appWidthHalf) {
    this.x = appWidthHalf - this.width + paddleWidthHalf;
    this.x_speed = 0;
  }
};

// computer Movement
// eslint-disable-next-line
computer.update = function(ball) {
  const x_pos = ball.x;
  let diff = -(computer.x + paddleWidthHalf - x_pos);
  if (diff < 0 && diff < -computerSpeed) {
    diff = -ballSize;
  } else if (diff > 0 && diff > computerSpeed) {
    diff = ballSize;
  }
  computer.position.set(diff, 0);
  if (computer.x < 0) {
    computer.x = 0;
  } else if (computer.x + paddleWidthHalf > appWidth) {
    computer.x = appWidth - paddleWidthHalf;
  }
};

// Ball Movement
ball.update = function (paddle1, paddle2) {
  this.x += this.x_speed;
  this.y += this.y_speed;
  const top_x = this.x - ballSize;
  const top_y = this.y - ballSize;
  const bottom_x = this.x + ballSize;
  const bottom_y = this.y + ballSize;
  if (this.x - ballSize < 0) {
    this.x = ballSize;
    this.x_speed = -this.x_speed;
  } else if (this.x + ballSize > appWidth) {
    this.x = appWidth - ballSize;
    this.x_speed = -this.x_speed;
  }

  if (this.y < 0 || this.y > appHeight) {
    this.x_speed = 0;
    this.y_speed = ballSpeed;
    this.x = appWidthHalf;
    this.y = appHeightHalf;
  }

  if (top_y > appHeightHalf) {
    if (
      top_y < paddle1.y + paddle1.height &&
      bottom_y > paddle1.y &&
      top_x < paddle1.x + paddle1.width &&
      bottom_x > paddle1.x
    ) {
      this.y_speed = -ballSpeed;
      this.x_speed += paddle1.x_speed / 2;
      this.y += this.y_speed;
    }
  } else if (
    top_y < paddle2.y + paddle2.height &&
    bottom_y > paddle2.y &&
    top_x < paddle2.x + paddle2.width &&
    bottom_x > paddle2.x
  ) {
    this.y_speed = ballSpeed;
    this.x_speed += paddle2.x_speed / 2;
    this.y += this.y_speed;
  }
};

// controls
const keysDown = {};

window.addEventListener('keydown', (event) => {
  keysDown[event.keyCode] = true;
});

window.addEventListener('keyup', (event) => {
  delete keysDown[event.keyCode];
});

// update function
function update() {
  player.update();
  computer.update(ball);
  ball.update(player, computer);
}

// append childs to app
app.stage.addChild(player);
app.stage.addChild(computer);
app.stage.addChild(ball);

// game loop
app.ticker.add(update);

Fiddle 1 肯定有问题,因为您没有更改那里的 ball.x 和 y,而是更改图形对象,在 fiddle2 中,您似乎在做 干得好。您只是在代码中有一些逻辑错误,关于设置 x 和 y 坐标以及球的运动。

因此,如果您在 fiddle2 中的 ball.update 函数内添加 console.log(this.x, this.y),您会注意到 NaN 值。

要查看球的移动,如果您将初始值设置为:

ball.x_speed = 0;
ball.y_speed = 0;

然后

paddle.x_speed
paddle.y_speed

paddle.x
paddle.y

你看到球至少在移动(尽管碰撞逻辑不起作用),(修改后的示例在​​下面的 fiddle 中) https://jsfiddle.net/4L6zbd01/