帆布简单游戏DRY重构

时间:2015-10-25 01:44:37

标签: javascript canvas html5-canvas prototype

我是本网站的日常读者,但通常不是作家。由于我已经学习了几个星期的JavaScript,我根据几个对象做了一个小帆布/ JS交叉游戏游戏,我试图改进它。游戏非常简单:你可以看到完整的代码并在这里玩:https://jsfiddle.net/vhrqb5xb/1/ 在这里:http://codepen.io/Pggo/pen/NGyQXK

    // The car variable 
    var Car = {}

    // How I create it
    var resetCar = function () {

      Car.x = 300 + (Math.random() * (canvas.width-600));
      Car.y = -10

    };


    // How it's drawn
    function drawCar(){

      ctx.beginPath();
      ctx.rect(Car.x,Car.y,32,32);
      ctx.fillStyle = 'white';
      ctx.fill();
      Car.y += Math.random() * 80

      if (Car.y > canvas.height){
        resetCar();
      };

    }


    // How game is reseit if player touch car
    function drawTouchCar(){

    // Evaluate coordonates of both objects, reset of touch
    if (
      player.x <= (Car.x + 32)
      && Car.x <= (player.x + 10)
      && player.y <= (Car.y + 30) &&
      Car.y <= (player.y + 10)
      ){
    ++numberOfDeaths; // +1 Die
    resetPlayer();
    }
    // if player pass arival line
    if(player.x > (canvas.width - 170 )){
      resetPlayer();
    ++numberOfWins; // +1 Win
    }
    }

现在,我使用的技巧是我有一个快速的车速来渲染它如此之快似乎有不止一个,但我的游戏只依赖于一个物体,汽车。我希望能够动态添加更多汽车(而不是通过创建自己的car2对象)。为了使用原型来创建我的对象,我已经进行了多次研究和尝试,我能够轻松地创建更多对象但我的问题是我无法访问它们的x和y属性来使用它我的碰撞函数。 / p>

所以,问题是,如何处理为实际对象车实现原型,可以创建动态新车对象并返回其x和y属性,以便我可以在碰撞功能中重复使用它。实际上我只是在这里了解原因我被困住了,但我并没有找到开箱即用的解决方案。

提前感谢您的回复,有一个好的

1 个答案:

答案 0 :(得分:0)

创建Object有很多种方法。每种方法都有其优点和缺点。

最快的方法是使用对象工厂add hoc根据需要创建未命名的对象。此方法创建最快的代码。

var drawCar = function () { // function to draw a car;
    ctx.beginPath();
    // "this" is the car object and should be bound to a car object
    ctx.rect(this.x, this.y, 32, 32);
    ctx.fillStyle = 'red';
    ctx.fill();
    // do your test to see if car is over the line
    // and call
    this.reset(); // to reset the car
}

var resetCar = function () {
    // car reset function TODO add your reset code
}

var carFactory = function () { // creates add hoc unnamed car objects
    var car = {}; // create a new object;
    car.x = 0; // give it properties
    car.y = 0;
    // add the reset function to the car and bind it to the new car
    car.reset = resetCar.bind(car);
    car.draw = drawCar.bind(car); // same for draw
    car.reset(); // reset the car ready to go;
    return car; // return the new car
}

var testCar = function (car) { // function to test if car hits player
    if (
        player.x <= (car.x + 32) // access the car position by its x and y properties
         && car.x <= (player.x + 10)
         && player.y <= (car.y + 30) &&
        car.y <= (player.y + 10)) {
        ++numberOfDeaths; // +1 Die
        resetPlayer();
    }
}

var car1 = carFactory(); // create a new car
var car2 = carFactory(); // and another;

var mainLoop() { // called once every frame
    car1.draw();
    car2.draw();
    testCar(car1);
    testCar(car2);
    // TODO the other stuff
}

接下来是正式的方法,它稍慢,因为引擎盖下发生了更多的事情(可以这么说)

function Car() {
    // "this" is bound automatic to the car object with the call new Car()
    // the car also is a named type in Javascript
    this.x = 0;
    this.y = 0;
    this.reset(); // reset the new car

    // "this" is returned here automatically like in the factory but in this 
    // case you dont have to type it in 
}

// add draw to the car prototype
Car.prototype.draw = function () { // function to draw a car;
    ctx.beginPath();
    ctx.rect(this.x, this.y, 32, 32);
    ctx.fillStyle = 'red';
    ctx.fill();
    // this.reset(); // to reset the car
}

// add reset to the car prototype
Car.prototype.reset = function () {
    // car reset function TODO add your reset code }
}

var testCar = function (car) { // function to test if car hits player
    if (
        player.x <= (car.x + 32) // access the car position by its x and y properties
         && car.x <= (player.x + 10)
         && player.y <= (car.y + 30) &&
        car.y <= (player.y + 10)) {
        ++numberOfDeaths; // +1 Die
        resetPlayer();
    }
}
var car1 = new Car(); // create a new car
var car2 = new Car(); // and another;


var mainLoop() { // called once every frame
    car1.draw();
    car2.draw();
    testCar(car1);
    testCar(car2);
}

您还可以使用class在ECMAScript 6中创建汽车。您还可以在Car函数中声明所有原型,允许您使用闭包来添加隐藏属性。创造一辆新车的速度稍微慢一些,但是新车的运行速度会稍微快一些......

如果你想要绝对控制,你可以直接使用Object方法,允许你创建具有可写,可枚举,可配置选项的属性,你可以创建getter和setter,你可以更多地冻结对象和整个堆。就个人而言,我把这些东西留给了大师。

希望这有帮助。